Saltar al contingut principal

Capítol 5.4 · Part II · L'ofici

Format del document: imatges, taules i vídeos

Els recursos en el text: referències i insercions, numeració, col·locació i on va a parar un flotant, ajust del text, mida dels mapes de bits, zones segures, àncores de còmic i vídeos

Actualitzat 2026-10-1644 minAl capítol 5 Format del documentenescadefritptzhjaar

En poques paraules

Aquesta pàgina explica les imatges, les taules i els vídeos d'un llibre. Els afegeixes una vegada i els esmentes en el text, i Postext col·loca cadascun a prop del lloc on s'esmenta per primera vegada. Pots triar on va: a dalt d'una pàgina, a tota l'amplada de les columnes o just on l'escrius. El text pot envoltar una imatge. Una imatge pot marcar la part que sempre s'ha de veure quan es retalla perquè hi càpiga. Els vídeos es reprodueixen a la vista web i als llibres electrònics, i en paper mostren una imatge.

#Recursos

Les imatges, els SVG, les taules i els vídeos no s'escriuen en línia. Es declaren una sola vegada com a recursos (gestionats al tauler Recursos del Sandbox, que ofereix pujada d'imatges i SVG, un editor interactiu de taules, vídeos de YouTube, de Vimeo o pujats, i edició de peus i de col·locació) i després es connecten al text per id. N'hi ha prou de fer referència a un recurs per incorporar-lo: l'esmentes una vegada amb :ref{id="…"} i el motor fa flotar la figura o la taula al primer espai lliure després d'aquesta referència — el final de la columna on l'esmentes, el principi de la següent, una banda de la pàgina següent —, igual que faria un tipògraf d'impremta. No el col·loques una segona vegada.

Totes dues formes de sota són sintaxi completament nova que no xoca amb CommonMark, de manera que un document que les faci servir continua llegint-se com a text pla en qualsevol altre visor de markdown.

#Referència en línia (la forma principal)

Fes referència a un recurs des del text amb :ref{id="…"}. La primera referència incorpora el recurs (perquè es col·loqui a la pàgina) i renderitza el seu número calculat, precedit per defecte per l'etiqueta curta del tipus:

Com es veu a :ref{id="lighthouse-diagram"}, la sala de la llanterna queda sobre la galeria.

es renderitza com: Com es veu a Fig. 1.7, la sala de la llanterna queda sobre la galeria. — i el diagrama mateix flota al primer espai lliure després de la frase (el final d'aquesta columna, el principi de la següent, o una banda de la pàgina següent), mentre aquesta frase i el text posterior continuen fluint sense interrupció.

El text no es talla mai al punt de la referència. On aterra el recurs —el primer espai lliure, o només un espai superior o inferior; en una sola columna o a tota l'amplada— ho decideix la seva col·locació (vegeu Col·locació més avall), juntament amb el lloc on l'esmentes: la cerca comença just després de la referència.

#Inserció en bloc (opcional, col·locació en línia explícita)

A vegades vols que un recurs quedi en un punt exacte del flux en lloc de flotar. Renuncia al flotament donant al recurs placement.position: "here" i inserint-lo amb ::resource{id="…"} en una línia pròpia:

Aquí hi ha el plànol que vam comentar.
 
::resource{id="lighthouse-diagram"}
 
Les dependències del faroner ocupen l'ala est.

Per a un recurs que flota, la directiva ::resource és innecessària —el :ref ja l'ha col·locat, i un ::resource redundant per al mateix id es tracta com una altra referència, no com una segona còpia. Un ::resource només renderitza el recurs en línia quan la col·locació resolta és "here". Un recurs en línia conserva una línia d'espai a sobre (el buit dels flotants), com ho faria un flotant, tret que el bloc anterior en demani més. En el text corregut conserva el mateix espai a sota; després, el text que segueix torna a la retícula de base, i això pot afegir fins a una línia més. Un encapçalament, una llista, un requadre o un altre recurs en línia just després comparteix aquest espai amb el seu propi espai superior: s'aplica el més gran dels dos, no la suma. (Fins a postext 1.4, l'espai de sota era només el que deixava l'ajust a la retícula, entre res i una línia; layout.inlineResourceGap: 'above' manté aquesta regla, i els llibres desats abans de la 1.5 es llegeixen d'aquesta manera). Dins d'un requadre (:::callout) el recurs conserva el mateix espai, una línia del text del mateix requadre a sobre i, amb 'around', a sota; al principi o al final del requadre ja el separa el farciment. (Fins a postext 1.4 quedava enganxat al text del requadre; layout.inlineResourceGapInBoxes: false ho manté, i els llibres desats abans de la 1.5 amb requadres que insereixen un recurs es llegeixen així).

Un recurs en línia la col·locació del qual diu a més span: 'page' (placement: { position: 'here', span: 'page' }) ocupa l'amplada de la pàgina al punt de la seva directiva quan la maqueta té diverses columnes, com un requadre de pàgina: les columnes de sobre es tanquen a la mateixa alçada (equilibrades, o el recurs passa al cap de la pàgina següent si no es pot), es compon a tota l'amplada de la caixa amb el mateix espai a sobre i a sota, i el text continua a totes les columnes per sota. En una pàgina d'una sola columna es compon com abans, a tota la mesura. Un recurs span: 'column' amb columns es queda a la seva columna quan s'insereix en línia: les columnes només compten per als flotants. Des de postext 1.19.

L'id ha de coincidir amb un recurs definit al tauler Recursos. El motor renderitza el recurs (imatge, SVG o taula) amb el peu dibuixat a sota a manera de peu de figura/taula. El text del peu es compon a partir del captionPrefix del tipus de recurs, el número calculat i el peu propi del recurs — p. ex. Figura 1.7. El plànol original del far. La seva tipografia es controla des de Configuració › Estil de peus de recurs: l'etiqueta i la descripció comparteixen tipografia i mida, mentre que l'etiqueta conserva la seva pròpia configuració de negreta/cursiva/color; la separació sobre el peu és per defecte 0.75em i l'alineació, a l'esquerra. El peu es pot situar en canvi a sobre del recurs (captionStyle.position: 'above', de manera global o per tipus de recurs), opcionalment sobre una barra de color. Un recurs també pot portar una note — una línia breu de font o crèdits, amb el mateix format en línia i les mateixes marques :ref que el peu — composta en una mida menor sota el recurs (sota el peu quan aquest va a sota, sota el cos quan va a sobre) i estilitzada mitjançant captionStyle.note.

Salts de línia en peus i notes. Un peu o una nota és un únic paràgraf compost a la mida del seu buit, i un salt de línia escrit dins compta com un espai. Per començar una línia nova, escriu \\ —el salt forçat dels títols— o acaba la línia amb una barra inversa, el salt dur de Markdown: ¹ Mesurat a 20 °C. \\ ² Mitjana de tres assajos. compon cada nota d'una taula ampla en una línia pròpia. La línia anterior a un salt conserva la seva amplada natural, sense estirar-se fins a la mida, i dos salts seguits no deixen una línia buida (un espai de no separació entre ells, sí). En una cel·la de taula, \\ fa el mateix que un salt de línia: obre un paràgraf nou, i el sagnat de la línia següent es conserva, de manera que dos espais inicials continuen niant un element de llista. En el text mateix les dues barres són sempre un salt i no tenen escapament: per imprimir-les, escriu-les en codi en línia, on les barres s'imprimeixen tal com són. En la destinació d'un enllaç continuen formant part de l'URL, i en els atributs d'una directiva (el text d'un :ref), del valor; dins d'un xip, que es compon en una sola línia, un salt és un espai. (Fins a postext 1.4 les barres s'imprimien, i un peu o una nota només canviava de línia quan s'esgotava la mida).

