@fayz-ai/plugin-forms 0.15.13 → 0.15.15

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/lib/html-text.ts","../src/lib/plain-text.ts","../src/components/fields/StencilCamera.tsx","../src/components/FormRenderer.tsx"],"names":["htmlToPlainText","jsxs","jsx","t","React","Fragment"],"mappings":"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","file":"chunk-RB7UYZLA.js","sourcesContent":["// ============================================================\n// HTML guardado num campo de formulário → texto legível\n// ============================================================\n//\n// Os campos `richtext` (e alguns `memo` vindos de importação) guardam HTML: o\n// conteúdo trazido do Feegow chega como `<p dir=\"ltr\"><b id=\"docs-internal-guid-\n// …\">Está triste, mas sabe que vai superar.&nbsp;</b></p>` — colado de um Google\n// Docs, com atributos e tudo.\n//\n// Isso dá dois jeitos ERRADOS de mostrar, e o produto já teve os dois:\n//\n// • escapar e imprimir → a pessoa lê `&lt;p dir=&quot;ltr&quot;&gt;` numa\n// ficha de atendimento. Era o que a impressão fazia.\n// • injetar como HTML → a marcação some da tela, mas o documento passa a poder\n// trazer <script>/<img onerror> de dentro do banco para dentro da página.\n// Consertar a primeira coisa caindo na segunda seria trocar um problema de\n// leitura por um de execução.\n//\n// O certo é o terceiro: extrair o TEXTO do HTML e escapar esse texto. Fica\n// legível e nada do que estava guardado é executado — o parser monta os nós, e\n// `textContent` nunca roda nenhum deles.\n\n/** Parece HTML? Uma tag de abertura ou fechamento basta. */\nexport function looksLikeHtml(value: string): boolean {\n return /<\\/?[a-z][^>]*>/i.test(value)\n}\n\n// Blocos viram quebra de linha ANTES de extrair o texto. `textContent` sozinho\n// cola os parágrafos — \"…17.07.26Está triste, mas sabe…\" — e numa evolução\n// clínica o parágrafo É a estrutura do que foi dito.\nconst BLOCKS = 'p, div, li, tr, h1, h2, h3, h4, h5, h6, blockquote, section, article'\n\n/** Espaço rígido (U+00A0): o parser decodifica `&nbsp;` para ele, mas ele não\n * quebra linha e o `trim()` não o remove. Vira espaço comum. */\nconst NBSP = / /g\n\nexport function htmlToPlainText(value: string): string {\n if (!value) return ''\n\n if (typeof document === 'undefined') {\n // Sem DOM (teste em node, render no servidor). Um \"parser\" de regex é uma\n // aproximação, e está assumido como tal: derruba as tags para não devolver\n // marcação, e não pretende estar certo para HTML arbitrário.\n return value\n .replace(/<br\\s*\\/?>/gi, '\\n')\n .replace(/<\\/(p|div|li|tr|h[1-6]|blockquote)>/gi, '\\n')\n .replace(/<[^>]*>/g, '')\n .replace(/&nbsp;/g, ' ')\n .replace(/&lt;/g, '<')\n .replace(/&gt;/g, '>')\n .replace(/&quot;/g, '\"')\n .replace(/&#39;/g, \"'\")\n // `&amp;` por último: antes dos outros, ele transformaria `&amp;lt;` em\n // `<` — decodificando uma vez a mais do que o texto pedia.\n .replace(/&amp;/g, '&')\n .replace(/\\n{3,}/g, '\\n\\n')\n .trim()\n }\n\n const el = document.createElement('div')\n el.innerHTML = value\n for (const br of Array.from(el.querySelectorAll('br'))) {\n br.replaceWith('\\n')\n }\n for (const block of Array.from(el.querySelectorAll(BLOCKS))) {\n block.append('\\n')\n }\n\n return (el.textContent ?? '')\n .replace(NBSP, ' ')\n .replace(/[ \\t]+\\n/g, '\\n')\n .replace(/\\n{3,}/g, '\\n\\n')\n .trim()\n}\n\n/** Texto legível de um campo longo, seja ele HTML guardado ou texto puro. */\nexport function fieldTextValue(value: unknown): string {\n if (typeof value !== 'string') return ''\n // Um memo digitado à mão passa intacto: converter tudo faria \"a < b virou c\"\n // perder o que vem depois do `<`.\n return looksLikeHtml(value) ? htmlToPlainText(value) : value\n}\n\n// ============================================================\n// Sanitização — mostrar a FORMATAÇÃO sem executar o documento\n// ============================================================\n//\n// Texto puro resolve a legibilidade e perde o resto: negrito, parágrafo, lista.\n// Numa evolução clínica colada do Docs, o negrito costuma ser o que a\n// terapeuta destacou, e a lista é a lista. Achatar tudo é jogar fora sentido\n// que estava lá.\n//\n// Então o HTML volta a ser HTML — mas passando por uma lista de permissão. O\n// que não está nela não é \"provavelmente inofensivo\": é removido. Isso é o\n// contrário de uma lista de proibições, que só protege do que alguém lembrou\n// de proibir.\n//\n// `DOMParser` com 'text/html' monta um documento INERTE: nenhum script roda,\n// nenhuma imagem é buscada, nenhum `onerror` dispara — nem durante a análise,\n// nem enquanto caminhamos pela árvore. É por isso que a limpeza acontece aqui e\n// não com regex sobre a string, que nunca dá conta de HTML malformado (e é\n// justamente com HTML malformado que se burla um filtro de regex).\n\n/** Some com o elemento E com o conteúdo dele. Desembrulhar um <script> jogaria\n * o código para dentro do texto visível. */\nconst DROP_WITH_CONTENT = new Set([\n 'script', 'style', 'iframe', 'object', 'embed', 'svg', 'math', 'link', 'meta',\n 'form', 'input', 'button', 'textarea', 'select', 'template', 'noscript',\n])\n\n/** Some com a TAG e mantém os filhos: um `<font>` ou um `<span>` desconhecido\n * não deve levar embora a frase que estava dentro dele. */\nconst ALLOWED_TAGS = new Set([\n 'p', 'br', 'hr', 'div', 'span',\n 'b', 'strong', 'i', 'em', 'u', 's', 'sub', 'sup', 'mark', 'small',\n 'ul', 'ol', 'li', 'blockquote', 'pre', 'code',\n 'h1', 'h2', 'h3', 'h4', 'h5', 'h6',\n 'table', 'thead', 'tbody', 'tfoot', 'tr', 'td', 'th', 'caption',\n 'a',\n])\n\n/** Só o que é preciso para um link funcionar. `style`, `class`, `id` e todo\n * `on*` ficam de fora — o `id=\"docs-internal-guid-…\"` que vem do Google Docs\n * é lixo de origem, e `style` é caminho para `expression()`/`url(javascript:)`\n * em motores antigos. */\nconst ALLOWED_ATTRS: Record<string, Set<string>> = {\n a: new Set(['href', 'title']),\n td: new Set(['colspan', 'rowspan']),\n th: new Set(['colspan', 'rowspan']),\n}\n\nconst SAFE_HREF = /^(https?:|mailto:|tel:)/i\n\nfunction cleanElement(el: Element): void {\n // Percorre uma CÓPIA: remover/desembrulhar filhos mexe na lista viva.\n for (const child of Array.from(el.children)) {\n cleanElement(child)\n }\n\n const tag = el.tagName.toLowerCase()\n\n if (DROP_WITH_CONTENT.has(tag)) {\n el.remove()\n return\n }\n\n for (const attr of Array.from(el.attributes)) {\n const name = attr.name.toLowerCase()\n const allowed = ALLOWED_ATTRS[tag]?.has(name) ?? false\n if (!allowed) {\n el.removeAttribute(attr.name)\n continue\n }\n // `href=\"javascript:…\"` é o caso clássico de atributo permitido com valor\n // que não é.\n if (name === 'href' && !SAFE_HREF.test(attr.value.trim())) {\n el.removeAttribute(attr.name)\n }\n }\n\n if (!ALLOWED_TAGS.has(tag)) {\n el.replaceWith(...Array.from(el.childNodes))\n return\n }\n\n if (tag === 'a') {\n // Um <a> que perdeu o href (era `javascript:`) continuaria azul e\n // sublinhado, prometendo um destino que não existe. Vira o texto que é.\n if (!el.getAttribute('href')) {\n el.replaceWith(...Array.from(el.childNodes))\n return\n }\n el.setAttribute('target', '_blank')\n el.setAttribute('rel', 'noopener noreferrer nofollow')\n }\n}\n\n/**\n * HTML guardado → HTML seguro de renderizar.\n *\n * Sem DOMParser (node, SSR) devolve string vazia em vez de deixar passar: quem\n * chama tem o texto puro como alternativa, e \"não consegui limpar\" nunca pode\n * virar \"então mando cru\".\n */\nexport function sanitizeHtml(value: string): string {\n if (!value) return ''\n if (typeof DOMParser === 'undefined') return ''\n\n const doc = new DOMParser().parseFromString(value, 'text/html')\n for (const child of Array.from(doc.body.children)) {\n cleanElement(child)\n }\n return doc.body.innerHTML\n}\n\n/** O campo longo pronto para exibir: `html` quando dá para formatar com\n * segurança, `text` quando não (e o chamador escapa esse). */\nexport function fieldRichValue(value: unknown): { html: string } | { text: string } {\n if (typeof value !== 'string' || !value) return { text: '' }\n if (!looksLikeHtml(value)) return { text: value }\n const html = sanitizeHtml(value)\n return html ? { html } : { text: htmlToPlainText(value) }\n}\n","// ---------------------------------------------------------------------------\n// O MODELO IMPORTADO TRAZ HTML, E O INPUT NÃO LÊ HTML.\n//\n// Os 23 moldes migrados do Feegow guardavam a instrução do campo como corpo de\n// página, e ela chegava inteira ao `placeholder`:\n//\n// <p>Doen&ccedil;a cr&ocirc;nica / heredit&aacute;ria:</p> <p>Uso de\n// medicamentos. Quais:</p> <p>&nbsp;</p>\n//\n// Um `<input placeholder>` e um `<textarea placeholder>` renderizam TEXTO — a\n// marcação não some, ela aparece. O psicólogo abria a anamnese e via a fonte do\n// documento em vez da pergunta.\n//\n// Converter na LEITURA, e não migrar o dado: o mesmo molde é lido pelo\n// construtor, pelo visualizador e pelo portal, e uma migração que \"limpasse\"\n// acertaria um consumidor e perderia o original para os outros. Aqui o original\n// fica intacto no banco.\n// ---------------------------------------------------------------------------\n\nconst ENTITIES: Record<string, string> = {\n amp: '&', lt: '<', gt: '>', quot: '\"', apos: \"'\", nbsp: ' ',\n // Os acentos do português, que é o que 23 moldes do Feegow trouxeram. Escrito\n // à mão e não resolvido pelo DOM porque esta função também roda em teste e\n // fora do navegador — e um `&ccedil;` visível na anamnese é o defeito que\n // ela veio consertar.\n ...Object.fromEntries(\n ('agrave à aacute á acirc â atilde ã auml ä ccedil ç egrave è eacute é ecirc ê '\n + 'euml ë igrave ì iacute í icirc î iuml ï ntilde ñ ograve ò oacute ó ocirc ô '\n + 'otilde õ ouml ö ugrave ù uacute ú ucirc û uuml ü')\n .split(' ')\n .reduce<Array<[string, string]>>((acc, part, i, all) => {\n if (i % 2 === 0) acc.push([part, all[i + 1]])\n return acc\n }, [])\n // A maiúscula é a mesma entidade com a inicial maiúscula (&Ccedil; → Ç).\n .flatMap(([name, char]) => [\n [name, char],\n [name.charAt(0).toUpperCase() + name.slice(1), char.toUpperCase()],\n ]),\n ),\n}\n\n/** `&ccedil;` → `ç`, `&#233;` → `é`, `&#xE9;` → `é`. */\nfunction decodeEntities(value: string): string {\n return value.replace(/&(#x?[0-9a-f]+|[a-z]+);/gi, (whole, body: string) => {\n if (body[0] === '#') {\n const code = body[1] === 'x' || body[1] === 'X'\n ? parseInt(body.slice(2), 16)\n : parseInt(body.slice(1), 10)\n return Number.isFinite(code) ? String.fromCodePoint(code) : whole\n }\n const named = ENTITIES[body] ?? ENTITIES[body.toLowerCase()]\n if (named) return named\n // Uma entidade que este mapa não conhece sai DECODIFICADA pelo navegador,\n // que conhece todas. Fora dele (teste, SSR) volta como veio: melhor um\n // `&ccedil;` visível do que um campo vazio.\n if (typeof document === 'undefined') return whole\n const el = document.createElement('textarea')\n el.innerHTML = whole\n return el.value\n })\n}\n\n/**\n * HTML de molde → texto de uma linha por parágrafo.\n *\n * Devolve o valor intocado quando não há marcação nenhuma: a esmagadora maioria\n * dos moldes é texto simples, e passá-los por um regex de tags seria cobrar de\n * todo mundo o defeito de vinte e três.\n */\nexport function htmlToPlainText(value: string | undefined): string | undefined {\n if (!value || !/[<&]/.test(value)) return value\n const text = decodeEntities(\n value\n // Bloco vira quebra de linha — é o que o parágrafo significava.\n .replace(/<\\s*br\\s*\\/?\\s*>/gi, '\\n')\n .replace(/<\\s*\\/\\s*(p|div|li|h[1-6])\\s*>/gi, '\\n')\n .replace(/<[^>]*>/g, ''),\n )\n return text\n .split('\\n')\n .map((line) => line.replace(/\\s+/g, ' ').trim())\n .filter(Boolean)\n .join('\\n') || undefined\n}\n","import React from 'react'\nimport { createPortal } from 'react-dom'\nimport { X, Camera, RotateCcw, Check, SwitchCamera, SkipForward, ImageUp } from 'lucide-react'\nimport { Button } from '@fayz-ai/ui'\n\nexport interface StencilCameraProps {\n title: string\n overlayUrl: string | null\n opacity: number\n aspect: '3:4' | '1:1' | '4:3'\n camera: 'user' | 'environment'\n burnOverlay: boolean\n onCapture: (photo: Blob) => void\n onSkip?: () => void\n onClose: () => void\n}\n\nconst ratioOf = (a: StencilCameraProps['aspect']) => (a === '1:1' ? 1 : a === '4:3' ? 4 / 3 : 3 / 4)\n\n/**\n * Full-screen camera with the stencil drawn over the live image (V1 StencilCameraCapture). Portaled\n * to <body> so the form's scroll container can't trap it. Without a camera (desktop, permission\n * refused) it falls back to picking a file instead of closing on the user.\n */\nexport function StencilCamera({\n title, overlayUrl, opacity, aspect, camera, burnOverlay, onCapture, onSkip, onClose,\n}: StencilCameraProps) {\n const videoRef = React.useRef<HTMLVideoElement>(null)\n const streamRef = React.useRef<MediaStream | null>(null)\n const fileRef = React.useRef<HTMLInputElement>(null)\n const [facing, setFacing] = React.useState(camera)\n const [preview, setPreview] = React.useState<{ blob: Blob; url: string } | null>(null)\n const [starting, setStarting] = React.useState(true)\n const [noCamera, setNoCamera] = React.useState(false)\n const [retake, setRetake] = React.useState(0)\n const ratio = ratioOf(aspect)\n\n const stop = () => {\n streamRef.current?.getTracks().forEach((t) => t.stop())\n streamRef.current = null\n }\n\n React.useEffect(() => {\n if (preview) return\n let alive = true\n ;(async () => {\n setStarting(true)\n try {\n if (!navigator.mediaDevices?.getUserMedia) throw new Error('unsupported')\n stop()\n const stream = await navigator.mediaDevices.getUserMedia({\n video: { facingMode: { ideal: facing }, width: { ideal: 1920 }, height: { ideal: 1920 } },\n audio: false,\n })\n if (!alive) { stream.getTracks().forEach((t) => t.stop()); return }\n streamRef.current = stream\n if (videoRef.current) {\n videoRef.current.srcObject = stream\n await videoRef.current.play().catch(() => {})\n }\n setNoCamera(false)\n } catch {\n if (alive) setNoCamera(true)\n } finally {\n if (alive) setStarting(false)\n }\n })()\n return () => { alive = false }\n // `preview` is deliberately out: a retake restarts through `retake`, not every preview change.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [facing, retake])\n\n React.useEffect(() => () => stop(), [])\n\n React.useEffect(() => {\n const onKey = (e: KeyboardEvent) => {\n if (e.key !== 'Escape') return\n e.stopPropagation()\n e.preventDefault()\n onClose()\n }\n window.addEventListener('keydown', onKey, true)\n return () => window.removeEventListener('keydown', onKey, true)\n }, [onClose])\n\n async function drawOverlay(ctx: CanvasRenderingContext2D, w: number, h: number) {\n if (!burnOverlay || !overlayUrl) return\n // A stencil that fails to load must never block the photo.\n await new Promise<void>((resolve) => {\n const timer = setTimeout(resolve, 2500)\n const img = new Image()\n img.crossOrigin = 'anonymous'\n img.onload = () => {\n try {\n const s = Math.min(w / img.width, h / img.height)\n ctx.globalAlpha = opacity\n ctx.drawImage(img, (w - img.width * s) / 2, (h - img.height * s) / 2, img.width * s, img.height * s)\n ctx.globalAlpha = 1\n } catch { /* tainted: keep the photo without the stencil */ }\n clearTimeout(timer); resolve()\n }\n img.onerror = () => { clearTimeout(timer); resolve() }\n img.src = overlayUrl\n })\n }\n\n async function capture() {\n const video = videoRef.current\n if (!video || !video.videoWidth) return\n const vw = video.videoWidth, vh = video.videoHeight\n let cw = vw, ch = vh\n if (vw / vh > ratio) cw = vh * ratio; else ch = vw / ratio\n const canvas = document.createElement('canvas')\n canvas.width = Math.round(cw); canvas.height = Math.round(ch)\n const ctx = canvas.getContext('2d')!\n if (facing === 'user') { ctx.translate(canvas.width, 0); ctx.scale(-1, 1) }\n ctx.drawImage(video, (vw - cw) / 2, (vh - ch) / 2, cw, ch, 0, 0, canvas.width, canvas.height)\n ctx.setTransform(1, 0, 0, 1, 0, 0)\n await drawOverlay(ctx, canvas.width, canvas.height)\n const blob = await new Promise<Blob | null>((r) => {\n try { canvas.toBlob(r, 'image/jpeg', 0.9) } catch { r(null) }\n })\n if (!blob) return\n stop()\n setPreview({ blob, url: URL.createObjectURL(blob) })\n }\n\n function pickFile(file: File | undefined) {\n if (!file) return\n setPreview({ blob: file, url: URL.createObjectURL(file) })\n }\n\n // A full-screen camera above everything, not a modal: ui's Modal would frame it and sit under other layers.\n return createPortal(\n <div className=\"fixed inset-0 z-[2147483647] flex select-none flex-col bg-black text-white\" role=\"dialog\" aria-label={title}>\n <div className=\"flex items-center justify-between p-3\">\n <Button variant=\"bare\" size=\"bare\" type=\"button\" onClick={onClose} aria-label=\"Fechar\"\n className=\"font-normal flex h-10 w-10 items-center justify-center rounded-full bg-white/10 hover:bg-white/20\">\n <X className=\"h-5 w-5\" />\n </Button>\n <div className=\"truncate px-2 text-sm font-medium\">{title}</div>\n {!preview && !noCamera ? (\n <Button variant=\"bare\" size=\"bare\" type=\"button\" onClick={() => setFacing((f) => (f === 'user' ? 'environment' : 'user'))}\n aria-label=\"Trocar câmera\"\n className=\"font-normal flex h-10 w-10 items-center justify-center rounded-full bg-white/10 hover:bg-white/20\">\n <SwitchCamera className=\"h-5 w-5\" />\n </Button>\n ) : <div className=\"w-10\" />}\n </div>\n\n <div className=\"flex flex-1 items-center justify-center overflow-hidden\">\n <div className=\"relative h-full max-h-full max-w-full bg-black\" style={{ aspectRatio: String(ratio) }}>\n {preview ? (\n <img src={preview.url} alt=\"\" className=\"h-full w-full object-contain\" />\n ) : noCamera ? (\n <div className=\"flex h-full w-full flex-col items-center justify-center gap-3 px-6 text-center text-sm text-white/80\">\n {overlayUrl && <img src={overlayUrl} alt=\"\" className=\"max-h-[50%] opacity-60\" />}\n <p>Não foi possível abrir a câmera neste aparelho. Escolha uma foto do arquivo.</p>\n </div>\n ) : (\n <>\n <video ref={videoRef} playsInline muted className=\"h-full w-full object-cover\"\n style={{ transform: facing === 'user' ? 'scaleX(-1)' : undefined }} />\n {overlayUrl && (\n <img src={overlayUrl} alt=\"\" className=\"pointer-events-none absolute inset-0 h-full w-full object-contain\"\n style={{ opacity }} />\n )}\n {starting && (\n <div className=\"absolute inset-0 flex items-center justify-center text-sm text-white/80\">Iniciando câmera…</div>\n )}\n </>\n )}\n </div>\n </div>\n\n <input ref={fileRef} type=\"file\" accept=\"image/*\" className=\"hidden\" onChange={(e) => pickFile(e.target.files?.[0])} />\n\n <div className=\"relative flex items-center justify-center gap-6 p-4 pb-[calc(2rem+env(safe-area-inset-bottom))]\">\n {preview ? (\n <>\n <Button type=\"button\" variant=\"secondary\" size=\"lg\" className=\"gap-2\"\n onClick={() => { URL.revokeObjectURL(preview.url); setPreview(null); setRetake((n) => n + 1) }}>\n <RotateCcw className=\"h-4 w-4\" /> Tirar novamente\n </Button>\n <Button type=\"button\" size=\"lg\" className=\"gap-2\" onClick={() => onCapture(preview.blob)}>\n <Check className=\"h-4 w-4\" /> Usar foto\n </Button>\n </>\n ) : noCamera ? (\n <Button type=\"button\" size=\"lg\" className=\"gap-2\" onClick={() => fileRef.current?.click()}>\n <ImageUp className=\"h-4 w-4\" /> Escolher foto\n </Button>\n ) : (\n <>\n <Button variant=\"bare\" size=\"bare\" type=\"button\" disabled={starting} onClick={capture} aria-label=\"Capturar\"\n className=\"font-normal flex h-16 w-16 items-center justify-center rounded-full border-4 border-white/40 bg-white transition-transform active:scale-95 disabled:opacity-60\">\n <Camera className=\"h-6 w-6 text-black\" />\n </Button>\n <Button variant=\"bare\" size=\"bare\" type=\"button\" onClick={() => fileRef.current?.click()} aria-label=\"Escolher do arquivo\"\n className=\"font-normal absolute left-6 flex h-12 w-12 items-center justify-center rounded-full bg-white/10 hover:bg-white/20\">\n <ImageUp className=\"h-5 w-5\" />\n </Button>\n </>\n )}\n {!preview && onSkip && (\n <Button variant=\"bare\" size=\"bare\" type=\"button\" onClick={onSkip} aria-label=\"Pular esta foto\"\n className=\"font-normal absolute right-6 flex h-12 w-12 items-center justify-center rounded-full bg-white/10 hover:bg-white/20\">\n <SkipForward className=\"h-5 w-5\" />\n </Button>\n )}\n </div>\n </div>,\n document.body,\n )\n}\n","import React, { useCallback } from 'react'\nimport { Checkbox, Input, Textarea } from '@fayz-ai/ui'\nimport {\n Select,\n SelectContent,\n SelectItem,\n SelectTrigger,\n SelectValue,\n} from '@fayz-ai/ui'\nimport { Badge } from '@fayz-ai/ui'\nimport { useTranslation, describeError } from '@fayz-ai/core'\nimport { fieldRichValue } from '../lib/html-text'\nimport type { FormFieldDef, FormSchema, MediaValue, RecommendationLine } from '@fayz-ai/forms/domain/template'\nimport { htmlToPlainText } from '../lib/plain-text'\nimport {\n AnswerAlertNote, GalleryField, GalleryView, RecommendationField, RecommendationView, SignatureField,\n StencilPhotoField, YesNoField, YesNoTextField, answerAlerts, aspectRatioOf, stencilOf, yesNoAnswer,\n type RecommendationShortcut,\n} from './fields/fields'\nimport { MediaImage, isMedia, useMediaUpload, useMediaUrl } from './fields/media'\nimport { StencilCamera } from './fields/StencilCamera'\n\n// O HTML sanitizado chega sem `class` nenhuma (a lista de permissão derruba\n// todas), então o espaçamento e os pesos vêm daqui, pelo seletor de filho. Sem\n// isto o Tailwind zera as margens de `<p>`/`<ul>` no preflight e os parágrafos\n// do documento voltam a se colar uns nos outros.\nconst RICH_TEXT_CLASS = [\n 'space-y-2',\n '[&_p]:leading-relaxed',\n '[&_b]:font-semibold [&_strong]:font-semibold',\n '[&_i]:italic [&_em]:italic',\n '[&_u]:underline',\n '[&_ul]:list-disc [&_ul]:pl-5 [&_ol]:list-decimal [&_ol]:pl-5 [&_li]:leading-relaxed',\n '[&_blockquote]:border-l-2 [&_blockquote]:border-border [&_blockquote]:pl-3 [&_blockquote]:text-muted-foreground',\n '[&_a]:text-primary [&_a]:underline',\n '[&_h1]:font-semibold [&_h2]:font-semibold [&_h3]:font-semibold',\n '[&_table]:w-full [&_td]:border [&_td]:border-border [&_td]:px-2 [&_td]:py-1',\n '[&_th]:border [&_th]:border-border [&_th]:px-2 [&_th]:py-1 [&_th]:font-medium',\n].join(' ')\n\ninterface FormRendererProps {\n schema: FormSchema\n data: Record<string, unknown>\n onChange: (data: Record<string, unknown>) => void\n readOnly?: boolean\n /** Required fields left empty on the last save attempt — outlined until filled. */\n missing?: ReadonlySet<string>\n /** One-tap lines above `recommendation` fields (the host knows the client's prepaid services). */\n recommendationShortcuts?: RecommendationShortcut[]\n}\n\n/** Is a required field still unanswered? Shared by the fill dialog's save gate. */\nexport function isFieldEmpty(field: FormFieldDef, value: unknown): boolean {\n if (field.type === 'title') return false\n if (value == null || value === '' || value === false) return true\n if (Array.isArray(value)) return value.length === 0\n if (field.type === 'yes_no' || field.type === 'yes_no_text') return yesNoAnswer(value) === ''\n return false\n}\n\n/**\n * Leitura é uma APRESENTAÇÃO, não um formulário travado.\n *\n * `readOnly` chegava no `<input readOnly>` e parava aí: caixa, borda, cursor de\n * texto, radio marcado — pixel por pixel a mesma tela de preencher. Abrir uma\n * anamnese de fevereiro parecia estar editando a anamnese de fevereiro, e a\n * única pista do contrário era o campo não aceitar digitação. Aqui o valor vira\n * texto e some a moldura: dá para ler de cima a baixo sem confundir com um\n * rascunho aberto.\n */\nfunction ReadField({ label, children }: { label?: string; children: React.ReactNode }) {\n return (\n <div className=\"space-y-0.5\">\n {label && <p className=\"text-xs font-medium text-muted-foreground\">{label}</p>}\n <div className=\"text-sm text-foreground\">{children}</div>\n </div>\n )\n}\n\nfunction EmptyValue() {\n return <span className=\"text-muted-foreground/50\">—</span>\n}\n\n/** O rótulo escolhido, não o valor cru: um documento que mostra \"prefer_not_say\"\n * faz a pessoa traduzir de cabeça o que a tela já sabia dizer. */\nfunction optionLabel(field: FormFieldDef, value: unknown): string | null {\n if (value == null || value === '') return null\n const match = (field.options ?? []).find((o) => o.value === value)\n return match?.label ?? String(value)\n}\n\nfunction ReadValue({ field, value }: { field: FormFieldDef; value: unknown }) {\n switch (field.type) {\n case 'memo':\n case 'richtext': {\n // Formatação preservada, documento não executado: o valor passa pela\n // lista de permissão de lib/html-text.ts e volta como HTML seguro. O\n // negrito que a terapeuta aplicou continua negrito; o\n // `id=\"docs-internal-guid-…\"` que veio junto do Google Docs não sobrevive.\n //\n // Sem tag nenhuma (memo digitado à mão) é texto puro mesmo, com as\n // quebras respeitadas pelo `whitespace-pre-wrap`.\n const rich = fieldRichValue(value)\n return (\n <ReadField label={field.label}>\n {'html' in rich ? (\n <div className={RICH_TEXT_CLASS} dangerouslySetInnerHTML={{ __html: rich.html }} />\n ) : rich.text ? (\n <p className=\"whitespace-pre-wrap\">{rich.text}</p>\n ) : (\n <EmptyValue />\n )}\n </ReadField>\n )\n }\n\n case 'date': {\n const raw = typeof value === 'string' ? value : ''\n const date = raw ? new Date(raw) : null\n const text = date && !Number.isNaN(date.getTime())\n // `T00:00` faz o Date nascer em UTC e o fuso do Brasil o joga para o dia\n // anterior — daí o corte manual em vez de toLocaleDateString direto.\n ? raw.slice(0, 10).split('-').reverse().join('/')\n : raw\n return <ReadField label={field.label}>{text || <EmptyValue />}</ReadField>\n }\n\n case 'select':\n case 'radio': {\n const label = optionLabel(field, value)\n return <ReadField label={field.label}>{label ?? <EmptyValue />}</ReadField>\n }\n\n case 'tags': {\n const selected = Array.isArray(value) ? (value as string[]) : []\n return (\n <ReadField label={field.label}>\n {selected.length > 0 ? (\n <div className=\"flex flex-wrap gap-1.5\">\n {selected.map((v) => (\n <Badge key={v} variant=\"secondary\" className=\"text-xs\">\n {optionLabel(field, v) ?? v}\n </Badge>\n ))}\n </div>\n ) : (\n <EmptyValue />\n )}\n </ReadField>\n )\n }\n\n case 'checkbox':\n // Sem rótulo próprio: o texto do checkbox JÁ é a pergunta (\"Autoriza uso\n // de imagem\"), então repeti-lo acima da resposta diria duas vezes a mesma\n // coisa.\n return (\n <ReadField>\n <span className=\"font-medium\">{field.label}</span>\n <span className=\"text-muted-foreground\"> · </span>\n <span>{value ? 'Sim' : 'Não'}</span>\n </ReadField>\n )\n\n case 'yes_no':\n case 'yes_no_text': {\n const answer = yesNoAnswer(value)\n const text = value && typeof value === 'object' ? (value as { text?: string }).text?.trim() : ''\n const alert = answerAlerts(field, value)\n return (\n <ReadField label={field.label}>\n {answer ? <span className=\"font-medium\">{answer === 'sim' ? 'Sim' : 'Não'}</span> : <EmptyValue />}\n {text ? <span className=\"text-muted-foreground\"> — {text}</span> : null}\n {alert && <div><AnswerAlertNote alert={alert} /></div>}\n </ReadField>\n )\n }\n\n case 'stencil_photo':\n case 'signature':\n return (\n <ReadField label={field.label}>\n {isMedia(value) ? (\n <MediaImage value={value} alt={field.label}\n className={field.type === 'signature' ? 'max-h-32 rounded-md border bg-white' : 'w-full max-w-xs rounded-lg border object-cover'}\n style={field.type === 'signature' ? undefined : { aspectRatio: String(aspectRatioOf(stencilOf(field))) }} />\n ) : <EmptyValue />}\n </ReadField>\n )\n\n case 'gallery': {\n const items = Array.isArray(value) ? (value as MediaValue[]).filter(isMedia) : []\n return <ReadField label={field.label}>{items.length ? <GalleryView items={items} /> : <EmptyValue />}</ReadField>\n }\n\n case 'recommendation':\n return (\n <ReadField label={field.label}>\n <RecommendationView items={Array.isArray(value) ? (value as RecommendationLine[]) : []} />\n </ReadField>\n )\n\n default: {\n const text = value == null || value === '' ? null : String(value)\n return <ReadField label={field.label}>{text ?? <EmptyValue />}</ReadField>\n }\n }\n}\n\nfunction FieldLabel({ field }: { field: FormFieldDef }) {\n return (\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n )\n}\n\nfunction FieldRenderer({\n field,\n value,\n onChange,\n readOnly,\n onOpenCamera,\n uploading,\n shortcuts,\n}: {\n field: FormFieldDef\n value: unknown\n onChange: (value: unknown) => void\n readOnly?: boolean\n onOpenCamera?: () => void\n uploading?: boolean\n shortcuts?: RecommendationShortcut[]\n}) {\n const t = useTranslation()\n\n // Título e os blocos ainda não implementados continuam iguais nos dois modos:\n // um é estrutura do documento, os outros não têm valor para apresentar.\n if (readOnly && field.type !== 'title' && field.type !== 'image' && field.type !== 'budget') {\n return <ReadValue field={field} value={value} />\n }\n\n switch (field.type) {\n case 'title':\n return (\n <h3 className=\"text-base font-semibold pt-2 pb-1 border-b\">\n {field.label}\n </h3>\n )\n\n case 'text':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <Input\n value={(value as string) ?? ''}\n onChange={(e) => onChange(e.target.value)}\n placeholder={htmlToPlainText(field.placeholder)}\n className=\"h-9 text-sm\"\n readOnly={readOnly}\n />\n </div>\n )\n\n case 'memo':\n case 'richtext':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <Textarea\n value={(value as string) ?? ''}\n onChange={(e) => onChange(e.target.value)}\n placeholder={htmlToPlainText(field.placeholder)}\n className=\"min-h-[100px] bg-background shadow-none\"\n readOnly={readOnly}\n />\n </div>\n )\n\n case 'date':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <Input\n type=\"date\"\n value={(value as string) ?? ''}\n onChange={(e) => onChange(e.target.value)}\n className=\"h-9 text-sm\"\n readOnly={readOnly}\n />\n </div>\n )\n\n case 'select':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n {readOnly ? (\n <p className=\"text-sm py-1\">{(value as string) ?? '-'}</p>\n ) : (\n <Select value={(value as string) ?? ''} onValueChange={onChange}>\n <SelectTrigger className=\"h-9 text-sm\">\n <SelectValue placeholder={htmlToPlainText(field.placeholder) ?? '...'} />\n </SelectTrigger>\n <SelectContent>\n {(field.options ?? []).map((opt) => (\n <SelectItem key={opt.value} value={opt.value}>\n {opt.label}\n </SelectItem>\n ))}\n </SelectContent>\n </Select>\n )}\n </div>\n )\n\n case 'radio':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <div className=\"space-y-1\">\n {(field.options ?? []).map((opt) => (\n <label key={opt.value} className=\"flex items-center gap-2 cursor-pointer\">\n <input\n type=\"radio\"\n name={field.id}\n value={opt.value}\n checked={value === opt.value}\n onChange={() => onChange(opt.value)}\n disabled={readOnly}\n className=\"text-primary\"\n />\n <span className=\"text-sm\">{opt.label}</span>\n </label>\n ))}\n </div>\n </div>\n )\n\n case 'tags': {\n const selectedTags = Array.isArray(value) ? (value as string[]) : []\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <div className=\"flex flex-wrap gap-1.5\">\n {(field.options ?? []).map((opt) => {\n const active = selectedTags.includes(opt.value)\n return (\n <Badge\n key={opt.value}\n variant={active ? 'default' : 'outline'}\n className={`cursor-pointer text-xs ${readOnly ? 'pointer-events-none' : ''}`}\n onClick={() => {\n if (readOnly) return\n onChange(\n active\n ? selectedTags.filter((t) => t !== opt.value)\n : [...selectedTags, opt.value],\n )\n }}\n >\n {opt.label}\n </Badge>\n )\n })}\n </div>\n </div>\n )\n }\n\n case 'checkbox':\n return (\n <label className=\"flex items-center gap-2 cursor-pointer py-1\">\n <Checkbox checked={!!value} onChange={onChange} disabled={readOnly} />\n <span className=\"text-sm font-medium\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </span>\n </label>\n )\n\n case 'yes_no':\n return <div className=\"space-y-1.5\"><FieldLabel field={field} /><YesNoField field={field} value={value} onChange={onChange} /></div>\n\n case 'yes_no_text':\n return <div className=\"space-y-1.5\"><FieldLabel field={field} /><YesNoTextField field={field} value={value} onChange={onChange} /></div>\n\n case 'stencil_photo':\n return (\n <div className=\"space-y-1.5\">\n <FieldLabel field={field} />\n <StencilPhotoField field={field} value={value} onChange={onChange} uploading={uploading}\n onOpenCamera={() => onOpenCamera?.()} />\n </div>\n )\n\n case 'gallery':\n return <div className=\"space-y-1.5\"><FieldLabel field={field} /><GalleryField field={field} value={value} onChange={onChange} /></div>\n\n case 'recommendation':\n return (\n <div className=\"space-y-1.5\">\n <FieldLabel field={field} />\n <RecommendationField value={value} onChange={onChange} shortcuts={shortcuts} />\n </div>\n )\n\n case 'signature':\n return <div className=\"space-y-1.5\"><FieldLabel field={field} /><SignatureField field={field} value={value} onChange={onChange} /></div>\n\n case 'image':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <div className=\"flex items-center justify-center rounded-lg border-2 border-dashed py-8 text-sm text-muted-foreground\">\n Image upload — v2\n </div>\n </div>\n )\n\n case 'budget':\n return (\n <div className=\"space-y-1.5\">\n <label className=\"text-xs font-medium block\">\n {field.label}\n {field.required && <span className=\"text-destructive ml-0.5\">*</span>}\n </label>\n <div className=\"flex items-center justify-center rounded-lg border-2 border-dashed py-8 text-sm text-muted-foreground\">\n Budget / line items — v2\n </div>\n </div>\n )\n\n default:\n return null\n }\n}\n\nexport function FormRenderer({ schema, data, onChange, readOnly, missing, recommendationShortcuts }: FormRendererProps) {\n const sortedFields = [...schema.fields].sort((a, b) => a.row - b.row || a.col - b.col)\n const upload = useMediaUpload()\n const [camera, setCamera] = React.useState<FormFieldDef | null>(null)\n const [uploading, setUploading] = React.useState<string | null>(null)\n const [cameraError, setCameraError] = React.useState<string | null>(null)\n // The camera answers after the user has moved on: read the newest data, not the render's.\n const dataRef = React.useRef(data)\n dataRef.current = data\n\n const handleFieldChange = useCallback(\n (fieldId: string, value: unknown) => {\n onChange({ ...dataRef.current, [fieldId]: value })\n },\n [onChange],\n )\n\n const nextStencil = (afterId: string) => {\n const i = sortedFields.findIndex((f) => f.id === afterId)\n return sortedFields.slice(i + 1).find((f) => f.type === 'stencil_photo' && !isMedia(dataRef.current[f.id])) ?? null\n }\n\n async function onCapture(photo: Blob) {\n const field = camera\n if (!field || !upload) return\n // V1 walks the photo sequence: after one pose, the next empty one opens.\n setCamera(nextStencil(field.id))\n setUploading(field.id)\n setCameraError(null)\n try {\n const { path } = await upload(photo, `uploads/${field.id}`, 'foto.jpg')\n handleFieldChange(field.id, { path, type: 'photo' } satisfies MediaValue)\n } catch (e) {\n setCameraError(`${field.label}: ${describeError(e, 'não foi possível enviar a foto')}`)\n } finally {\n setUploading(null)\n }\n }\n\n return (\n <>\n {cameraError && <p className=\"mb-3 rounded-lg bg-destructive/10 px-3 py-2 text-xs text-destructive\">{cameraError}</p>}\n <div\n className=\"grid gap-x-4 gap-y-3\"\n style={{ gridTemplateColumns: 'repeat(12, 1fr)' }}\n >\n {sortedFields.map((field) => (\n <div\n key={field.id}\n id={`ff-field-${field.id}`}\n style={{ gridColumn: `span ${field.colSpan}` }}\n className={missing?.has(field.id) ? 'rounded-lg ring-2 ring-destructive/60 ring-offset-4 ring-offset-background' : undefined}\n >\n <FieldRenderer\n field={field}\n value={data[field.id]}\n onChange={(v) => handleFieldChange(field.id, v)}\n readOnly={readOnly}\n uploading={uploading === field.id}\n onOpenCamera={() => setCamera(field)}\n shortcuts={recommendationShortcuts}\n />\n </div>\n ))}\n </div>\n {camera && <CameraHost field={camera} onCapture={onCapture} onSkip={() => setCamera(nextStencil(camera.id))} onClose={() => setCamera(null)} />}\n </>\n )\n}\n\nfunction CameraHost({ field, onCapture, onSkip, onClose }: {\n field: FormFieldDef\n onCapture: (b: Blob) => void\n onSkip: () => void\n onClose: () => void\n}) {\n const cfg = stencilOf(field)\n const overlay = useMediaUrl(cfg.overlayPath)\n return (\n <StencilCamera\n key={field.id}\n title={field.label}\n overlayUrl={overlay}\n opacity={cfg.opacity ?? 0.6}\n aspect={cfg.aspect ?? '3:4'}\n camera={cfg.camera ?? 'environment'}\n burnOverlay={!!cfg.burnOverlay}\n onCapture={onCapture}\n onSkip={onSkip}\n onClose={onClose}\n />\n )\n}\n"]}
@@ -0,0 +1,223 @@
1
+ import { fieldRichValue } from './chunk-RB7UYZLA.js';
2
+
3
+ // src/lib/print.ts
4
+ function esc(value) {
5
+ return String(value ?? "").replace(
6
+ /[&<>"']/g,
7
+ (c) => ({ "&": "&amp;", "<": "&lt;", ">": "&gt;", '"': "&quot;", "'": "&#39;" })[c]
8
+ );
9
+ }
10
+ function nl2br(value) {
11
+ return esc(value).replace(/\r?\n/g, "<br/>");
12
+ }
13
+ function formatDate(value) {
14
+ const m = /^(\d{4})-(\d{2})-(\d{2})/.exec(value);
15
+ if (!m) return esc(value);
16
+ return `${m[3]}/${m[2]}/${m[1]}`;
17
+ }
18
+ function optionLabel(field, value) {
19
+ const opt = (field.options ?? []).find((o) => o.value === value);
20
+ return esc(opt ? opt.label : value);
21
+ }
22
+ function renderValue(field, value) {
23
+ const empty = '<span class="empty">\u2014</span>';
24
+ switch (field.type) {
25
+ case "memo":
26
+ case "richtext": {
27
+ const rich = fieldRichValue(value);
28
+ if ("html" in rich) return `<div class="long rich">${rich.html}</div>`;
29
+ return rich.text ? `<div class="long">${nl2br(rich.text)}</div>` : empty;
30
+ }
31
+ case "date":
32
+ return value ? formatDate(String(value)) : empty;
33
+ case "select":
34
+ case "radio":
35
+ return value ? optionLabel(field, value) : empty;
36
+ case "tags": {
37
+ const arr = Array.isArray(value) ? value : [];
38
+ return arr.length ? arr.map((v) => optionLabel(field, v)).join(", ") : empty;
39
+ }
40
+ case "checkbox":
41
+ return value ? "Sim" : "N\xE3o";
42
+ case "yes_no":
43
+ case "yes_no_text": {
44
+ const v = value;
45
+ const a = typeof v === "string" ? v : v?.answer;
46
+ const text = typeof v === "object" && v?.text?.trim() ? ` \u2014 ${esc(v.text.trim())}` : "";
47
+ return a === "sim" ? `Sim${text}` : a === "nao" ? `N\xE3o${text}` : empty;
48
+ }
49
+ case "recommendation": {
50
+ const lines = Array.isArray(value) ? value : [];
51
+ return lines.length ? lines.map((l) => esc(`${l.quantity > 1 ? `${l.quantity}\xD7 ` : ""}${l.name}`)).join("<br>") : empty;
52
+ }
53
+ case "image":
54
+ case "gallery":
55
+ case "budget":
56
+ case "stencil_photo":
57
+ case "signature":
58
+ return "";
59
+ // not meaningful on a printed contract
60
+ default:
61
+ return value ? esc(value) : empty;
62
+ }
63
+ }
64
+ function buildPrintHtml(template, doc, opts = {}) {
65
+ const heading = opts.heading ?? doc.title ?? template.name;
66
+ const subParts = [opts.subheading ?? doc.personName, new Date(doc.createdAt).toLocaleDateString()].filter(Boolean).map((s) => esc(s)).join(" &middot; ");
67
+ const fields = [...template.schema.fields].sort((a, b) => a.row - b.row || a.col - b.col);
68
+ const clampSpan = (n) => Math.max(1, Math.min(12, Number(n) || 12));
69
+ const body = fields.map((field) => {
70
+ if (field.type === "title") {
71
+ return `<h2 class="section" style="grid-column: 1 / -1">${esc(field.label)}</h2>`;
72
+ }
73
+ const rendered = renderValue(field, doc.data[field.id]);
74
+ if (rendered === "") return "";
75
+ const isLong = field.type === "memo" || field.type === "richtext";
76
+ return `<div class="field${isLong ? " field--long" : ""}" style="grid-column: span ${clampSpan(field.colSpan)}">
77
+ <div class="label">${esc(field.label)}</div>
78
+ <div class="value">${rendered}</div>
79
+ </div>`;
80
+ }).join("\n");
81
+ return `<!doctype html>
82
+ <html lang="pt-BR">
83
+ <head>
84
+ <meta charset="utf-8"/>
85
+ <title>${esc(heading)}</title>
86
+ <style>
87
+ @page { size: A4; margin: 20mm; }
88
+ * { box-sizing: border-box; }
89
+ html, body { margin: 0; padding: 0; }
90
+ body {
91
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif;
92
+ color: #111; font-size: 12pt; line-height: 1.5;
93
+ -webkit-print-color-adjust: exact; print-color-adjust: exact;
94
+ }
95
+ .page { max-width: 170mm; margin: 0 auto; padding: 12mm 0; }
96
+ header { border-bottom: 2px solid #111; padding-bottom: 8px; margin-bottom: 20px; }
97
+ header h1 { font-size: 18pt; margin: 0 0 2px; }
98
+ header .sub { font-size: 10pt; color: #555; }
99
+ /* 12-column grid \u2014 mirrors the builder Preview (FormRenderer) so the print
100
+ keeps the authored column layout. */
101
+ .grid { display: grid; grid-template-columns: repeat(12, 1fr); column-gap: 16px; row-gap: 12px; align-items: start; }
102
+ h2.section { font-size: 13pt; margin: 22px 0 4px; padding-bottom: 3px; border-bottom: 1px solid #ccc; }
103
+ .grid > h2.section:first-child { margin-top: 4px; }
104
+ .field { margin: 0; min-width: 0; }
105
+ .field .label { font-size: 9pt; text-transform: uppercase; letter-spacing: .04em; color: #666; margin-bottom: 2px; }
106
+ .field .value { font-size: 12pt; }
107
+ .field--long .value .long { white-space: normal; text-align: justify; }
108
+ /* Conteudo formatado (sanitizado em lib/html-text.ts). O HTML chega sem
109
+ class nenhuma, entao o estilo vem por tag. orphans/widows evitam que um
110
+ paragrafo deixe uma linha solta virando a pagina. */
111
+ .long.rich p { margin: 0 0 8px; orphans: 2; widows: 2; }
112
+ .long.rich p:last-child { margin-bottom: 0; }
113
+ .long.rich ul, .long.rich ol { margin: 0 0 8px; padding-left: 20px; }
114
+ .long.rich li { margin: 0 0 3px; }
115
+ .long.rich b, .long.rich strong { font-weight: 600; }
116
+ .long.rich blockquote { margin: 0 0 8px; padding-left: 10px; border-left: 2px solid #ccc; color: #444; }
117
+ .long.rich a { color: #111; text-decoration: underline; }
118
+ .long.rich table { width: 100%; border-collapse: collapse; margin: 0 0 8px; }
119
+ .long.rich td, .long.rich th { border: 1px solid #ccc; padding: 4px 6px; text-align: left; }
120
+ .long.rich h1, .long.rich h2, .long.rich h3,
121
+ .long.rich h4, .long.rich h5, .long.rich h6 { font-size: 12pt; font-weight: 600; margin: 10px 0 4px; }
122
+ .empty { color: #bbb; }
123
+ footer { margin-top: 40px; font-size: 9pt; color: #888; text-align: center; }
124
+ @media screen { body { background: #f3f3f3; } .page { background: #fff; max-width: 210mm; min-height: 297mm; padding: 20mm; box-shadow: 0 1px 8px rgba(0,0,0,.15); } }
125
+ </style>
126
+ </head>
127
+ <body>
128
+ <div class="page">
129
+ <header>
130
+ <h1>${esc(heading)}</h1>
131
+ ${subParts ? `<div class="sub">${subParts}</div>` : ""}
132
+ </header>
133
+ <div class="grid">
134
+ ${body}
135
+ </div>
136
+ </div>
137
+ </body>
138
+ </html>`;
139
+ }
140
+ function printHtml(html) {
141
+ if (typeof document === "undefined") return;
142
+ const iframe = document.createElement("iframe");
143
+ iframe.setAttribute("aria-hidden", "true");
144
+ iframe.style.position = "fixed";
145
+ iframe.style.right = "0";
146
+ iframe.style.bottom = "0";
147
+ iframe.style.width = "0";
148
+ iframe.style.height = "0";
149
+ iframe.style.border = "0";
150
+ document.body.appendChild(iframe);
151
+ const cleanup = () => {
152
+ setTimeout(() => {
153
+ if (iframe.parentNode) iframe.parentNode.removeChild(iframe);
154
+ }, 1e3);
155
+ };
156
+ const win = iframe.contentWindow;
157
+ const idoc = iframe.contentDocument || win?.document;
158
+ if (!win || !idoc) {
159
+ cleanup();
160
+ return;
161
+ }
162
+ idoc.open();
163
+ idoc.write(html);
164
+ idoc.close();
165
+ const doPrint = () => {
166
+ try {
167
+ win.focus();
168
+ win.print();
169
+ } finally {
170
+ cleanup();
171
+ }
172
+ };
173
+ if (idoc.readyState === "complete") {
174
+ setTimeout(doPrint, 50);
175
+ } else {
176
+ iframe.addEventListener("load", () => setTimeout(doPrint, 50), { once: true });
177
+ }
178
+ }
179
+ function printDocument(template, doc, opts) {
180
+ printHtml(buildPrintHtml(template, doc, opts));
181
+ }
182
+
183
+ // src/lib/person-fields.ts
184
+ var PERSON_FIELD_OPTIONS = [
185
+ { value: "name", labelKey: "customForms.personField.name" },
186
+ { value: "documentNumber", labelKey: "customForms.personField.documentNumber" },
187
+ { value: "email", labelKey: "customForms.personField.email" },
188
+ { value: "phone", labelKey: "customForms.personField.phone" },
189
+ { value: "dateOfBirth", labelKey: "customForms.personField.dateOfBirth" },
190
+ { value: "guardianName", labelKey: "customForms.personField.guardianName" },
191
+ { value: "address", labelKey: "customForms.personField.address" },
192
+ { value: "city", labelKey: "customForms.personField.city" },
193
+ { value: "state", labelKey: "customForms.personField.state" }
194
+ ];
195
+ var toSnake = (k) => k.replace(/[A-Z]/g, (m) => "_" + m.toLowerCase());
196
+ var toCamel = (k) => k.replace(/_([a-z])/g, (_, c) => c.toUpperCase());
197
+ function resolvePersonValue(person, mapKey) {
198
+ if (!person || !mapKey) return void 0;
199
+ for (const key of [mapKey, toSnake(mapKey), toCamel(mapKey)]) {
200
+ const v = person[key];
201
+ if (v != null && v !== "") return v;
202
+ }
203
+ return void 0;
204
+ }
205
+ function prefillFromPerson(schema, person, existing = {}) {
206
+ const data = { ...existing };
207
+ if (!schema) return data;
208
+ for (const field of schema.fields) {
209
+ const current = data[field.id];
210
+ if (current != null && current !== "") continue;
211
+ const mapped = field.map ? resolvePersonValue(person, field.map) : void 0;
212
+ if (mapped != null) {
213
+ data[field.id] = mapped;
214
+ } else if (field.defaultValue != null) {
215
+ data[field.id] = field.defaultValue;
216
+ }
217
+ }
218
+ return data;
219
+ }
220
+
221
+ export { PERSON_FIELD_OPTIONS, buildPrintHtml, prefillFromPerson, printDocument };
222
+ //# sourceMappingURL=chunk-X6CU44B4.js.map
223
+ //# sourceMappingURL=chunk-X6CU44B4.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/lib/print.ts","../src/lib/person-fields.ts"],"names":[],"mappings":";;;AAaA,SAAS,IAAI,KAAA,EAAwB;AACnC,EAAA,OAAO,MAAA,CAAO,KAAA,IAAS,EAAE,CAAA,CAAE,OAAA;AAAA,IAAQ,UAAA;AAAA,IAAY,CAAC,CAAA,KAAA,CAC7C,EAAE,GAAA,EAAK,SAAS,GAAA,EAAK,MAAA,EAAQ,GAAA,EAAK,MAAA,EAAQ,GAAA,EAAK,QAAA,EAAU,GAAA,EAAK,OAAA,IAAU,CAAC;AAAA,GAC5E;AACF;AAEA,SAAS,MAAM,KAAA,EAAuB;AACpC,EAAA,OAAO,GAAA,CAAI,KAAK,CAAA,CAAE,OAAA,CAAQ,UAAU,OAAO,CAAA;AAC7C;AAEA,SAAS,WAAW,KAAA,EAAuB;AAEzC,EAAA,MAAM,CAAA,GAAI,0BAAA,CAA2B,IAAA,CAAK,KAAK,CAAA;AAC/C,EAAA,IAAI,CAAC,CAAA,EAAG,OAAO,GAAA,CAAI,KAAK,CAAA;AACxB,EAAA,OAAO,CAAA,EAAG,CAAA,CAAE,CAAC,CAAC,CAAA,CAAA,EAAI,CAAA,CAAE,CAAC,CAAC,CAAA,CAAA,EAAI,CAAA,CAAE,CAAC,CAAC,CAAA,CAAA;AAChC;AAEA,SAAS,WAAA,CAAY,OAAqB,KAAA,EAAwB;AAChE,EAAA,MAAM,GAAA,GAAA,CAAO,KAAA,CAAM,OAAA,IAAW,EAAC,EAAG,KAAK,CAAC,CAAA,KAAM,CAAA,CAAE,KAAA,KAAU,KAAK,CAAA;AAC/D,EAAA,OAAO,GAAA,CAAI,GAAA,GAAM,GAAA,CAAI,KAAA,GAAQ,KAAK,CAAA;AACpC;AAGA,SAAS,WAAA,CAAY,OAAqB,KAAA,EAAwB;AAChE,EAAA,MAAM,KAAA,GAAQ,mCAAA;AACd,EAAA,QAAQ,MAAM,IAAA;AAAM,IAClB,KAAK,MAAA;AAAA,IACL,KAAK,UAAA,EAAY;AAQf,MAAA,MAAM,IAAA,GAAO,eAAe,KAAK,CAAA;AACjC,MAAA,IAAI,MAAA,IAAU,IAAA,EAAM,OAAO,CAAA,uBAAA,EAA0B,KAAK,IAAI,CAAA,MAAA,CAAA;AAC9D,MAAA,OAAO,KAAK,IAAA,GAAO,CAAA,kBAAA,EAAqB,MAAM,IAAA,CAAK,IAAI,CAAC,CAAA,MAAA,CAAA,GAAW,KAAA;AAAA,IACrE;AAAA,IACA,KAAK,MAAA;AACH,MAAA,OAAO,KAAA,GAAQ,UAAA,CAAW,MAAA,CAAO,KAAK,CAAC,CAAA,GAAI,KAAA;AAAA,IAC7C,KAAK,QAAA;AAAA,IACL,KAAK,OAAA;AACH,MAAA,OAAO,KAAA,GAAQ,WAAA,CAAY,KAAA,EAAO,KAAK,CAAA,GAAI,KAAA;AAAA,IAC7C,KAAK,MAAA,EAAQ;AACX,MAAA,MAAM,MAAM,KAAA,CAAM,OAAA,CAAQ,KAAK,CAAA,GAAI,QAAQ,EAAC;AAC5C,MAAA,OAAO,GAAA,CAAI,MAAA,GACP,GAAA,CAAI,GAAA,CAAI,CAAC,CAAA,KAAM,WAAA,CAAY,KAAA,EAAO,CAAC,CAAC,CAAA,CAAE,IAAA,CAAK,IAAI,CAAA,GAC/C,KAAA;AAAA,IACN;AAAA,IACA,KAAK,UAAA;AACH,MAAA,OAAO,QAAQ,KAAA,GAAQ,QAAA;AAAA,IACzB,KAAK,QAAA;AAAA,IACL,KAAK,aAAA,EAAe;AAClB,MAAA,MAAM,CAAA,GAAI,KAAA;AACV,MAAA,MAAM,CAAA,GAAI,OAAO,CAAA,KAAM,QAAA,GAAW,IAAI,CAAA,EAAG,MAAA;AACzC,MAAA,MAAM,IAAA,GAAO,OAAO,CAAA,KAAM,QAAA,IAAY,GAAG,IAAA,EAAM,IAAA,EAAK,GAAI,CAAA,QAAA,EAAM,IAAI,CAAA,CAAE,IAAA,CAAK,IAAA,EAAM,CAAC,CAAA,CAAA,GAAK,EAAA;AACrF,MAAA,OAAO,CAAA,KAAM,QAAQ,CAAA,GAAA,EAAM,IAAI,KAAK,CAAA,KAAM,KAAA,GAAQ,CAAA,MAAA,EAAM,IAAI,CAAA,CAAA,GAAK,KAAA;AAAA,IACnE;AAAA,IACA,KAAK,gBAAA,EAAkB;AACrB,MAAA,MAAM,QAAQ,KAAA,CAAM,OAAA,CAAQ,KAAK,CAAA,GAAK,QAAsD,EAAC;AAC7F,MAAA,OAAO,KAAA,CAAM,MAAA,GAAS,KAAA,CAAM,GAAA,CAAI,CAAC,MAAM,GAAA,CAAI,CAAA,EAAG,CAAA,CAAE,QAAA,GAAW,CAAA,GAAI,CAAA,EAAG,EAAE,QAAQ,CAAA,KAAA,CAAA,GAAO,EAAE,CAAA,EAAG,CAAA,CAAE,IAAI,EAAE,CAAC,CAAA,CAAE,IAAA,CAAK,MAAM,CAAA,GAAI,KAAA;AAAA,IACpH;AAAA,IACA,KAAK,OAAA;AAAA,IACL,KAAK,SAAA;AAAA,IACL,KAAK,QAAA;AAAA,IACL,KAAK,eAAA;AAAA,IACL,KAAK,WAAA;AACH,MAAA,OAAO,EAAA;AAAA;AAAA,IACT;AACE,MAAA,OAAO,KAAA,GAAQ,GAAA,CAAI,KAAK,CAAA,GAAI,KAAA;AAAA;AAElC;AAUO,SAAS,cAAA,CACd,QAAA,EACA,GAAA,EACA,IAAA,GAA0B,EAAC,EACnB;AACR,EAAA,MAAM,OAAA,GAAU,IAAA,CAAK,OAAA,IAAW,GAAA,CAAI,SAAS,QAAA,CAAS,IAAA;AACtD,EAAA,MAAM,QAAA,GAAW,CAAC,IAAA,CAAK,UAAA,IAAc,GAAA,CAAI,YAAY,IAAI,IAAA,CAAK,GAAA,CAAI,SAAS,CAAA,CAAE,kBAAA,EAAoB,CAAA,CAC9F,MAAA,CAAO,OAAO,CAAA,CACd,GAAA,CAAI,CAAC,CAAA,KAAM,GAAA,CAAI,CAAC,CAAC,CAAA,CACjB,IAAA,CAAK,YAAY,CAAA;AAEpB,EAAA,MAAM,SAAS,CAAC,GAAG,SAAS,MAAA,CAAO,MAAM,EAAE,IAAA,CAAK,CAAC,CAAA,EAAG,CAAA,KAAM,EAAE,GAAA,GAAM,CAAA,CAAE,OAAO,CAAA,CAAE,GAAA,GAAM,EAAE,GAAG,CAAA;AAExF,EAAA,MAAM,SAAA,GAAY,CAAC,CAAA,KAAe,IAAA,CAAK,GAAA,CAAI,CAAA,EAAG,IAAA,CAAK,GAAA,CAAI,EAAA,EAAI,MAAA,CAAO,CAAC,CAAA,IAAK,EAAE,CAAC,CAAA;AAI3E,EAAA,MAAM,IAAA,GAAO,MAAA,CACV,GAAA,CAAI,CAAC,KAAA,KAAU;AACd,IAAA,IAAI,KAAA,CAAM,SAAS,OAAA,EAAS;AAC1B,MAAA,OAAO,CAAA,gDAAA,EAAmD,GAAA,CAAI,KAAA,CAAM,KAAK,CAAC,CAAA,KAAA,CAAA;AAAA,IAC5E;AACA,IAAA,MAAM,WAAW,WAAA,CAAY,KAAA,EAAO,IAAI,IAAA,CAAK,KAAA,CAAM,EAAE,CAAC,CAAA;AACtD,IAAA,IAAI,QAAA,KAAa,IAAI,OAAO,EAAA;AAC5B,IAAA,MAAM,MAAA,GAAS,KAAA,CAAM,IAAA,KAAS,MAAA,IAAU,MAAM,IAAA,KAAS,UAAA;AACvD,IAAA,OAAO,CAAA,iBAAA,EAAoB,SAAS,cAAA,GAAiB,EAAE,8BAA8B,SAAA,CAAU,KAAA,CAAM,OAAO,CAAC,CAAA;AAAA,2BAAA,EACtF,GAAA,CAAI,KAAA,CAAM,KAAK,CAAC,CAAA;AAAA,2BAAA,EAChB,QAAQ,CAAA;AAAA,YAAA,CAAA;AAAA,EAEjC,CAAC,CAAA,CACA,IAAA,CAAK,IAAI,CAAA;AAEZ,EAAA,OAAO,CAAA;AAAA;AAAA;AAAA;AAAA,OAAA,EAIA,GAAA,CAAI,OAAO,CAAC,CAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,UAAA,EA6CT,GAAA,CAAI,OAAO,CAAC,CAAA;AAAA,MAAA,EAChB,QAAA,GAAW,CAAA,iBAAA,EAAoB,QAAQ,CAAA,MAAA,CAAA,GAAW,EAAE;AAAA;AAAA;AAAA,MAAA,EAGpD,IAAI;AAAA;AAAA;AAAA;AAAA,OAAA,CAAA;AAKZ;AAMO,SAAS,UAAU,IAAA,EAAoB;AAC5C,EAAA,IAAI,OAAO,aAAa,WAAA,EAAa;AACrC,EAAA,MAAM,MAAA,GAAS,QAAA,CAAS,aAAA,CAAc,QAAQ,CAAA;AAC9C,EAAA,MAAA,CAAO,YAAA,CAAa,eAAe,MAAM,CAAA;AACzC,EAAA,MAAA,CAAO,MAAM,QAAA,GAAW,OAAA;AACxB,EAAA,MAAA,CAAO,MAAM,KAAA,GAAQ,GAAA;AACrB,EAAA,MAAA,CAAO,MAAM,MAAA,GAAS,GAAA;AACtB,EAAA,MAAA,CAAO,MAAM,KAAA,GAAQ,GAAA;AACrB,EAAA,MAAA,CAAO,MAAM,MAAA,GAAS,GAAA;AACtB,EAAA,MAAA,CAAO,MAAM,MAAA,GAAS,GAAA;AACtB,EAAA,QAAA,CAAS,IAAA,CAAK,YAAY,MAAM,CAAA;AAEhC,EAAA,MAAM,UAAU,MAAM;AAEpB,IAAA,UAAA,CAAW,MAAM;AACf,MAAA,IAAI,MAAA,CAAO,UAAA,EAAY,MAAA,CAAO,UAAA,CAAW,YAAY,MAAM,CAAA;AAAA,IAC7D,GAAG,GAAI,CAAA;AAAA,EACT,CAAA;AAEA,EAAA,MAAM,MAAM,MAAA,CAAO,aAAA;AACnB,EAAA,MAAM,IAAA,GAAO,MAAA,CAAO,eAAA,IAAmB,GAAA,EAAK,QAAA;AAC5C,EAAA,IAAI,CAAC,GAAA,IAAO,CAAC,IAAA,EAAM;AACjB,IAAA,OAAA,EAAQ;AACR,IAAA;AAAA,EACF;AAEA,EAAA,IAAA,CAAK,IAAA,EAAK;AACV,EAAA,IAAA,CAAK,MAAM,IAAI,CAAA;AACf,EAAA,IAAA,CAAK,KAAA,EAAM;AAEX,EAAA,MAAM,UAAU,MAAM;AACpB,IAAA,IAAI;AACF,MAAA,GAAA,CAAI,KAAA,EAAM;AACV,MAAA,GAAA,CAAI,KAAA,EAAM;AAAA,IACZ,CAAA,SAAE;AACA,MAAA,OAAA,EAAQ;AAAA,IACV;AAAA,EACF,CAAA;AAGA,EAAA,IAAI,IAAA,CAAK,eAAe,UAAA,EAAY;AAClC,IAAA,UAAA,CAAW,SAAS,EAAE,CAAA;AAAA,EACxB,CAAA,MAAO;AACL,IAAA,MAAA,CAAO,gBAAA,CAAiB,MAAA,EAAQ,MAAM,UAAA,CAAW,OAAA,EAAS,EAAE,CAAA,EAAG,EAAE,IAAA,EAAM,IAAA,EAAM,CAAA;AAAA,EAC/E;AACF;AAGO,SAAS,aAAA,CACd,QAAA,EACA,GAAA,EACA,IAAA,EACM;AACN,EAAA,SAAA,CAAU,cAAA,CAAe,QAAA,EAAU,GAAA,EAAK,IAAI,CAAC,CAAA;AAC/C;;;ACvOO,IAAM,oBAAA,GAAmE;AAAA,EAC9E,EAAE,KAAA,EAAO,MAAA,EAAQ,QAAA,EAAU,8BAAA,EAA+B;AAAA,EAC1D,EAAE,KAAA,EAAO,gBAAA,EAAkB,QAAA,EAAU,wCAAA,EAAyC;AAAA,EAC9E,EAAE,KAAA,EAAO,OAAA,EAAS,QAAA,EAAU,+BAAA,EAAgC;AAAA,EAC5D,EAAE,KAAA,EAAO,OAAA,EAAS,QAAA,EAAU,+BAAA,EAAgC;AAAA,EAC5D,EAAE,KAAA,EAAO,aAAA,EAAe,QAAA,EAAU,qCAAA,EAAsC;AAAA,EACxE,EAAE,KAAA,EAAO,cAAA,EAAgB,QAAA,EAAU,sCAAA,EAAuC;AAAA,EAC1E,EAAE,KAAA,EAAO,SAAA,EAAW,QAAA,EAAU,iCAAA,EAAkC;AAAA,EAChE,EAAE,KAAA,EAAO,MAAA,EAAQ,QAAA,EAAU,8BAAA,EAA+B;AAAA,EAC1D,EAAE,KAAA,EAAO,OAAA,EAAS,QAAA,EAAU,+BAAA;AAC9B;AAEA,IAAM,OAAA,GAAU,CAAC,CAAA,KAAc,CAAA,CAAE,OAAA,CAAQ,QAAA,EAAU,CAAC,CAAA,KAAM,GAAA,GAAM,CAAA,CAAE,WAAA,EAAa,CAAA;AAC/E,IAAM,OAAA,GAAU,CAAC,CAAA,KAAc,CAAA,CAAE,OAAA,CAAQ,WAAA,EAAa,CAAC,CAAA,EAAG,CAAA,KAAc,CAAA,CAAE,WAAA,EAAa,CAAA;AAGhF,SAAS,kBAAA,CACd,QACA,MAAA,EACS;AACT,EAAA,IAAI,CAAC,MAAA,IAAU,CAAC,MAAA,EAAQ,OAAO,MAAA;AAC/B,EAAA,KAAA,MAAW,GAAA,IAAO,CAAC,MAAA,EAAQ,OAAA,CAAQ,MAAM,CAAA,EAAG,OAAA,CAAQ,MAAM,CAAC,CAAA,EAAG;AAC5D,IAAA,MAAM,CAAA,GAAI,OAAO,GAAG,CAAA;AACpB,IAAA,IAAI,CAAA,IAAK,IAAA,IAAQ,CAAA,KAAM,EAAA,EAAI,OAAO,CAAA;AAAA,EACpC;AACA,EAAA,OAAO,MAAA;AACT;AAQO,SAAS,iBAAA,CACd,MAAA,EACA,MAAA,EACA,QAAA,GAAoC,EAAC,EACZ;AACzB,EAAA,MAAM,IAAA,GAAgC,EAAE,GAAG,QAAA,EAAS;AACpD,EAAA,IAAI,CAAC,QAAQ,OAAO,IAAA;AACpB,EAAA,KAAA,MAAW,KAAA,IAAS,OAAO,MAAA,EAAQ;AACjC,IAAA,MAAM,OAAA,GAAU,IAAA,CAAK,KAAA,CAAM,EAAE,CAAA;AAC7B,IAAA,IAAI,OAAA,IAAW,IAAA,IAAQ,OAAA,KAAY,EAAA,EAAI;AACvC,IAAA,MAAM,SAAS,KAAA,CAAM,GAAA,GAAM,mBAAmB,MAAA,EAAQ,KAAA,CAAM,GAAG,CAAA,GAAI,MAAA;AACnE,IAAA,IAAI,UAAU,IAAA,EAAM;AAClB,MAAA,IAAA,CAAK,KAAA,CAAM,EAAE,CAAA,GAAI,MAAA;AAAA,IACnB,CAAA,MAAA,IAAW,KAAA,CAAM,YAAA,IAAgB,IAAA,EAAM;AACrC,MAAA,IAAA,CAAK,KAAA,CAAM,EAAE,CAAA,GAAI,KAAA,CAAM,YAAA;AAAA,IACzB;AAAA,EACF;AACA,EAAA,OAAO,IAAA;AACT","file":"chunk-X6CU44B4.js","sourcesContent":["// ============================================================\n// PRINT / PDF — render a filled document to a printable A4 page\n// ============================================================\n//\n// Browser print-to-PDF: we build a clean, self-contained A4 HTML document from\n// the template schema + saved data, drop it into a hidden iframe, and call\n// print() on it. The browser's print dialog covers both physical printing and\n// \"Save as PDF\". No external deps.\n\nimport type { FormDocument } from '@fayz-ai/forms/domain/document'\nimport type { FormFieldDef, FormTemplate } from '@fayz-ai/forms/domain/template'\nimport { fieldRichValue } from './html-text'\n\nfunction esc(value: unknown): string {\n return String(value ?? '').replace(/[&<>\"']/g, (c) =>\n ({ '&': '&amp;', '<': '&lt;', '>': '&gt;', '\"': '&quot;', \"'\": '&#39;' }[c] as string),\n )\n}\n\nfunction nl2br(value: string): string {\n return esc(value).replace(/\\r?\\n/g, '<br/>')\n}\n\nfunction formatDate(value: string): string {\n // ISO date (YYYY-MM-DD) → locale date; anything else passes through.\n const m = /^(\\d{4})-(\\d{2})-(\\d{2})/.exec(value)\n if (!m) return esc(value)\n return `${m[3]}/${m[2]}/${m[1]}`\n}\n\nfunction optionLabel(field: FormFieldDef, value: unknown): string {\n const opt = (field.options ?? []).find((o) => o.value === value)\n return esc(opt ? opt.label : value)\n}\n\n/** Render one field's value as an HTML fragment for the printed page. */\nfunction renderValue(field: FormFieldDef, value: unknown): string {\n const empty = '<span class=\"empty\">—</span>'\n switch (field.type) {\n case 'memo':\n case 'richtext': {\n // Texto primeiro, escape depois. `nl2br` já escapava — e era exatamente\n // por isso que a folha impressa saía com `&lt;p dir=&quot;ltr&quot;&gt;`\n // no lugar da evolução do atendimento: escapar HTML guardado mostra a\n // marcação. Ver lib/html-text.ts.\n // Agora o valor passa pela lista de permissão e a folha sai formatada,\n // igual à tela. O escape continua no caminho de texto puro, que é onde\n // ele sempre foi o certo.\n const rich = fieldRichValue(value)\n if ('html' in rich) return `<div class=\"long rich\">${rich.html}</div>`\n return rich.text ? `<div class=\"long\">${nl2br(rich.text)}</div>` : empty\n }\n case 'date':\n return value ? formatDate(String(value)) : empty\n case 'select':\n case 'radio':\n return value ? optionLabel(field, value) : empty\n case 'tags': {\n const arr = Array.isArray(value) ? value : []\n return arr.length\n ? arr.map((v) => optionLabel(field, v)).join(', ')\n : empty\n }\n case 'checkbox':\n return value ? 'Sim' : 'Não'\n case 'yes_no':\n case 'yes_no_text': {\n const v = value as { answer?: string; text?: string } | string | null\n const a = typeof v === 'string' ? v : v?.answer\n const text = typeof v === 'object' && v?.text?.trim() ? ` — ${esc(v.text.trim())}` : ''\n return a === 'sim' ? `Sim${text}` : a === 'nao' ? `Não${text}` : empty\n }\n case 'recommendation': {\n const lines = Array.isArray(value) ? (value as Array<{ name: string; quantity: number }>) : []\n return lines.length ? lines.map((l) => esc(`${l.quantity > 1 ? `${l.quantity}× ` : ''}${l.name}`)).join('<br>') : empty\n }\n case 'image':\n case 'gallery':\n case 'budget':\n case 'stencil_photo':\n case 'signature':\n return '' // not meaningful on a printed contract\n default:\n return value ? esc(value) : empty\n }\n}\n\nexport interface BuildPrintOptions {\n /** Heading shown at the top of the page (defaults to the document title). */\n heading?: string\n /** Small line under the heading (e.g. person name). */\n subheading?: string\n}\n\n/** Build a full, self-contained printable HTML document. */\nexport function buildPrintHtml(\n template: FormTemplate,\n doc: FormDocument,\n opts: BuildPrintOptions = {},\n): string {\n const heading = opts.heading ?? doc.title ?? template.name\n const subParts = [opts.subheading ?? doc.personName, new Date(doc.createdAt).toLocaleDateString()]\n .filter(Boolean)\n .map((s) => esc(s))\n .join(' &middot; ')\n\n const fields = [...template.schema.fields].sort((a, b) => a.row - b.row || a.col - b.col)\n\n const clampSpan = (n: unknown) => Math.max(1, Math.min(12, Number(n) || 12))\n\n // Mirror the builder's 12-column grid so the print keeps the authored layout\n // (side-by-side fields stay side by side). Titles span the full row.\n const body = fields\n .map((field) => {\n if (field.type === 'title') {\n return `<h2 class=\"section\" style=\"grid-column: 1 / -1\">${esc(field.label)}</h2>`\n }\n const rendered = renderValue(field, doc.data[field.id])\n if (rendered === '') return ''\n const isLong = field.type === 'memo' || field.type === 'richtext'\n return `<div class=\"field${isLong ? ' field--long' : ''}\" style=\"grid-column: span ${clampSpan(field.colSpan)}\">\n <div class=\"label\">${esc(field.label)}</div>\n <div class=\"value\">${rendered}</div>\n </div>`\n })\n .join('\\n')\n\n return `<!doctype html>\n<html lang=\"pt-BR\">\n<head>\n<meta charset=\"utf-8\"/>\n<title>${esc(heading)}</title>\n<style>\n @page { size: A4; margin: 20mm; }\n * { box-sizing: border-box; }\n html, body { margin: 0; padding: 0; }\n body {\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif;\n color: #111; font-size: 12pt; line-height: 1.5;\n -webkit-print-color-adjust: exact; print-color-adjust: exact;\n }\n .page { max-width: 170mm; margin: 0 auto; padding: 12mm 0; }\n header { border-bottom: 2px solid #111; padding-bottom: 8px; margin-bottom: 20px; }\n header h1 { font-size: 18pt; margin: 0 0 2px; }\n header .sub { font-size: 10pt; color: #555; }\n /* 12-column grid — mirrors the builder Preview (FormRenderer) so the print\n keeps the authored column layout. */\n .grid { display: grid; grid-template-columns: repeat(12, 1fr); column-gap: 16px; row-gap: 12px; align-items: start; }\n h2.section { font-size: 13pt; margin: 22px 0 4px; padding-bottom: 3px; border-bottom: 1px solid #ccc; }\n .grid > h2.section:first-child { margin-top: 4px; }\n .field { margin: 0; min-width: 0; }\n .field .label { font-size: 9pt; text-transform: uppercase; letter-spacing: .04em; color: #666; margin-bottom: 2px; }\n .field .value { font-size: 12pt; }\n .field--long .value .long { white-space: normal; text-align: justify; }\n /* Conteudo formatado (sanitizado em lib/html-text.ts). O HTML chega sem\n class nenhuma, entao o estilo vem por tag. orphans/widows evitam que um\n paragrafo deixe uma linha solta virando a pagina. */\n .long.rich p { margin: 0 0 8px; orphans: 2; widows: 2; }\n .long.rich p:last-child { margin-bottom: 0; }\n .long.rich ul, .long.rich ol { margin: 0 0 8px; padding-left: 20px; }\n .long.rich li { margin: 0 0 3px; }\n .long.rich b, .long.rich strong { font-weight: 600; }\n .long.rich blockquote { margin: 0 0 8px; padding-left: 10px; border-left: 2px solid #ccc; color: #444; }\n .long.rich a { color: #111; text-decoration: underline; }\n .long.rich table { width: 100%; border-collapse: collapse; margin: 0 0 8px; }\n .long.rich td, .long.rich th { border: 1px solid #ccc; padding: 4px 6px; text-align: left; }\n .long.rich h1, .long.rich h2, .long.rich h3,\n .long.rich h4, .long.rich h5, .long.rich h6 { font-size: 12pt; font-weight: 600; margin: 10px 0 4px; }\n .empty { color: #bbb; }\n footer { margin-top: 40px; font-size: 9pt; color: #888; text-align: center; }\n @media screen { body { background: #f3f3f3; } .page { background: #fff; max-width: 210mm; min-height: 297mm; padding: 20mm; box-shadow: 0 1px 8px rgba(0,0,0,.15); } }\n</style>\n</head>\n<body>\n <div class=\"page\">\n <header>\n <h1>${esc(heading)}</h1>\n ${subParts ? `<div class=\"sub\">${subParts}</div>` : ''}\n </header>\n <div class=\"grid\">\n ${body}\n </div>\n </div>\n</body>\n</html>`\n}\n\n/**\n * Print a prebuilt HTML document via a hidden iframe (popup-blocker safe).\n * The browser print dialog handles both printing and \"Save as PDF\".\n */\nexport function printHtml(html: string): void {\n if (typeof document === 'undefined') return\n const iframe = document.createElement('iframe')\n iframe.setAttribute('aria-hidden', 'true')\n iframe.style.position = 'fixed'\n iframe.style.right = '0'\n iframe.style.bottom = '0'\n iframe.style.width = '0'\n iframe.style.height = '0'\n iframe.style.border = '0'\n document.body.appendChild(iframe)\n\n const cleanup = () => {\n // Give the print dialog a beat before tearing the frame down.\n setTimeout(() => {\n if (iframe.parentNode) iframe.parentNode.removeChild(iframe)\n }, 1000)\n }\n\n const win = iframe.contentWindow\n const idoc = iframe.contentDocument || win?.document\n if (!win || !idoc) {\n cleanup()\n return\n }\n\n idoc.open()\n idoc.write(html)\n idoc.close()\n\n const doPrint = () => {\n try {\n win.focus()\n win.print()\n } finally {\n cleanup()\n }\n }\n\n // Wait for the frame document to be ready before printing.\n if (idoc.readyState === 'complete') {\n setTimeout(doPrint, 50)\n } else {\n iframe.addEventListener('load', () => setTimeout(doPrint, 50), { once: true })\n }\n}\n\n/** Convenience: build + print a document in one call. */\nexport function printDocument(\n template: FormTemplate,\n doc: FormDocument,\n opts?: BuildPrintOptions,\n): void {\n printHtml(buildPrintHtml(template, doc, opts))\n}\n","// ============================================================\n// PERSON FIELD MAPPING — prefill a document from a person record\n// ============================================================\n//\n// A template field can declare `map: '<personKey>'` (see FormFieldDef.map).\n// When a document is created from a person's profile, fields with a mapping are\n// pre-filled from that person's record. The person record reaching the widget\n// is the host app's CRUD detail `item`, keyed by the entity's field keys\n// (camelCase, e.g. `documentNumber`). We resolve tolerantly so the same mapping\n// works whether the host exposes camelCase or snake_case keys.\n\nimport type { FormSchema } from '@fayz-ai/forms/domain/template'\n\n/** Curated, vertical-agnostic person keys offered in the field builder. */\nexport const PERSON_FIELD_OPTIONS: Array<{ value: string; labelKey: string }> = [\n { value: 'name', labelKey: 'customForms.personField.name' },\n { value: 'documentNumber', labelKey: 'customForms.personField.documentNumber' },\n { value: 'email', labelKey: 'customForms.personField.email' },\n { value: 'phone', labelKey: 'customForms.personField.phone' },\n { value: 'dateOfBirth', labelKey: 'customForms.personField.dateOfBirth' },\n { value: 'guardianName', labelKey: 'customForms.personField.guardianName' },\n { value: 'address', labelKey: 'customForms.personField.address' },\n { value: 'city', labelKey: 'customForms.personField.city' },\n { value: 'state', labelKey: 'customForms.personField.state' },\n]\n\nconst toSnake = (k: string) => k.replace(/[A-Z]/g, (m) => '_' + m.toLowerCase())\nconst toCamel = (k: string) => k.replace(/_([a-z])/g, (_, c: string) => c.toUpperCase())\n\n/** Read a person field value, tolerating camelCase/snake_case key variants. */\nexport function resolvePersonValue(\n person: Record<string, unknown> | undefined | null,\n mapKey: string | undefined,\n): unknown {\n if (!person || !mapKey) return undefined\n for (const key of [mapKey, toSnake(mapKey), toCamel(mapKey)]) {\n const v = person[key]\n if (v != null && v !== '') return v\n }\n return undefined\n}\n\n/**\n * Build the initial document data for a template. For each field, applies (in\n * priority order) an existing value, then the mapped person value, then the\n * field's static `defaultValue`. Never overwrites a value already present in\n * `existing`.\n */\nexport function prefillFromPerson(\n schema: FormSchema | undefined,\n person: Record<string, unknown> | undefined | null,\n existing: Record<string, unknown> = {},\n): Record<string, unknown> {\n const data: Record<string, unknown> = { ...existing }\n if (!schema) return data\n for (const field of schema.fields) {\n const current = data[field.id]\n if (current != null && current !== '') continue\n const mapped = field.map ? resolvePersonValue(person, field.map) : undefined\n if (mapped != null) {\n data[field.id] = mapped\n } else if (field.defaultValue != null) {\n data[field.id] = field.defaultValue\n }\n }\n return data\n}\n"]}