Cambie el nombre de una hoja de "Summary" a "Overview" en un libro de trabajo generado, y cada hipervínculo interno que apuntaba a Summary!A1 deja de llevar a algún lado. Ninguna excepción al guardar, ninguna al abrir. El enlace sigue renderizándose, sigue pareciendo clicable, y se resuelve silenciosamente en nada. El mismo tipo de rotura aparece después de una conversión con guardar como o de una ida y vuelta .xls/.xlsx, cuando un comentario cae una columna corrida o un enlace relativo pierde su destino. Ambas funciones llevan estado de revisión sobre el que actúan personas reales, así que cuando se rompen el fallo es invisible hasta que un revisor hace clic y no pasa nada
Esa es la razón práctica por la que los comentarios y los hipervínculos merecen más cuidado del que sugiere su apariencia cosmética. HotXLS da al código Delphi y C++Builder acceso de escritura directo a ambos, en XLS y XLSX, sin automatización de Excel de por medio. La otra cara de ese control es la responsabilidad: la biblioteca escribe exactamente los destinos que usted le entrega y no valida ninguno, así que mantener intacto un flujo de trabajo de revisión es tarea de su código, no de Excel
Comentarios de celda como registros de revisión escritos por máquina
En el modelo de clases de XLSX un comentario es un objeto a nivel de hoja de cálculo: conoce su fila, su columna, un autor y un cuerpo de texto. El campo de autor se gana su lugar. Cuando un libro de trabajo que generó su código recorre una cadena de revisión, la primera pregunta que hace un auditor es quién escribió una nota determinada, y una nota dejada sin autor responde esa pregunta con un espacio en blanco. Marque los comentarios generados con una identidad de servicio para que la procedencia nunca sea ambigua
var
Book: TXLSXWorkbook;
Sheet: TXLSXWorksheet;
Note: TXLSXComment;
begin
Book := TXLSXWorkbook.Create;
try
Book.Open('reconciliation.xlsx');
Sheet := Book.Sheets[0];
// Nota con autor sobre la cifra ajustada
Sheet.AddComment(14, 4, 'Manual adjustment: late FX rate, see ticket FIN-2214',
'recon-service');
// Actualice una nota existente en lugar de apilar una segunda
Note := Sheet.Comments.FindAt(14, 4);
if Note <> nil then
Note.Text := Note.Text + ' [verified 2026-06-11]';
Book.SaveAs('reconciliation-reviewed.xlsx');
finally
Book.Free;
end;
end;
La sonda FindAt tiene más peso del que aparenta. Un trabajo por lotes que reintenta después de un fallo transitorio llamará sin problema a AddComment por segunda vez sobre una celda que ya anotó, y la celda termina con dos notas apiladas que nadie pidió. Sondee primero con FindAt, y actualice el objeto que devuelve. La colección Comments también expone DeleteAt y DeleteInRange. Esa variante de rango es la que conviene usar cuando sanea un libro de trabajo antes de que salga del edificio: limpiar las anotaciones internas de control de calidad de toda una región es una sola llamada en lugar de un bucle escrito a mano sobre las celdas
Las URL externas y los saltos dentro del libro son API distintas
OOXML guarda los dos tipos de enlace en lugares distintos. Una URL externa se convierte en una entrada de relación en la parte .rels de la hoja, con la celda apuntando a la relación por id. Un salto interno nunca toca la capa de relaciones; es una cadena de ubicación simple como Summary!A1 almacenada directamente en el enlace. HotXLS mantiene esa distinción visible en la API en lugar de sobrecargar un único método, lo que significa que usted elige la llamada correcta sabiendo dónde vive el destino:
Sheet.Cells[2, 1].Value := 'Source record';
Sheet.AddHyperlink(2, 1, 'https://intranet.example.com/records/2214',
'Open record 2214', 'ERP source entry');
Sheet.Cells[3, 1].Value := 'Totals';
Sheet.AddHyperlinkToCell(3, 1, 'Overview!B12', 'Jump to totals');
En el objeto TXLSXHyperlink resultante, Url y Location son mutuamente excluyentes, e IsInternal le indica cuál de los dos está poblado. Esa bandera es la que se comprueba cuando inventaría los enlaces de un libro de trabajo abierto y necesita tratar "sale del archivo" y "se queda en el archivo" con reglas distintas: un host externo puede enfrentarse a una lista de permitidos mientras que un destino interno solo tiene que nombrar una hoja que exista. Los enlaces internos no llevan partes de relación detrás, lo que también los hace más baratos de reescribir en masa
La rotura de la introducción vive por completo del lado interno, y se deriva de un hecho: una cadena de ubicación no es una referencia analizada. HotXLS escribe el texto exacto que usted le entrega, y nada vuelve a apuntar ese texto cuando una hoja se renombra después. Dos defensas se sostienen en la práctica. La primera es disciplina en el orden: renombre todas las hojas antes de generar un solo enlace, y luego trate los nombres de hoja como identificadores congelados. La segunda es más robusta y sobrevive a los renombrados hechos a posteriori. Apunte el enlace a un nombre definido a nivel de libro en lugar de a una dirección Sheet!Cell en bruto, porque Excel reescribe la definición de un nombre cuando la hoja subyacente cambia, así que el enlace se ajusta automáticamente. Ese segundo enfoque se combina de forma natural con las técnicas de nombres definidos y fórmulas entre hojas en HotXLS
El lado XLS: los mismos conceptos, tuberías más antiguas
La fachada BIFF8 cuelga los comentarios de los rangos en lugar de una colección a nivel de hoja de cálculo. Usted llama a AddComment sobre un IXLSRange y recibe un TXLSComment; la propiedad Comment del rango lee una nota existente, y ClearComments las borra. El filo aquí es posicional. Un TXLSComment no expone públicamente su propia fila y columna, así que el bucle natural, "recorrer cada comentario y reportar dónde está", va a contracorriente de la API. Tiene que partir de las celdas. O bien impulse la auditoría desde la lista de direcciones que anotó, o mantenga su propio registro de posiciones mientras escribe, porque el objeto de comentario no le dirá después dónde vive
var
Book: IXLSWorkbook;
Sheet: IXLSWorksheet;
Remark: TXLSComment;
begin
Book := TXLSWorkbook.Create;
Sheet := Book.Sheets.Add;
Sheet.Name := 'Review';
Sheet.Cells.Item[5, 2].Value := 4821.50;
Remark := Sheet.Cells.Item[5, 2].AddComment('Awaiting sign-off from controller');
Remark.Visible := True; // muestra la nota abierta en la primera vista
Sheet.AddHyperlink(7, 2, 'https://intranet.example.com/signoff/4821',
'Sign-off form', 'Opens the controller queue');
Book.SaveAs('review.xls');
end;
Fijar Visible en True es la forma heredada de hacer que una nota sea imposible de pasar por alto: el cuadro amarillo permanece abierto en la hoja en lugar de esperar a que el cursor pase encima. TXLSComment va un paso más allá que su contraparte XLSX al exponer TextRuns, así que una sola nota puede llevar una advertencia en negrita junto a una explicación normal, un formato que la API de comentarios de XLSX no expone de la misma manera. Los hipervínculos de este lado llegan mediante tres sobrecargas progresivas (solo dirección, luego con texto para mostrar, luego con una sugerencia en pantalla) y se leen de vuelta a través de la colección HyperLinks de la hoja de cálculo, donde cada enlace expone Address, SubAddress, DisplayText y ScreenTip
Una hoja de índice de revisión supera a las notas dispersas
Pasada una docena de anotaciones, leer al pasar el cursor deja de escalar silenciosamente. Las notas se acumulan en hojas que un revisor nunca abre, y las que más importan son exactamente las más fáciles de pasar por alto. La estructura que mejor ha resistido es una hoja de índice generada: una fila por ubicación anotada, que lista su nombre de hoja, dirección de celda, autor y un breve extracto de la nota. La última columna lleva un hipervínculo interno construido con AddHyperlinkToCell que salta directamente a la celda anotada. Ahora el revisor lee una lista hacia abajo en lugar de cazar por una cuadrícula, y el conteo de filas de ese índice sirve también como su inventario de comentarios para la pasada de auditoría de más abajo
El índice es barato de construir porque su generador ya conoce cada posición que tocó. Anexe una tupla (hoja, fila, columna, autor, resumen) a una lista mientras escribe cada comentario, y luego emita la hoja de índice al final para que su conteo de filas sea definitivo antes de guardar. Dos refinamientos rinden: ordene el índice por severidad o por hoja en lugar de por secuencia de inserción, y ponga un enlace de retorno en el encabezado del índice para que un revisor pueda volver arriba después de cada elemento. Como los enlaces internos son cadenas de ubicación simples sin nada en la capa de relaciones detrás, incluso un índice de mil filas agrega casi nada al tamaño del archivo o al tiempo de guardado
Esa misma hoja rinde de nuevo en el viaje de vuelta. Cuando el libro de trabajo revisado regresa, su código lee valores de estado escritos en celdas junto a las filas del índice en lugar de volver a escanear cada hoja en busca de comentarios que pueden haber cambiado. Una columna de celdas de estado estructuradas se analiza limpiamente; una dispersión de notas de texto libre no
Una pasada de auditoría previa a la entrega que de verdad atrapa la rotura
Ninguna de estas API valida un destino. Un enlace a una hoja que eliminó, un host de intranet mal escrito, un recurso compartido de archivos dado de baja el trimestre pasado: todos se guardan sin un murmullo. ECMA-376 especifica cómo se almacena un enlace, no que se resuelva en algo. Por lo tanto, un libro de trabajo que lleva metadatos de revisión se merece una breve etapa de auditoría propia, ejecutada justo antes de SaveAs:
- Recopile cada ubicación interna escrita durante la generación y confirme que el nombre de hoja antes del signo de exclamación todavía existe en la colección de hojas del libro de trabajo
- Compruebe las URL externas contra una lista de permitidos de esquemas y hosts. Las rutas
file://y UNC desnudas filtran detalles del entorno y se rompen en el momento en que el archivo sale de su red - Cuente los comentarios por hoja y compárelos con lo que su generador pretendía escribir. Un reintento que duplicó las notas aparece aquí y no en la bandeja de entrada del revisor
- Elimine las anotaciones de uso interno con
DeleteInRangesiempre que el destinatario esté fuera de la organización
Los equipos que construyen sus libros de trabajo desde una capa de datos pueden plegar esta etapa en el mismo paso del pipeline que ya valida los datos, para que la comprobación de metadatos viaje sin costo. La mecánica es la descrita en exportar resultados de consultas de base de datos a informes de Excel, orientada hacia enlaces y comentarios en lugar de filas
Un detalle de entrecomillado hace tropezar a la gente cuando construye cadenas de ubicación a mano. Una hoja cuyo nombre contiene un espacio tiene que ir entre comillas dentro de la ubicación, exactamente como la entrecomilla la barra de fórmulas: 'Quarterly Totals'!A1, no Quarterly Totals!A1. HotXLS aplica las mismas reglas que usa el motor de fórmulas para las referencias entre hojas, así que si un enlace funciona en una fórmula de hoja de cálculo su entrecomillado funcionará aquí también. Entréguele un nombre con espacio sin comillas y obtendrá el mismo enlace muerto silencioso del que advertía la introducción
Los comentarios y los hipervínculos son las partes de un libro de trabajo generado sobre las que los revisores actúan sin una segunda mirada, que es exactamente por lo que un destino que apunta a nada hace daño real antes de que alguien lo note. Construya la pasada de validación una vez, ejecútela en cada libro de trabajo antes de que se entregue, y el flujo de trabajo de revisión se mantiene intacto a través de renombrados y conversiones. La superficie completa de la API tanto de la fachada XLS como de la XLSX está documentada en la página de producto de HotXLS Delphi Component