Els recursos de taula dibuixen la seva pròpia retícula, amb l'estil definit a Configuració › Estil de taules: les cel·les de cos i de capçalera tenen tipografia totalment independent, el fons de la capçalera és per defecte #f0f0f0, les vores 0.75pt i el cellPadding 0.375em — qualsevol camp sense definir hereta del text del cos. Les amplades de columna formen part de la taula mateixa: TableModel.columnWidths desa un pes relatiu per columna ([2, 1, 1] dona a la primera columna la meitat de l'amplada); si no s'indica, les columnes es reparteixen l'amplada a parts iguals. Una taula també es pot compondre amb una variant amb nom: table.styleId tria un dels tableStyles del document (vegeu Configuració › Estils de taula amb nom), els camps sense definir del qual hereten de tableStyle; un id desconegut o absent conserva tableStyle.

Una cel·la col·loca el contingut amb TableCell.align (left, center, right; els elements de llista continuen alineats a l'esquerra) i TableCell.verticalAlign (top, per defecte, middle o bottom). L'alineació vertical mou tot el contingut de la cel·la —la imatge i el text que va a sota, com una sola unitat— dins d'una cel·la més alta que ell: una fila estirada per una veïna més llarga, o les files que abasta un rowSpan. S'aplica a totes les sortides (canvas, HTML, PDF), a les taules girades i a cada tram d'una taula partida entre pàgines. Totes dues es fixen per cel·la des dels botons d'alineació de la barra de l'editor de taules del sandbox.

Una cel·la de taula també pot contenir una imatge. TableCell.image anomena un recurs d'imatge o SVG pel seu id ({ "resourceId": "fig-brazo", "width": 0.7 }): la imatge es dibuixa dins de la cel·la — mai no es numera, no flota ni porta peu — ajustada a l'amplada interior de la cel·la (o a la fracció que indiqui width, per defecte 1) conservant la proporció, alineada com el text de la cel·la, i el text de la cel·la, si n'hi ha, va a sota. La fila creix per allotjar-la. A l'editor de taules del sandbox, el botó d'imatge de la barra tria el recurs per a la cel·la activa i un camp d'amplada fixa la fracció. Un id que no correspongui a cap recurs d'imatge deixa la cel·la només amb text.

Una cel·la pot portar el seu propi farciment. TableCell.background és un valor de color ({ "hex": "#c1dfd6", "model": "hex" }, opcionalment vinculat a una entrada de la paleta del document amb paletteId) que es pinta en lloc del fons de capçalera o de cos de l'estil — així una matriu de compatibilitats ombreja les seves cel·les en verd, vermell i groc. A l'editor de taules del sandbox es fixa amb el control de farciment de la barra. Per donar la clau d'aquests farciments, la llegenda, la nota i qualsevol bloc de text admeten una mostra de color en línia: :swatch{color="#c1dfd6"} (un hexadecimal, o l'id d'una entrada de la paleta — :swatch{color="table-compatible"}) compon un petit quadrat sobre la línia de base, de tres quarts del cos, farcit amb el color i perfilat amb el color del text, de manera que una nota pot dir :swatch{color="ok"}: compatibles; :swatch{color="no"}: incompatibles. Un color que no es resol en res dibuixa només el perfil. L'hexadecimal pot portar canal alfa (#rrggbbaa, #rgba), i també serveixen els colors rgb() / rgba(), de manera que un farciment de cel·la translúcid té una clau igual de translúcida (consulta Configuració › Transparència).

Els recursos SVG també es poden recolorir per a impressió a una sola tinta plana mitjançant diagramStyle.singleInk (per defecte false). En activar-lo, cada color del diagrama SVG es reassigna a un matís de diagramStyle.inkColor segons la seva luminància (per defecte el color principal de la paleta, #295AA3) — el blanc s'assigna al paper i el negre a la tinta plena — de manera que les figures es reprodueixen amb fidelitat quan el document s'imprimeix amb una única tinta plana. Vegeu Configuració › Estil de diagrames.

Una inserció mal formada (sense id, amb id buit, amb l'id sense cometes o entre cometes simples, o amb atributs de més) no es promou a bloc de recurs; recau en l'anàlisi de paràgraf normal i continua sent visible a la sortida. El mateix li passa a una línia d'inserció ben formada enganxada sota una línia de paràgraf sense una línia en blanc entre totes dues: es llegeix com a part d'aquest paràgraf. Totes dues generen un avís malformedEmbed, que el tauler Revisió del sandbox mostra com a Inserció composta com a text.

Les referències en línia es reconeixen dins de qualsevol bloc de text — paràgrafs, encapçalaments, citacions i elements de llista — i poden conviure amb negreta, cursiva, codi en línia i matemàtiques en línia.

Opcions de la referència

La directiva :ref admet tres atributs opcionals, en qualsevol ordre. style selecciona com es renderitza l'etiqueta calculada: style="number" imprimeix el número sol (1.7), style="full" imprimeix el nom complet del tipus seguit del número (Figura 1.7), i quan s'omet style s'usa l'etiqueta curta (shortLabel) del tipus seguida del número (Fig. 1.7). case canvia les majúscules i minúscules només de la part de l'etiqueta — lower, upper o capitalize — sense tocar el número. text és una anul·lació literal que substitueix qualsevol etiqueta calculada i té prioritat tant sobre style com sobre case. Les opcions de renderització, una al costat de l'altra:

SintaxiRenderitzaNotes
:ref{id="…"}Fig. 1.7Estil per defecte: l'etiqueta curta (shortLabel) del tipus seguida del número, unides amb un espai indivisible perquè no se separin mai al final de la línia.
:ref{id="…" style="number"}1.7El número calculat sol, sense etiqueta.
:ref{id="…" style="full"}Figura 1.7El nom complet (name) del tipus seguit del número. Útil a l'inici d'una frase o on l'abreviatura es llegeixi malament.
:ref{id="…" case="lower"}fig. 1.7Canvia la caixa només de l'etiqueta: lower (fig. 1.7), upper (FIG. 1.7) o capitalize (primera lletra en majúscula). Es combina amb style="full" (figura 1.7); el número no es toca mai, i un valor no reconegut s'ignora.
:ref{id="…" text="vegeu el plànol"}vegeu el plànolUna anul·lació explícita. El text donat s'usa literalment en lloc de qualsevol etiqueta calculada — útil per a enllaços de prosa com "com hem vist abans". Quan hi és, text té prioritat sobre style i case.

Si un :ref (o un ::resource) anomena un id sense recurs corresponent, l'etiqueta recau en ? (amb text= s'imprimeix aquesta etiqueta, igualment sense número ni enllaç) i el sandbox emet un avís de recurs desconegut. El motor el registra com una entrada unknownResourceId als contentWarnings del document, amb el rang d'origen i la pàgina de la referència; també per a un :ref dins del peu, la nota o una cel·la de taula d'un recurs que el text usa.

#Numeració per primera referència

El número d'un recurs s'assigna la primera vegada que s'esmenta en ordre de lectura — tant si aquesta primera menció és una inserció en bloc ::resource com una referència en línia :ref. A partir d'aquí, tota referència al mateix id imprimeix aquest mateix número.

Això vol dir que els números segueixen l'ordre en què el lector els troba, no l'ordre en què es van crear els recursos al tauler:

  • Si fas :ref d'una figura a la introducció i només la insereixes (::resource) dues pàgines després, igualment pren el número de la introducció — la referència ha arribat primer.
  • Inserir una referència nova abans en el document renumera automàticament tot el que ve després. No hi ha cap numeració manual que calgui mantenir sincronitzada.

La numeració és per tipus de recurs i respecta l'àmbit de reinici i el format de comptador de cada tipus — vegeu Configuració › Tipus de recurs per als tokens de plantilla ({h1}, {n}), resetOn i counterFormat.

Només compta el que el text referencia: un recurs que només dibuixa un disseny (un element d'imatge d'una obertura de capítol, per exemple) no porta número i deixa el comptador com estava. I {h1} compta tots els encapçalaments de nivell 1 l'estil dels quals no fixi numbered: false, també els que tenen un numberingTemplate buit, així que un article l'únic H1 del qual és el títol numera les figures 1.1, 1.2… per defecte. Configuració › Què es numera explica les dues regles i la configuració per obtenir Figura 1, 2….

#Col·locació

Cada recurs té una col·locació que decideix on aterra el seu flotant, resolta per recurs (el seu propi placement), després el defaultPlacement del seu tipus, i finalment el valor per defecte integrat auto / column:

CampValorsSignificat
position"auto" · "top" · "bottom" · "here""auto" (el valor per defecte) pren el primer buit lliure després de la referència, a dalt o a baix; "top" / "bottom" només accepten buits d'aquest tipus; "here" renuncia al flotament i insereix el recurs en línia a la directiva ::resource (una taula col·locada allà es talla entre files quan no cap en el que queda de la seva columna; vegeu Taules més altes que la pàgina).
width, align0 < width < 1; "left" · "center" · "right"Un recurs més estret que el seu buit: width és la fracció de l'amplada de la columna (o de la pàgina) que ocupa i align on se situa dins del buit (una taula petita centrada a la seva columna; una banda a amplada de pàgina amb una imatge que abasta una sola columna). Una imatge més estreta que el seu buit —un mapa de bits més petit que la columna, o una que layout.fitFiguresToPage ha reduït— també s'hi situa segons align, sota un peu que conserva la mida del buit. Val tant per als flotants com per a les insercions ::resource en línia.
captionSidetrue · falseEn una maquetació de columna i mitja amb la columna lateral reservada a flotants (layout.sideColumnRole: 'floats'), un flotant "column" amb captionSide manté el cos a la columna principal i compon el peu (i la nota) a la columna lateral, a l'altura de la vora superior de la figura —o de la inferior en un flotant de peu—; la columna lateral cedeix aquesta banda. Una pàgina sense aquesta columna deixa el peu sota la figura. Des de postext 1.28 un recurs posat en el text ("here"), d'una columna, també l'admet: el seu peu i la seva nota van a la columna lateral, a l'altura de la vora superior del seu cos, el bloc en el text fa el que fa el cos sol, i les figures i requadres laterals que venen després respecten el peu. On la columna lateral està ocupada al costat del recurs, el peu queda sota el cos; un recurs que passa a la columna o pàgina següent ho torna a decidir allà. No dins d'un requadre, ni en una pàgina vertical, ni en una imatge envoltada pel text. layout.inlineCaptionSide: false deixa els peus al marge només per als flotants de columna.
span"column" · "page"Ocupa una sola columna, o trenca el flux de columnes i abasta tota l'amplada del contingut travessant totes les columnes. En una maquetació d'una sola columna totes dues opcions són idèntiques.
columnsun nombre enter, 1 per defecteEn una pàgina de diverses columnes, un flotant "column" sobre aquest nombre de columnes contigües, espais entre columnes inclosos: una foto sobre dues de les cinc columnes d'un diari. Ocupa el cap d'una sèrie de columnes buides que comencen a la mateixa altura, o el peu de la columna que el cita i de les columnes buides que la segueixen. Tantes columnes com té la pàgina, o més, el converteixen en un flotant a tota l'amplada. No s'aplica als span "page" i "side", a un recurs girat ni a una inserció en línia ("here"); captionSide només val per a un flotant d'una columna. Des de postext 1.18.
rotate"ccw" · "cw"Compon el recurs girat un quart de volta — una taula apaïsada en un llibre vertical. "ccw" el gira en sentit antihorari, amb la capçalera cap a la vora esquerra de la pàgina (el lector gira el llibre en sentit horari), la convenció habitual; "cw" en l'altre sentit. Un recurs girat és sempre un flotant a tota l'amplada en una pàgina pròpia: es compon al llarg de l'alçada de l'àrea de contingut, arrodonida cap avall a línies senceres de la retícula i menys una línia del cos, el buit que deixa tota banda de flotants (una àrea de text de 237 mm amb una retícula de 14 pt té 47 línies, 232,1 mm, així que el recurs n'ocupa 46, 227,2 mm), queda enganxat al llom quan els marges són simètrics (a l'esquerra si no ho són) i una taula massa ampla per a una pàgina es talla entre files i continua, girada, a les pàgines següents amb la capçalera repetida, exactament com una taula vertical més alta que la pàgina. Una figura girada s'escala per cabre a la pàgina. S'ignora en una inserció en línia ("here").
shrink, minScale"never" · "page" · "slot"; 0 < minScale ≤ 1, per defecte 0.7Redueix una imatge flotant (mapa de bits, SVG, el pòster d'un vídeo), sense canviar-ne les proporcions, a l'espai que té un buit en lloc de portar-la més endavant. "never" (el valor per defecte) la compon a la seva mida. "page" la redueix només quan és massa alta per a la banda d'una pàgina nova: l'àrea de contingut menys el que ja hi ha a la pàgina (una obertura, altres flotants, notes al peu) i l'espai del flotant, com una làmina de catàleg que s'ajusta a la seva pàgina. "slot" també la redueix perquè entri en un buit de la pàgina que la cita, o en l'espai que queda al costat d'una altra banda, si hi cap a minScale o més; si no, continua endavant com sempre. Els buits es proven en el seu ordre habitual i la banda continua acabant a la retícula de línies de base. Una imatge amb zona segura es retalla dins d'aquesta abans de reduir-se (vegeu Zona segura). En una pàgina nova, on no té cap altre lloc on anar, una imatge que no hi cap ni a minScale es compon a aquesta escala i sobresurt de la banda. La maquetació avisa de cada flotant reduït amb un avís floatShrunk. Les taules (que es divideixen), les caixes flotants, les tires de còmic, els recursos girats i les insercions en línia no es redueixen mai. El valor del document és layout.floatShrink. Des de postext 1.24.
captionMeasure"slot" · "body"La mesura del peu i la nota d'una imatge més estreta que el seu buit (reduïda, o un mapa de bits més petit que la columna): "slot" (el valor per defecte) manté la mesura del buit; "body" els compon tan amples com la imatge, a sota segons align, de manera que una làmina centrada porta el peu centrat a sota. Per a flotants i insercions en línia per igual. Des de postext 1.24.
wrap, wrapGap"none" · "left" · "right" · "start" · "end"; una longitudCompon el text al costat del recurs: aquest es col·loca en aquest costat de la columna, i les línies del costat s'ajusten a la mesura que queda, a wrapGap de la seva caixa (peu inclòs), i tornen a la mesura completa a sota. L'admeten una inserció en línia ("here") i un flotant d'una columna al capdamunt o al peu d'una columna; els flotants de pàgina, de diverses columnes, de columna lateral i girats conserven la seva banda. El recurs ocupa width de la columna, o layout.wrap.defaultWidth (0,45). wrapGap val per defecte layout.wrap.gap, o una línia del cos. Vegeu Ajust del text. Des de postext 1.24.
citingPagetrue · false, per defecte falseDeixa que un flotant "top" o "auto" ocupi el capdamunt de la pàgina (un flotant a l'amplada de la pàgina) o de la columna (un flotant de columna, també a l'amplada de columns) on cau la línia que el cita per primer cop, com fa la col·locació t de LaTeX, en lloc del primer espai lliure després d'aquesta línia. El text que hi ha damunt de la referència baixa sota el flotant. Només ho fa quan el flotant hi cap dins de layout.maxTopFraction de la columna (0,7 per defecte), quan els flotants anteriors de la seva seqüència de numeració ja estan col·locats, quan cap salt explícit no obre la pàgina (la primera pàgina d'un capítol, una part, un :::pagebreak) i res a l'amplada de la pàgina no queda damunt de la línia que el cita, i quan, així col·locat, la línia que el cita continua caient en aquesta pàgina (en una columna que el flotant encapçala); si no, el flotant pren el seu espai habitual. Els flotants girats, els de la columna lateral i la resta d'una taula partida entre pàgines no es mouen mai així. Per defecte: el defaultPlacement del tipus i després layout.floatsAtCitingPage. Des de postext 1.25.

Un flotant ocupa el primer buit lliure després de la seva primera referència, en ordre de lectura: el final de la columna on hi ha la referència, després el principi i el final de la columna buida següent de la mateixa pàgina, i després les bandes de la pàgina següent que obri el flux (un flotant a amplada de pàgina ocupa el peu de la pàgina quan totes les columnes encara hi tenen lloc per a ell; si no, una banda de la pàgina següent). També compta una pàgina que obre una figura o una taula en línia: un flotant que espera aquesta pàgina n'ocupa la capçalera, per sobre de la figura o la taula, quan totes dues hi caben; si no hi caben, la figura o la taula es queda amb la pàgina i el flotant espera la següent. Fins a postext 1.4 aquesta pàgina se saltava, i el flotant esperava la de després encara que hi cabessin totes dues. Es compon a la seva mida tret que el seu shrink li permeti reduir-se a l'espai d'un buit (vegeu la taula de dalt), i mai no aterra abans de la seva referència. Els flotants d'una mateixa seqüència de numeració apareixen en ordre de referència: una figura que no cap enlloc d'una pàgina reté les figures que vénen darrere (una taula en espera no reté una figura, ni a l'inrevés), així que la figura 12 no apareix mai abans que la figura 11. Una taula que hauria d'esperar, en lloc d'això, es talla: si rep la capçalera d'una columna buida, pren les files que hi caben i continua al buit següent — la columna del costat o la pàgina següent — amb les files de capçalera repetides (vegeu tableStyle.overflow). Un flotant top o auto amb citingPage activat pot encapçalar en canvi la pàgina (o la columna) on cau la línia que el cita, i el text de damunt de la referència baixa sota seu: queda pintat damunt de la seva referència a la mateixa pàgina, mai en una d'anterior, i en un PDF etiquetat i en l'HTML es continua llegint després d'ella. El motor ho resol en unes quantes passades més i només ho manté mentre la línia que el cita continuï en aquesta pàgina.

Els flotants no s'escapen mai del seu capítol: en una obertura de capítol (un nivell d'encapçalament amb breakBefore o span: 'page'), en un :::part, en un estil d'avís amb floatBarrier: true (la caixa de «punts clau» que tanca el capítol) i al final del document, tot flotant pendent es col·loca primer — als buits lliures de la pàgina, o en pàgines obertes per davant del límit. Un flotant que cita per primera vegada la mateixa obertura (un títol de capítol que anomena la seva figura), o el primer bloc després d'un :::part, pertany al capítol nou: cau després d'aquesta línia, com qualsevol altre. Una figura o taula que ha demanat el cap d'una pàgina pot ocupar llavors el peu de la pàgina de tancament del capítol, sota les columnes equilibrades, en lloc d'una pàgina pròpia. Un :::pagebreak simplement envia els flotants pendents a la pàgina que el segueix.

Sota una obertura a amplada de pàgina composta sobre dues o més columnes de text, la columna de la mateixa obertura compta com a buida al capdamunt mentre res no segueixi l'obertura en ella: una caixa flotant posada just després de l'obertura, o un recurs inserit allà amb ::resource, ocupa el capdamunt de la primera columna, sota l'obertura i a l'alçada dels capdamunts de les altres columnes (en diverses columnes a partir d'aquesta amb columns), i el text de la columna comença a sota. Un flotant citat al text continua anant després de la línia que el cita. Fins a postext 1.24 la primera columna no oferia aquest buit i el flotant queia a partir de la segona; layout.floatsUnderOpener: false ho manté (vegeu Configuració › Disposició).

Les caixes laterals (span="side") tampoc no surten del seu capítol. Una caixa que no cap a la columna lateral de la seva pàgina ocupa la de la pàgina següent; si abans s'acaba el capítol, o el document, cada caixa que encara espera es compon a la columna lateral d'una pàgina oberta després del text, en l'ordre de les seves tanques, i una figura lateral citada després d'elles queda al darrere. Aquesta pàgina no té text, de manera que la composició avisa de cada caixa i figura que hi ha (afterText). Una caixa més alta que una columna lateral buida es compon igualment i s'avisa (calloutOverflow), i el que tot i així no troba pàgina també s'avisa (unplaced) en lloc de perdre's. Fins a postext 1.24 només s'obria la primera d'aquestes pàgines i les caixes restants es perdien sense avís.

Les bandes de flotants es corregeixen contra la retícula de base perquè el text del voltant mantingui el ritme vertical de tota la pàgina. Una banda superior amplia el seu marge inferior fins a la línia següent de la retícula, de manera que el text sota el flotant queda alineat amb les columnes veïnes i amb la pàgina encarada. Un flotant inferior s'ancora de manera que l'última línia de la seva llegenda comparteixi línia de base amb l'última línia de text de les altres columnes (el contingut sense llegenda alinea la vora inferior amb l'última cel·la de la retícula) — així, les pàgines plenes acaben a la mateixa altura entre columnes i entre pàgines encarades.

A la pàgina de tancament d'un capítol —i del document— res no segueix les figures i taules a l'amplada de la pàgina que queden sota l'última banda de text, així que pugen fins a quedar a un buit de flotant per sota, apilades en el seu ordre, en lloc de deixar blanc entre el text i una figura al peu de la pàgina. Val també per a un flotant position: 'bottom'. Per deixar-les al peu, com a qualsevol altra pàgina, posa layout.hugClosingFloats: false (consulta Configuració › Disposició). A les pàgines amb columna lateral no es mouen mai.

Els tres backends — la previsualització en canvas, el visor HTML i la sortida PDF — renderitzen recursos. Al backend HTML, les imatges viuen fora del document, així que l'amfitrió les subministra mitjançant l'opció de resolució resourceImageUrl(fileId); quan falta el resolutor (o no retorna res per a un fitxer), el recurs es renderitza com una caixa neutra de farciment perquè la maquetació es mantingui estable. El fitxer d'un vídeo arriba de la mateixa manera per resourceVideoUrl(fileId) (vegeu Vídeos).

On pot caure un flotant

«Mai abans de la seva referència» es compta des de la línia que cita el flotant: el flotant espera que aquesta línia estigui composta i ocupa el primer buit lliure que la segueix en ordre de lectura — el cap de la pàgina on es compon la línia ve abans. Un flotant lateral (span: 'side', a la columna lateral reservada a flotants d'una disposició de columna i mitja) és l'excepció: s'apila a la columna lateral al costat del text que el cita, i pot quedar a la pàgina més amunt que la línia que el cita. Per a una figura citada a la pàgina 5:

Col·locacióA la pàgina 5Si no
top, span: 'page'Mai: la banda del cap de la pàgina és per sobre de la línia que la cita.La banda superior de la pàgina 6.
top, span: 'column'El cap d'una columna posterior que continuï buida — citada a la primera de dues columnes, pot obrir la segona.El cap d'una columna de la pàgina 6.
auto o bottom, span: 'page'La banda del peu de la pàgina 5, quan totes les columnes encara hi tenen lloc per a ell.Una banda de la pàgina 6.
auto o bottom, span: 'column'El peu de la columna que el cita; després el peu (tots dos) o el cap (només auto) d'una columna posterior buida.La pàgina 6.
  • La pàgina d'una obertura de capítol segueix les mateixes regles: un flotant a amplada de pàgina auto o bottom citat al primer paràgraf de l'obertura pot ocupar la banda del peu d'aquesta pàgina, sota el text; un de top obre la pàgina següent. Per tenir la imatge a la pàgina que la cita, usa auto o bottom, o dibuixa-la com a element d'imatge del disseny de l'obertura.
  • Dos flotants de columna citats al mateix paràgraf ocupen els dos buits següents: normalment el primer, el peu de la columna que els cita, i el segon, el cap de la columna buida següent — l'un al costat de l'altre a la pàgina.
  • En una disposició d'una columna un flotant a amplada de pàgina és un flotant de columna, i valen les mateixes regles: un flotant top citat en una pàgina cau al cap de la següent.
  • Un paràgraf que passa d'una pàgina a la següent també compta des de la seva línia de cita. Quan el paràgraf comença al peu de la pàgina 5 i la referència cau a la 6 — o el paràgraf sencer passa a la 6 perquè al peu de la 5 no hi caben prou línies seves —, la referència és a la 6: un flotant top obre la pàgina 7, i un d'auto ocupa el peu de la 6 si hi cap. El mateix val entre les columnes d'una pàgina i per a una caixa partida entre pàgines: la figura que cita la seva segona part espera aquesta part.
  • Canvia a postext 1.5. Fins a postext 1.4 un flotant entrava a la cua quan la maquetació arribava al paràgraf que el cita, així que la pàgina a la qual aquest paràgraf passava (o es traslladava sencer) es podia obrir amb el flotant, per sobre de la línia que porta la referència. Aquesta figura cau ara una pàgina més tard, o al peu de la pàgina quan demana auto; el nombre de pàgines pot canviar.

#Ajust del text

Una imatge, una taula o una caixa més estreta que la columna es pot col·locar a un dels costats amb el text compost al costat, com en una revista o un butlletí. Dona a la seva col·locació un costat de wrap i, si vols, un width:

{ "id": "bed", "typeId": "figure", "kind": "svg", "caption": "El nou bancal.",
  "placement": { "position": "here", "wrap": "right", "width": 0.4 } }
  • En línia ("here"). El recurs es col·loca al seu costat de la columna, amb la part superior a l'altura de la part superior de la línia següent a la línia ::resource, i els paràgrafs, cites i elements de llista que segueixen es componen al costat a la mesura que queda, i després a sota a la mesura completa. Un paràgraf que comença al costat i acaba a sota continua sent un sol paràgraf: sense tall ni espai afegit al peu de la imatge. Totes les línies continuen a la retícula de línies base; l'espai sota la imatge és la seva separació arrodonida a línies senceres de la retícula.
  • Un flotant de columna. Un flotant span: "column" d'una columna d'amplada, al capdamunt ("top", o "auto" al capdamunt d'una columna) o al peu ("bottom", "auto") d'una columna, es col·loca a la seva banda com qualsevol flotant; les primeres línies de la columna, o les últimes, es componen llavors al costat. En una pàgina de dues columnes el flotant pertany a la seva columna, i l'altra va a tota l'amplada.
  • Una caixa. Un :::callout admet els mateixos ajustos com a atributs: :::callout{wrap="right" width=0.4} col·loca una cita destacada o un requadre on apareix, amb el text que el segueix al costat, i placement="top" o "bottom" amb wrap el fa flotar al capdamunt o al peu d'una columna. Una caixa ajustada es compon sencera i mai no es divideix.
  • Què va a sota. Un encapçalament, una fórmula destacada, una figura o taula, una caixa i un poema no es componen al costat d'un element ajustat: van a sota, i el blanc al costat per damunt d'ells queda buit. Sortir de la columna (el peu, un :::columnbreak, un salt de pàgina) acaba allà l'ajust: l'element pertany a la seva columna. Quan el bloc que segueix un recurs en línia no pot anar al costat, el recurs ocupa la seva banda, com sense wrap.
  • Separació i límits. wrapGap (o layout.wrap.gap, o una línia del cos) separa l'element, peu inclòs, del text del costat i del de sota. Si el text del costat quedés més estret que layout.wrap.minTextWidth (12 em del cos), o l'element fos més baix que layout.wrap.minLinesBeside línies (2), ocupa la banda sencera i un avís textWrap ho indica. Un en línia massa alt per a l'espai que queda a la columna passa a la següent amb la seva àncora, amb el mateix avís.
  • Costats. left i right són costats del flux del text, com a align: en un llibre de dreta a esquerra left és la dreta del full. start i end anomenen els mateixos costats.
  • Sortides. El llenç, el visor HTML, el PDF i l'EPUB de maquetació fixa componen les línies tal com es van maquetar; un PDF etiquetat llegeix la imatge o la caixa abans del paràgraf que va al costat. Un EPUB adaptable la fa flotar al seu costat amb CSS, amb la mateixa part de l'amplada del text.
  • Encara no. Text a tots dos costats d'una imatge, ajust al contorn, ajust dins el contingut d'una caixa i ajust en escriptura vertical (l'element conserva la banda, amb un avís). Les columnes amb un element ajustat queden fora de l'equilibrat de columnes.

#Mida dels mapes de bits

Un mapa de bits declara els seus píxels: bitmap.width i bitmap.height són els píxels del fitxer, no una mida d'impressió. Quants n'entren en una polzada decideix a quina mida es compon la imatge abans que el seu buit la limiti. Hi ha tres maneres de donar-li mida:

  • Els seus píxels als dpi de la pàgina (el valor per defecte). Sense resolució, un píxel de la imatge és un píxel de la maquetació (page.dpi, 300 si no s'indica): una fotografia de 2400 px fa 8 polzades (203,2 mm) d'amplada en una pàgina a 300 dpi, i el doble en una a 150.
  • Una resolució. bitmap.resolution són els ppp de la imatge a la seva mida natural d'impressió, de manera que la seva amplada natural és width × page.dpi / resolution en una pàgina de qualsevol resolució: 2400 px amb resolution: 300 fan 203,2 mm d'amplada en una pàgina maquetada a 150 dpi o a 300. layout.bitmapResolution dona una resolució a tot mapa de bits que no en tingui una de pròpia: un nombre (300), o 'file', la resolució que indica el seu fitxer (bitmap.fileResolution: el pHYs d'un PNG, la densitat JFIF o EXIF d'un JPEG, l'EXIF d'un WebP; en una imatge importada de Word, la mida a què Word la imprimia). Les càmeres, les captures de pantalla i les exportacions per al web sovint indiquen 72 o 96 ppp quan no saben res d'una mida d'impressió, així que amb 'file' aquests dos valors compten com a no indicats i la imatge conserva els seus píxels als dpi de la pàgina; un 72 declarat al recurs mateix es pren tal com està escrit. 'document', el valor per defecte, és la primera manera.
  • Una part de la columna. placement.width estreny un flotant o una inserció en línia a una fracció de la seva columna (o de la pàgina), i una imatge més gran que aquesta part s'hi redueix, tingui els píxels que tingui (vegeu Col·locació).

En tots els casos el buit limita la imatge, sense canviar-ne les proporcions, i una imatge més petita no s'amplia mai. La mateixa mida natural val per a una imatge en una cel·la de taula i per a un element image d'un disseny amb mida 'auto'. El PDF incrusta el fitxer tal com és, a la mida col·locada. El preflight revisa la resolució a què s'imprimeix cada imatge, i el tauler Recursos del Sandbox la mostra per a cada imatge. Des de postext 1.24.

{ "id": "port", "typeId": "figure", "kind": "bitmap", "caption": "El port a l'alba.",
  "bitmap": { "fileId": "port.jpg", "format": "jpeg", "width": 2400, "height": 1600, "resolution": 300 } }

bitmapInfo(bytes) (de postext i postext/bundle) llegeix els píxels d'un fitxer i la resolució que indica, { width, height, resolution?: { x, y, source } }; un paquet obert amb 'file' n'omple fileResolution, i el Sandbox la conserva per a cada imatge que s'hi puja.

#Zona segura

Un recurs bitmap o SVG pot marcar una zona segura: el rectangle de la imatge que conté allò que importa (una persona i una franja del paisatge que l'envolta, la part dibuixada d'un gràfic) i que sempre es veu. És el camp safeArea del recurs, quatre fraccions (0–1) de la mida intrínseca de la imatge mesurades des del seu angle superior esquerre: x i width són fraccions de l'amplada, y i height de l'alçada. El nom diu què s'ha de conservar; una caixa de retall diria per on tallar.

const port: Resource = {
  id: 'port', typeId: 'figure', kind: 'bitmap', caption: 'El port a l\'alba.',
  createdAt: 0, updatedAt: 0,
  bitmap: { fileId: 'port.jpg', format: 'jpeg', width: 2400, height: 1600 },
  // les barques i el moll: del 18 al 68 % de l'amplada, del 25 al 85 % de l'alçada
  safeArea: { x: 0.18, y: 0.25, width: 0.5, height: 0.6 },
};

Només es retalla una imatge que tingui zona segura. Aleshores el motor la pot mostrar amb qualsevol proporció entre la imatge sencera i la zona segura: més alta que la seva proporció pròpia retallant-ne els costats, com a màxim fins a l'amplada de la zona segura, o més baixa retallant-ne la part de dalt i la de baix, com a màxim fins a la seva alçada. L'amplada de la figura no canvia mai, només l'alçada. El que queda fora de la zona segura es retalla per cada costat en proporció al marge que hi ha, de manera que un motiu a l'esquerra del centre continua a l'esquerra del centre. Composta a 60 mm d'amplada, la imatge del port fa 40 mm d'alçada sencera i es pot mostrar amb qualsevol alçada entre 24 mm (dalt i baix retallats fins al 60 % de l'alçada) i 80 mm (els costats retallats fins a la meitat de l'amplada). Els valors que surten de la imatge s'ajusten a les vores; una zona amb algun valor que no és un nombre o amb un costat de menys del 2 % de la imatge, o que cobreix la imatge sencera, s'ignora, igual que el camp en una taula. Sense zona segura la imatge es mostra sempre sencera, com fins ara.

El motor aprofita aquest marge en quatre casos:

  • L'espai que queda en una columna. Una imatge en línia (position: 'here') una mica més alta que l'espai que li queda a la columna, també quan és el seu peu el que quedaria fora de la pàgina, es retalla dins de la zona segura per quedar-s'hi, en lloc de passar a la columna o la pàgina següent i deixar aquesta curta.
  • Pàgines més baixes que la figura. Amb layout.fitFiguresToPage, una imatge massa alta per a la pàgina primer es retalla dins de la zona segura, mantenint l'amplada, i només es redueix si encara no hi cap (vegeu Configuració › Disposició).
  • Bandes més baixes que la figura. Un flotant que placement.shrink redueix a l'espai del seu buit es retalla primer dins la seva zona segura, mantenint-ne l'amplada, i només després es redueix; la palanca flexFigure de sota no el fa créixer mai més enllà d'aquest espai.
  • Equilibratge de columnes. Una imatge amb zona segura col·locada en línia en una columna curta, o flotada al cap o al peu d'aquesta columna i només sobre ella, creix en línies senceres de la retícula de base fins a omplir les línies buides de la columna. Una imatge més alta no deixa cap forat visible, així que aquesta palanca, flexFigure, es prova just després de la caixa que tanca la columna i abans d'afegir espai sobre els encapçalaments o després de les llistes. Un flotant al cap d'una columna de la pàgina de tancament d'un capítol, o d'una banda de tancament, no creix, perquè allà els caps de columna queden anivellats (vegeu Configuració › Equilibratge de columnes).

El VDT anota el retall al bloc del recurs: bodySource és la part de la imatge que es veu a bodyRect, en les mateixes fraccions (no hi és quan es veu la imatge sencera), i bodyFlex dona els px que el cos encara podria encongir i créixer i els px que ja li han canviat les palanques ({ shrink, grow, delta }). La previsualització en canvas i el PDF retallen al cos i dibuixen la imatge sencera a la seva mida sense retallar; el visor HTML i l'EPUB de maquetació fixa posen la imatge amb object-fit: cover i l'object-position corresponent; un EPUB adaptable, que no té pàgina per omplir, mostra la imatge sencera. Un amfitrió que dibuixi les imatges pel seu compte té les funcions que exporta postext: resourceSafeArea i normalizeSafeArea (la zona tal com la llegeix el motor, o undefined), safeAreaHeightRange (el cos més baix i el més alt a una amplada), safeAreaSource (la part que es veu a una alçada donada) i uncroppedPictureBox (on dibuixar la imatge sencera abans de retallar), amb el tipus ResourceSafeArea. Al Sandbox el camp és Zona segura, en una imatge del tauler Recursos.

La recepta núm. 116 del Receptari, Fotos que creixen fins a omplir la columna, compon dues vegades un reportatge de revista a dues columnes, sense zones segures i amb elles, per comparar les pàgines l'una al costat de l'altra.

#Àncores dels personatges i zones lliures

Un dibuix que fa de vinyeta en un còmic també pot dir on són les seves persones, per a la retolació (vegeu Còmics). anchors enumera un punt per personatge i avoid les zones que cap bafarada no tapa, totes dues en fraccions del dibuix, com la zona segura:

const radio: Resource = {
  id: 'lh-radio', typeId: 'figure', kind: 'bitmap', createdAt: 0, updatedAt: 0,
  bitmap: { fileId: 'lh-radio.jpg', format: 'jpeg', width: 1000, height: 1000 },
  safeArea: { x: 0, y: 0.36, width: 0.62, height: 0.56 },
  anchors: [
    // el faroner: boca, cap (per a les bafarades de pensament) i cara
    { id: 'tomas', x: 0.345, y: 0.52, head: { x: 0.38, y: 0.44 }, face: { x: 0.29, y: 0.4, width: 0.16, height: 0.18 } },
  ],
  avoid: [{ x: 0, y: 0.44, width: 0.22, height: 0.26 }], // la ràdio
};

L'id d'una àncora és la clau del personatge al guió (tomas: …), o sfx per al punt on s'agrupen les onomatopeies de la vinyeta; x i y són la boca on apunta la cua d'una bafarada de diàleg, head el punt on apunten les bombolles d'una bafarada de pensament (la boca si no es defineix) i face un rectangle que cap bafarada no tapa. El motor passa cada punt a través del retall i del reflex de la vinyeta, de manera que una cua es manté sobre el seu personatge sigui quina sigui la forma de la vinyeta; una àncora fora de la zona segura genera comicAnchorOutsideSafeArea, perquè un retall la pot tallar. Les àncores pertanyen al dibuix i serveixen per a totes les traduccions del còmic. Una tercera llista, faces, desa les cares de qui no parla, com a rectangles iguals als d'avoid: cap bafarada no les tapa, mentre que una zona lliure cedeix quan a la vinyeta no li queda cap altre lloc. Només les llegeixen les vinyetes de còmic; una figura les ignora. Al Sandbox es marquen al diàleg Zona segura i retolació del tauler Recursos.

#Vídeos

Un recurs de vídeo (kind: 'video') és un vídeo de YouTube o de Vimeo, o un vídeo propi: un fitxer desat dins del llibre (MP4, WebM) o un vídeo en una adreça web, sigui un fitxer en un servidor o un flux HLS (una llista de reproducció .m3u8). Es col·loca, porta peu, flota i es cita com una imatge, i es numera en una seqüència pròpia: el tipus integrat video imprimeix Vídeo 1.1, Vídeo 1.2… al costat de Figura 1.1 i Taula 1.1 (vegeu Configuració › Tipus de recurs). Cada sortida el mostra com pot:

SortidaQuè mostra
Canvas, PDFLa portada, un fotograma del vídeo, amb una marca de reproducció i un codi QR que obre el vídeo (Configuració › Estil de vídeo). Al PDF la portada també és un enllaç al vídeo.
FolioLa portada, tal com s'imprimeix. Un clic a sobre reprodueix el vídeo a la mateixa pàgina, i el vídeo continua mentre el full passa (vegeu Vídeos a les pàgines de Folio, més avall). Els vídeos de YouTube i de Vimeo es queden en portada.
Visor HTMLEl reproductor del vídeo: el de YouTube o el de Vimeo, o el reproductor HTML5 del navegador per a un fitxer o una adreça. Safari i les versions recents de Chrome reprodueixen un flux HLS pel seu compte; en els altres navegadors l'amfitrió hi posa un reproductor com hls.js, com fa el Sandbox. Amb videoStyle.html: 'poster' mostra en el seu lloc la portada impresa.
EPUBUn fitxer es reprodueix al reproductor del mateix lector, empaquetat dins del llibre o llegit des de la seva adreça de producció. Un vídeo de YouTube o de Vimeo és la seva portada, enllaçada amb el vídeo: un EPUB no pot inserir el reproductor d'una pàgina web. Un flux HLS també és la seva portada enllaçada: una llista HLS no és cap tipus de mitjà que un EPUB pugui reproduir. Si el lector executa scripts, els fitxers d'una mateixa pàgina o capítol segueixen player.exclusive: en començar-ne un es posen en pausa els altres amb què no es reprodueix alhora.
const talk: Resource = {
  id: 'keeper-talk', typeId: 'video', kind: 'video',
  caption: 'The keeper explains the lamp.',
  altText: 'A lighthouse keeper beside the lamp',
  createdAt: 0, updatedAt: 0,
  video: {
    source: 'youtube',                        // 'youtube' | 'vimeo' | 'file'
    url: 'https://youtu.be/aqz-KE-bpKQ',
    poster: { fileId: 'talk.jpg', format: 'jpeg', width: 1280, height: 720 },
    start: 30,                                // es reprodueix des de 0:30; l'enllaç imprès també hi comença
  },
};

El text cita un vídeo com cita una figura: :ref{id="keeper-talk"} imprimeix Vídeo 1.1 i fa flotar la portada al primer espai lliure després de la referència, i ::resource{id="keeper-talk"} amb placement.position: 'here' la posa en línia. Els camps de Resource.video (ResourceVideo):

CampTipusSignificat
source'youtube' · 'vimeo' · 'file'D'on es reprodueix el vídeo: una pàgina de YouTube o de Vimeo, o un vídeo propi ('file'), pujat o en una adreça.
urlstringYouTube o Vimeo: l'adreça del vídeo, en qualsevol forma (una pàgina de visualització, youtu.be, Shorts, un enllaç d'inserció, youtube-nocookie.com; una pàgina de Vimeo, una pàgina de canal o un enllaç ocult amb el seu hash). Un fitxer: la seva adreça de producció, on el trobarà el llibre publicat. Un vídeo propi sense fitxer es reprodueix des d'aquesta adreça: un MP4 o un WebM en un servidor, o un flux HLS (…/master.m3u8).
fileId, formatstringUn fitxer: el vídeo pujat, desat fora de banda com un bitmap, i el seu format: 'mp4', 'webm', 'ogv', 'mov' o 'hls' per a un flux HLS. Sense format, el dedueix l'extensió de l'adreça (.m3u8 és 'hls'), i si no, 'mp4'.
posterEl fotograma de portada, un bitmap.
width, height, durationnumberLa mida del fotograma del vídeo en px (la seva proporció quan no hi ha portada) i la durada en segons.
posterTimenumberEl segon del fitxer el fotograma del qual fa de portada, desat perquè es pugui tornar a triar.
start, endnumberReprodueix des del segon start fins al segon end. El codi QR i l'enllaç del PDF també comencen a start.
playerVideoPlayerOptionsLes opcions de reproductor d'aquest vídeo, aplicades per sobre de videoStyle.player.

La portada. Es compon a la mesura del seu espai (o a la fracció placement.width d'aquest espai), amb la seva proporció i sigui quina sigui la seva mida en píxels: un fotograma de la mida d'una pantalla s'amplia en lloc d'imprimir-se petit. Com un bitmap, pot portar una zona segura i seguir placement.align. Un vídeo sense portada imprimeix un requadre fosc amb la proporció del vídeo (16:9 si no se'n sap res) i les marques a sobre, i genera l'avís de contingut videoWithoutPoster. Al Sandbox, la portada d'un vídeo de YouTube o de Vimeo es baixa de la plataforma en introduir-ne l'adreça, i la d'un fitxer és un fotograma que tries dins del vídeo.

L'adreça. El codi QR i l'enllaç del PDF obren la pàgina del vídeo, https://youtu.be/<id> o https://vimeo.com/<id>, des de start. Un fitxer no té pàgina: obren la seva adreça de producció, que és també d'on es reprodueix un vídeo sense fitxer propi (un MP4 en un servidor, un flux HLS). Sense adreça, la versió impresa no porta codi QR ni enllaç (videoWithoutUrl), i una sortida HTML o EPUB que no porti el fitxer mostra la portada. Una adreça de YouTube o de Vimeo que no anomena cap vídeo d'aquesta plataforma genera videoUrlInvalid, i es mostra la portada en lloc d'un reproductor.

Els reproductors. Les opcions de reproductor (controls, botó de baixada, pantalla completa, menú de velocitat, imatge en imatge, enviament a una altra pantalla, reproducció automàtica, començar sense so, repetició, precàrrega, insercions amb més privadesa) es fixen per a tot el llibre a videoStyle.player i per a un sol vídeo a video.player; cada reproductor respecta les que pot (vegeu Configuració › Estil de vídeo). El backend HTML rep la URL reproduïble d'un fitxer per l'opció resourceVideoUrl(fileId), com rep les imatges per resourceImageUrl, i si no n'hi ha fa servir l'adreça de producció. La seva opció videos: { files, streams, hls } tria entre reproductor i portada per a cada origen, per sobre de videoStyle.html (hls, un vídeo que es reprodueix des d'una adreça HLS, segueix files si no s'indica); l'escriptor EPUB la fa servir. Un <video> que reprodueix una adreça HLS porta data-pt-hls, perquè l'amfitrió li pugui donar un reproductor en els navegadors sense HLS propi (Safari i les versions recents de Chrome el reprodueixen tal com és). En un llibre de dreta a esquerra el reproductor i les marques de la portada es tornen a girar com una imatge, perquè el codi QR es pugui llegir.

Al VDT. El bloc de recurs d'un vídeo té kind: 'video', la portada com a fileId / format (es dibuixa com un bitmap) i video (VDTResourceVideo): l'enllaç link al qual s'envia el lector, l'embedUrl de YouTube o de Vimeo amb les opcions de reproductor aplicades, el fileId d'un fitxer, el mimeType d'un vídeo propi (del seu fitxer o només de la seva adreça, application/vnd.apple.mpegurl per a HLS), l'interval start / end, el player resolt, linkPoster, html, i les marques playMark i qr (els mòduls del QR com a files de '0' / '1'), amb rectangles relatius a l'angle superior esquerre del cos. Un amfitrió que dibuixi els vídeos pel seu compte té les funcions que exporta postext: parseVideoUrl, videoWatchUrl, resourceVideoLink, videoEmbedUrl, videoEmbedAllow, videoElementAttributes, mediaFragment, videoMimeType, videoFormatOfUrl, resourceVideoFormat, isHlsMimeType, HLS_MIME_TYPE, youtubePosterUrls, encodeQr, layoutVideo, playMarkTriangle i qrModuleRuns.

En un paquet. Un .postext porta el fitxer (resources/<id>.mp4) i la portada (resources/<id>.poster.jpg): l'entrada del manifest els anomena a file i poster, dona la mida de la portada a width / height i desa la resta a video sense identificadors de fitxer. bundleVideoUrl(bundle) és el resolutor resourceVideoUrl sobre els fitxers d'un paquet. Un vídeo que es reprodueix només des d'una adreça no porta cap fitxer: la seva entrada només té la portada. En un paquet bilingüe, una llengua pot donar a un vídeo la seva pròpia poster i el seu propi video (un altre muntatge, a la seva adreça) a localized[…].resources.

Vídeos a les pàgines de Folio

Al llibre en 3D, un vídeo propi es reprodueix a la pàgina on està imprès. Un clic a la portada l'engega allà mateix, faci el que faci el punter sobre el llibre (passar pàgines, orbitar la vista o seleccionar text): el shader de la pàgina dibuixa els fotogrames del vídeo damunt de la portada, de manera que la imatge es doblega i es corba amb el paper mentre el full passa, i el vídeo no s'atura durant el gir. Un clic sobre un vídeo en marxa el posa en pausa, un clic sobre un vídeo en pausa el reprèn, i la barra d'espai o la tecla de retorn fan el mateix amb el primer vídeo del plec obert. Engegar un altre vídeo atura el que es reprodueix (torna a la seva portada), i un vídeo s'atura quan el llibre queda quiet en un plec on ja no apareix, o quan arriba al seu end. Damunt d'un vídeo que es pot reproduir, el punter es converteix en una mà; un arrossegament que comença sobre el vídeo continua passant la pàgina o girant la vista. Un vídeo que s'ha de reproduir sol (video.player.autoplay) s'engega la primera vegada que el llibre queda quiet en el seu plec, un cop el llibre s'ha assentat (també si l'amfitrió el compon per etapes), i no es torna a engegar mai més en aquell visor.

Un vídeo que es reprodueix amb d'altres (video.player.exclusive: false, des de postext 1.18) canvia les dues regles. En començar-lo només s'aturen els vídeos exclusius, de manera que se'n reprodueixen diversos alhora; començar un vídeo exclusiu també l'atura. Amb autoplay comença, sense so, cada cop que el llibre s'atura al seu plec, i s'atura quan es passa a un altre: els bucles sense so (loop) d'una pàgina corren junts cada cop que el lector hi arriba.

  • Què es reprodueix. Un fitxer (l'amfitrió converteix el seu fileId en una URL amb l'opció videoUrl; al Sandbox, una URL d'objecte) o, si no n'hi ha, la seva adreça: MP4, WebM o un flux HLS. Un flux HLS es reprodueix amb hls.js a qualsevol navegador que tingui Media Source Extensions (es carrega en la primera reproducció; és una dependència peer opcional de postext-folio), limitat a la variant més propera a la mida que la imatge té a la pantalla, de manera que una imatge de pocs centenars de píxels d'alçada no demana mai una variant 4K; sense Media Source Extensions, el reprodueix el HLS del mateix navegador. Les seves peticions porten un paràmetre pt-cors propi, perquè la memòria cau del navegador no els doni mai una còpia que un altre reproductor hagi baixat sense CORS. YouTube i Vimeo es reprodueixen en iframes, que WebGL no pot dibuixar: un clic a la seva portada passa la pàgina com a qualsevol altre lloc.
  • Lectures des d'un altre origen. WebGL només dibuixa un vídeo si el seu servidor en permet la lectura (CORS, Access-Control-Allow-Origin). Un vídeo que no es pot llegir es queda en portada, i onVideo rep error.
  • So. El clic permet que el vídeo es reprodueixi amb so; si el navegador encara s'hi nega, sona silenciat. Un vídeo que s'engega sol té so si el lector ja ha fet clic o ha escrit a la pàgina (haver-hi passat compta); si no, comença sense so, i un clic a sobre li torna el so abans que el següent el posi en pausa. video.player.muted l'engega sense so, loop el torna a reproduir, i start / end delimiten el fragment que es reprodueix.
  • A qualsevol pàgina. La imatge es dibuixa on la posa la composició: girada en un recurs girat, dreta en una pàgina vertical i sense invertir en un llibre de dreta a esquerra, igual que la portada. Una portada retallada dins de la seva zona segura retalla el vídeo de la mateixa manera.
  • Sense WebGL2, o amb menys moviment, el vídeo es reprodueix en un <video> HTML posat damunt de la pàgina.
const book = createFolioFromDocument(container, doc, {
  // La URL reproduïble d'un vídeo pujat (una URL d'objecte sobre els seus bytes).
  videoUrl: (fileId) => urls.get(fileId),
  onVideo: ({ resourceId, state }) => console.log(resourceId, state), // playing | paused | stopped | error
});
book.stopVideo();

videos: false ho desactiva. toggleVideoAt({ page, x, y }) fa el mateix que un clic en aquell punt, i pageVideoSpots(page, doc) llista on és cada vídeo d'una pàgina, per a un amfitrió que dibuixi els seus propis controls.

Dues receptes del Receptari posen vídeos: la núm. 131, Programa de cineclub amb codis QR a les portades, imprimeix cada pel·lícula com una cartel·la amb la marca de reproducció i un codi QR, i la núm. 132, Full de pràctiques amb vídeos per a la pantalla i l'EPUB, fixa les opcions de reproductor de l'edició HTML i empaqueta els seus propis vídeos en un EPUB de maquetació fixa.