Formats10 min de lectura

Cómo funciona la edición de texto en un PDF: streams de contenido, codificaciones de fuente y por qué solo se edita una línea cada vez

Una página PDF no tiene párrafos ni cuadros de texto, solo instrucciones para dibujar glifos con una fuente en una posición. Editar una línea borra las instrucciones antiguas y escribe otras nuevas en el mismo sitio, y eso decide qué se puede editar y qué no.

PDF123 · Updated 2026-10-14
Cómo funciona la edición de texto en un PDF: streams de contenido, codificaciones de fuente y por qué solo se edita una línea cada vez

Una página PDF no tiene párrafos ni cuadros de texto. Tiene una lista de instrucciones: en esta posición, con esta fuente y este tamaño, dibuja estos glifos. Cambiar el texto significa borrar las instrucciones que dibujan esa línea y escribir otras nuevas en la misma posición, con la misma fuente, tamaño y color. Por eso Editar PDF edita una línea cada vez y no puede hacer que el texto salte de línea automáticamente: es consecuencia de cómo se almacena el texto.

Qué aspecto tiene una línea de texto en el archivo

El contenido de una página vive en un stream de contenido, un programa pequeño hecho de operadores. Cuatro operadores hacen la mayor parte del trabajo con el texto: BT y ET delimitan un bloque de texto, Tf elige la fuente y el tamaño, Td se mueve a la posición siguiente y Tj dibuja una cadena. Con una fuente estándar, el caso más simple es este:

BT /F1 18 Tf 20 150 Td (Hello World) Tj ET

Significa: elige la fuente F1 a 18 puntos, muévete a x 20, y 150 y dibuja Hello World. Un PDF impreso desde Chrome suele ser distinto: los paréntesis ya no contienen caracteres sino números de glifo de la fuente, y Tm fija la posición una sola vez. Esta es la línea Hello World from Georgia de una página exportada por Chrome, donde cada cuatro dígitos hexadecimales son un número de glifo:

BT /F4 24 Tf 1 0 0 -1 30 52 Tm <002b0048004f004f00520003003a00520055004f0047000300490055005200500003002a004800520055004a004c0044> Tj ET

002b es H, 0048 es e, 004f es l, 0003 es un espacio, 003a es W, y así sucesivamente. Estos números solo significan algo dentro de esa fuente concreta; no son Unicode. Cuando copias el texto, el visor convierte los números otra vez en caracteres con una tabla de consulta guardada en otro lugar del archivo.

De aquí se deducen dos cosas. Primero, nada en el stream de contenido dice «esto es un párrafo»: un salto de línea es otro Td o Tm que mueve la posición a la línea siguiente, y cuántas líneas tiene un párrafo hay que deducirlo a partir de las posiciones. Segundo, para escribir un carácter nuevo en una línea necesitas el número de ese carácter en esa fuente, y la fuente suele contener solo los glifos que se usaron cuando se escribió el archivo. Es el resultado del subsetting de fuentes.

Puedes expandir los streams con qpdf:

qpdf --qdf --object-streams=disable in.pdf out.pdf

Abre out.pdf en un editor de texto y busca Tj para ver todas las cadenas que se dibujan en la página. Para saber qué más contiene un PDF, consulta Qué hay dentro de un PDF: objetos, streams y la tabla de referencias cruzadas.

Cómo reconstruye el editor una «línea» a partir de glifos

El editor tiene que agrupar primero los glifos sueltos en una línea sobre la que el usuario pueda hacer clic. Los glifos con la misma fuente, tamaño y color cuya separación respecto al glifo anterior no supera un tamaño de fuente forman un mismo tramo (un grupo de glifos contiguos); un salto de línea, una fuente nueva o un color nuevo ponen fin al tramo. El texto que va de derecha a izquierda, o en vertical, no se agrupa y no se puede abrir para editarlo.

Hay dos consecuencias que se observan directamente. Una línea que mezcla dos fuentes, como una línea en chino con una palabra en inglés, se divide en dos tramos contiguos sobre los que se hace clic por separado. Tras una edición ocurre lo mismo: si el texto nuevo usa otra fuente, la línea pasa a ser dos tramos, y editar uno de ellos deja el otro sin cambios.

Editar una línea: borrar el texto antiguo y escribir el nuevo

El borrado usa el ennegrecido solo de texto: los glifos que caen dentro del área de la línea se eliminan del stream de contenido, las imágenes y las líneas se dejan como están y no se dibuja ningún recuadro de color sobre el texto antiguo, de modo que copiar y buscar ya no lo encuentran. Solo cambia el contenido de la página; si el mismo texto aparece también en una anotación o en las propiedades del documento, estas no se tocan.

La escritura añade una instrucción de texto nueva al final del stream de contenido de la página, a partir de la posición de la línea base de la línea original y reutilizando su tamaño y color. Tras cambiar la línea anterior a Hello World 2, lo que se añade al final de la página es:

q 1 0 0 1 22.5 148.92 cm 0 0 0 rg
/Span <</ActualText <feff00480065006c006c006f00200057006f0072006c006400200032>>> BDC
BT /F4 18 Tf 0 0 Td <002b0048004f004f00520003003a00520055004f00470003> Tj ET
BT /F9 18 Tf 102.18 0 Td (2) Tj ET
EMC
Q

