@templatical/editor 0.0.4 → 0.0.5
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.
- package/dist/{AiChatSidebar-CjfhTZwo.js → AiChatSidebar-DwME3f-a.js} +84 -70
- package/dist/{AiFeatureMenu-K44aZa_P.js → AiFeatureMenu-DJvWL1GZ.js} +23 -23
- package/dist/CloudEditor-Fe0ssRgi.js +1082 -0
- package/dist/{CollaboratorBar-BuCEcdbB.js → CollaboratorBar-DTT0EkZn.js} +1 -1
- package/dist/{CommentsSidebar-2lcqMfIP.js → CommentsSidebar-DrJhQRXK.js} +131 -131
- package/dist/{DesignReferenceSidebar-CNMu4Zrx.js → DesignReferenceSidebar-DdOht5zn.js} +49 -49
- package/dist/{ModuleBrowserModal-CvQ0xyQf.js → ModuleBrowserModal-CiV_jOEM.js} +58 -58
- package/dist/{ModulePreviewCanvas-Be2B3Y07.js → ModulePreviewCanvas-Bmy6Y1WE.js} +1 -1
- package/dist/ParagraphEditor-CoQ3NlS7.js +688 -0
- package/dist/{SaveModuleDialog-BaaeH5Xm.js → SaveModuleDialog-CD2ZYq1o.js} +25 -25
- package/dist/{SnapshotHistory-BPfjiuu1.js → SnapshotHistory-DltsKvhP.js} +1 -1
- package/dist/TemplateScoringPanel-DmnmUE3y.js +254 -0
- package/dist/{TestEmailModal-DIAlB3e_.js → TestEmailModal-Dl633j9o.js} +2 -2
- package/dist/{TitleEditor-D9DPjQkX.js → TitleEditor-C7fds2Nc.js} +3 -3
- package/dist/{TplModal-CmTSvCY-.js → TplModal-C5_CF-qn.js} +1 -1
- package/dist/{blockTypeIcons-D1RTWOkx.js → blockTypeIcons-BrKZB10B.js} +1 -1
- package/dist/cdn/chunks/AiChatSidebar-X_Bv3Qys.js +2 -0
- package/dist/cdn/chunks/{AiFeatureMenu-lxVm1RjH.js → AiFeatureMenu-C5UQmEgV.js} +16 -16
- package/dist/cdn/chunks/AiFeatureMenu-C5UQmEgV.js.map +1 -0
- package/dist/cdn/chunks/CloudEditor-DeTolKnf.js +1056 -0
- package/dist/cdn/chunks/CloudEditor-DeTolKnf.js.map +1 -0
- package/dist/cdn/chunks/{CollaboratorBar-D2PKtlOw.js → CollaboratorBar-DO1nxSrr.js} +3 -3
- package/dist/cdn/chunks/{CollaboratorBar-D2PKtlOw.js.map → CollaboratorBar-DO1nxSrr.js.map} +1 -1
- package/dist/cdn/chunks/CommentsSidebar-4MTw_hue.js +2 -0
- package/dist/cdn/chunks/DesignReferenceSidebar-Bswh4Yx4.js +2 -0
- package/dist/cdn/chunks/{ModuleBrowserModal-CxDXzkKS.js → ModuleBrowserModal-ChBr3aXj.js} +52 -52
- package/dist/cdn/chunks/ModuleBrowserModal-ChBr3aXj.js.map +1 -0
- package/dist/cdn/chunks/{ModulePreviewCanvas-DEfHampA.js → ModulePreviewCanvas-DkSvri9H.js} +2 -2
- package/dist/cdn/chunks/{ModulePreviewCanvas-DEfHampA.js.map → ModulePreviewCanvas-DkSvri9H.js.map} +1 -1
- package/dist/cdn/chunks/ParagraphEditor-DU3oUKA7.js +539 -0
- package/dist/cdn/chunks/ParagraphEditor-DU3oUKA7.js.map +1 -0
- package/dist/cdn/chunks/{RichTextEditorContent-DWUzizsC.js → RichTextEditorContent-BrsW1p9s.js} +4 -4
- package/dist/cdn/chunks/{RichTextEditorContent-DWUzizsC.js.map → RichTextEditorContent-BrsW1p9s.js.map} +1 -1
- package/dist/cdn/chunks/{SaveModuleDialog-DVna2xUl.js → SaveModuleDialog-CjqKkTEc.js} +24 -24
- package/dist/cdn/chunks/SaveModuleDialog-CjqKkTEc.js.map +1 -0
- package/dist/cdn/chunks/SnapshotHistory-KME4xmn_.js +2 -0
- package/dist/cdn/chunks/TemplateScoringPanel-DgB3xDN6.js +2 -0
- package/dist/cdn/chunks/TestEmailModal-DdpvRbYf.js +2 -0
- package/dist/cdn/chunks/{TitleEditor-DDf_OcHS.js → TitleEditor-C8FYbadT.js} +9 -9
- package/dist/cdn/chunks/{TitleEditor-DDf_OcHS.js.map → TitleEditor-C8FYbadT.js.map} +1 -1
- package/dist/cdn/chunks/{blockTypeIcons-BnobReQm.js → blockTypeIcons-5QwYklNq.js} +3 -3
- package/dist/cdn/chunks/{blockTypeIcons-BnobReQm.js.map → blockTypeIcons-5QwYklNq.js.map} +1 -1
- package/dist/cdn/chunks/{dist-CJcMnY7o.js → dist-BF5c3Dr-.js} +1 -1
- package/dist/cdn/chunks/dist-BGzvIxcJ.js +2 -0
- package/dist/cdn/chunks/dist-CFemF8rI.js +2 -0
- package/dist/cdn/chunks/dist-Co6uFhFK.js +2 -0
- package/dist/cdn/chunks/{dist-BkETaOfw.js → dist-DCikBY9K.js} +1 -1
- package/dist/cdn/chunks/dist-DUILafAC.js +2 -0
- package/dist/cdn/chunks/dist-DghiKH0A.js +2 -0
- package/dist/cdn/chunks/dist-Dw8ckvfK.js +2 -0
- package/dist/cdn/chunks/dist-H07p0KAw.js +2 -0
- package/dist/cdn/chunks/{dist-B878xb_62.js → dist-KYv9v_1z2.js} +11 -11
- package/dist/cdn/chunks/{dist-B878xb_62.js.map → dist-KYv9v_1z2.js.map} +1 -1
- package/dist/cdn/chunks/{dist-DLWHlekl.js → dist-MjnKIc0W.js} +1 -1
- package/dist/cdn/chunks/{dist-CllLxIMQ.js → dist-odp0vGRv.js} +1 -1
- package/dist/cdn/chunks/{extensions-B_kcV0tK.js → extensions-Bj7USRLr.js} +20 -20
- package/dist/cdn/chunks/{extensions-B_kcV0tK.js.map → extensions-Bj7USRLr.js.map} +1 -1
- package/dist/cdn/chunks/{features-ofOGnSC0.js → features-Ds0XUfte.js} +1235 -1198
- package/dist/cdn/chunks/features-Ds0XUfte.js.map +1 -0
- package/dist/cdn/chunks/{icons-bIb7PBOE.js → icons-fWsuSvgd.js} +2 -2
- package/dist/cdn/chunks/{icons-bIb7PBOE.js.map → icons-fWsuSvgd.js.map} +1 -1
- package/dist/cdn/chunks/{media-library-BIYzV2Y2.js → media-library-BGQm_OyC.js} +528 -528
- package/dist/cdn/chunks/{media-library-BIYzV2Y2.js.map → media-library-BGQm_OyC.js.map} +1 -1
- package/dist/cdn/chunks/{src-BuW9oYtm.js → src-3i8rPuqd.js} +4 -4
- package/dist/cdn/chunks/{src-BuW9oYtm.js.map → src-3i8rPuqd.js.map} +1 -1
- package/dist/cdn/chunks/{styleConstants-1KwsBMxJ.js → styleConstants-DFe3I4Op.js} +6 -6
- package/dist/cdn/chunks/{styleConstants-1KwsBMxJ.js.map → styleConstants-DFe3I4Op.js.map} +1 -1
- package/dist/cdn/chunks/{styles-DQFExz-T.js → styles-Dgijy53u.js} +1224 -1096
- package/dist/cdn/chunks/styles-Dgijy53u.js.map +1 -0
- package/dist/cdn/chunks/{tiptap-DplY-S-k.js → tiptap-BhxaWR8R.js} +2 -2
- package/dist/cdn/chunks/{tiptap-DplY-S-k.js.map → tiptap-BhxaWR8R.js.map} +1 -1
- package/dist/cdn/editor.css +1 -1
- package/dist/cdn/editor.js +110 -139
- package/dist/cdn/editor.js.map +1 -1
- package/dist/{dist-BkIys9zn.js → dist-Ci5lFuUy.js} +1 -1
- package/dist/{extensions-DEjfEFhD.js → extensions-DWx_jj8v.js} +1 -1
- package/dist/{styleConstants-D4SOZGBV.js → styleConstants-Cxw88naD.js} +5 -5
- package/dist/{styles-CgLaxDfu.js → styles-fdXNRqI3.js} +1341 -1213
- package/dist/templatical-editor.css +1 -1
- package/dist/templatical-editor.js +99 -129
- package/dist/templatical-editor.umd.cjs +55 -64
- package/dist/{useEditorCore-CjwRMl7K.js → useEditorCore-DUGD6pq_.js} +1054 -1033
- package/package.json +4 -2
- package/dist/CloudEditor-DFyuRxUV.js +0 -926
- package/dist/ParagraphEditor-CcMPnbDr.js +0 -652
- package/dist/TemplateScoringPanel-D58A23Vq.js +0 -249
- package/dist/cdn/chunks/AiChatSidebar-CmPTbTFG.js +0 -2
- package/dist/cdn/chunks/AiFeatureMenu-lxVm1RjH.js.map +0 -1
- package/dist/cdn/chunks/CloudEditor-Bmp5IlWi.js +0 -900
- package/dist/cdn/chunks/CloudEditor-Bmp5IlWi.js.map +0 -1
- package/dist/cdn/chunks/CommentsSidebar-BOelj4Ca.js +0 -2
- package/dist/cdn/chunks/DesignReferenceSidebar-Bf6rg0A7.js +0 -2
- package/dist/cdn/chunks/ModuleBrowserModal-CxDXzkKS.js.map +0 -1
- package/dist/cdn/chunks/ParagraphEditor-DHdu6lb3.js +0 -503
- package/dist/cdn/chunks/ParagraphEditor-DHdu6lb3.js.map +0 -1
- package/dist/cdn/chunks/SaveModuleDialog-DVna2xUl.js.map +0 -1
- package/dist/cdn/chunks/SnapshotHistory-BFF2SsTN.js +0 -2
- package/dist/cdn/chunks/TemplateScoringPanel-gi8wc_m7.js +0 -2
- package/dist/cdn/chunks/TestEmailModal-Qtd6aC-6.js +0 -2
- package/dist/cdn/chunks/dist-B6AUkMyh.js +0 -2
- package/dist/cdn/chunks/dist-Bf1Op9A1.js +0 -2
- package/dist/cdn/chunks/dist-CWsl6S1K.js +0 -2
- package/dist/cdn/chunks/dist-Cs0wFwdw.js +0 -2
- package/dist/cdn/chunks/dist-DS3_HVpX.js +0 -2
- package/dist/cdn/chunks/dist-DTXopj1a.js +0 -2
- package/dist/cdn/chunks/dist-DnwLoNLm.js +0 -2
- package/dist/cdn/chunks/features-ofOGnSC0.js.map +0 -1
- package/dist/cdn/chunks/styles-DQFExz-T.js.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"dist-B878xb_62.js","names":["isSection2"],"sources":["../../../../renderer/dist/index.js"],"sourcesContent":["// src/index.ts\nimport { isSection as isSection2 } from \"@templatical/types\";\n\n// src/render-context.ts\nvar BUILT_IN_FONT_FALLBACKS = {\n arial: \"Arial, sans-serif\",\n helvetica: \"Helvetica, sans-serif\",\n georgia: \"Georgia, serif\",\n \"times new roman\": \"'Times New Roman', serif\",\n verdana: \"Verdana, sans-serif\",\n \"trebuchet ms\": \"'Trebuchet MS', sans-serif\",\n \"courier new\": \"'Courier New', monospace\",\n tahoma: \"Tahoma, sans-serif\"\n};\nvar RenderContext = class _RenderContext {\n constructor(containerWidth, customFonts, defaultFallbackFont, allowHtmlBlocks) {\n this.containerWidth = containerWidth;\n this.customFonts = customFonts;\n this.defaultFallbackFont = defaultFallbackFont;\n this.allowHtmlBlocks = allowHtmlBlocks;\n }\n /**\n * Create a new context with a different container width.\n * Used when rendering columns with narrower widths.\n */\n withContainerWidth(width) {\n return new _RenderContext(\n width,\n this.customFonts,\n this.defaultFallbackFont,\n this.allowHtmlBlocks\n );\n }\n /**\n * Resolve a font family name to include custom font fallbacks.\n * If the font matches a custom font, returns `'FontName', fallback`.\n * Otherwise returns the original font family string.\n */\n resolveFontFamily(fontFamily) {\n for (const customFont of this.customFonts) {\n if (customFont.name.toLowerCase() === fontFamily.toLowerCase()) {\n const fallback = customFont.fallback ?? this.defaultFallbackFont;\n return `'${customFont.name}', ${fallback}`;\n }\n }\n const builtIn = BUILT_IN_FONT_FALLBACKS[fontFamily.toLowerCase()];\n if (builtIn) {\n return builtIn;\n }\n return fontFamily;\n }\n};\n\n// src/renderers/index.ts\nimport {\n isSection,\n isTitle,\n isParagraph,\n isImage,\n isButton,\n isDivider,\n isSpacer,\n isHtml,\n isSocialIcons,\n isMenu,\n isTable,\n isVideo,\n isCustomBlock\n} from \"@templatical/types\";\n\n// src/renderers/title.ts\nimport { HEADING_LEVEL_FONT_SIZE } from \"@templatical/types\";\n\n// src/escape.ts\nvar HTML_ENTITIES = {\n \"&\": \"&\",\n \"<\": \"<\",\n \">\": \">\",\n '\"': \""\",\n \"'\": \"'\"\n};\nvar HTML_ENTITY_REGEX = /[&<>\"']/g;\nfunction escapeHtml(text) {\n if (text === \"\") {\n return \"\";\n }\n return text.replace(HTML_ENTITY_REGEX, (char) => HTML_ENTITIES[char] ?? char);\n}\nfunction escapeAttr(text) {\n if (text === \"\") {\n return \"\";\n }\n return text.replace(HTML_ENTITY_REGEX, (char) => HTML_ENTITIES[char] ?? char);\n}\nfunction convertMergeTagsToValues(html) {\n if (html === \"\") {\n return \"\";\n }\n let result = html.replace(\n /<span[^>]*\\bdata-merge-tag=\"([^\"]*)\"[^>]*>.*?<\\/span>/gs,\n \"$1\"\n );\n result = result.replace(\n /<span[^>]*\\bdata-logic-merge-tag=\"([^\"]*)\"[^>]*>.*?<\\/span>/gs,\n \"$1\"\n );\n return result;\n}\n\n// src/padding.ts\nfunction toPaddingString(padding) {\n return `${padding.top}px ${padding.right}px ${padding.bottom}px ${padding.left}px`;\n}\n\n// src/visibility.ts\nfunction isHiddenOnAll(block) {\n const visibility = block.visibility;\n if (!visibility) {\n return false;\n }\n return !visibility.desktop && !visibility.tablet && !visibility.mobile;\n}\nfunction getCssClassAttr(block) {\n const classes = getCssClasses(block);\n if (classes === \"\") {\n return \"\";\n }\n return ` css-class=\"${classes}\"`;\n}\nfunction getCssClasses(block) {\n const visibility = block.visibility;\n if (!visibility) {\n return \"\";\n }\n const classes = [];\n if (!visibility.desktop) {\n classes.push(\"tpl-hide-desktop\");\n }\n if (!visibility.tablet) {\n classes.push(\"tpl-hide-tablet\");\n }\n if (!visibility.mobile) {\n classes.push(\"tpl-hide-mobile\");\n }\n return classes.join(\" \");\n}\n\n// src/renderers/title.ts\nfunction renderTitle(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const content = convertMergeTagsToValues(block.content);\n const fontSize = HEADING_LEVEL_FONT_SIZE[block.level];\n const color = block.color;\n const align = block.textAlign;\n const fontFamilyAttr = renderFontFamilyAttr(block.fontFamily, context);\n const visibilityAttr = getCssClassAttr(block);\n const tag = `h${block.level}`;\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.3\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n><${tag} style=\"margin:0;font-size:inherit;color:inherit;line-height:inherit\">${content}</${tag}></mj-text>`;\n}\nfunction renderFontFamilyAttr(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/paragraph.ts\nfunction renderParagraph(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const content = convertMergeTagsToValues(block.content);\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n>${content}</mj-text>`;\n}\n\n// src/renderers/image.ts\nfunction renderImage(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? context.containerWidth + \"px\" : block.width + \"px\";\n const visibilityAttr = getCssClassAttr(block);\n let linkAttr = \"\";\n if (block.linkUrl) {\n linkAttr = ` href=\"${escapeAttr(block.linkUrl)}\"`;\n if (block.linkOpenInNewTab) {\n linkAttr += ' target=\"_blank\"';\n }\n }\n const src = escapeAttr(block.src);\n const alt = escapeAttr(block.alt);\n const align = block.align;\n return `<mj-image\n src=\"${src}\"\n alt=\"${alt}\"\n width=\"${width}\"\n align=\"${align}\"\n padding=\"${padding}\"${bgColor}${linkAttr}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/button.ts\nfunction renderButton(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const buttonPadding = toPaddingString(block.buttonPadding);\n const href = escapeAttr(block.url);\n const backgroundColor = block.backgroundColor;\n const textColor = block.textColor;\n const fontSize = block.fontSize;\n const borderRadius = block.borderRadius;\n const text = escapeHtml(block.text);\n const targetAttr = block.openInNewTab ? ' target=\"_blank\"' : \"\";\n const fontFamilyAttr = renderFontFamilyAttr2(block.fontFamily, context);\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-button\n href=\"${href}\"${targetAttr}\n background-color=\"${backgroundColor}\"\n color=\"${textColor}\"\n font-size=\"${fontSize}px\"\n font-weight=\"bold\"\n border-radius=\"${borderRadius}px\"\n inner-padding=\"${buttonPadding}\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${text}</mj-button>`;\n}\nfunction renderFontFamilyAttr2(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/divider.ts\nfunction renderDivider(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? \"100%\" : block.width + \"px\";\n const thickness = block.thickness;\n const lineStyle = block.lineStyle;\n const color = block.color;\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-divider\n border-width=\"${thickness}px\"\n border-style=\"${lineStyle}\"\n border-color=\"${color}\"\n width=\"${width}\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/spacer.ts\nfunction renderSpacer(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const height = block.height;\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-spacer height=\"${height}px\" padding=\"${padding}\"${bgColor}${visibilityAttr} />`;\n}\n\n// src/renderers/html.ts\nfunction renderHtml(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (!context.allowHtmlBlocks) {\n return \"\";\n }\n const content = block.content;\n if (content === \"\") {\n return \"\";\n }\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text${visibilityAttr}>\n${content}\n</mj-text>`;\n}\n\n// src/social-icons.ts\nvar SOCIAL_ICONS = {\n facebook: {\n path: \"M24 12.073c0-6.627-5.373-12-12-12s-12 5.373-12 12c0 5.99 4.388 10.954 10.125 11.854v-8.385H7.078v-3.47h3.047V9.43c0-3.007 1.792-4.669 4.533-4.669 1.312 0 2.686.235 2.686.235v2.953H15.83c-1.491 0-1.956.925-1.956 1.874v2.25h3.328l-.532 3.47h-2.796v8.385C19.612 23.027 24 18.062 24 12.073z\",\n color: \"#1877F2\"\n },\n twitter: {\n path: \"M18.244 2.25h3.308l-7.227 8.26 8.502 11.24H16.17l-5.214-6.817L4.99 21.75H1.68l7.73-8.835L1.254 2.25H8.08l4.713 6.231zm-1.161 17.52h1.833L7.084 4.126H5.117z\",\n color: \"#000000\"\n },\n instagram: {\n path: \"M12 0C8.74 0 8.333.015 7.053.072 5.775.132 4.905.333 4.14.63c-.789.306-1.459.717-2.126 1.384S.935 3.35.63 4.14C.333 4.905.131 5.775.072 7.053.012 8.333 0 8.74 0 12s.015 3.667.072 4.947c.06 1.277.261 2.148.558 2.913.306.788.717 1.459 1.384 2.126.667.666 1.336 1.079 2.126 1.384.766.296 1.636.499 2.913.558C8.333 23.988 8.74 24 12 24s3.667-.015 4.947-.072c1.277-.06 2.148-.262 2.913-.558.788-.306 1.459-.718 2.126-1.384.666-.667 1.079-1.335 1.384-2.126.296-.765.499-1.636.558-2.913.06-1.28.072-1.687.072-4.947s-.015-3.667-.072-4.947c-.06-1.277-.262-2.149-.558-2.913-.306-.789-.718-1.459-1.384-2.126C21.319 1.347 20.651.935 19.86.63c-.765-.297-1.636-.499-2.913-.558C15.667.012 15.26 0 12 0zm0 2.16c3.203 0 3.585.016 4.85.071 1.17.055 1.805.249 2.227.415.562.217.96.477 1.382.896.419.42.679.819.896 1.381.164.422.36 1.057.413 2.227.057 1.266.07 1.646.07 4.85s-.015 3.585-.074 4.85c-.061 1.17-.256 1.805-.421 2.227-.224.562-.479.96-.899 1.382-.419.419-.824.679-1.38.896-.42.164-1.065.36-2.235.413-1.274.057-1.649.07-4.859.07-3.211 0-3.586-.015-4.859-.074-1.171-.061-1.816-.256-2.236-.421-.569-.224-.96-.479-1.379-.899-.421-.419-.69-.824-.9-1.38-.165-.42-.359-1.065-.42-2.235-.045-1.26-.061-1.649-.061-4.844 0-3.196.016-3.586.061-4.861.061-1.17.255-1.814.42-2.234.21-.57.479-.96.9-1.381.419-.419.81-.689 1.379-.898.42-.166 1.051-.361 2.221-.421 1.275-.045 1.65-.06 4.859-.06l.045.03zm0 3.678c-3.405 0-6.162 2.76-6.162 6.162 0 3.405 2.76 6.162 6.162 6.162 3.405 0 6.162-2.76 6.162-6.162 0-3.405-2.76-6.162-6.162-6.162zM12 16c-2.21 0-4-1.79-4-4s1.79-4 4-4 4 1.79 4 4-1.79 4-4 4zm7.846-10.405c0 .795-.646 1.44-1.44 1.44-.795 0-1.44-.646-1.44-1.44 0-.794.646-1.439 1.44-1.439.793-.001 1.44.645 1.44 1.439z\",\n color: \"#E4405F\"\n },\n linkedin: {\n path: \"M20.447 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.351V9h3.414v1.561h.046c.477-.9 1.637-1.85 3.37-1.85 3.601 0 4.267 2.37 4.267 5.455v6.286zM5.337 7.433c-1.144 0-2.063-.926-2.063-2.065 0-1.138.92-2.063 2.063-2.063 1.14 0 2.064.925 2.064 2.063 0 1.139-.925 2.065-2.064 2.065zm1.782 13.019H3.555V9h3.564v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z\",\n color: \"#0A66C2\"\n },\n youtube: {\n path: \"M23.498 6.186a3.016 3.016 0 0 0-2.122-2.136C19.505 3.545 12 3.545 12 3.545s-7.505 0-9.377.505A3.017 3.017 0 0 0 .502 6.186C0 8.07 0 12 0 12s0 3.93.502 5.814a3.016 3.016 0 0 0 2.122 2.136c1.871.505 9.376.505 9.376.505s7.505 0 9.377-.505a3.015 3.015 0 0 0 2.122-2.136C24 15.93 24 12 24 12s0-3.93-.502-5.814zM9.545 15.568V8.432L15.818 12l-6.273 3.568z\",\n color: \"#FF0000\"\n },\n tiktok: {\n path: \"M12.525.02c1.31-.02 2.61-.01 3.91-.02.08 1.53.63 3.09 1.75 4.17 1.12 1.11 2.7 1.62 4.24 1.79v4.03c-1.44-.05-2.89-.35-4.2-.97-.57-.26-1.1-.59-1.62-.93-.01 2.92.01 5.84-.02 8.75-.08 1.4-.54 2.79-1.35 3.94-1.31 1.92-3.58 3.17-5.91 3.21-1.43.08-2.86-.31-4.08-1.03-2.02-1.19-3.44-3.37-3.65-5.71-.02-.5-.03-1-.01-1.49.18-1.9 1.12-3.72 2.58-4.96 1.66-1.44 3.98-2.13 6.15-1.72.02 1.48-.04 2.96-.04 4.44-.99-.32-2.15-.23-3.02.37-.63.41-1.11 1.04-1.36 1.75-.21.51-.15 1.07-.14 1.61.24 1.64 1.82 3.02 3.5 2.87 1.12-.01 2.19-.66 2.77-1.61.19-.33.4-.67.41-1.06.1-1.79.06-3.57.07-5.36.01-4.03-.01-8.05.02-12.07z\",\n color: \"#000000\"\n },\n pinterest: {\n path: \"M12 0C5.373 0 0 5.372 0 12c0 5.084 3.163 9.426 7.627 11.174-.105-.949-.2-2.405.042-3.441.218-.937 1.407-5.965 1.407-5.965s-.359-.719-.359-1.782c0-1.668.967-2.914 2.171-2.914 1.023 0 1.518.769 1.518 1.69 0 1.029-.655 2.568-.994 3.995-.283 1.194.599 2.169 1.777 2.169 2.133 0 3.772-2.249 3.772-5.495 0-2.873-2.064-4.882-5.012-4.882-3.414 0-5.418 2.561-5.418 5.207 0 1.031.397 2.138.893 2.738.098.119.112.224.083.345l-.333 1.36c-.053.22-.174.267-.402.161-1.499-.698-2.436-2.889-2.436-4.649 0-3.785 2.75-7.262 7.929-7.262 4.163 0 7.398 2.967 7.398 6.931 0 4.136-2.607 7.464-6.227 7.464-1.216 0-2.359-.631-2.75-1.378l-.748 2.853c-.271 1.043-1.002 2.35-1.492 3.146C9.57 23.812 10.763 24 12 24c6.627 0 12-5.373 12-12 0-6.628-5.373-12-12-12z\",\n color: \"#BD081C\"\n },\n email: {\n path: \"M1.5 8.67v8.58a3 3 0 003 3h15a3 3 0 003-3V8.67l-8.928 5.493a3 3 0 01-3.144 0L1.5 8.67z M22.5 6.908V6.75a3 3 0 00-3-3h-15a3 3 0 00-3 3v.158l9.714 5.978a1.5 1.5 0 001.572 0L22.5 6.908z\",\n color: \"#6B7280\"\n },\n whatsapp: {\n path: \"M17.472 14.382c-.297-.149-1.758-.867-2.03-.967-.273-.099-.471-.148-.67.15-.197.297-.767.966-.94 1.164-.173.199-.347.223-.644.075-.297-.15-1.255-.463-2.39-1.475-.883-.788-1.48-1.761-1.653-2.059-.173-.297-.018-.458.13-.606.134-.133.298-.347.446-.52.149-.174.198-.298.298-.497.099-.198.05-.371-.025-.52-.075-.149-.669-1.612-.916-2.207-.242-.579-.487-.5-.669-.51-.173-.008-.371-.01-.57-.01-.198 0-.52.074-.792.372-.272.297-1.04 1.016-1.04 2.479 0 1.462 1.065 2.875 1.213 3.074.149.198 2.096 3.2 5.077 4.487.709.306 1.262.489 1.694.625.712.227 1.36.195 1.871.118.571-.085 1.758-.719 2.006-1.413.248-.694.248-1.289.173-1.413-.074-.124-.272-.198-.57-.347m-5.421 7.403h-.004a9.87 9.87 0 01-5.031-1.378l-.361-.214-3.741.982.998-3.648-.235-.374a9.86 9.86 0 01-1.51-5.26c.001-5.45 4.436-9.884 9.888-9.884 2.64 0 5.122 1.03 6.988 2.898a9.825 9.825 0 012.893 6.994c-.003 5.45-4.437 9.884-9.885 9.884m8.413-18.297A11.815 11.815 0 0012.05 0C5.495 0 .16 5.335.157 11.892c0 2.096.547 4.142 1.588 5.945L.057 24l6.305-1.654a11.882 11.882 0 005.683 1.448h.005c6.554 0 11.89-5.335 11.893-11.893a11.821 11.821 0 00-3.48-8.413z\",\n color: \"#25D366\"\n },\n telegram: {\n path: \"M11.944 0A12 12 0 0 0 0 12a12 12 0 0 0 12 12 12 12 0 0 0 12-12A12 12 0 0 0 12 0a12 12 0 0 0-.056 0zm4.962 7.224c.1-.002.321.023.465.14a.506.506 0 0 1 .171.325c.016.093.036.306.02.472-.18 1.898-.962 6.502-1.36 8.627-.168.9-.499 1.201-.82 1.23-.696.065-1.225-.46-1.9-.902-1.056-.693-1.653-1.124-2.678-1.8-1.185-.78-.417-1.21.258-1.91.177-.184 3.247-2.977 3.307-3.23.007-.032.014-.15-.056-.212s-.174-.041-.249-.024c-.106.024-1.793 1.14-5.061 3.345-.48.33-.913.49-1.302.48-.428-.008-1.252-.241-1.865-.44-.752-.245-1.349-.374-1.297-.789.027-.216.325-.437.893-.663 3.498-1.524 5.83-2.529 6.998-3.014 3.332-1.386 4.025-1.627 4.476-1.635z\",\n color: \"#26A5E4\"\n },\n discord: {\n path: \"M20.317 4.3698a19.7913 19.7913 0 00-4.8851-1.5152.0741.0741 0 00-.0785.0371c-.211.3753-.4447.8648-.6083 1.2495-1.8447-.2762-3.68-.2762-5.4868 0-.1636-.3933-.4058-.8742-.6177-1.2495a.077.077 0 00-.0785-.037 19.7363 19.7363 0 00-4.8852 1.515.0699.0699 0 00-.0321.0277C.5334 9.0458-.319 13.5799.0992 18.0578a.0824.0824 0 00.0312.0561c2.0528 1.5076 4.0413 2.4228 5.9929 3.0294a.0777.0777 0 00.0842-.0276c.4616-.6304.8731-1.2952 1.226-1.9942a.076.076 0 00-.0416-.1057c-.6528-.2476-1.2743-.5495-1.8722-.8923a.077.077 0 01-.0076-.1277c.1258-.0943.2517-.1923.3718-.2914a.0743.0743 0 01.0776-.0105c3.9278 1.7933 8.18 1.7933 12.0614 0a.0739.0739 0 01.0785.0095c.1202.099.246.1981.3728.2924a.077.077 0 01-.0066.1276 12.2986 12.2986 0 01-1.873.8914.0766.0766 0 00-.0407.1067c.3604.698.7719 1.3628 1.225 1.9932a.076.076 0 00.0842.0286c1.961-.6067 3.9495-1.5219 6.0023-3.0294a.077.077 0 00.0313-.0552c.5004-5.177-.8382-9.6739-3.5485-13.6604a.061.061 0 00-.0312-.0286zM8.02 15.3312c-1.1825 0-2.1569-1.0857-2.1569-2.419 0-1.3332.9555-2.4189 2.157-2.4189 1.2108 0 2.1757 1.0952 2.1568 2.419 0 1.3332-.9555 2.4189-2.1569 2.4189zm7.9748 0c-1.1825 0-2.1569-1.0857-2.1569-2.419 0-1.3332.9554-2.4189 2.1569-2.4189 1.2108 0 2.1757 1.0952 2.1568 2.419 0 1.3332-.946 2.4189-2.1568 2.4189z\",\n color: \"#5865F2\"\n },\n snapchat: {\n path: \"M12.017 0C5.396 0 .029 5.367.029 11.987c0 5.079 3.158 9.417 7.618 11.162-.105-.949-.199-2.403.041-3.439.219-.937 1.406-5.957 1.406-5.957s-.359-.72-.359-1.781c0-1.668.967-2.914 2.171-2.914 1.023 0 1.518.769 1.518 1.69 0 1.029-.655 2.568-.994 3.995-.283 1.194.599 2.169 1.777 2.169 2.133 0 3.772-2.249 3.772-5.495 0-2.873-2.064-4.882-5.012-4.882-3.414 0-5.418 2.561-5.418 5.207 0 1.031.397 2.138.893 2.738a.36.36 0 01.083.345l-.333 1.36c-.053.22-.174.267-.402.161-1.499-.698-2.436-2.889-2.436-4.649 0-3.785 2.75-7.262 7.929-7.262 4.163 0 7.398 2.967 7.398 6.931 0 4.136-2.607 7.464-6.227 7.464-1.216 0-2.359-.631-2.75-1.378l-.748 2.853c-.271 1.043-1.002 2.35-1.492 3.146 1.124.347 2.317.535 3.554.535 6.627 0 12.017-5.373 12.017-12.001C24.034 5.367 18.644 0 12.017 0z\",\n color: \"#FFFC00\"\n },\n reddit: {\n path: \"M12 0A12 12 0 0 0 0 12a12 12 0 0 0 12 12 12 12 0 0 0 12-12A12 12 0 0 0 12 0zm5.01 4.744c.688 0 1.25.561 1.25 1.249a1.25 1.25 0 0 1-2.498.056l-2.597-.547-.8 3.747c1.824.07 3.48.632 4.674 1.488.308-.309.73-.491 1.207-.491.968 0 1.754.786 1.754 1.754 0 .716-.435 1.333-1.01 1.614a3.111 3.111 0 0 1 .042.52c0 2.694-3.13 4.87-7.004 4.87-3.874 0-7.004-2.176-7.004-4.87 0-.183.015-.366.043-.534A1.748 1.748 0 0 1 4.028 12c0-.968.786-1.754 1.754-1.754.463 0 .898.196 1.207.49 1.207-.883 2.878-1.43 4.744-1.487l.885-4.182a.342.342 0 0 1 .14-.197.35.35 0 0 1 .238-.042l2.906.617a1.214 1.214 0 0 1 1.108-.701zM9.25 12C8.561 12 8 12.562 8 13.25c0 .687.561 1.248 1.25 1.248.687 0 1.248-.561 1.248-1.249 0-.688-.561-1.249-1.249-1.249zm5.5 0c-.687 0-1.248.561-1.248 1.25 0 .687.561 1.248 1.249 1.248.688 0 1.249-.561 1.249-1.249 0-.687-.562-1.249-1.25-1.249zm-5.466 3.99a.327.327 0 0 0-.231.094.33.33 0 0 0 0 .463c.842.842 2.484.913 2.961.913.477 0 2.105-.056 2.961-.913a.361.361 0 0 0 .029-.463.33.33 0 0 0-.464 0c-.547.533-1.684.73-2.512.73-.828 0-1.979-.196-2.512-.73a.326.326 0 0 0-.232-.095z\",\n color: \"#FF4500\"\n },\n github: {\n path: \"M12 .297c-6.63 0-12 5.373-12 12 0 5.303 3.438 9.8 8.205 11.385.6.113.82-.258.82-.577 0-.285-.01-1.04-.015-2.04-3.338.724-4.042-1.61-4.042-1.61C4.422 18.07 3.633 17.7 3.633 17.7c-1.087-.744.084-.729.084-.729 1.205.084 1.838 1.236 1.838 1.236 1.07 1.835 2.809 1.305 3.495.998.108-.776.417-1.305.76-1.605-2.665-.3-5.466-1.332-5.466-5.93 0-1.31.465-2.38 1.235-3.22-.135-.303-.54-1.523.105-3.176 0 0 1.005-.322 3.3 1.23.96-.267 1.98-.399 3-.405 1.02.006 2.04.138 3 .405 2.28-1.552 3.285-1.23 3.285-1.23.645 1.653.24 2.873.12 3.176.765.84 1.23 1.91 1.23 3.22 0 4.61-2.805 5.625-5.475 5.92.42.36.81 1.096.81 2.22 0 1.606-.015 2.896-.015 3.286 0 .315.21.69.825.57C20.565 22.092 24 17.592 24 12.297c0-6.627-5.373-12-12-12\",\n color: \"#181717\"\n },\n dribbble: {\n path: \"M12 24C5.385 24 0 18.615 0 12S5.385 0 12 0s12 5.385 12 12-5.385 12-12 12zm10.12-10.358c-.35-.11-3.17-.953-6.384-.438 1.34 3.684 1.887 6.684 1.992 7.308 2.3-1.555 3.936-4.02 4.392-6.87zm-6.115 7.808c-.153-.9-.75-4.032-2.19-7.77l-.066.02c-5.79 2.015-7.86 6.025-8.04 6.4 1.73 1.358 3.92 2.166 6.29 2.166 1.42 0 2.77-.29 4-.814zm-11.62-2.58c.232-.4 3.045-5.055 8.332-6.765.135-.045.27-.084.405-.12-.26-.585-.54-1.167-.832-1.74C7.17 11.775 2.206 11.71 1.756 11.7l-.004.312c0 2.633.998 5.037 2.634 6.855zm-2.42-8.955c.46.008 4.683.026 9.477-1.248-1.698-3.018-3.53-5.558-3.8-5.928-2.868 1.35-5.01 3.99-5.676 7.17zM9.6 2.052c.282.38 2.145 2.914 3.822 6 3.645-1.365 5.19-3.44 5.373-3.702-1.81-1.61-4.19-2.586-6.795-2.586-.825 0-1.63.1-2.4.285zm10.335 3.483c-.218.29-1.935 2.493-5.724 4.04.24.49.47.985.68 1.486.08.18.15.36.22.53 3.41-.43 6.8.26 7.14.33-.02-2.42-.88-4.64-2.31-6.38z\",\n color: \"#EA4C89\"\n },\n behance: {\n path: \"M22 7h-7V5h7v2zm1.726 10c-.442 1.297-2.029 3-5.101 3-3.074 0-5.564-1.729-5.564-5.675 0-3.91 2.325-5.92 5.466-5.92 3.082 0 4.964 1.782 5.375 4.426.078.506.109 1.188.095 2.14H15.97c.13 3.211 3.483 3.312 4.588 2.029h3.168zm-7.686-4h4.965c-.105-1.547-1.136-2.219-2.477-2.219-1.466 0-2.277.768-2.488 2.219zm-9.574 6.988H0V5.021h6.953c5.476.081 5.58 5.444 2.72 6.906 3.461 1.26 3.577 8.061-3.207 8.061zM3 11h3.584c2.508 0 2.906-3-.312-3H3v3zm3.391 3H3v3.016h3.341c3.055 0 2.868-3.016.05-3.016z\",\n color: \"#1769FF\"\n }\n};\nfunction generateSocialIconDataUri(platform, style, size) {\n const iconData = SOCIAL_ICONS[platform];\n const path = iconData?.path ?? \"\";\n const brandColor = iconData?.color ?? \"#6B7280\";\n if (path === \"\") {\n return \"\";\n }\n const isOutlined = style === \"outlined\";\n const iconColor = isOutlined ? brandColor : \"#ffffff\";\n let bgShape;\n switch (style) {\n case \"circle\":\n bgShape = `<circle cx=\"12\" cy=\"12\" r=\"12\" fill=\"${brandColor}\"/>`;\n break;\n case \"rounded\":\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"6\" fill=\"${brandColor}\"/>`;\n break;\n case \"square\":\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"0\" fill=\"${brandColor}\"/>`;\n break;\n case \"outlined\":\n bgShape = `<rect width=\"22\" height=\"22\" x=\"1\" y=\"1\" rx=\"3\" fill=\"transparent\" stroke=\"${brandColor}\" stroke-width=\"2\"/>`;\n break;\n default:\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"3\" fill=\"${brandColor}\"/>`;\n break;\n }\n const svg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" width=\"${size}\" height=\"${size}\">` + bgShape + `<g transform=\"translate(4.8, 4.8) scale(0.6)\"><path d=\"${path}\" fill=\"${iconColor}\"/></g></svg>`;\n return \"data:image/svg+xml;base64,\" + btoa(svg);\n}\n\n// src/renderers/social.ts\nfunction renderSocialIcons(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const icons = block.icons;\n if (icons.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const align = block.align;\n const iconSize = block.iconSize;\n const iconStyle = block.iconStyle;\n const spacing = block.spacing;\n let iconSizePx;\n switch (iconSize) {\n case \"small\":\n iconSizePx = 24;\n break;\n case \"large\":\n iconSizePx = 48;\n break;\n default:\n iconSizePx = 32;\n break;\n }\n let borderRadius;\n switch (iconStyle) {\n case \"circle\":\n borderRadius = \"50%\";\n break;\n case \"rounded\":\n borderRadius = \"8px\";\n break;\n case \"square\":\n borderRadius = \"0\";\n break;\n default:\n borderRadius = \"4px\";\n break;\n }\n const iconCount = icons.length;\n const socialElements = icons.map((icon, index) => {\n const platform = icon.platform;\n const url = escapeAttr(icon.url);\n const iconSrc = generateSocialIconDataUri(platform, iconStyle, iconSizePx);\n const rightPad = index === iconCount - 1 ? 0 : spacing;\n return `<mj-social-element src=\"${iconSrc}\" href=\"${url}\" icon-size=\"${iconSizePx}px\" padding=\"0 ${rightPad}px 0 0\" border-radius=\"${borderRadius}\" background-color=\"transparent\"></mj-social-element>`;\n });\n const socialContent = socialElements.join(\"\\n\");\n return `<mj-social\n mode=\"horizontal\"\n align=\"${align}\"\n icon-padding=\"0\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n>\n${socialContent}\n</mj-social>`;\n}\n\n// src/renderers/menu.ts\nfunction renderMenu(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (block.items.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const fontFamilyAttr = renderFontFamilyAttr3(block.fontFamily, context);\n const align = block.textAlign;\n const fontSize = block.fontSize;\n const color = block.color;\n const content = renderMenuItems(block);\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${content}</mj-text>`;\n}\nfunction renderMenuItems(block) {\n const items = block.items;\n const separator = escapeHtml(block.separator);\n const separatorColor = escapeAttr(block.separatorColor);\n const spacing = block.spacing;\n const linkColor = block.linkColor ?? block.color;\n const parts = [];\n const itemCount = items.length;\n for (let index = 0; index < itemCount; index++) {\n parts.push(renderMenuItem(items[index], linkColor));\n if (index < itemCount - 1) {\n parts.push(\n `<span style=\"color: ${separatorColor}; padding: 0 ${spacing}px;\">${separator}</span>`\n );\n }\n }\n return parts.join(\"\");\n}\nfunction renderMenuItem(item, linkColor) {\n const text = escapeHtml(item.text);\n const url = escapeAttr(item.url);\n const color = item.color ?? linkColor;\n const target = item.openInNewTab ? ' target=\"_blank\"' : \"\";\n const styles = [`color: ${color}`, \"text-decoration: none\"];\n if (item.bold) {\n styles.push(\"font-weight: bold\");\n }\n if (item.underline) {\n styles.push(\"text-decoration: underline\");\n }\n const styleAttr = styles.join(\"; \");\n return `<a href=\"${url}\" style=\"${styleAttr}\"${target}>${text}</a>`;\n}\nfunction renderFontFamilyAttr3(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/table.ts\nfunction renderTable(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (block.rows.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const fontFamilyAttr = renderFontFamilyAttr4(block.fontFamily, context);\n const fontSize = block.fontSize;\n const color = block.color;\n const align = block.textAlign;\n const tableHtml = renderTableElement(block);\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${tableHtml}</mj-text>`;\n}\nfunction renderTableElement(block) {\n const borderColor = escapeAttr(block.borderColor);\n const borderWidth = block.borderWidth;\n const tableStyle = \"width: 100%; border-collapse: collapse;\";\n let rowsHtml = \"\";\n for (let index = 0; index < block.rows.length; index++) {\n const row = block.rows[index];\n const isHeader = block.hasHeaderRow && index === 0;\n rowsHtml += renderRow(row, block, isHeader, borderColor, borderWidth);\n }\n return `<table style=\"${tableStyle}\">${rowsHtml}</table>`;\n}\nfunction renderRow(row, block, isHeader, borderColor, borderWidth) {\n let cellsHtml = \"\";\n for (const cell of row.cells) {\n cellsHtml += renderCell(cell, block, isHeader, borderColor, borderWidth);\n }\n return `<tr>${cellsHtml}</tr>`;\n}\nfunction renderCell(cell, block, isHeader, borderColor, borderWidth) {\n const cellPadding = block.cellPadding;\n const styles = [\n `border: ${borderWidth}px solid ${borderColor}`,\n `padding: ${cellPadding}px`\n ];\n if (isHeader) {\n styles.push(\"font-weight: bold\");\n if (block.headerBackgroundColor) {\n styles.push(\n `background-color: ${escapeAttr(block.headerBackgroundColor)}`\n );\n }\n }\n const styleAttr = styles.join(\"; \");\n const content = convertMergeTagsToValues(cell.content);\n const tag = isHeader ? \"th\" : \"td\";\n return `<${tag} style=\"${styleAttr}\">${content}</${tag}>`;\n}\nfunction renderFontFamilyAttr4(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/custom.ts\nfunction renderCustom(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const content = block.renderedHtml;\n if (!content || content === \"\") {\n return \"\";\n }\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text${visibilityAttr}>\n${content}\n</mj-text>`;\n}\n\n// src/columns.ts\nfunction getWidthPercentages(layout) {\n switch (layout) {\n case \"2\":\n return [\"50%\", \"50%\"];\n case \"3\":\n return [\"33.33%\", \"33.33%\", \"33.33%\"];\n case \"1-2\":\n return [\"33.33%\", \"66.67%\"];\n case \"2-1\":\n return [\"66.67%\", \"33.33%\"];\n default:\n return [\"100%\"];\n }\n}\nfunction getWidthPixels(layout, containerWidth) {\n switch (layout) {\n case \"2\":\n return [containerWidth * 0.5, containerWidth * 0.5];\n case \"3\":\n return [containerWidth / 3, containerWidth / 3, containerWidth / 3];\n case \"1-2\":\n return [containerWidth / 3, containerWidth * 2 / 3];\n case \"2-1\":\n return [containerWidth * 2 / 3, containerWidth / 3];\n default:\n return [containerWidth];\n }\n}\n\n// src/renderers/section.ts\nfunction renderSection(block, context, renderBlock2) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const columnsLayout = block.columns;\n const columnWidths = getWidthPercentages(columnsLayout);\n const columnWidthsPx = getWidthPixels(columnsLayout, context.containerWidth);\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const children = block.children;\n const columnsContent = [];\n for (let index = 0; index < children.length; index++) {\n const column = children[index];\n const width = columnWidths[index] ?? \"100%\";\n const columnWidth = Math.floor(\n columnWidthsPx[index] ?? context.containerWidth\n );\n const filteredColumn = filterHtmlBlocks(column, context.allowHtmlBlocks);\n const columnContext = context.withContainerWidth(columnWidth);\n const columnBlocks = filteredColumn.map((child) => renderBlock2(child, columnContext)).filter((value) => value !== \"\").join(\"\\n\");\n const content = columnBlocks === \"\" ? \"<mj-text> </mj-text>\" : columnBlocks;\n columnsContent.push(`<mj-column width=\"${width}\">\n${content}\n</mj-column>`);\n }\n const columns = columnsContent.join(\"\\n\");\n return `<mj-section${bgColor} padding=\"${padding}\"${visibilityAttr}>\n${columns}\n</mj-section>`;\n}\nfunction filterHtmlBlocks(blocks, allowHtmlBlocks) {\n if (allowHtmlBlocks) {\n return blocks;\n }\n return blocks.filter((block) => block.type !== \"html\");\n}\n\n// src/renderers/video.ts\nfunction getVideoThumbnail(url, customThumbnail) {\n if (customThumbnail) {\n return customThumbnail;\n }\n if (!url) {\n return null;\n }\n const youtubePatterns = [\n /(?:youtube\\.com\\/watch\\?v=|youtu\\.be\\/|youtube\\.com\\/embed\\/)([a-zA-Z0-9_-]{11})/,\n /youtube\\.com\\/shorts\\/([a-zA-Z0-9_-]{11})/\n ];\n for (const pattern of youtubePatterns) {\n const match = url.match(pattern);\n if (match) {\n return `https://img.youtube.com/vi/${match[1]}/maxresdefault.jpg`;\n }\n }\n const vimeoMatch = url.match(/vimeo\\.com\\/(?:video\\/)?(\\d+)/);\n if (vimeoMatch) {\n return `https://vumbnail.com/${vimeoMatch[1]}.jpg`;\n }\n return null;\n}\nfunction renderVideo(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const thumbnailUrl = getVideoThumbnail(block.url, block.thumbnailUrl);\n if (!thumbnailUrl) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? context.containerWidth + \"px\" : block.width + \"px\";\n const visibilityAttr = getCssClassAttr(block);\n const src = escapeAttr(thumbnailUrl);\n const alt = escapeAttr(block.alt);\n const align = block.align;\n const href = escapeAttr(block.url);\n return `<mj-image\n src=\"${src}\"\n alt=\"${alt}\"\n width=\"${width}\"\n align=\"${align}\"\n padding=\"${padding}\"\n href=\"${href}\"\n target=\"_blank\"${bgColor}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/index.ts\nfunction renderBlock(block, context) {\n if (isSection(block)) {\n return renderSection(block, context, renderBlock);\n }\n if (isTitle(block)) {\n return renderTitle(block, context);\n }\n if (isParagraph(block)) {\n return renderParagraph(block, context);\n }\n if (isImage(block)) {\n return renderImage(block, context);\n }\n if (isButton(block)) {\n return renderButton(block, context);\n }\n if (isDivider(block)) {\n return renderDivider(block, context);\n }\n if (isSpacer(block)) {\n return renderSpacer(block, context);\n }\n if (isHtml(block)) {\n return renderHtml(block, context);\n }\n if (isSocialIcons(block)) {\n return renderSocialIcons(block, context);\n }\n if (isMenu(block)) {\n return renderMenu(block, context);\n }\n if (isTable(block)) {\n return renderTable(block, context);\n }\n if (isVideo(block)) {\n return renderVideo(block, context);\n }\n if (isCustomBlock(block)) {\n return renderCustom(block, context);\n }\n return \"\";\n}\n\n// src/index.ts\nfunction renderToMjml(content, options) {\n const customFonts = options?.customFonts ?? [];\n const defaultFallbackFont = options?.defaultFallbackFont ?? \"Arial, sans-serif\";\n const allowHtmlBlocks = options?.allowHtmlBlocks ?? true;\n const renderContext = new RenderContext(\n content.settings.width,\n customFonts,\n defaultFallbackFont,\n allowHtmlBlocks\n );\n const blocks = filterHtmlBlocks2(content.blocks, allowHtmlBlocks);\n const fontFamily = renderContext.resolveFontFamily(\n content.settings.fontFamily\n );\n const backgroundColor = content.settings.backgroundColor;\n const bodyContent = blocks.map((block) => renderTopLevelBlock(block, renderContext)).filter((value) => value !== \"\").join(\"\\n\");\n const fontDeclarations = generateFontDeclarations(customFonts);\n const previewTag = generatePreviewTag(content.settings.preheaderText);\n return `<mjml>\n <mj-head>${previewTag}\n <mj-attributes>\n <mj-all font-family=\"${fontFamily}\" />\n <mj-section padding=\"0\" />\n <mj-column padding=\"0\" />\n <mj-image fluid-on-mobile=\"true\" />\n </mj-attributes>${fontDeclarations}\n <mj-style>\n a { color: inherit; text-decoration: none; }\n @media only screen and (max-width: 480px) {\n .tpl-hide-mobile { display: none !important; mso-hide: all !important; }\n }\n @media only screen and (min-width: 481px) and (max-width: 768px) {\n .tpl-hide-tablet { display: none !important; mso-hide: all !important; }\n }\n @media only screen and (min-width: 769px) {\n .tpl-hide-desktop { display: none !important; mso-hide: all !important; }\n }\n </mj-style>\n </mj-head>\n <mj-body width=\"${renderContext.containerWidth}px\" background-color=\"${backgroundColor}\">\n${bodyContent}\n </mj-body>\n</mjml>`;\n}\nfunction renderTopLevelBlock(block, context) {\n if (isSection2(block)) {\n const rendered = renderBlock(block, context);\n return wrapWithDisplayCondition(block, rendered);\n }\n const content = renderBlock(block, context);\n const wrapped = wrapInSection(content);\n return wrapWithDisplayCondition(block, wrapped);\n}\nfunction wrapWithDisplayCondition(block, rendered) {\n if (rendered === \"\") {\n return \"\";\n }\n const displayCondition = block.displayCondition;\n if (!displayCondition) {\n return rendered;\n }\n return `<mj-raw>${displayCondition.before}</mj-raw>\n` + rendered + `\n<mj-raw>${displayCondition.after}</mj-raw>`;\n}\nfunction wrapInSection(content) {\n if (content === \"\") {\n return \"\";\n }\n return `<mj-section>\n <mj-column>\n${content}\n </mj-column>\n</mj-section>`;\n}\nfunction generatePreviewTag(preheaderText) {\n if (!preheaderText) {\n return \"\";\n }\n const trimmed = preheaderText.trim();\n if (trimmed === \"\") {\n return \"\";\n }\n const escaped = escapeHtml(trimmed);\n return `\n <mj-preview>${escaped}</mj-preview>`;\n}\nfunction generateFontDeclarations(customFonts) {\n if (customFonts.length === 0) {\n return \"\";\n }\n return customFonts.map(\n (font) => `\n <mj-font name=\"${escapeAttr(font.name)}\" href=\"${escapeAttr(font.url)}\" />`\n ).join(\"\");\n}\nfunction filterHtmlBlocks2(blocks, allowHtmlBlocks) {\n if (allowHtmlBlocks) {\n return blocks;\n }\n return blocks.filter((block) => block.type !== \"html\");\n}\nexport {\n RenderContext,\n SOCIAL_ICONS,\n convertMergeTagsToValues,\n escapeAttr,\n escapeHtml,\n generateSocialIconDataUri,\n getCssClassAttr,\n getCssClasses,\n getWidthPercentages,\n getWidthPixels,\n isHiddenOnAll,\n renderBlock,\n renderToMjml,\n toPaddingString\n};\n//# sourceMappingURL=index.js.map"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"dist-KYv9v_1z2.js","names":["isSection2"],"sources":["../../../../renderer/dist/index.js"],"sourcesContent":["// src/index.ts\nimport { isSection as isSection2 } from \"@templatical/types\";\n\n// src/render-context.ts\nvar BUILT_IN_FONT_FALLBACKS = {\n arial: \"Arial, sans-serif\",\n helvetica: \"Helvetica, sans-serif\",\n georgia: \"Georgia, serif\",\n \"times new roman\": \"'Times New Roman', serif\",\n verdana: \"Verdana, sans-serif\",\n \"trebuchet ms\": \"'Trebuchet MS', sans-serif\",\n \"courier new\": \"'Courier New', monospace\",\n tahoma: \"Tahoma, sans-serif\"\n};\nvar RenderContext = class _RenderContext {\n constructor(containerWidth, customFonts, defaultFallbackFont, allowHtmlBlocks) {\n this.containerWidth = containerWidth;\n this.customFonts = customFonts;\n this.defaultFallbackFont = defaultFallbackFont;\n this.allowHtmlBlocks = allowHtmlBlocks;\n }\n /**\n * Create a new context with a different container width.\n * Used when rendering columns with narrower widths.\n */\n withContainerWidth(width) {\n return new _RenderContext(\n width,\n this.customFonts,\n this.defaultFallbackFont,\n this.allowHtmlBlocks\n );\n }\n /**\n * Resolve a font family name to include custom font fallbacks.\n * If the font matches a custom font, returns `'FontName', fallback`.\n * Otherwise returns the original font family string.\n */\n resolveFontFamily(fontFamily) {\n for (const customFont of this.customFonts) {\n if (customFont.name.toLowerCase() === fontFamily.toLowerCase()) {\n const fallback = customFont.fallback ?? this.defaultFallbackFont;\n return `'${customFont.name}', ${fallback}`;\n }\n }\n const builtIn = BUILT_IN_FONT_FALLBACKS[fontFamily.toLowerCase()];\n if (builtIn) {\n return builtIn;\n }\n return fontFamily;\n }\n};\n\n// src/renderers/index.ts\nimport {\n isSection,\n isTitle,\n isParagraph,\n isImage,\n isButton,\n isDivider,\n isSpacer,\n isHtml,\n isSocialIcons,\n isMenu,\n isTable,\n isVideo,\n isCustomBlock\n} from \"@templatical/types\";\n\n// src/renderers/title.ts\nimport { HEADING_LEVEL_FONT_SIZE } from \"@templatical/types\";\n\n// src/escape.ts\nvar HTML_ENTITIES = {\n \"&\": \"&\",\n \"<\": \"<\",\n \">\": \">\",\n '\"': \""\",\n \"'\": \"'\"\n};\nvar HTML_ENTITY_REGEX = /[&<>\"']/g;\nfunction escapeHtml(text) {\n if (text === \"\") {\n return \"\";\n }\n return text.replace(HTML_ENTITY_REGEX, (char) => HTML_ENTITIES[char] ?? char);\n}\nfunction escapeAttr(text) {\n if (text === \"\") {\n return \"\";\n }\n return text.replace(HTML_ENTITY_REGEX, (char) => HTML_ENTITIES[char] ?? char);\n}\nfunction convertMergeTagsToValues(html) {\n if (html === \"\") {\n return \"\";\n }\n let result = html.replace(\n /<span[^>]*\\bdata-merge-tag=\"([^\"]*)\"[^>]*>.*?<\\/span>/gs,\n \"$1\"\n );\n result = result.replace(\n /<span[^>]*\\bdata-logic-merge-tag=\"([^\"]*)\"[^>]*>.*?<\\/span>/gs,\n \"$1\"\n );\n return result;\n}\n\n// src/padding.ts\nfunction toPaddingString(padding) {\n return `${padding.top}px ${padding.right}px ${padding.bottom}px ${padding.left}px`;\n}\n\n// src/visibility.ts\nfunction isHiddenOnAll(block) {\n const visibility = block.visibility;\n if (!visibility) {\n return false;\n }\n return !visibility.desktop && !visibility.tablet && !visibility.mobile;\n}\nfunction getCssClassAttr(block) {\n const classes = getCssClasses(block);\n if (classes === \"\") {\n return \"\";\n }\n return ` css-class=\"${classes}\"`;\n}\nfunction getCssClasses(block) {\n const visibility = block.visibility;\n if (!visibility) {\n return \"\";\n }\n const classes = [];\n if (!visibility.desktop) {\n classes.push(\"tpl-hide-desktop\");\n }\n if (!visibility.tablet) {\n classes.push(\"tpl-hide-tablet\");\n }\n if (!visibility.mobile) {\n classes.push(\"tpl-hide-mobile\");\n }\n return classes.join(\" \");\n}\n\n// src/renderers/title.ts\nfunction renderTitle(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const content = convertMergeTagsToValues(block.content);\n const fontSize = HEADING_LEVEL_FONT_SIZE[block.level];\n const color = block.color;\n const align = block.textAlign;\n const fontFamilyAttr = renderFontFamilyAttr(block.fontFamily, context);\n const visibilityAttr = getCssClassAttr(block);\n const tag = `h${block.level}`;\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.3\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n><${tag} style=\"margin:0;font-size:inherit;color:inherit;line-height:inherit\">${content}</${tag}></mj-text>`;\n}\nfunction renderFontFamilyAttr(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/paragraph.ts\nfunction renderParagraph(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const content = convertMergeTagsToValues(block.content);\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n>${content}</mj-text>`;\n}\n\n// src/renderers/image.ts\nfunction renderImage(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? context.containerWidth + \"px\" : block.width + \"px\";\n const visibilityAttr = getCssClassAttr(block);\n let linkAttr = \"\";\n if (block.linkUrl) {\n linkAttr = ` href=\"${escapeAttr(block.linkUrl)}\"`;\n if (block.linkOpenInNewTab) {\n linkAttr += ' target=\"_blank\"';\n }\n }\n const src = escapeAttr(block.src);\n const alt = escapeAttr(block.alt);\n const align = block.align;\n return `<mj-image\n src=\"${src}\"\n alt=\"${alt}\"\n width=\"${width}\"\n align=\"${align}\"\n padding=\"${padding}\"${bgColor}${linkAttr}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/button.ts\nfunction renderButton(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const buttonPadding = toPaddingString(block.buttonPadding);\n const href = escapeAttr(block.url);\n const backgroundColor = block.backgroundColor;\n const textColor = block.textColor;\n const fontSize = block.fontSize;\n const borderRadius = block.borderRadius;\n const text = escapeHtml(block.text);\n const targetAttr = block.openInNewTab ? ' target=\"_blank\"' : \"\";\n const fontFamilyAttr = renderFontFamilyAttr2(block.fontFamily, context);\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-button\n href=\"${href}\"${targetAttr}\n background-color=\"${backgroundColor}\"\n color=\"${textColor}\"\n font-size=\"${fontSize}px\"\n font-weight=\"bold\"\n border-radius=\"${borderRadius}px\"\n inner-padding=\"${buttonPadding}\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${text}</mj-button>`;\n}\nfunction renderFontFamilyAttr2(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/divider.ts\nfunction renderDivider(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? \"100%\" : block.width + \"px\";\n const thickness = block.thickness;\n const lineStyle = block.lineStyle;\n const color = block.color;\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-divider\n border-width=\"${thickness}px\"\n border-style=\"${lineStyle}\"\n border-color=\"${color}\"\n width=\"${width}\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/spacer.ts\nfunction renderSpacer(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const height = block.height;\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-spacer height=\"${height}px\" padding=\"${padding}\"${bgColor}${visibilityAttr} />`;\n}\n\n// src/renderers/html.ts\nfunction renderHtml(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (!context.allowHtmlBlocks) {\n return \"\";\n }\n const content = block.content;\n if (content === \"\") {\n return \"\";\n }\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text${visibilityAttr}>\n${content}\n</mj-text>`;\n}\n\n// src/social-icons.ts\nvar SOCIAL_ICONS = {\n facebook: {\n path: \"M24 12.073c0-6.627-5.373-12-12-12s-12 5.373-12 12c0 5.99 4.388 10.954 10.125 11.854v-8.385H7.078v-3.47h3.047V9.43c0-3.007 1.792-4.669 4.533-4.669 1.312 0 2.686.235 2.686.235v2.953H15.83c-1.491 0-1.956.925-1.956 1.874v2.25h3.328l-.532 3.47h-2.796v8.385C19.612 23.027 24 18.062 24 12.073z\",\n color: \"#1877F2\"\n },\n twitter: {\n path: \"M18.244 2.25h3.308l-7.227 8.26 8.502 11.24H16.17l-5.214-6.817L4.99 21.75H1.68l7.73-8.835L1.254 2.25H8.08l4.713 6.231zm-1.161 17.52h1.833L7.084 4.126H5.117z\",\n color: \"#000000\"\n },\n instagram: {\n path: \"M12 0C8.74 0 8.333.015 7.053.072 5.775.132 4.905.333 4.14.63c-.789.306-1.459.717-2.126 1.384S.935 3.35.63 4.14C.333 4.905.131 5.775.072 7.053.012 8.333 0 8.74 0 12s.015 3.667.072 4.947c.06 1.277.261 2.148.558 2.913.306.788.717 1.459 1.384 2.126.667.666 1.336 1.079 2.126 1.384.766.296 1.636.499 2.913.558C8.333 23.988 8.74 24 12 24s3.667-.015 4.947-.072c1.277-.06 2.148-.262 2.913-.558.788-.306 1.459-.718 2.126-1.384.666-.667 1.079-1.335 1.384-2.126.296-.765.499-1.636.558-2.913.06-1.28.072-1.687.072-4.947s-.015-3.667-.072-4.947c-.06-1.277-.262-2.149-.558-2.913-.306-.789-.718-1.459-1.384-2.126C21.319 1.347 20.651.935 19.86.63c-.765-.297-1.636-.499-2.913-.558C15.667.012 15.26 0 12 0zm0 2.16c3.203 0 3.585.016 4.85.071 1.17.055 1.805.249 2.227.415.562.217.96.477 1.382.896.419.42.679.819.896 1.381.164.422.36 1.057.413 2.227.057 1.266.07 1.646.07 4.85s-.015 3.585-.074 4.85c-.061 1.17-.256 1.805-.421 2.227-.224.562-.479.96-.899 1.382-.419.419-.824.679-1.38.896-.42.164-1.065.36-2.235.413-1.274.057-1.649.07-4.859.07-3.211 0-3.586-.015-4.859-.074-1.171-.061-1.816-.256-2.236-.421-.569-.224-.96-.479-1.379-.899-.421-.419-.69-.824-.9-1.38-.165-.42-.359-1.065-.42-2.235-.045-1.26-.061-1.649-.061-4.844 0-3.196.016-3.586.061-4.861.061-1.17.255-1.814.42-2.234.21-.57.479-.96.9-1.381.419-.419.81-.689 1.379-.898.42-.166 1.051-.361 2.221-.421 1.275-.045 1.65-.06 4.859-.06l.045.03zm0 3.678c-3.405 0-6.162 2.76-6.162 6.162 0 3.405 2.76 6.162 6.162 6.162 3.405 0 6.162-2.76 6.162-6.162 0-3.405-2.76-6.162-6.162-6.162zM12 16c-2.21 0-4-1.79-4-4s1.79-4 4-4 4 1.79 4 4-1.79 4-4 4zm7.846-10.405c0 .795-.646 1.44-1.44 1.44-.795 0-1.44-.646-1.44-1.44 0-.794.646-1.439 1.44-1.439.793-.001 1.44.645 1.44 1.439z\",\n color: \"#E4405F\"\n },\n linkedin: {\n path: \"M20.447 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.351V9h3.414v1.561h.046c.477-.9 1.637-1.85 3.37-1.85 3.601 0 4.267 2.37 4.267 5.455v6.286zM5.337 7.433c-1.144 0-2.063-.926-2.063-2.065 0-1.138.92-2.063 2.063-2.063 1.14 0 2.064.925 2.064 2.063 0 1.139-.925 2.065-2.064 2.065zm1.782 13.019H3.555V9h3.564v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z\",\n color: \"#0A66C2\"\n },\n youtube: {\n path: \"M23.498 6.186a3.016 3.016 0 0 0-2.122-2.136C19.505 3.545 12 3.545 12 3.545s-7.505 0-9.377.505A3.017 3.017 0 0 0 .502 6.186C0 8.07 0 12 0 12s0 3.93.502 5.814a3.016 3.016 0 0 0 2.122 2.136c1.871.505 9.376.505 9.376.505s7.505 0 9.377-.505a3.015 3.015 0 0 0 2.122-2.136C24 15.93 24 12 24 12s0-3.93-.502-5.814zM9.545 15.568V8.432L15.818 12l-6.273 3.568z\",\n color: \"#FF0000\"\n },\n tiktok: {\n path: \"M12.525.02c1.31-.02 2.61-.01 3.91-.02.08 1.53.63 3.09 1.75 4.17 1.12 1.11 2.7 1.62 4.24 1.79v4.03c-1.44-.05-2.89-.35-4.2-.97-.57-.26-1.1-.59-1.62-.93-.01 2.92.01 5.84-.02 8.75-.08 1.4-.54 2.79-1.35 3.94-1.31 1.92-3.58 3.17-5.91 3.21-1.43.08-2.86-.31-4.08-1.03-2.02-1.19-3.44-3.37-3.65-5.71-.02-.5-.03-1-.01-1.49.18-1.9 1.12-3.72 2.58-4.96 1.66-1.44 3.98-2.13 6.15-1.72.02 1.48-.04 2.96-.04 4.44-.99-.32-2.15-.23-3.02.37-.63.41-1.11 1.04-1.36 1.75-.21.51-.15 1.07-.14 1.61.24 1.64 1.82 3.02 3.5 2.87 1.12-.01 2.19-.66 2.77-1.61.19-.33.4-.67.41-1.06.1-1.79.06-3.57.07-5.36.01-4.03-.01-8.05.02-12.07z\",\n color: \"#000000\"\n },\n pinterest: {\n path: \"M12 0C5.373 0 0 5.372 0 12c0 5.084 3.163 9.426 7.627 11.174-.105-.949-.2-2.405.042-3.441.218-.937 1.407-5.965 1.407-5.965s-.359-.719-.359-1.782c0-1.668.967-2.914 2.171-2.914 1.023 0 1.518.769 1.518 1.69 0 1.029-.655 2.568-.994 3.995-.283 1.194.599 2.169 1.777 2.169 2.133 0 3.772-2.249 3.772-5.495 0-2.873-2.064-4.882-5.012-4.882-3.414 0-5.418 2.561-5.418 5.207 0 1.031.397 2.138.893 2.738.098.119.112.224.083.345l-.333 1.36c-.053.22-.174.267-.402.161-1.499-.698-2.436-2.889-2.436-4.649 0-3.785 2.75-7.262 7.929-7.262 4.163 0 7.398 2.967 7.398 6.931 0 4.136-2.607 7.464-6.227 7.464-1.216 0-2.359-.631-2.75-1.378l-.748 2.853c-.271 1.043-1.002 2.35-1.492 3.146C9.57 23.812 10.763 24 12 24c6.627 0 12-5.373 12-12 0-6.628-5.373-12-12-12z\",\n color: \"#BD081C\"\n },\n email: {\n path: \"M1.5 8.67v8.58a3 3 0 003 3h15a3 3 0 003-3V8.67l-8.928 5.493a3 3 0 01-3.144 0L1.5 8.67z M22.5 6.908V6.75a3 3 0 00-3-3h-15a3 3 0 00-3 3v.158l9.714 5.978a1.5 1.5 0 001.572 0L22.5 6.908z\",\n color: \"#6B7280\"\n },\n whatsapp: {\n path: \"M17.472 14.382c-.297-.149-1.758-.867-2.03-.967-.273-.099-.471-.148-.67.15-.197.297-.767.966-.94 1.164-.173.199-.347.223-.644.075-.297-.15-1.255-.463-2.39-1.475-.883-.788-1.48-1.761-1.653-2.059-.173-.297-.018-.458.13-.606.134-.133.298-.347.446-.52.149-.174.198-.298.298-.497.099-.198.05-.371-.025-.52-.075-.149-.669-1.612-.916-2.207-.242-.579-.487-.5-.669-.51-.173-.008-.371-.01-.57-.01-.198 0-.52.074-.792.372-.272.297-1.04 1.016-1.04 2.479 0 1.462 1.065 2.875 1.213 3.074.149.198 2.096 3.2 5.077 4.487.709.306 1.262.489 1.694.625.712.227 1.36.195 1.871.118.571-.085 1.758-.719 2.006-1.413.248-.694.248-1.289.173-1.413-.074-.124-.272-.198-.57-.347m-5.421 7.403h-.004a9.87 9.87 0 01-5.031-1.378l-.361-.214-3.741.982.998-3.648-.235-.374a9.86 9.86 0 01-1.51-5.26c.001-5.45 4.436-9.884 9.888-9.884 2.64 0 5.122 1.03 6.988 2.898a9.825 9.825 0 012.893 6.994c-.003 5.45-4.437 9.884-9.885 9.884m8.413-18.297A11.815 11.815 0 0012.05 0C5.495 0 .16 5.335.157 11.892c0 2.096.547 4.142 1.588 5.945L.057 24l6.305-1.654a11.882 11.882 0 005.683 1.448h.005c6.554 0 11.89-5.335 11.893-11.893a11.821 11.821 0 00-3.48-8.413z\",\n color: \"#25D366\"\n },\n telegram: {\n path: \"M11.944 0A12 12 0 0 0 0 12a12 12 0 0 0 12 12 12 12 0 0 0 12-12A12 12 0 0 0 12 0a12 12 0 0 0-.056 0zm4.962 7.224c.1-.002.321.023.465.14a.506.506 0 0 1 .171.325c.016.093.036.306.02.472-.18 1.898-.962 6.502-1.36 8.627-.168.9-.499 1.201-.82 1.23-.696.065-1.225-.46-1.9-.902-1.056-.693-1.653-1.124-2.678-1.8-1.185-.78-.417-1.21.258-1.91.177-.184 3.247-2.977 3.307-3.23.007-.032.014-.15-.056-.212s-.174-.041-.249-.024c-.106.024-1.793 1.14-5.061 3.345-.48.33-.913.49-1.302.48-.428-.008-1.252-.241-1.865-.44-.752-.245-1.349-.374-1.297-.789.027-.216.325-.437.893-.663 3.498-1.524 5.83-2.529 6.998-3.014 3.332-1.386 4.025-1.627 4.476-1.635z\",\n color: \"#26A5E4\"\n },\n discord: {\n path: \"M20.317 4.3698a19.7913 19.7913 0 00-4.8851-1.5152.0741.0741 0 00-.0785.0371c-.211.3753-.4447.8648-.6083 1.2495-1.8447-.2762-3.68-.2762-5.4868 0-.1636-.3933-.4058-.8742-.6177-1.2495a.077.077 0 00-.0785-.037 19.7363 19.7363 0 00-4.8852 1.515.0699.0699 0 00-.0321.0277C.5334 9.0458-.319 13.5799.0992 18.0578a.0824.0824 0 00.0312.0561c2.0528 1.5076 4.0413 2.4228 5.9929 3.0294a.0777.0777 0 00.0842-.0276c.4616-.6304.8731-1.2952 1.226-1.9942a.076.076 0 00-.0416-.1057c-.6528-.2476-1.2743-.5495-1.8722-.8923a.077.077 0 01-.0076-.1277c.1258-.0943.2517-.1923.3718-.2914a.0743.0743 0 01.0776-.0105c3.9278 1.7933 8.18 1.7933 12.0614 0a.0739.0739 0 01.0785.0095c.1202.099.246.1981.3728.2924a.077.077 0 01-.0066.1276 12.2986 12.2986 0 01-1.873.8914.0766.0766 0 00-.0407.1067c.3604.698.7719 1.3628 1.225 1.9932a.076.076 0 00.0842.0286c1.961-.6067 3.9495-1.5219 6.0023-3.0294a.077.077 0 00.0313-.0552c.5004-5.177-.8382-9.6739-3.5485-13.6604a.061.061 0 00-.0312-.0286zM8.02 15.3312c-1.1825 0-2.1569-1.0857-2.1569-2.419 0-1.3332.9555-2.4189 2.157-2.4189 1.2108 0 2.1757 1.0952 2.1568 2.419 0 1.3332-.9555 2.4189-2.1569 2.4189zm7.9748 0c-1.1825 0-2.1569-1.0857-2.1569-2.419 0-1.3332.9554-2.4189 2.1569-2.4189 1.2108 0 2.1757 1.0952 2.1568 2.419 0 1.3332-.946 2.4189-2.1568 2.4189z\",\n color: \"#5865F2\"\n },\n snapchat: {\n path: \"M12.017 0C5.396 0 .029 5.367.029 11.987c0 5.079 3.158 9.417 7.618 11.162-.105-.949-.199-2.403.041-3.439.219-.937 1.406-5.957 1.406-5.957s-.359-.72-.359-1.781c0-1.668.967-2.914 2.171-2.914 1.023 0 1.518.769 1.518 1.69 0 1.029-.655 2.568-.994 3.995-.283 1.194.599 2.169 1.777 2.169 2.133 0 3.772-2.249 3.772-5.495 0-2.873-2.064-4.882-5.012-4.882-3.414 0-5.418 2.561-5.418 5.207 0 1.031.397 2.138.893 2.738a.36.36 0 01.083.345l-.333 1.36c-.053.22-.174.267-.402.161-1.499-.698-2.436-2.889-2.436-4.649 0-3.785 2.75-7.262 7.929-7.262 4.163 0 7.398 2.967 7.398 6.931 0 4.136-2.607 7.464-6.227 7.464-1.216 0-2.359-.631-2.75-1.378l-.748 2.853c-.271 1.043-1.002 2.35-1.492 3.146 1.124.347 2.317.535 3.554.535 6.627 0 12.017-5.373 12.017-12.001C24.034 5.367 18.644 0 12.017 0z\",\n color: \"#FFFC00\"\n },\n reddit: {\n path: \"M12 0A12 12 0 0 0 0 12a12 12 0 0 0 12 12 12 12 0 0 0 12-12A12 12 0 0 0 12 0zm5.01 4.744c.688 0 1.25.561 1.25 1.249a1.25 1.25 0 0 1-2.498.056l-2.597-.547-.8 3.747c1.824.07 3.48.632 4.674 1.488.308-.309.73-.491 1.207-.491.968 0 1.754.786 1.754 1.754 0 .716-.435 1.333-1.01 1.614a3.111 3.111 0 0 1 .042.52c0 2.694-3.13 4.87-7.004 4.87-3.874 0-7.004-2.176-7.004-4.87 0-.183.015-.366.043-.534A1.748 1.748 0 0 1 4.028 12c0-.968.786-1.754 1.754-1.754.463 0 .898.196 1.207.49 1.207-.883 2.878-1.43 4.744-1.487l.885-4.182a.342.342 0 0 1 .14-.197.35.35 0 0 1 .238-.042l2.906.617a1.214 1.214 0 0 1 1.108-.701zM9.25 12C8.561 12 8 12.562 8 13.25c0 .687.561 1.248 1.25 1.248.687 0 1.248-.561 1.248-1.249 0-.688-.561-1.249-1.249-1.249zm5.5 0c-.687 0-1.248.561-1.248 1.25 0 .687.561 1.248 1.249 1.248.688 0 1.249-.561 1.249-1.249 0-.687-.562-1.249-1.25-1.249zm-5.466 3.99a.327.327 0 0 0-.231.094.33.33 0 0 0 0 .463c.842.842 2.484.913 2.961.913.477 0 2.105-.056 2.961-.913a.361.361 0 0 0 .029-.463.33.33 0 0 0-.464 0c-.547.533-1.684.73-2.512.73-.828 0-1.979-.196-2.512-.73a.326.326 0 0 0-.232-.095z\",\n color: \"#FF4500\"\n },\n github: {\n path: \"M12 .297c-6.63 0-12 5.373-12 12 0 5.303 3.438 9.8 8.205 11.385.6.113.82-.258.82-.577 0-.285-.01-1.04-.015-2.04-3.338.724-4.042-1.61-4.042-1.61C4.422 18.07 3.633 17.7 3.633 17.7c-1.087-.744.084-.729.084-.729 1.205.084 1.838 1.236 1.838 1.236 1.07 1.835 2.809 1.305 3.495.998.108-.776.417-1.305.76-1.605-2.665-.3-5.466-1.332-5.466-5.93 0-1.31.465-2.38 1.235-3.22-.135-.303-.54-1.523.105-3.176 0 0 1.005-.322 3.3 1.23.96-.267 1.98-.399 3-.405 1.02.006 2.04.138 3 .405 2.28-1.552 3.285-1.23 3.285-1.23.645 1.653.24 2.873.12 3.176.765.84 1.23 1.91 1.23 3.22 0 4.61-2.805 5.625-5.475 5.92.42.36.81 1.096.81 2.22 0 1.606-.015 2.896-.015 3.286 0 .315.21.69.825.57C20.565 22.092 24 17.592 24 12.297c0-6.627-5.373-12-12-12\",\n color: \"#181717\"\n },\n dribbble: {\n path: \"M12 24C5.385 24 0 18.615 0 12S5.385 0 12 0s12 5.385 12 12-5.385 12-12 12zm10.12-10.358c-.35-.11-3.17-.953-6.384-.438 1.34 3.684 1.887 6.684 1.992 7.308 2.3-1.555 3.936-4.02 4.392-6.87zm-6.115 7.808c-.153-.9-.75-4.032-2.19-7.77l-.066.02c-5.79 2.015-7.86 6.025-8.04 6.4 1.73 1.358 3.92 2.166 6.29 2.166 1.42 0 2.77-.29 4-.814zm-11.62-2.58c.232-.4 3.045-5.055 8.332-6.765.135-.045.27-.084.405-.12-.26-.585-.54-1.167-.832-1.74C7.17 11.775 2.206 11.71 1.756 11.7l-.004.312c0 2.633.998 5.037 2.634 6.855zm-2.42-8.955c.46.008 4.683.026 9.477-1.248-1.698-3.018-3.53-5.558-3.8-5.928-2.868 1.35-5.01 3.99-5.676 7.17zM9.6 2.052c.282.38 2.145 2.914 3.822 6 3.645-1.365 5.19-3.44 5.373-3.702-1.81-1.61-4.19-2.586-6.795-2.586-.825 0-1.63.1-2.4.285zm10.335 3.483c-.218.29-1.935 2.493-5.724 4.04.24.49.47.985.68 1.486.08.18.15.36.22.53 3.41-.43 6.8.26 7.14.33-.02-2.42-.88-4.64-2.31-6.38z\",\n color: \"#EA4C89\"\n },\n behance: {\n path: \"M22 7h-7V5h7v2zm1.726 10c-.442 1.297-2.029 3-5.101 3-3.074 0-5.564-1.729-5.564-5.675 0-3.91 2.325-5.92 5.466-5.92 3.082 0 4.964 1.782 5.375 4.426.078.506.109 1.188.095 2.14H15.97c.13 3.211 3.483 3.312 4.588 2.029h3.168zm-7.686-4h4.965c-.105-1.547-1.136-2.219-2.477-2.219-1.466 0-2.277.768-2.488 2.219zm-9.574 6.988H0V5.021h6.953c5.476.081 5.58 5.444 2.72 6.906 3.461 1.26 3.577 8.061-3.207 8.061zM3 11h3.584c2.508 0 2.906-3-.312-3H3v3zm3.391 3H3v3.016h3.341c3.055 0 2.868-3.016.05-3.016z\",\n color: \"#1769FF\"\n }\n};\nfunction generateSocialIconDataUri(platform, style, size) {\n const iconData = SOCIAL_ICONS[platform];\n const path = iconData?.path ?? \"\";\n const brandColor = iconData?.color ?? \"#6B7280\";\n if (path === \"\") {\n return \"\";\n }\n const isOutlined = style === \"outlined\";\n const iconColor = isOutlined ? brandColor : \"#ffffff\";\n let bgShape;\n switch (style) {\n case \"circle\":\n bgShape = `<circle cx=\"12\" cy=\"12\" r=\"12\" fill=\"${brandColor}\"/>`;\n break;\n case \"rounded\":\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"6\" fill=\"${brandColor}\"/>`;\n break;\n case \"square\":\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"0\" fill=\"${brandColor}\"/>`;\n break;\n case \"outlined\":\n bgShape = `<rect width=\"22\" height=\"22\" x=\"1\" y=\"1\" rx=\"3\" fill=\"transparent\" stroke=\"${brandColor}\" stroke-width=\"2\"/>`;\n break;\n default:\n bgShape = `<rect width=\"24\" height=\"24\" rx=\"3\" fill=\"${brandColor}\"/>`;\n break;\n }\n const svg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" width=\"${size}\" height=\"${size}\">` + bgShape + `<g transform=\"translate(4.8, 4.8) scale(0.6)\"><path d=\"${path}\" fill=\"${iconColor}\"/></g></svg>`;\n return \"data:image/svg+xml;base64,\" + btoa(svg);\n}\n\n// src/renderers/social.ts\nfunction renderSocialIcons(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const icons = block.icons;\n if (icons.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` container-background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const align = block.align;\n const iconSize = block.iconSize;\n const iconStyle = block.iconStyle;\n const spacing = block.spacing;\n let iconSizePx;\n switch (iconSize) {\n case \"small\":\n iconSizePx = 24;\n break;\n case \"large\":\n iconSizePx = 48;\n break;\n default:\n iconSizePx = 32;\n break;\n }\n let borderRadius;\n switch (iconStyle) {\n case \"circle\":\n borderRadius = \"50%\";\n break;\n case \"rounded\":\n borderRadius = \"8px\";\n break;\n case \"square\":\n borderRadius = \"0\";\n break;\n default:\n borderRadius = \"4px\";\n break;\n }\n const iconCount = icons.length;\n const socialElements = icons.map((icon, index) => {\n const platform = icon.platform;\n const url = escapeAttr(icon.url);\n const iconSrc = generateSocialIconDataUri(platform, iconStyle, iconSizePx);\n const rightPad = index === iconCount - 1 ? 0 : spacing;\n return `<mj-social-element src=\"${iconSrc}\" href=\"${url}\" icon-size=\"${iconSizePx}px\" padding=\"0 ${rightPad}px 0 0\" border-radius=\"${borderRadius}\" background-color=\"transparent\"></mj-social-element>`;\n });\n const socialContent = socialElements.join(\"\\n\");\n return `<mj-social\n mode=\"horizontal\"\n align=\"${align}\"\n icon-padding=\"0\"\n padding=\"${padding}\"${bgColor}${visibilityAttr}\n>\n${socialContent}\n</mj-social>`;\n}\n\n// src/renderers/menu.ts\nfunction renderMenu(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (block.items.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const fontFamilyAttr = renderFontFamilyAttr3(block.fontFamily, context);\n const align = block.textAlign;\n const fontSize = block.fontSize;\n const color = block.color;\n const content = renderMenuItems(block);\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${content}</mj-text>`;\n}\nfunction renderMenuItems(block) {\n const items = block.items;\n const separator = escapeHtml(block.separator);\n const separatorColor = escapeAttr(block.separatorColor);\n const spacing = block.spacing;\n const linkColor = block.linkColor ?? block.color;\n const parts = [];\n const itemCount = items.length;\n for (let index = 0; index < itemCount; index++) {\n parts.push(renderMenuItem(items[index], linkColor));\n if (index < itemCount - 1) {\n parts.push(\n `<span style=\"color: ${separatorColor}; padding: 0 ${spacing}px;\">${separator}</span>`\n );\n }\n }\n return parts.join(\"\");\n}\nfunction renderMenuItem(item, linkColor) {\n const text = escapeHtml(item.text);\n const url = escapeAttr(item.url);\n const color = item.color ?? linkColor;\n const target = item.openInNewTab ? ' target=\"_blank\"' : \"\";\n const styles = [`color: ${color}`, \"text-decoration: none\"];\n if (item.bold) {\n styles.push(\"font-weight: bold\");\n }\n if (item.underline) {\n styles.push(\"text-decoration: underline\");\n }\n const styleAttr = styles.join(\"; \");\n return `<a href=\"${url}\" style=\"${styleAttr}\"${target}>${text}</a>`;\n}\nfunction renderFontFamilyAttr3(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/table.ts\nfunction renderTable(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n if (block.rows.length === 0) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const fontFamilyAttr = renderFontFamilyAttr4(block.fontFamily, context);\n const fontSize = block.fontSize;\n const color = block.color;\n const align = block.textAlign;\n const tableHtml = renderTableElement(block);\n return `<mj-text\n font-size=\"${fontSize}px\"\n color=\"${color}\"\n align=\"${align}\"\n line-height=\"1.5\"\n padding=\"${padding}\"${bgColor}${fontFamilyAttr}${visibilityAttr}\n>${tableHtml}</mj-text>`;\n}\nfunction renderTableElement(block) {\n const borderColor = escapeAttr(block.borderColor);\n const borderWidth = block.borderWidth;\n const tableStyle = \"width: 100%; border-collapse: collapse;\";\n let rowsHtml = \"\";\n for (let index = 0; index < block.rows.length; index++) {\n const row = block.rows[index];\n const isHeader = block.hasHeaderRow && index === 0;\n rowsHtml += renderRow(row, block, isHeader, borderColor, borderWidth);\n }\n return `<table style=\"${tableStyle}\">${rowsHtml}</table>`;\n}\nfunction renderRow(row, block, isHeader, borderColor, borderWidth) {\n let cellsHtml = \"\";\n for (const cell of row.cells) {\n cellsHtml += renderCell(cell, block, isHeader, borderColor, borderWidth);\n }\n return `<tr>${cellsHtml}</tr>`;\n}\nfunction renderCell(cell, block, isHeader, borderColor, borderWidth) {\n const cellPadding = block.cellPadding;\n const styles = [\n `border: ${borderWidth}px solid ${borderColor}`,\n `padding: ${cellPadding}px`\n ];\n if (isHeader) {\n styles.push(\"font-weight: bold\");\n if (block.headerBackgroundColor) {\n styles.push(\n `background-color: ${escapeAttr(block.headerBackgroundColor)}`\n );\n }\n }\n const styleAttr = styles.join(\"; \");\n const content = convertMergeTagsToValues(cell.content);\n const tag = isHeader ? \"th\" : \"td\";\n return `<${tag} style=\"${styleAttr}\">${content}</${tag}>`;\n}\nfunction renderFontFamilyAttr4(fontFamily, context) {\n if (!fontFamily) {\n return \"\";\n }\n const resolved = context.resolveFontFamily(fontFamily);\n return ` font-family=\"${resolved}\"`;\n}\n\n// src/renderers/custom.ts\nfunction renderCustom(block, _context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const content = block.renderedHtml;\n if (!content || content === \"\") {\n return \"\";\n }\n const visibilityAttr = getCssClassAttr(block);\n return `<mj-text${visibilityAttr}>\n${content}\n</mj-text>`;\n}\n\n// src/columns.ts\nfunction getWidthPercentages(layout) {\n switch (layout) {\n case \"2\":\n return [\"50%\", \"50%\"];\n case \"3\":\n return [\"33.33%\", \"33.33%\", \"33.33%\"];\n case \"1-2\":\n return [\"33.33%\", \"66.67%\"];\n case \"2-1\":\n return [\"66.67%\", \"33.33%\"];\n default:\n return [\"100%\"];\n }\n}\nfunction getWidthPixels(layout, containerWidth) {\n switch (layout) {\n case \"2\":\n return [containerWidth * 0.5, containerWidth * 0.5];\n case \"3\":\n return [containerWidth / 3, containerWidth / 3, containerWidth / 3];\n case \"1-2\":\n return [containerWidth / 3, containerWidth * 2 / 3];\n case \"2-1\":\n return [containerWidth * 2 / 3, containerWidth / 3];\n default:\n return [containerWidth];\n }\n}\n\n// src/renderers/section.ts\nfunction renderSection(block, context, renderBlock2) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const columnsLayout = block.columns;\n const columnWidths = getWidthPercentages(columnsLayout);\n const columnWidthsPx = getWidthPixels(columnsLayout, context.containerWidth);\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const visibilityAttr = getCssClassAttr(block);\n const children = block.children;\n const columnsContent = [];\n for (let index = 0; index < children.length; index++) {\n const column = children[index];\n const width = columnWidths[index] ?? \"100%\";\n const columnWidth = Math.floor(\n columnWidthsPx[index] ?? context.containerWidth\n );\n const filteredColumn = filterHtmlBlocks(column, context.allowHtmlBlocks);\n const columnContext = context.withContainerWidth(columnWidth);\n const columnBlocks = filteredColumn.map((child) => renderBlock2(child, columnContext)).filter((value) => value !== \"\").join(\"\\n\");\n const content = columnBlocks === \"\" ? \"<mj-text> </mj-text>\" : columnBlocks;\n columnsContent.push(`<mj-column width=\"${width}\">\n${content}\n</mj-column>`);\n }\n const columns = columnsContent.join(\"\\n\");\n return `<mj-section${bgColor} padding=\"${padding}\"${visibilityAttr}>\n${columns}\n</mj-section>`;\n}\nfunction filterHtmlBlocks(blocks, allowHtmlBlocks) {\n if (allowHtmlBlocks) {\n return blocks;\n }\n return blocks.filter((block) => block.type !== \"html\");\n}\n\n// src/renderers/video.ts\nfunction getVideoThumbnail(url, customThumbnail) {\n if (customThumbnail) {\n return customThumbnail;\n }\n if (!url) {\n return null;\n }\n const youtubePatterns = [\n /(?:youtube\\.com\\/watch\\?v=|youtu\\.be\\/|youtube\\.com\\/embed\\/)([a-zA-Z0-9_-]{11})/,\n /youtube\\.com\\/shorts\\/([a-zA-Z0-9_-]{11})/\n ];\n for (const pattern of youtubePatterns) {\n const match = url.match(pattern);\n if (match) {\n return `https://img.youtube.com/vi/${match[1]}/maxresdefault.jpg`;\n }\n }\n const vimeoMatch = url.match(/vimeo\\.com\\/(?:video\\/)?(\\d+)/);\n if (vimeoMatch) {\n return `https://vumbnail.com/${vimeoMatch[1]}.jpg`;\n }\n return null;\n}\nfunction renderVideo(block, context) {\n if (isHiddenOnAll(block)) {\n return \"\";\n }\n const thumbnailUrl = getVideoThumbnail(block.url, block.thumbnailUrl);\n if (!thumbnailUrl) {\n return \"\";\n }\n const padding = toPaddingString(block.styles.padding);\n const bgColor = block.styles.backgroundColor ? ` background-color=\"${block.styles.backgroundColor}\"` : \"\";\n const width = block.width === \"full\" ? context.containerWidth + \"px\" : block.width + \"px\";\n const visibilityAttr = getCssClassAttr(block);\n const src = escapeAttr(thumbnailUrl);\n const alt = escapeAttr(block.alt);\n const align = block.align;\n const href = escapeAttr(block.url);\n return `<mj-image\n src=\"${src}\"\n alt=\"${alt}\"\n width=\"${width}\"\n align=\"${align}\"\n padding=\"${padding}\"\n href=\"${href}\"\n target=\"_blank\"${bgColor}${visibilityAttr}\n/>`;\n}\n\n// src/renderers/index.ts\nfunction renderBlock(block, context) {\n if (isSection(block)) {\n return renderSection(block, context, renderBlock);\n }\n if (isTitle(block)) {\n return renderTitle(block, context);\n }\n if (isParagraph(block)) {\n return renderParagraph(block, context);\n }\n if (isImage(block)) {\n return renderImage(block, context);\n }\n if (isButton(block)) {\n return renderButton(block, context);\n }\n if (isDivider(block)) {\n return renderDivider(block, context);\n }\n if (isSpacer(block)) {\n return renderSpacer(block, context);\n }\n if (isHtml(block)) {\n return renderHtml(block, context);\n }\n if (isSocialIcons(block)) {\n return renderSocialIcons(block, context);\n }\n if (isMenu(block)) {\n return renderMenu(block, context);\n }\n if (isTable(block)) {\n return renderTable(block, context);\n }\n if (isVideo(block)) {\n return renderVideo(block, context);\n }\n if (isCustomBlock(block)) {\n return renderCustom(block, context);\n }\n return \"\";\n}\n\n// src/index.ts\nfunction renderToMjml(content, options) {\n const customFonts = options?.customFonts ?? [];\n const defaultFallbackFont = options?.defaultFallbackFont ?? \"Arial, sans-serif\";\n const allowHtmlBlocks = options?.allowHtmlBlocks ?? true;\n const renderContext = new RenderContext(\n content.settings.width,\n customFonts,\n defaultFallbackFont,\n allowHtmlBlocks\n );\n const blocks = filterHtmlBlocks2(content.blocks, allowHtmlBlocks);\n const fontFamily = renderContext.resolveFontFamily(\n content.settings.fontFamily\n );\n const backgroundColor = content.settings.backgroundColor;\n const bodyContent = blocks.map((block) => renderTopLevelBlock(block, renderContext)).filter((value) => value !== \"\").join(\"\\n\");\n const fontDeclarations = generateFontDeclarations(customFonts);\n const previewTag = generatePreviewTag(content.settings.preheaderText);\n return `<mjml>\n <mj-head>${previewTag}\n <mj-attributes>\n <mj-all font-family=\"${fontFamily}\" />\n <mj-section padding=\"0\" />\n <mj-column padding=\"0\" />\n <mj-image fluid-on-mobile=\"true\" />\n </mj-attributes>${fontDeclarations}\n <mj-style>\n a { color: inherit; text-decoration: none; }\n @media only screen and (max-width: 480px) {\n .tpl-hide-mobile { display: none !important; mso-hide: all !important; }\n }\n @media only screen and (min-width: 481px) and (max-width: 768px) {\n .tpl-hide-tablet { display: none !important; mso-hide: all !important; }\n }\n @media only screen and (min-width: 769px) {\n .tpl-hide-desktop { display: none !important; mso-hide: all !important; }\n }\n </mj-style>\n </mj-head>\n <mj-body width=\"${renderContext.containerWidth}px\" background-color=\"${backgroundColor}\">\n${bodyContent}\n </mj-body>\n</mjml>`;\n}\nfunction renderTopLevelBlock(block, context) {\n if (isSection2(block)) {\n const rendered = renderBlock(block, context);\n return wrapWithDisplayCondition(block, rendered);\n }\n const content = renderBlock(block, context);\n const wrapped = wrapInSection(content);\n return wrapWithDisplayCondition(block, wrapped);\n}\nfunction wrapWithDisplayCondition(block, rendered) {\n if (rendered === \"\") {\n return \"\";\n }\n const displayCondition = block.displayCondition;\n if (!displayCondition) {\n return rendered;\n }\n return `<mj-raw>${displayCondition.before}</mj-raw>\n` + rendered + `\n<mj-raw>${displayCondition.after}</mj-raw>`;\n}\nfunction wrapInSection(content) {\n if (content === \"\") {\n return \"\";\n }\n return `<mj-section>\n <mj-column>\n${content}\n </mj-column>\n</mj-section>`;\n}\nfunction generatePreviewTag(preheaderText) {\n if (!preheaderText) {\n return \"\";\n }\n const trimmed = preheaderText.trim();\n if (trimmed === \"\") {\n return \"\";\n }\n const escaped = escapeHtml(trimmed);\n return `\n <mj-preview>${escaped}</mj-preview>`;\n}\nfunction generateFontDeclarations(customFonts) {\n if (customFonts.length === 0) {\n return \"\";\n }\n return customFonts.map(\n (font) => `\n <mj-font name=\"${escapeAttr(font.name)}\" href=\"${escapeAttr(font.url)}\" />`\n ).join(\"\");\n}\nfunction filterHtmlBlocks2(blocks, allowHtmlBlocks) {\n if (allowHtmlBlocks) {\n return blocks;\n }\n return blocks.filter((block) => block.type !== \"html\");\n}\nexport {\n RenderContext,\n SOCIAL_ICONS,\n convertMergeTagsToValues,\n escapeAttr,\n escapeHtml,\n generateSocialIconDataUri,\n getCssClassAttr,\n getCssClasses,\n getWidthPercentages,\n getWidthPixels,\n isHiddenOnAll,\n renderBlock,\n renderToMjml,\n toPaddingString\n};\n//# sourceMappingURL=index.js.map"],"mappings":"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"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { F as e, I as t, L as n, N as r, P as i, R as a, z as o } from "./tiptap-
|
|
1
|
+
import { F as e, I as t, L as n, N as r, P as i, R as a, z as o } from "./tiptap-BhxaWR8R.js";
|
|
2
2
|
export { r as BackgroundColor, i as Color, e as FontFamily, t as FontSize, n as LineHeight, a as TextStyle, o as TextStyleKit };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { C as e, E as t, T as n, w as r } from "./tiptap-
|
|
1
|
+
import { C as e, E as t, T as n, w as r } from "./tiptap-BhxaWR8R.js";
|
|
2
2
|
export { e as Link, r as default, n as isAllowedUri, t as pasteRegex };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { $ as e, H as t, N as n, S as r, U as i, _ as a, at as o, ct as s, g as c, h as l, k as u, l as d, lt as f, m as p, p as m, s as h, st as g, u as _ } from "./draggable-BQNU47zu.js";
|
|
2
|
-
import {
|
|
3
|
-
import { H as w, J as T, On as E, W as D, Z as O, a as k, c as A } from "./tiptap-
|
|
2
|
+
import { Z as v, dn as y, jt as b, ln as x, sn as S, un as C } from "./features-Ds0XUfte.js";
|
|
3
|
+
import { H as w, J as T, On as E, W as D, Z as O, a as k, c as A } from "./tiptap-BhxaWR8R.js";
|
|
4
4
|
//#region src/extensions/FontSize.ts
|
|
5
5
|
var j = w.create({
|
|
6
6
|
name: "fontSize",
|
|
@@ -82,9 +82,9 @@ var j = w.create({
|
|
|
82
82
|
updateAttributes: { type: Function }
|
|
83
83
|
},
|
|
84
84
|
setup(r) {
|
|
85
|
-
let
|
|
85
|
+
let S = r, { syntax: C } = v(), { t: w } = b(), T = m(() => y(S.node.attrs.value, C)), E = m(() => x(S.node.attrs.value, C)), D = e(!1), O = e(""), A = e(null), j = !1;
|
|
86
86
|
function M() {
|
|
87
|
-
O.value =
|
|
87
|
+
O.value = S.node.attrs.value, j = !1, D.value = !0, u(() => {
|
|
88
88
|
A.value?.focus(), A.value?.select();
|
|
89
89
|
});
|
|
90
90
|
}
|
|
@@ -96,9 +96,9 @@ var j = w.create({
|
|
|
96
96
|
D.value = !1;
|
|
97
97
|
return;
|
|
98
98
|
}
|
|
99
|
-
e !==
|
|
99
|
+
e !== S.node.attrs.value && S.updateAttributes({
|
|
100
100
|
value: e,
|
|
101
|
-
keyword:
|
|
101
|
+
keyword: y(e, C) ? x(e, C) : ""
|
|
102
102
|
}), D.value = !1;
|
|
103
103
|
}
|
|
104
104
|
function L(e) {
|
|
@@ -186,7 +186,7 @@ var B = T.create({
|
|
|
186
186
|
inline: !0,
|
|
187
187
|
atom: !0,
|
|
188
188
|
addOptions() {
|
|
189
|
-
return { syntax:
|
|
189
|
+
return { syntax: S.liquid };
|
|
190
190
|
},
|
|
191
191
|
addAttributes() {
|
|
192
192
|
return {
|
|
@@ -204,12 +204,12 @@ var B = T.create({
|
|
|
204
204
|
return [{ tag: "span[data-logic-merge-tag]" }];
|
|
205
205
|
},
|
|
206
206
|
renderHTML({ node: e, HTMLAttributes: t }) {
|
|
207
|
-
if (!
|
|
207
|
+
if (!y(e.attrs.value, this.options.syntax)) return [
|
|
208
208
|
"span",
|
|
209
209
|
{},
|
|
210
210
|
e.attrs.value
|
|
211
211
|
];
|
|
212
|
-
let n =
|
|
212
|
+
let n = x(e.attrs.value, this.options.syntax);
|
|
213
213
|
return [
|
|
214
214
|
"span",
|
|
215
215
|
E(t, {
|
|
@@ -233,8 +233,8 @@ var B = T.create({
|
|
|
233
233
|
find: RegExp(this.options.syntax.logic.source + "$", ""),
|
|
234
234
|
handler: ({ state: e, range: t, match: n }) => {
|
|
235
235
|
let r = n[0];
|
|
236
|
-
if (!
|
|
237
|
-
let i =
|
|
236
|
+
if (!y(r, this.options.syntax)) return;
|
|
237
|
+
let i = x(r, this.options.syntax), a = this.type.create({
|
|
238
238
|
value: r,
|
|
239
239
|
keyword: i
|
|
240
240
|
});
|
|
@@ -247,8 +247,8 @@ var B = T.create({
|
|
|
247
247
|
find: new RegExp(this.options.syntax.logic.source, "g"),
|
|
248
248
|
handler: ({ state: e, range: t, match: n }) => {
|
|
249
249
|
let r = n[0];
|
|
250
|
-
if (!
|
|
251
|
-
let i =
|
|
250
|
+
if (!y(r, this.options.syntax)) return;
|
|
251
|
+
let i = x(r, this.options.syntax), a = this.type.create({
|
|
252
252
|
value: r,
|
|
253
253
|
keyword: i
|
|
254
254
|
});
|
|
@@ -268,7 +268,7 @@ var B = T.create({
|
|
|
268
268
|
updateAttributes: { type: Function }
|
|
269
269
|
},
|
|
270
270
|
setup(r) {
|
|
271
|
-
let s = r, { getMergeTagLabel: c } =
|
|
271
|
+
let s = r, { getMergeTagLabel: c } = v(), { t: g } = b(), y = m(() => c(s.node.attrs.value)), x = e(!1), S = e(""), C = e(null);
|
|
272
272
|
function w() {
|
|
273
273
|
S.value = s.node.attrs.value, x.value = !0, u(() => {
|
|
274
274
|
C.value?.focus(), C.value?.select();
|
|
@@ -308,7 +308,7 @@ var B = T.create({
|
|
|
308
308
|
"data-tooltip": r.node.attrs.value,
|
|
309
309
|
onClick: _(w, ["stop"]),
|
|
310
310
|
onKeydown: [d(_(w, ["stop"]), ["enter"]), d(_(w, ["prevent", "stop"]), ["space"])]
|
|
311
|
-
}, f(
|
|
311
|
+
}, f(y.value), 41, V)), p("button", {
|
|
312
312
|
type: "button",
|
|
313
313
|
"aria-label": o(g).mergeTag.deleteMergeTag,
|
|
314
314
|
class: "tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]",
|
|
@@ -344,7 +344,7 @@ var B = T.create({
|
|
|
344
344
|
addOptions() {
|
|
345
345
|
return {
|
|
346
346
|
mergeTags: [],
|
|
347
|
-
syntax:
|
|
347
|
+
syntax: S.liquid
|
|
348
348
|
};
|
|
349
349
|
},
|
|
350
350
|
addAttributes() {
|
|
@@ -363,7 +363,7 @@ var B = T.create({
|
|
|
363
363
|
return [{ tag: "span[data-merge-tag]" }];
|
|
364
364
|
},
|
|
365
365
|
renderHTML({ node: e, HTMLAttributes: t }) {
|
|
366
|
-
let n =
|
|
366
|
+
let n = C(e.attrs.value, this.options.mergeTags);
|
|
367
367
|
return [
|
|
368
368
|
"span",
|
|
369
369
|
E(t, {
|
|
@@ -392,7 +392,7 @@ var B = T.create({
|
|
|
392
392
|
return [new D({
|
|
393
393
|
find: RegExp(this.options.syntax.value.source + "$", ""),
|
|
394
394
|
handler: ({ state: e, range: t, match: n }) => {
|
|
395
|
-
let r = n[0], i =
|
|
395
|
+
let r = n[0], i = C(r, this.options.mergeTags), a = this.type.create({
|
|
396
396
|
label: i,
|
|
397
397
|
value: r
|
|
398
398
|
});
|
|
@@ -404,7 +404,7 @@ var B = T.create({
|
|
|
404
404
|
return [new O({
|
|
405
405
|
find: new RegExp(this.options.syntax.value.source, "g"),
|
|
406
406
|
handler: ({ state: e, range: t, match: n }) => {
|
|
407
|
-
let r = n[0], i =
|
|
407
|
+
let r = n[0], i = C(r, this.options.mergeTags), a = this.type.create({
|
|
408
408
|
label: i,
|
|
409
409
|
value: r
|
|
410
410
|
});
|
|
@@ -416,4 +416,4 @@ var B = T.create({
|
|
|
416
416
|
//#endregion
|
|
417
417
|
export { j as FontSize, M as LetterSpacing, N as LineHeight, B as LogicMergeTagNode, W as MergeTagNode };
|
|
418
418
|
|
|
419
|
-
//# sourceMappingURL=extensions-
|
|
419
|
+
//# sourceMappingURL=extensions-Bj7USRLr.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"extensions-B_kcV0tK.js","names":[],"sources":["../../../src/extensions/FontSize.ts","../../../src/extensions/LetterSpacing.ts","../../../src/extensions/LineHeight.ts","../../../src/extensions/LogicMergeTagNodeView.vue","../../../src/extensions/LogicMergeTagNodeView.vue","../../../src/extensions/isNodeSelected.ts","../../../src/extensions/renderVueNodeView.ts","../../../src/extensions/LogicMergeTagNode.ts","../../../src/extensions/MergeTagNodeView.vue","../../../src/extensions/MergeTagNodeView.vue","../../../src/extensions/MergeTagNode.ts"],"sourcesContent":["import { Extension } from \"@tiptap/core\";\n\nexport interface FontSizeOptions {\n types: string[];\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n fontSize: {\n setFontSize: (size: string) => ReturnType;\n unsetFontSize: () => ReturnType;\n };\n }\n}\n\nexport const FontSize = Extension.create<FontSizeOptions>({\n name: \"fontSize\",\n\n addOptions() {\n return {\n types: [\"textStyle\"],\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n fontSize: {\n default: null,\n parseHTML: (element) =>\n element.style.fontSize?.replace(/['\"]+/g, \"\") || null,\n renderHTML: (attributes) => {\n if (!attributes.fontSize) {\n return {};\n }\n return {\n style: `font-size: ${attributes.fontSize}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setFontSize:\n (size: string) =>\n ({ chain }) => {\n return chain().setMark(\"textStyle\", { fontSize: size }).run();\n },\n unsetFontSize:\n () =>\n ({ chain }) => {\n return chain()\n .setMark(\"textStyle\", { fontSize: null })\n .removeEmptyTextStyle()\n .run();\n },\n };\n },\n});\n","import { Extension } from \"@tiptap/core\";\n\nexport interface LetterSpacingOptions {\n types: string[];\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n letterSpacing: {\n setLetterSpacing: (spacing: string) => ReturnType;\n unsetLetterSpacing: () => ReturnType;\n };\n }\n}\n\nexport const LetterSpacing = Extension.create<LetterSpacingOptions>({\n name: \"letterSpacing\",\n\n addOptions() {\n return {\n types: [\"textStyle\"],\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n letterSpacing: {\n default: null,\n parseHTML: (element) =>\n element.style.letterSpacing?.replace(/['\"]+/g, \"\") || null,\n renderHTML: (attributes) => {\n if (!attributes.letterSpacing) {\n return {};\n }\n return {\n style: `letter-spacing: ${attributes.letterSpacing}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setLetterSpacing:\n (spacing: string) =>\n ({ chain }) => {\n return chain().setMark(\"textStyle\", { letterSpacing: spacing }).run();\n },\n unsetLetterSpacing:\n () =>\n ({ chain }) => {\n return chain()\n .setMark(\"textStyle\", { letterSpacing: null })\n .removeEmptyTextStyle()\n .run();\n },\n };\n },\n});\n","import { Extension } from \"@tiptap/core\";\n\nexport interface LineHeightOptions {\n types: string[];\n defaultLineHeight: string;\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n lineHeight: {\n setLineHeight: (lineHeight: string) => ReturnType;\n unsetLineHeight: () => ReturnType;\n };\n }\n}\n\nexport const LineHeight = Extension.create<LineHeightOptions>({\n name: \"lineHeight\",\n\n addOptions() {\n return {\n types: [\"paragraph\"],\n defaultLineHeight: \"1.5\",\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n lineHeight: {\n default: null,\n parseHTML: (element) => element.style.lineHeight || null,\n renderHTML: (attributes) => {\n if (!attributes.lineHeight) {\n return {};\n }\n return {\n style: `line-height: ${attributes.lineHeight}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setLineHeight:\n (lineHeight: string) =>\n ({ commands }) => {\n return this.options.types.every((type) =>\n commands.updateAttributes(type, { lineHeight }),\n );\n },\n unsetLineHeight:\n () =>\n ({ commands }) => {\n return this.options.types.every((type) =>\n commands.resetAttributes(type, \"lineHeight\"),\n );\n },\n };\n },\n});\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n} from \"@templatical/types\";\nimport type { Editor } from \"@tiptap/core\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n value: string;\n keyword: string;\n };\n };\n editor: Editor;\n getPos: () => number;\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { syntax } = useMergeTag();\nconst { t } = useI18n();\n\nconst isValid = computed(() =>\n isLogicMergeTagValue(props.node.attrs.value, syntax),\n);\nconst displayKeyword = computed(() =>\n getLogicMergeTagKeyword(props.node.attrs.value, syntax),\n);\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\nlet handled = false;\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n handled = false;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n if (handled) {\n return;\n }\n handled = true;\n\n const newValue = editValue.value.trim();\n if (!newValue) {\n isEditing.value = false;\n return;\n }\n\n if (newValue !== props.node.attrs.value) {\n props.updateAttributes({\n value: newValue,\n keyword: isLogicMergeTagValue(newValue, syntax)\n ? getLogicMergeTagKeyword(newValue, syntax)\n : \"\",\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n :class=\"\n isValid\n ? 'tpl-logic-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.8em] tpl:font-bold tpl:tracking-wide tpl:uppercase tpl:select-none'\n : ''\n \"\n :style=\"\n isValid\n ? 'background-color: transparent; border: 1.5px solid color-mix(in srgb, var(--tpl-primary) 50%, transparent); color: var(--tpl-primary);'\n : ''\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-40 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:normal-case tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode: valid merge tag -->\n <span\n v-else-if=\"isValid\"\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayKeyword }}\n </span>\n <!-- Display mode: invalid (plain text) -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ node.attrs.value }}\n </span>\n <button\n v-if=\"isValid\"\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n} from \"@templatical/types\";\nimport type { Editor } from \"@tiptap/core\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n value: string;\n keyword: string;\n };\n };\n editor: Editor;\n getPos: () => number;\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { syntax } = useMergeTag();\nconst { t } = useI18n();\n\nconst isValid = computed(() =>\n isLogicMergeTagValue(props.node.attrs.value, syntax),\n);\nconst displayKeyword = computed(() =>\n getLogicMergeTagKeyword(props.node.attrs.value, syntax),\n);\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\nlet handled = false;\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n handled = false;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n if (handled) {\n return;\n }\n handled = true;\n\n const newValue = editValue.value.trim();\n if (!newValue) {\n isEditing.value = false;\n return;\n }\n\n if (newValue !== props.node.attrs.value) {\n props.updateAttributes({\n value: newValue,\n keyword: isLogicMergeTagValue(newValue, syntax)\n ? getLogicMergeTagKeyword(newValue, syntax)\n : \"\",\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n :class=\"\n isValid\n ? 'tpl-logic-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.8em] tpl:font-bold tpl:tracking-wide tpl:uppercase tpl:select-none'\n : ''\n \"\n :style=\"\n isValid\n ? 'background-color: transparent; border: 1.5px solid color-mix(in srgb, var(--tpl-primary) 50%, transparent); color: var(--tpl-primary);'\n : ''\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-40 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:normal-case tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode: valid merge tag -->\n <span\n v-else-if=\"isValid\"\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayKeyword }}\n </span>\n <!-- Display mode: invalid (plain text) -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ node.attrs.value }}\n </span>\n <button\n v-if=\"isValid\"\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","import type { Editor } from \"@tiptap/core\";\n\n/**\n * Checks whether a TipTap node of the given type is selected, or if the cursor\n * is immediately adjacent to one (for Backspace/Delete handling).\n *\n * Shared by MergeTagNode and LogicMergeTagNode keyboard shortcuts.\n */\nexport function isNodeSelected(editor: Editor, nodeTypeName: string): boolean {\n const { selection } = editor.state;\n const { $from, $to } = selection;\n\n // Check if selection contains a node of this type\n let found = false;\n editor.state.doc.nodesBetween($from.pos, $to.pos, (node) => {\n if (node.type.name === nodeTypeName) {\n found = true;\n return false;\n }\n });\n\n if (found) {\n return true;\n }\n\n // Check if cursor is right after the node (for Backspace)\n if ($from.pos > 0 && $from.nodeBefore?.type.name === nodeTypeName) {\n return true;\n }\n\n // Check if cursor is right before the node (for Delete)\n if ($from.nodeAfter?.type.name === nodeTypeName) {\n return true;\n }\n\n return false;\n}\n","import type { Component } from \"vue\";\nimport { VueNodeViewRenderer } from \"@tiptap/vue-3\";\n\n/**\n * Typed wrapper for VueNodeViewRenderer that handles the known type mismatch\n * between Vue SFC default exports and TipTap's expected component type.\n */\nexport function renderVueNodeView(component: Component) {\n return VueNodeViewRenderer(\n component as Parameters<typeof VueNodeViewRenderer>[0],\n );\n}\n","import LogicMergeTagNodeView from \"./LogicMergeTagNodeView.vue\";\nimport type { SyntaxPreset } from \"@templatical/types\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n SYNTAX_PRESETS,\n} from \"@templatical/types\";\nimport { InputRule, mergeAttributes, Node, PasteRule } from \"@tiptap/core\";\nimport { isNodeSelected } from \"./isNodeSelected\";\nimport { renderVueNodeView } from \"./renderVueNodeView\";\n\nexport interface LogicMergeTagNodeOptions {\n syntax: SyntaxPreset;\n}\n\nexport const LogicMergeTagNode = Node.create<LogicMergeTagNodeOptions>({\n name: \"logicMergeTagNode\",\n\n group: \"inline\",\n\n inline: true,\n\n atom: true,\n\n addOptions() {\n return {\n syntax: SYNTAX_PRESETS.liquid,\n };\n },\n\n addAttributes() {\n return {\n value: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-logic-merge-tag\") || \"\",\n },\n keyword: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-keyword\") || element.textContent || \"\",\n },\n };\n },\n\n parseHTML() {\n return [\n {\n tag: \"span[data-logic-merge-tag]\",\n },\n ];\n },\n\n renderHTML({ node, HTMLAttributes }) {\n if (!isLogicMergeTagValue(node.attrs.value, this.options.syntax)) {\n return [\"span\", {}, node.attrs.value];\n }\n\n const keyword = getLogicMergeTagKeyword(\n node.attrs.value,\n this.options.syntax,\n );\n\n return [\n \"span\",\n mergeAttributes(HTMLAttributes, {\n \"data-logic-merge-tag\": node.attrs.value,\n \"data-keyword\": keyword,\n }),\n keyword,\n ];\n },\n\n addNodeView() {\n return renderVueNodeView(LogicMergeTagNodeView);\n },\n\n addKeyboardShortcuts() {\n return {\n Backspace: () => isNodeSelected(this.editor, this.name),\n Delete: () => isNodeSelected(this.editor, this.name),\n };\n },\n\n addInputRules() {\n const inputRegex = new RegExp(this.options.syntax.logic.source + \"$\", \"\");\n\n return [\n new InputRule({\n find: inputRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n if (!isLogicMergeTagValue(fullValue, this.options.syntax)) {\n return;\n }\n\n const keyword = getLogicMergeTagKeyword(\n fullValue,\n this.options.syntax,\n );\n\n const node = this.type.create({\n value: fullValue,\n keyword,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n\n addPasteRules() {\n const pasteRegex = new RegExp(this.options.syntax.logic.source, \"g\");\n\n return [\n new PasteRule({\n find: pasteRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n if (!isLogicMergeTagValue(fullValue, this.options.syntax)) {\n return;\n }\n\n const keyword = getLogicMergeTagKeyword(\n fullValue,\n this.options.syntax,\n );\n\n const node = this.type.create({\n value: fullValue,\n keyword,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n});\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n label: string;\n value: string;\n };\n };\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { getMergeTagLabel } = useMergeTag();\nconst { t } = useI18n();\n\nconst displayLabel = computed(() => getMergeTagLabel(props.node.attrs.value));\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n const newValue = editValue.value.trim();\n if (newValue && newValue !== props.node.attrs.value) {\n // Update with new value and derive label from it\n props.updateAttributes({\n value: newValue,\n label: getMergeTagLabel(newValue),\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n class=\"tpl-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.9em] tpl:font-medium tpl:select-none tpl:text-[var(--tpl-primary)]\"\n style=\"\n background-color: color-mix(in srgb, var(--tpl-primary) 20%, transparent);\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-32 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayLabel }}\n </span>\n <button\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n label: string;\n value: string;\n };\n };\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { getMergeTagLabel } = useMergeTag();\nconst { t } = useI18n();\n\nconst displayLabel = computed(() => getMergeTagLabel(props.node.attrs.value));\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n const newValue = editValue.value.trim();\n if (newValue && newValue !== props.node.attrs.value) {\n // Update with new value and derive label from it\n props.updateAttributes({\n value: newValue,\n label: getMergeTagLabel(newValue),\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n class=\"tpl-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.9em] tpl:font-medium tpl:select-none tpl:text-[var(--tpl-primary)]\"\n style=\"\n background-color: color-mix(in srgb, var(--tpl-primary) 20%, transparent);\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-32 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayLabel }}\n </span>\n <button\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","import MergeTagNodeView from \"./MergeTagNodeView.vue\";\nimport type { MergeTag, SyntaxPreset } from \"@templatical/types\";\nimport { getMergeTagLabel, SYNTAX_PRESETS } from \"@templatical/types\";\nimport { InputRule, mergeAttributes, Node, PasteRule } from \"@tiptap/core\";\nimport { isNodeSelected } from \"./isNodeSelected\";\nimport { renderVueNodeView } from \"./renderVueNodeView\";\n\nexport interface MergeTagNodeOptions {\n mergeTags: MergeTag[];\n syntax: SyntaxPreset;\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n mergeTagNode: {\n insertMergeTag: (attrs: MergeTag) => ReturnType;\n };\n }\n}\n\nexport const MergeTagNode = Node.create<MergeTagNodeOptions>({\n name: \"mergeTagNode\",\n\n group: \"inline\",\n\n inline: true,\n\n atom: true,\n\n addOptions() {\n return {\n mergeTags: [],\n syntax: SYNTAX_PRESETS.liquid,\n };\n },\n\n addAttributes() {\n return {\n label: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-label\") || element.textContent || \"\",\n },\n value: {\n default: \"\",\n parseHTML: (element) => element.getAttribute(\"data-merge-tag\") || \"\",\n },\n };\n },\n\n parseHTML() {\n return [\n {\n tag: \"span[data-merge-tag]\",\n },\n ];\n },\n\n renderHTML({ node, HTMLAttributes }) {\n const label = getMergeTagLabel(node.attrs.value, this.options.mergeTags);\n\n return [\n \"span\",\n mergeAttributes(HTMLAttributes, {\n \"data-merge-tag\": node.attrs.value,\n \"data-label\": label,\n }),\n label,\n ];\n },\n\n addNodeView() {\n return renderVueNodeView(MergeTagNodeView);\n },\n\n addCommands() {\n return {\n insertMergeTag:\n (attrs: MergeTag) =>\n ({ commands }) => {\n return commands.insertContent({\n type: this.name,\n attrs,\n });\n },\n };\n },\n\n addKeyboardShortcuts() {\n return {\n Backspace: () => isNodeSelected(this.editor, this.name),\n Delete: () => isNodeSelected(this.editor, this.name),\n };\n },\n\n addInputRules() {\n const inputRegex = new RegExp(this.options.syntax.value.source + \"$\", \"\");\n\n return [\n new InputRule({\n find: inputRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n const label = getMergeTagLabel(fullValue, this.options.mergeTags);\n\n const node = this.type.create({\n label,\n value: fullValue,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n\n addPasteRules() {\n const pasteRegex = new RegExp(this.options.syntax.value.source, \"g\");\n\n return [\n new PasteRule({\n find: pasteRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n const label = getMergeTagLabel(fullValue, this.options.mergeTags);\n\n const node = this.type.create({\n label,\n value: fullValue,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n});\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"extensions-Bj7USRLr.js","names":[],"sources":["../../../src/extensions/FontSize.ts","../../../src/extensions/LetterSpacing.ts","../../../src/extensions/LineHeight.ts","../../../src/extensions/LogicMergeTagNodeView.vue","../../../src/extensions/LogicMergeTagNodeView.vue","../../../src/extensions/isNodeSelected.ts","../../../src/extensions/renderVueNodeView.ts","../../../src/extensions/LogicMergeTagNode.ts","../../../src/extensions/MergeTagNodeView.vue","../../../src/extensions/MergeTagNodeView.vue","../../../src/extensions/MergeTagNode.ts"],"sourcesContent":["import { Extension } from \"@tiptap/core\";\n\nexport interface FontSizeOptions {\n types: string[];\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n fontSize: {\n setFontSize: (size: string) => ReturnType;\n unsetFontSize: () => ReturnType;\n };\n }\n}\n\nexport const FontSize = Extension.create<FontSizeOptions>({\n name: \"fontSize\",\n\n addOptions() {\n return {\n types: [\"textStyle\"],\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n fontSize: {\n default: null,\n parseHTML: (element) =>\n element.style.fontSize?.replace(/['\"]+/g, \"\") || null,\n renderHTML: (attributes) => {\n if (!attributes.fontSize) {\n return {};\n }\n return {\n style: `font-size: ${attributes.fontSize}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setFontSize:\n (size: string) =>\n ({ chain }) => {\n return chain().setMark(\"textStyle\", { fontSize: size }).run();\n },\n unsetFontSize:\n () =>\n ({ chain }) => {\n return chain()\n .setMark(\"textStyle\", { fontSize: null })\n .removeEmptyTextStyle()\n .run();\n },\n };\n },\n});\n","import { Extension } from \"@tiptap/core\";\n\nexport interface LetterSpacingOptions {\n types: string[];\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n letterSpacing: {\n setLetterSpacing: (spacing: string) => ReturnType;\n unsetLetterSpacing: () => ReturnType;\n };\n }\n}\n\nexport const LetterSpacing = Extension.create<LetterSpacingOptions>({\n name: \"letterSpacing\",\n\n addOptions() {\n return {\n types: [\"textStyle\"],\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n letterSpacing: {\n default: null,\n parseHTML: (element) =>\n element.style.letterSpacing?.replace(/['\"]+/g, \"\") || null,\n renderHTML: (attributes) => {\n if (!attributes.letterSpacing) {\n return {};\n }\n return {\n style: `letter-spacing: ${attributes.letterSpacing}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setLetterSpacing:\n (spacing: string) =>\n ({ chain }) => {\n return chain().setMark(\"textStyle\", { letterSpacing: spacing }).run();\n },\n unsetLetterSpacing:\n () =>\n ({ chain }) => {\n return chain()\n .setMark(\"textStyle\", { letterSpacing: null })\n .removeEmptyTextStyle()\n .run();\n },\n };\n },\n});\n","import { Extension } from \"@tiptap/core\";\n\nexport interface LineHeightOptions {\n types: string[];\n defaultLineHeight: string;\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n lineHeight: {\n setLineHeight: (lineHeight: string) => ReturnType;\n unsetLineHeight: () => ReturnType;\n };\n }\n}\n\nexport const LineHeight = Extension.create<LineHeightOptions>({\n name: \"lineHeight\",\n\n addOptions() {\n return {\n types: [\"paragraph\"],\n defaultLineHeight: \"1.5\",\n };\n },\n\n addGlobalAttributes() {\n return [\n {\n types: this.options.types,\n attributes: {\n lineHeight: {\n default: null,\n parseHTML: (element) => element.style.lineHeight || null,\n renderHTML: (attributes) => {\n if (!attributes.lineHeight) {\n return {};\n }\n return {\n style: `line-height: ${attributes.lineHeight}`,\n };\n },\n },\n },\n },\n ];\n },\n\n addCommands() {\n return {\n setLineHeight:\n (lineHeight: string) =>\n ({ commands }) => {\n return this.options.types.every((type) =>\n commands.updateAttributes(type, { lineHeight }),\n );\n },\n unsetLineHeight:\n () =>\n ({ commands }) => {\n return this.options.types.every((type) =>\n commands.resetAttributes(type, \"lineHeight\"),\n );\n },\n };\n },\n});\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n} from \"@templatical/types\";\nimport type { Editor } from \"@tiptap/core\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n value: string;\n keyword: string;\n };\n };\n editor: Editor;\n getPos: () => number;\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { syntax } = useMergeTag();\nconst { t } = useI18n();\n\nconst isValid = computed(() =>\n isLogicMergeTagValue(props.node.attrs.value, syntax),\n);\nconst displayKeyword = computed(() =>\n getLogicMergeTagKeyword(props.node.attrs.value, syntax),\n);\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\nlet handled = false;\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n handled = false;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n if (handled) {\n return;\n }\n handled = true;\n\n const newValue = editValue.value.trim();\n if (!newValue) {\n isEditing.value = false;\n return;\n }\n\n if (newValue !== props.node.attrs.value) {\n props.updateAttributes({\n value: newValue,\n keyword: isLogicMergeTagValue(newValue, syntax)\n ? getLogicMergeTagKeyword(newValue, syntax)\n : \"\",\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n :class=\"\n isValid\n ? 'tpl-logic-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.8em] tpl:font-bold tpl:tracking-wide tpl:uppercase tpl:select-none'\n : ''\n \"\n :style=\"\n isValid\n ? 'background-color: transparent; border: 1.5px solid color-mix(in srgb, var(--tpl-primary) 50%, transparent); color: var(--tpl-primary);'\n : ''\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-40 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:normal-case tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode: valid merge tag -->\n <span\n v-else-if=\"isValid\"\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayKeyword }}\n </span>\n <!-- Display mode: invalid (plain text) -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ node.attrs.value }}\n </span>\n <button\n v-if=\"isValid\"\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n} from \"@templatical/types\";\nimport type { Editor } from \"@tiptap/core\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n value: string;\n keyword: string;\n };\n };\n editor: Editor;\n getPos: () => number;\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { syntax } = useMergeTag();\nconst { t } = useI18n();\n\nconst isValid = computed(() =>\n isLogicMergeTagValue(props.node.attrs.value, syntax),\n);\nconst displayKeyword = computed(() =>\n getLogicMergeTagKeyword(props.node.attrs.value, syntax),\n);\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\nlet handled = false;\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n handled = false;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n if (handled) {\n return;\n }\n handled = true;\n\n const newValue = editValue.value.trim();\n if (!newValue) {\n isEditing.value = false;\n return;\n }\n\n if (newValue !== props.node.attrs.value) {\n props.updateAttributes({\n value: newValue,\n keyword: isLogicMergeTagValue(newValue, syntax)\n ? getLogicMergeTagKeyword(newValue, syntax)\n : \"\",\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n :class=\"\n isValid\n ? 'tpl-logic-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.8em] tpl:font-bold tpl:tracking-wide tpl:uppercase tpl:select-none'\n : ''\n \"\n :style=\"\n isValid\n ? 'background-color: transparent; border: 1.5px solid color-mix(in srgb, var(--tpl-primary) 50%, transparent); color: var(--tpl-primary);'\n : ''\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-40 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:normal-case tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode: valid merge tag -->\n <span\n v-else-if=\"isValid\"\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayKeyword }}\n </span>\n <!-- Display mode: invalid (plain text) -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ node.attrs.value }}\n </span>\n <button\n v-if=\"isValid\"\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","import type { Editor } from \"@tiptap/core\";\n\n/**\n * Checks whether a TipTap node of the given type is selected, or if the cursor\n * is immediately adjacent to one (for Backspace/Delete handling).\n *\n * Shared by MergeTagNode and LogicMergeTagNode keyboard shortcuts.\n */\nexport function isNodeSelected(editor: Editor, nodeTypeName: string): boolean {\n const { selection } = editor.state;\n const { $from, $to } = selection;\n\n // Check if selection contains a node of this type\n let found = false;\n editor.state.doc.nodesBetween($from.pos, $to.pos, (node) => {\n if (node.type.name === nodeTypeName) {\n found = true;\n return false;\n }\n });\n\n if (found) {\n return true;\n }\n\n // Check if cursor is right after the node (for Backspace)\n if ($from.pos > 0 && $from.nodeBefore?.type.name === nodeTypeName) {\n return true;\n }\n\n // Check if cursor is right before the node (for Delete)\n if ($from.nodeAfter?.type.name === nodeTypeName) {\n return true;\n }\n\n return false;\n}\n","import type { Component } from \"vue\";\nimport { VueNodeViewRenderer } from \"@tiptap/vue-3\";\n\n/**\n * Typed wrapper for VueNodeViewRenderer that handles the known type mismatch\n * between Vue SFC default exports and TipTap's expected component type.\n */\nexport function renderVueNodeView(component: Component) {\n return VueNodeViewRenderer(\n component as Parameters<typeof VueNodeViewRenderer>[0],\n );\n}\n","import LogicMergeTagNodeView from \"./LogicMergeTagNodeView.vue\";\nimport type { SyntaxPreset } from \"@templatical/types\";\nimport {\n getLogicMergeTagKeyword,\n isLogicMergeTagValue,\n SYNTAX_PRESETS,\n} from \"@templatical/types\";\nimport { InputRule, mergeAttributes, Node, PasteRule } from \"@tiptap/core\";\nimport { isNodeSelected } from \"./isNodeSelected\";\nimport { renderVueNodeView } from \"./renderVueNodeView\";\n\nexport interface LogicMergeTagNodeOptions {\n syntax: SyntaxPreset;\n}\n\nexport const LogicMergeTagNode = Node.create<LogicMergeTagNodeOptions>({\n name: \"logicMergeTagNode\",\n\n group: \"inline\",\n\n inline: true,\n\n atom: true,\n\n addOptions() {\n return {\n syntax: SYNTAX_PRESETS.liquid,\n };\n },\n\n addAttributes() {\n return {\n value: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-logic-merge-tag\") || \"\",\n },\n keyword: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-keyword\") || element.textContent || \"\",\n },\n };\n },\n\n parseHTML() {\n return [\n {\n tag: \"span[data-logic-merge-tag]\",\n },\n ];\n },\n\n renderHTML({ node, HTMLAttributes }) {\n if (!isLogicMergeTagValue(node.attrs.value, this.options.syntax)) {\n return [\"span\", {}, node.attrs.value];\n }\n\n const keyword = getLogicMergeTagKeyword(\n node.attrs.value,\n this.options.syntax,\n );\n\n return [\n \"span\",\n mergeAttributes(HTMLAttributes, {\n \"data-logic-merge-tag\": node.attrs.value,\n \"data-keyword\": keyword,\n }),\n keyword,\n ];\n },\n\n addNodeView() {\n return renderVueNodeView(LogicMergeTagNodeView);\n },\n\n addKeyboardShortcuts() {\n return {\n Backspace: () => isNodeSelected(this.editor, this.name),\n Delete: () => isNodeSelected(this.editor, this.name),\n };\n },\n\n addInputRules() {\n const inputRegex = new RegExp(this.options.syntax.logic.source + \"$\", \"\");\n\n return [\n new InputRule({\n find: inputRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n if (!isLogicMergeTagValue(fullValue, this.options.syntax)) {\n return;\n }\n\n const keyword = getLogicMergeTagKeyword(\n fullValue,\n this.options.syntax,\n );\n\n const node = this.type.create({\n value: fullValue,\n keyword,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n\n addPasteRules() {\n const pasteRegex = new RegExp(this.options.syntax.logic.source, \"g\");\n\n return [\n new PasteRule({\n find: pasteRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n if (!isLogicMergeTagValue(fullValue, this.options.syntax)) {\n return;\n }\n\n const keyword = getLogicMergeTagKeyword(\n fullValue,\n this.options.syntax,\n );\n\n const node = this.type.create({\n value: fullValue,\n keyword,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n});\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n label: string;\n value: string;\n };\n };\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { getMergeTagLabel } = useMergeTag();\nconst { t } = useI18n();\n\nconst displayLabel = computed(() => getMergeTagLabel(props.node.attrs.value));\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n const newValue = editValue.value.trim();\n if (newValue && newValue !== props.node.attrs.value) {\n // Update with new value and derive label from it\n props.updateAttributes({\n value: newValue,\n label: getMergeTagLabel(newValue),\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n class=\"tpl-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.9em] tpl:font-medium tpl:select-none tpl:text-[var(--tpl-primary)]\"\n style=\"\n background-color: color-mix(in srgb, var(--tpl-primary) 20%, transparent);\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-32 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayLabel }}\n </span>\n <button\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","<script setup lang=\"ts\">\nimport { useI18n } from \"../composables/useI18n\";\nimport { useMergeTag } from \"../composables/useMergeTag\";\nimport { NodeViewWrapper } from \"@tiptap/vue-3\";\nimport { computed, nextTick, ref } from \"vue\";\n\nconst props = defineProps<{\n node: {\n attrs: {\n label: string;\n value: string;\n };\n };\n deleteNode: () => void;\n updateAttributes: (attrs: Record<string, unknown>) => void;\n}>();\n\nconst { getMergeTagLabel } = useMergeTag();\nconst { t } = useI18n();\n\nconst displayLabel = computed(() => getMergeTagLabel(props.node.attrs.value));\n\nconst isEditing = ref(false);\nconst editValue = ref(\"\");\nconst inputRef = ref<HTMLInputElement | null>(null);\n\nfunction startEditing(): void {\n editValue.value = props.node.attrs.value;\n isEditing.value = true;\n nextTick(() => {\n inputRef.value?.focus();\n inputRef.value?.select();\n });\n}\n\nfunction finishEditing(): void {\n const newValue = editValue.value.trim();\n if (newValue && newValue !== props.node.attrs.value) {\n // Update with new value and derive label from it\n props.updateAttributes({\n value: newValue,\n label: getMergeTagLabel(newValue),\n });\n }\n isEditing.value = false;\n}\n\nfunction handleKeydown(event: KeyboardEvent): void {\n if (event.key === \"Enter\") {\n event.preventDefault();\n finishEditing();\n } else if (event.key === \"Escape\") {\n isEditing.value = false;\n }\n}\n</script>\n\n<template>\n <NodeViewWrapper\n as=\"span\"\n class=\"tpl-merge-tag-node tpl:group tpl:mx-0.5 tpl:inline-flex tpl:items-center tpl:gap-1 tpl:rounded tpl:px-1.5 tpl:py-0.5 tpl:text-[0.9em] tpl:font-medium tpl:select-none tpl:text-[var(--tpl-primary)]\"\n style=\"\n background-color: color-mix(in srgb, var(--tpl-primary) 20%, transparent);\n \"\n contenteditable=\"false\"\n >\n <!-- Edit mode -->\n <input\n v-if=\"isEditing\"\n ref=\"inputRef\"\n v-model=\"editValue\"\n type=\"text\"\n class=\"tpl:w-32 tpl:rounded tpl:border-none tpl:bg-transparent tpl:px-0.5 tpl:py-0 tpl:text-[1em] tpl:font-medium tpl:outline-none tpl:text-[var(--tpl-primary)]\"\n @blur=\"finishEditing\"\n @keydown=\"handleKeydown\"\n />\n <!-- Display mode -->\n <span\n v-else\n role=\"button\"\n tabindex=\"0\"\n :aria-label=\"t.mergeTag.editValue\"\n class=\"tpl-tooltip tpl:cursor-pointer\"\n :data-tooltip=\"node.attrs.value\"\n @click.stop=\"startEditing\"\n @keydown.enter.stop=\"startEditing\"\n @keydown.space.prevent.stop=\"startEditing\"\n >\n {{ displayLabel }}\n </span>\n <button\n type=\"button\"\n :aria-label=\"t.mergeTag.deleteMergeTag\"\n class=\"tpl-merge-tag-delete tpl:flex tpl:size-5 tpl:cursor-pointer tpl:items-center tpl:justify-center tpl:rounded-full tpl:border-none tpl:bg-transparent tpl:p-0 tpl:opacity-60 tpl:transition-all hover:tpl:opacity-100 tpl:text-[var(--tpl-primary)]\"\n contenteditable=\"false\"\n @click.stop.prevent=\"deleteNode\"\n >\n <svg\n width=\"10\"\n height=\"10\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n stroke-width=\"3\"\n aria-hidden=\"true\"\n >\n <line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" />\n <line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" />\n </svg>\n </button>\n </NodeViewWrapper>\n</template>\n","import MergeTagNodeView from \"./MergeTagNodeView.vue\";\nimport type { MergeTag, SyntaxPreset } from \"@templatical/types\";\nimport { getMergeTagLabel, SYNTAX_PRESETS } from \"@templatical/types\";\nimport { InputRule, mergeAttributes, Node, PasteRule } from \"@tiptap/core\";\nimport { isNodeSelected } from \"./isNodeSelected\";\nimport { renderVueNodeView } from \"./renderVueNodeView\";\n\nexport interface MergeTagNodeOptions {\n mergeTags: MergeTag[];\n syntax: SyntaxPreset;\n}\n\ndeclare module \"@tiptap/core\" {\n interface Commands<ReturnType> {\n mergeTagNode: {\n insertMergeTag: (attrs: MergeTag) => ReturnType;\n };\n }\n}\n\nexport const MergeTagNode = Node.create<MergeTagNodeOptions>({\n name: \"mergeTagNode\",\n\n group: \"inline\",\n\n inline: true,\n\n atom: true,\n\n addOptions() {\n return {\n mergeTags: [],\n syntax: SYNTAX_PRESETS.liquid,\n };\n },\n\n addAttributes() {\n return {\n label: {\n default: \"\",\n parseHTML: (element) =>\n element.getAttribute(\"data-label\") || element.textContent || \"\",\n },\n value: {\n default: \"\",\n parseHTML: (element) => element.getAttribute(\"data-merge-tag\") || \"\",\n },\n };\n },\n\n parseHTML() {\n return [\n {\n tag: \"span[data-merge-tag]\",\n },\n ];\n },\n\n renderHTML({ node, HTMLAttributes }) {\n const label = getMergeTagLabel(node.attrs.value, this.options.mergeTags);\n\n return [\n \"span\",\n mergeAttributes(HTMLAttributes, {\n \"data-merge-tag\": node.attrs.value,\n \"data-label\": label,\n }),\n label,\n ];\n },\n\n addNodeView() {\n return renderVueNodeView(MergeTagNodeView);\n },\n\n addCommands() {\n return {\n insertMergeTag:\n (attrs: MergeTag) =>\n ({ commands }) => {\n return commands.insertContent({\n type: this.name,\n attrs,\n });\n },\n };\n },\n\n addKeyboardShortcuts() {\n return {\n Backspace: () => isNodeSelected(this.editor, this.name),\n Delete: () => isNodeSelected(this.editor, this.name),\n };\n },\n\n addInputRules() {\n const inputRegex = new RegExp(this.options.syntax.value.source + \"$\", \"\");\n\n return [\n new InputRule({\n find: inputRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n const label = getMergeTagLabel(fullValue, this.options.mergeTags);\n\n const node = this.type.create({\n label,\n value: fullValue,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n\n addPasteRules() {\n const pasteRegex = new RegExp(this.options.syntax.value.source, \"g\");\n\n return [\n new PasteRule({\n find: pasteRegex,\n handler: ({ state, range, match }) => {\n const fullValue = match[0];\n const label = getMergeTagLabel(fullValue, this.options.mergeTags);\n\n const node = this.type.create({\n label,\n value: fullValue,\n });\n\n state.tr.replaceWith(range.from, range.to, node);\n },\n }),\n ];\n },\n});\n"],"mappings":";;;;AAeA,IAAa,IAAW,EAAU,OAAwB;CACxD,MAAM;CAEN,aAAa;AACX,SAAO,EACL,OAAO,CAAC,YAAY,EACrB;;CAGH,sBAAsB;AACpB,SAAO,CACL;GACE,OAAO,KAAK,QAAQ;GACpB,YAAY,EACV,UAAU;IACR,SAAS;IACT,YAAY,MACV,EAAQ,MAAM,UAAU,QAAQ,UAAU,GAAG,IAAI;IACnD,aAAa,MACN,EAAW,WAGT,EACL,OAAO,cAAc,EAAW,YACjC,GAJQ,EAAE;IAMd,EACF;GACF,CACF;;CAGH,cAAc;AACZ,SAAO;GACL,cACG,OACA,EAAE,eACM,GAAO,CAAC,QAAQ,aAAa,EAAE,UAAU,GAAM,CAAC,CAAC,KAAK;GAEjE,sBAEG,EAAE,eACM,GAAO,CACX,QAAQ,aAAa,EAAE,UAAU,MAAM,CAAC,CACxC,sBAAsB,CACtB,KAAK;GAEb;;CAEJ,CAAC,ECjDW,IAAgB,EAAU,OAA6B;CAClE,MAAM;CAEN,aAAa;AACX,SAAO,EACL,OAAO,CAAC,YAAY,EACrB;;CAGH,sBAAsB;AACpB,SAAO,CACL;GACE,OAAO,KAAK,QAAQ;GACpB,YAAY,EACV,eAAe;IACb,SAAS;IACT,YAAY,MACV,EAAQ,MAAM,eAAe,QAAQ,UAAU,GAAG,IAAI;IACxD,aAAa,MACN,EAAW,gBAGT,EACL,OAAO,mBAAmB,EAAW,iBACtC,GAJQ,EAAE;IAMd,EACF;GACF,CACF;;CAGH,cAAc;AACZ,SAAO;GACL,mBACG,OACA,EAAE,eACM,GAAO,CAAC,QAAQ,aAAa,EAAE,eAAe,GAAS,CAAC,CAAC,KAAK;GAEzE,2BAEG,EAAE,eACM,GAAO,CACX,QAAQ,aAAa,EAAE,eAAe,MAAM,CAAC,CAC7C,sBAAsB,CACtB,KAAK;GAEb;;CAEJ,CAAC,EChDW,IAAa,EAAU,OAA0B;CAC5D,MAAM;CAEN,aAAa;AACX,SAAO;GACL,OAAO,CAAC,YAAY;GACpB,mBAAmB;GACpB;;CAGH,sBAAsB;AACpB,SAAO,CACL;GACE,OAAO,KAAK,QAAQ;GACpB,YAAY,EACV,YAAY;IACV,SAAS;IACT,YAAY,MAAY,EAAQ,MAAM,cAAc;IACpD,aAAa,MACN,EAAW,aAGT,EACL,OAAO,gBAAgB,EAAW,cACnC,GAJQ,EAAE;IAMd,EACF;GACF,CACF;;CAGH,cAAc;AACZ,SAAO;GACL,gBACG,OACA,EAAE,kBACM,KAAK,QAAQ,MAAM,OAAO,MAC/B,EAAS,iBAAiB,GAAM,EAAE,eAAY,CAAC,CAChD;GAEL,wBAEG,EAAE,kBACM,KAAK,QAAQ,MAAM,OAAO,MAC/B,EAAS,gBAAgB,GAAM,aAAa,CAC7C;GAEN;;CAEJ,CAAC;;;;;;;;;;;;;;ECvDF,IAAM,IAAQ,GAaR,EAAE,cAAW,GAAa,EAC1B,EAAE,SAAM,GAAS,EAEjB,IAAU,QACd,EAAqB,EAAM,KAAK,MAAM,OAAO,EAAO,CACrD,EACK,IAAiB,QACrB,EAAwB,EAAM,KAAK,MAAM,OAAO,EAAO,CACxD,EAEK,IAAY,EAAI,GAAM,EACtB,IAAY,EAAI,GAAG,EACnB,IAAW,EAA6B,KAAK,EAC/C,IAAU;EAEd,SAAS,IAAqB;AAI5B,GAHA,EAAU,QAAQ,EAAM,KAAK,MAAM,OACnC,IAAU,IACV,EAAU,QAAQ,IAClB,QAAe;AAEb,IADA,EAAS,OAAO,OAAO,EACvB,EAAS,OAAO,QAAQ;KACxB;;EAGJ,SAAS,IAAsB;AAC7B,OAAI,EACF;AAEF,OAAU;GAEV,IAAM,IAAW,EAAU,MAAM,MAAM;AACvC,OAAI,CAAC,GAAU;AACb,MAAU,QAAQ;AAClB;;AAWF,GARI,MAAa,EAAM,KAAK,MAAM,SAChC,EAAM,iBAAiB;IACrB,OAAO;IACP,SAAS,EAAqB,GAAU,EAAM,GAC1C,EAAwB,GAAU,EAAM,GACxC;IACL,CAAC,EAEJ,EAAU,QAAQ;;EAGpB,SAAS,EAAc,GAA4B;AACjD,GAAI,EAAM,QAAQ,WAChB,EAAM,gBAAgB,EACtB,GAAe,IACN,EAAM,QAAQ,aACvB,EAAU,QAAQ;;yBAMpB,EAuEkB,EAAA,EAAA,EAAA;GAtEhB,IAAG;GACF,OAAK,EAAS,EAAA,QAAA,8MAAA,GAAA;GAKd,OAAK,EAAS,EAAA,QAAA,2IAAA,GAAA;GAKf,iBAAgB;;oBAWd,CAPM,EAAA,QAAA,GAAA,GAAA,EADR,EAQE,SAAA;;aANI;IAAJ,KAAI;6CACc,QAAA;IAClB,MAAK;IACL,OAAM;IACL,QAAM;IACN,WAAS;wBAJD,EAAA,MAAS,CAAA,CAAA,GAQP,EAAA,SAAA,GAAA,EADb,EAYO,QAAA;;IAVL,MAAK;IACL,UAAS;IACR,cAAY,EAAA,EAAC,CAAC,SAAS;IACxB,OAAM;IACL,gBAAc,EAAA,KAAK,MAAM;IACzB,SAAK,EAAO,GAAY,CAAA,OAAA,CAAA;IACxB,WAAO,CAAA,EAAA,EAAa,GAAY,CAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,EAAA,EAAA,EACJ,GAAY,CAAA,WAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,CAAA;QAEtC,EAAA,MAAc,EAAA,IAAA,EAAA,KAAA,GAAA,EAGnB,EAUO,QAAA;;IARL,MAAK;IACL,UAAS;IACR,cAAY,EAAA,EAAC,CAAC,SAAS;IACvB,SAAK,EAAO,GAAY,CAAA,OAAA,CAAA;IACxB,WAAO,CAAA,EAAA,EAAa,GAAY,CAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,EAAA,EAAA,EACJ,GAAY,CAAA,WAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,CAAA;QAEtC,EAAA,KAAK,MAAM,MAAK,EAAA,IAAA,EAAA,GAGb,EAAA,SAAA,GAAA,EADR,EAoBS,UAAA;;IAlBP,MAAK;IACJ,cAAY,EAAA,EAAC,CAAC,SAAS;IACxB,OAAM;IACN,iBAAgB;IACf,SAAK,AAAA,EAAA,OAAA,GAAA,GAAA,MAAe,EAAA,cAAA,EAAA,WAAA,GAAA,EAAU,EAAA,CAAA,QAAA,UAAA,CAAA;oBAE/B,EAWM,OAAA;IAVJ,OAAM;IACN,QAAO;IACP,SAAQ;IACR,MAAK;IACL,QAAO;IACP,gBAAa;IACb,eAAY;OAEZ,EAAsC,QAAA;IAAhC,IAAG;IAAK,IAAG;IAAI,IAAG;IAAI,IAAG;OAC/B,EAAsC,QAAA;IAAhC,IAAG;IAAI,IAAG;IAAI,IAAG;IAAK,IAAG;;;;;;;;AE/IvC,SAAgB,EAAe,GAAgB,GAA+B;CAC5E,IAAM,EAAE,iBAAc,EAAO,OACvB,EAAE,UAAO,WAAQ,GAGnB,IAAQ;AAsBZ,QArBA,EAAO,MAAM,IAAI,aAAa,EAAM,KAAK,EAAI,MAAM,MAAS;AAC1D,MAAI,EAAK,KAAK,SAAS,EAErB,QADA,IAAQ,IACD;GAET,EAYF,GAVI,KAKA,EAAM,MAAM,KAAK,EAAM,YAAY,KAAK,SAAS,KAKjD,EAAM,WAAW,KAAK,SAAS;;;;ACxBrC,SAAgB,EAAkB,GAAsB;AACtD,QAAO,EACL,EACD;;;;ACKH,IAAa,IAAoB,EAAK,OAAiC;CACrE,MAAM;CAEN,OAAO;CAEP,QAAQ;CAER,MAAM;CAEN,aAAa;AACX,SAAO,EACL,QAAQ,EAAe,QACxB;;CAGH,gBAAgB;AACd,SAAO;GACL,OAAO;IACL,SAAS;IACT,YAAY,MACV,EAAQ,aAAa,uBAAuB,IAAI;IACnD;GACD,SAAS;IACP,SAAS;IACT,YAAY,MACV,EAAQ,aAAa,eAAe,IAAI,EAAQ,eAAe;IAClE;GACF;;CAGH,YAAY;AACV,SAAO,CACL,EACE,KAAK,8BACN,CACF;;CAGH,WAAW,EAAE,SAAM,qBAAkB;AACnC,MAAI,CAAC,EAAqB,EAAK,MAAM,OAAO,KAAK,QAAQ,OAAO,CAC9D,QAAO;GAAC;GAAQ,EAAE;GAAE,EAAK,MAAM;GAAM;EAGvC,IAAM,IAAU,EACd,EAAK,MAAM,OACX,KAAK,QAAQ,OACd;AAED,SAAO;GACL;GACA,EAAgB,GAAgB;IAC9B,wBAAwB,EAAK,MAAM;IACnC,gBAAgB;IACjB,CAAC;GACF;GACD;;CAGH,cAAc;AACZ,SAAO,EAAkB,EAAsB;;CAGjD,uBAAuB;AACrB,SAAO;GACL,iBAAiB,EAAe,KAAK,QAAQ,KAAK,KAAK;GACvD,cAAc,EAAe,KAAK,QAAQ,KAAK,KAAK;GACrD;;CAGH,gBAAgB;AAGd,SAAO,CACL,IAAI,EAAU;GACZ,MAJmB,OAAO,KAAK,QAAQ,OAAO,MAAM,SAAS,KAAK,GAAG;GAKrE,UAAU,EAAE,UAAO,UAAO,eAAY;IACpC,IAAM,IAAY,EAAM;AACxB,QAAI,CAAC,EAAqB,GAAW,KAAK,QAAQ,OAAO,CACvD;IAGF,IAAM,IAAU,EACd,GACA,KAAK,QAAQ,OACd,EAEK,IAAO,KAAK,KAAK,OAAO;KAC5B,OAAO;KACP;KACD,CAAC;AAEF,MAAM,GAAG,YAAY,EAAM,MAAM,EAAM,IAAI,EAAK;;GAEnD,CAAC,CACH;;CAGH,gBAAgB;AAGd,SAAO,CACL,IAAI,EAAU;GACZ,MAJe,IAAI,OAAO,KAAK,QAAQ,OAAO,MAAM,QAAQ,IAAI;GAKhE,UAAU,EAAE,UAAO,UAAO,eAAY;IACpC,IAAM,IAAY,EAAM;AACxB,QAAI,CAAC,EAAqB,GAAW,KAAK,QAAQ,OAAO,CACvD;IAGF,IAAM,IAAU,EACd,GACA,KAAK,QAAQ,OACd,EAEK,IAAO,KAAK,KAAK,OAAO;KAC5B,OAAO;KACP;KACD,CAAC;AAEF,MAAM,GAAG,YAAY,EAAM,MAAM,EAAM,IAAI,EAAK;;GAEnD,CAAC,CACH;;CAEJ,CAAC;;;;;;;;;;;;ECrIF,IAAM,IAAQ,GAWR,EAAE,wBAAqB,GAAa,EACpC,EAAE,SAAM,GAAS,EAEjB,IAAe,QAAe,EAAiB,EAAM,KAAK,MAAM,MAAM,CAAC,EAEvE,IAAY,EAAI,GAAM,EACtB,IAAY,EAAI,GAAG,EACnB,IAAW,EAA6B,KAAK;EAEnD,SAAS,IAAqB;AAG5B,GAFA,EAAU,QAAQ,EAAM,KAAK,MAAM,OACnC,EAAU,QAAQ,IAClB,QAAe;AAEb,IADA,EAAS,OAAO,OAAO,EACvB,EAAS,OAAO,QAAQ;KACxB;;EAGJ,SAAS,IAAsB;GAC7B,IAAM,IAAW,EAAU,MAAM,MAAM;AAQvC,GAPI,KAAY,MAAa,EAAM,KAAK,MAAM,SAE5C,EAAM,iBAAiB;IACrB,OAAO;IACP,OAAO,EAAiB,EAAS;IAClC,CAAC,EAEJ,EAAU,QAAQ;;EAGpB,SAAS,EAAc,GAA4B;AACjD,GAAI,EAAM,QAAQ,WAChB,EAAM,gBAAgB,EACtB,GAAe,IACN,EAAM,QAAQ,aACvB,EAAU,QAAQ;;yBAMpB,EAoDkB,EAAA,EAAA,EAAA;GAnDhB,IAAG;GACH,OAAM;GACN,OAAA,EAAA,oBAAA,2DAEC;GACD,iBAAgB;;oBAWd,CAPM,EAAA,QAAA,GAAA,GAAA,EADR,EAQE,SAAA;;aANI;IAAJ,KAAI;6CACc,QAAA;IAClB,MAAK;IACL,OAAM;IACL,QAAM;IACN,WAAS;wBAJD,EAAA,MAAS,CAAA,CAAA,IAAA,GAAA,EAOpB,EAYO,QAAA;;IAVL,MAAK;IACL,UAAS;IACR,cAAY,EAAA,EAAC,CAAC,SAAS;IACxB,OAAM;IACL,gBAAc,EAAA,KAAK,MAAM;IACzB,SAAK,EAAO,GAAY,CAAA,OAAA,CAAA;IACxB,WAAO,CAAA,EAAA,EAAa,GAAY,CAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,EAAA,EAAA,EACJ,GAAY,CAAA,WAAA,OAAA,CAAA,EAAA,CAAA,QAAA,CAAA,CAAA;QAEtC,EAAA,MAAY,EAAA,IAAA,EAAA,GAEjB,EAmBS,UAAA;IAlBP,MAAK;IACJ,cAAY,EAAA,EAAC,CAAC,SAAS;IACxB,OAAM;IACN,iBAAgB;IACf,SAAK,AAAA,EAAA,OAAA,GAAA,GAAA,MAAe,EAAA,cAAA,EAAA,WAAA,GAAA,EAAU,EAAA,CAAA,QAAA,UAAA,CAAA;oBAE/B,EAWM,OAAA;IAVJ,OAAM;IACN,QAAO;IACP,SAAQ;IACR,MAAK;IACL,QAAO;IACP,gBAAa;IACb,eAAY;OAEZ,EAAsC,QAAA;IAAhC,IAAG;IAAK,IAAG;IAAI,IAAG;IAAI,IAAG;OAC/B,EAAsC,QAAA;IAAhC,IAAG;IAAI,IAAG;IAAI,IAAG;IAAK,IAAG;;;;;IEvF1B,IAAe,EAAK,OAA4B;CAC3D,MAAM;CAEN,OAAO;CAEP,QAAQ;CAER,MAAM;CAEN,aAAa;AACX,SAAO;GACL,WAAW,EAAE;GACb,QAAQ,EAAe;GACxB;;CAGH,gBAAgB;AACd,SAAO;GACL,OAAO;IACL,SAAS;IACT,YAAY,MACV,EAAQ,aAAa,aAAa,IAAI,EAAQ,eAAe;IAChE;GACD,OAAO;IACL,SAAS;IACT,YAAY,MAAY,EAAQ,aAAa,iBAAiB,IAAI;IACnE;GACF;;CAGH,YAAY;AACV,SAAO,CACL,EACE,KAAK,wBACN,CACF;;CAGH,WAAW,EAAE,SAAM,qBAAkB;EACnC,IAAM,IAAQ,EAAiB,EAAK,MAAM,OAAO,KAAK,QAAQ,UAAU;AAExE,SAAO;GACL;GACA,EAAgB,GAAgB;IAC9B,kBAAkB,EAAK,MAAM;IAC7B,cAAc;IACf,CAAC;GACF;GACD;;CAGH,cAAc;AACZ,SAAO,EAAkB,EAAiB;;CAG5C,cAAc;AACZ,SAAO,EACL,iBACG,OACA,EAAE,kBACM,EAAS,cAAc;GAC5B,MAAM,KAAK;GACX;GACD,CAAC,EAEP;;CAGH,uBAAuB;AACrB,SAAO;GACL,iBAAiB,EAAe,KAAK,QAAQ,KAAK,KAAK;GACvD,cAAc,EAAe,KAAK,QAAQ,KAAK,KAAK;GACrD;;CAGH,gBAAgB;AAGd,SAAO,CACL,IAAI,EAAU;GACZ,MAJmB,OAAO,KAAK,QAAQ,OAAO,MAAM,SAAS,KAAK,GAAG;GAKrE,UAAU,EAAE,UAAO,UAAO,eAAY;IACpC,IAAM,IAAY,EAAM,IAClB,IAAQ,EAAiB,GAAW,KAAK,QAAQ,UAAU,EAE3D,IAAO,KAAK,KAAK,OAAO;KAC5B;KACA,OAAO;KACR,CAAC;AAEF,MAAM,GAAG,YAAY,EAAM,MAAM,EAAM,IAAI,EAAK;;GAEnD,CAAC,CACH;;CAGH,gBAAgB;AAGd,SAAO,CACL,IAAI,EAAU;GACZ,MAJe,IAAI,OAAO,KAAK,QAAQ,OAAO,MAAM,QAAQ,IAAI;GAKhE,UAAU,EAAE,UAAO,UAAO,eAAY;IACpC,IAAM,IAAY,EAAM,IAClB,IAAQ,EAAiB,GAAW,KAAK,QAAQ,UAAU,EAE3D,IAAO,KAAK,KAAK,OAAO;KAC5B;KACA,OAAO;KACR,CAAC;AAEF,MAAM,GAAG,YAAY,EAAM,MAAM,EAAM,IAAI,EAAK;;GAEnD,CAAC,CACH;;CAEJ,CAAC"}
|