El primer BT usa la fuente original F4 y los números de glifo originales, así que Hello World se reutiliza exactamente como estaba. El «2» no está en el subconjunto de la fuente original, de modo que el segundo BT inicia una fuente Helvetica estándar nueva (F9) para dibujarlo. q y Q limitan la transformación de coordenadas y el color de este bloque a él mismo; el editor también envuelve el contenido original en un par q/Q, para que un estado que haya quedado sin equilibrar al final de la página original no pueda afectar al texto nuevo. Así se veía un tramo; los números varían según el archivo.

Añadir al final tiene tres consecuencias:

  • El texto nuevo se pinta en último lugar, encima de todo lo demás de la página. El texto que estaba debajo de una imagen o de un bloque de color aparece por encima después de una edición.
  • Una herramienta que extrae el texto en el orden del stream de contenido (como pdftotext -raw) lee la línea editada en último lugar en esa página, mientras que la extracción por posición (pdftotext -layout) no muestra ningún cambio. La página se ve igual, pero el orden de lectura ha cambiado.
  • El editor adjunta un ActualText al texto nuevo, que le indica al visor qué caracteres reales representan los glifos. Un glifo puede corresponder a varios caracteres, y buscarlo solo por el número de glifo a veces devuelve un carácter de compatibilidad (por ejemplo, leer 文 como el radical Kangxi ⽂); ActualText garantiza que lo que copias es lo que escribiste.

Qué fuente dibuja el texto nuevo

Reutilizar la fuente original es la opción más segura, porque la forma de los glifos, el peso y el ancho coinciden con lo que tienen al lado. Que se pueda reutilizar depende de si el editor puede saber qué código tiene un carácter en esa fuente:

  • Una fuente compuesta como la de arriba (Type0, números de glifo de dos bytes, codificación Identity-H): se busca el carácter en la fuente para obtener su número de glifo y se usa si se encuentra. Si no se encuentra, el carácter no está en el subconjunto.
  • Una fuente simple de un solo byte (TrueType, Type1) con codificación WinAnsi o MacRoman: la correspondencia entre carácter y byte es fija, y los anchos salen de la tabla de anchos del archivo.
  • Una fuente con una codificación personalizada (Differences) o que depende de la codificación incorporada de la fuente: no hay una correspondencia fiable, así que el editor no adivina y recurre a una fuente de reserva; de lo contrario el texto saldría ilegible.

Cuando un carácter no está en la fuente original, se usa una fuente de reserva. Las letras latinas sencillas usan la más cercana entre Helvetica, Times y Courier, fuentes estándar que tiene todo visor, así que no hace falta incrustar nada. Todo lo demás, como caracteres chinos, kana, hangul, tailandés, letras latinas con acento, cirílico y griego, usa una fuente Noto de código abierto: el servidor toma los caracteres de la petición y recorta solo esos glifos de la fuente completa con la biblioteca de subsetting de código abierto HarfBuzz, normalmente unos pocos KB, y el navegador los incrusta en tu archivo. La forma regional de un carácter chino sigue el idioma de la interfaz: chino simplificado, tradicional, japonés o coreano.

Los glifos se incrustan en lugar de escribir solo el nombre de una fuente porque una fuente referenciada solo por su nombre se sustituye por la que cada visor elija como reserva, y el peso puede variar de un visor a otro; una vez incrustada, todos los visores muestran las mismas formas.

Por qué solo una línea cada vez

El editor no tiene motor de maquetación. Cada posición de glifo está fijada en el archivo; el texto nuevo simplemente se dispone hacia la derecha desde el punto de partida usando los anchos de la fuente, sin lógica de «saltar de línea en el borde», y nada de lo que viene después se mueve. Si alargas una línea, los caracteres sobrantes siguen hacia la derecha, y lo que pase del borde de la página no se ve. Reescribir un párrafo o añadir filas a una tabla exige una maquetación nueva, lo que significa volver al archivo de origen con el que se hizo el PDF.

Los anchos son además solo los anchos de avance propios de la fuente (cuánto avanza la posición de escritura tras cada glifo), sin kerning ni sustitución de glifos. El texto que no necesita shaping (la elección y colocación de glifos según el contexto: latino, cirílico, griego y caracteres chinos) se dispone correctamente. Las marcas de tono del tailandés necesitan posicionamiento de glifos para quedar en su sitio, algo que el editor no hace, así que pueden quedar desplazadas. El árabe necesita formas de glifo que dependen del contexto y disposición de derecha a izquierda, el hebreo necesita disposición de derecha a izquierda y las escrituras índicas necesitan que consonantes y signos vocálicos se combinen en glifos; todo ello requiere shaping de texto completo, que el editor no hace por ahora, de modo que escribirlos se rechaza en lugar de producir caracteres erróneos.

Otros dos límites vienen del propio archivo. El contenido de una página escaneada es una sola imagen sin operadores de texto, así que no hay nada que borrar ni cambiar. Cuando se edita un archivo con firma digital, el contenido original que la firma protegía ha cambiado y la firma deja de ser válida.

Compruébalo tú mismo

Puedes ver los cambios descritos arriba en un archivo descargado con tres comandos:

pdftotext -raw edited.pdf -      # extrae en orden del stream de contenido: el texto antiguo ya no está, la línea editada va la última
pdffonts edited.pdf              # lista de fuentes: las fuentes originales que se reutilizaron y el subconjunto de fuente recién incrustado
qpdf --qdf --object-streams=disable edited.pdf edited.qdf   # expande el stream de contenido; el bloque BT ... ET añadido está al final

Sigue leyendo

Open tool
Process in the browser — no watermark, files removed after the job.
Open tool