@scrider/formatter 1.3.3 → 1.3.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/index.d.cts CHANGED
@@ -1292,6 +1292,65 @@ declare function validateDelta(delta: Delta, registry: Registry): boolean;
1292
1292
  */
1293
1293
  declare function cloneDelta(delta: Delta): Delta;
1294
1294
 
1295
+ /**
1296
+ * Document-level HTML presentation for deltaToHtml (clipboard, export).
1297
+ * Not stored in Delta — mirrors editor Settings (line spacing, first-line indent).
1298
+ */
1299
+ interface DocumentPresentation {
1300
+ /** Line spacing multiplier, e.g. 1.5 */
1301
+ lineSpacing?: number;
1302
+ /** First-line indent in centimeters, e.g. 1.25 */
1303
+ textIndentCm?: number;
1304
+ }
1305
+ interface ResolvedDocumentPresentation {
1306
+ lineSpacing: number | undefined;
1307
+ textIndentCm: number | undefined;
1308
+ }
1309
+ declare function resolveDocumentPresentation(presentation?: DocumentPresentation): ResolvedDocumentPresentation | undefined;
1310
+ declare function documentPresentationStyleParts(tag: string, resolved: ResolvedDocumentPresentation | undefined): string[];
1311
+
1312
+ /**
1313
+ * Simple Table HTML presentation options for deltaToHtml (clipboard, export).
1314
+ * Structural data stays in Delta (table-row, table-col-align); this only affects inline styles.
1315
+ */
1316
+ /** Column/cell horizontal alignment (GFM subset). */
1317
+ type TableCellAlign = 'left' | 'center' | 'right';
1318
+ /** Optional styling when serializing Simple Tables to HTML. */
1319
+ interface TablePresentation {
1320
+ /** Full 1px border on all cell sides. When true, `line` is ignored. */
1321
+ grid?: boolean;
1322
+ /** Bottom border only (DeepSeek / ChatGPT). Used when `grid` is not true. */
1323
+ line?: boolean;
1324
+ /** Border color as explicit hex (e.g. `#e7e7e7`). */
1325
+ borderColor?: string;
1326
+ /** Background on header cells (`th`). */
1327
+ headerShade?: boolean;
1328
+ /** Background on even table rows in the body (see `isZebraBodyRow`). */
1329
+ zebraRows?: boolean;
1330
+ /** `font-weight: bold` on `th`. */
1331
+ headerBold?: boolean;
1332
+ /** `text-align: center` on `th` (GitHub-style header). */
1333
+ headerCenter?: boolean;
1334
+ /**
1335
+ * Alignment for cells without `table-col-align` in Delta. Never overrides GFM column align.
1336
+ * @default 'left'
1337
+ */
1338
+ defaultCellAlign?: TableCellAlign;
1339
+ }
1340
+ interface ResolvedTablePresentation {
1341
+ grid: boolean;
1342
+ line: boolean;
1343
+ borderColor: string;
1344
+ headerShade: boolean;
1345
+ zebraRows: boolean;
1346
+ headerBold: boolean;
1347
+ headerCenter: boolean;
1348
+ defaultCellAlign: TableCellAlign;
1349
+ }
1350
+ declare function resolveTablePresentation(presentation?: TablePresentation): ResolvedTablePresentation;
1351
+ /** Match CSS `tr:nth-child(even) td` when header rows precede body in `<table>`. */
1352
+ declare function isZebraBodyRow(headerRowCount: number, bodyRowIndex: number): boolean;
1353
+
1295
1354
  /**
1296
1355
  * Delta → HTML Conversion
1297
1356
  *
@@ -1351,6 +1410,16 @@ interface DeltaToHtmlOptions {
1351
1410
  * This enables extensibility without modifying converter internals.
1352
1411
  */
1353
1412
  registry?: Registry;
1413
+ /**
1414
+ * Simple Table presentation (borders, shades, header style) as inline CSS for
1415
+ * Office/HTML export and clipboard. Does not change Delta; omitted = legacy bare `<table>`.
1416
+ */
1417
+ tablePresentation?: TablePresentation;
1418
+ /**
1419
+ * Document-level paragraph styles (line spacing, first-line indent) as inline CSS for
1420
+ * Office/HTML export and clipboard. Does not change Delta.
1421
+ */
1422
+ documentPresentation?: DocumentPresentation;
1354
1423
  }
1355
1424
  /**
1356
1425
  * Convert a Delta to an HTML string
@@ -1816,4 +1885,4 @@ declare function isTableNewlineOp(op: Op | undefined): boolean;
1816
1885
  */
1817
1886
  declare function extractTableRegion(ops: readonly Op[], hintOpIdx: number): TableRegion | null;
1818
1887
 
1819
- export { ALERT_TYPES, type AlertBlockData, type AlertType, type AlignType, BOX_FLOAT_VALUES, BOX_OVERFLOW_VALUES, type BlockContext, type BlockHandler, BlockHandlerRegistry, type BlockRenderOptions, type BoxBlockData, type BoxFloat, type BoxOpAttributes, type BoxOverflow, BrowserDOMAdapter, type CellAlign, type CellData, type ColumnsBlockData, type DOMAdapter, type DOMDocument, type DOMDocumentFragment, type DOMElement, type DOMNode, type DOMNodeList, type DeltaToHtmlOptions, type DeltaToMarkdownOptions, type FootnotesBlockData, type Format, type FormatDefinition, type FormatMatchResult, type FormatScope, type HtmlToDeltaOptions, type ListType, type MarkdownToDeltaOptions, NODE_TYPE, NodeDOMAdapter, Registry, type SanitizeOptions, type TableBlockData, type TableColAlignType, type TableRegion, alertBlockHandler, alignFormat, backgroundFormat, blockFormat, blockquoteFormat, boldFormat, boxBlockHandler, browserAdapter, cloneDelta, codeBlockFormat, codeFormat, colorFormat, columnsBlockHandler, createDefaultBlockHandlers, createDefaultRegistry, defaultBlockFormats, defaultEmbedFormats, defaultFormats, defaultInlineFormats, deltaToHtml, deltaToMarkdown, dividerFormat, escapeHtml, extractBoxOpAttributes, extractTableRegion, fontFormat, footnoteRefFormat, footnotesBlockHandler, formulaFormat, getAdapter, getNamedColors, headerFormat, headerIdFormat, htmlToDelta, imageFormat, indentFormat, isAdapterAvailable, isElement, isRemarkAvailable, isTableNewlineOp, isTextNode, isValidColor, isValidHexColor, italicFormat, kbdFormat, linkFormat, listFormat, markFormat, markdownToDelta, markdownToDeltaSync, nodeAdapter, normalizeDelta, preloadRemark, sanitizeDelta, sizeFormat, slugify, slugifyWithDedup, softBreakFormat, strikeFormat, subscriptFormat, superscriptFormat, tableBlockHandler, tableColAlignFormat, tableColFormat, tableHeaderFormat, tableRowFormat, toHexColor, underlineFormat, unescapeHtml, validateDelta, videoFormat };
1888
+ export { ALERT_TYPES, type AlertBlockData, type AlertType, type AlignType, BOX_FLOAT_VALUES, BOX_OVERFLOW_VALUES, type BlockContext, type BlockHandler, BlockHandlerRegistry, type BlockRenderOptions, type BoxBlockData, type BoxFloat, type BoxOpAttributes, type BoxOverflow, BrowserDOMAdapter, type CellAlign, type CellData, type ColumnsBlockData, type DOMAdapter, type DOMDocument, type DOMDocumentFragment, type DOMElement, type DOMNode, type DOMNodeList, type DeltaToHtmlOptions, type DeltaToMarkdownOptions, type DocumentPresentation, type FootnotesBlockData, type Format, type FormatDefinition, type FormatMatchResult, type FormatScope, type HtmlToDeltaOptions, type ListType, type MarkdownToDeltaOptions, NODE_TYPE, NodeDOMAdapter, Registry, type ResolvedDocumentPresentation, type ResolvedTablePresentation, type SanitizeOptions, type TableBlockData, type TableCellAlign, type TableColAlignType, type TablePresentation, type TableRegion, alertBlockHandler, alignFormat, backgroundFormat, blockFormat, blockquoteFormat, boldFormat, boxBlockHandler, browserAdapter, cloneDelta, codeBlockFormat, codeFormat, colorFormat, columnsBlockHandler, createDefaultBlockHandlers, createDefaultRegistry, defaultBlockFormats, defaultEmbedFormats, defaultFormats, defaultInlineFormats, deltaToHtml, deltaToMarkdown, dividerFormat, documentPresentationStyleParts, escapeHtml, extractBoxOpAttributes, extractTableRegion, fontFormat, footnoteRefFormat, footnotesBlockHandler, formulaFormat, getAdapter, getNamedColors, headerFormat, headerIdFormat, htmlToDelta, imageFormat, indentFormat, isAdapterAvailable, isElement, isRemarkAvailable, isTableNewlineOp, isTextNode, isValidColor, isValidHexColor, isZebraBodyRow, italicFormat, kbdFormat, linkFormat, listFormat, markFormat, markdownToDelta, markdownToDeltaSync, nodeAdapter, normalizeDelta, preloadRemark, resolveDocumentPresentation, resolveTablePresentation, sanitizeDelta, sizeFormat, slugify, slugifyWithDedup, softBreakFormat, strikeFormat, subscriptFormat, superscriptFormat, tableBlockHandler, tableColAlignFormat, tableColFormat, tableHeaderFormat, tableRowFormat, toHexColor, underlineFormat, unescapeHtml, validateDelta, videoFormat };
package/dist/index.d.ts CHANGED
@@ -1292,6 +1292,65 @@ declare function validateDelta(delta: Delta, registry: Registry): boolean;
1292
1292
  */
1293
1293
  declare function cloneDelta(delta: Delta): Delta;
1294
1294
 
1295
+ /**
1296
+ * Document-level HTML presentation for deltaToHtml (clipboard, export).
1297
+ * Not stored in Delta — mirrors editor Settings (line spacing, first-line indent).
1298
+ */
1299
+ interface DocumentPresentation {
1300
+ /** Line spacing multiplier, e.g. 1.5 */
1301
+ lineSpacing?: number;
1302
+ /** First-line indent in centimeters, e.g. 1.25 */
1303
+ textIndentCm?: number;
1304
+ }
1305
+ interface ResolvedDocumentPresentation {
1306
+ lineSpacing: number | undefined;
1307
+ textIndentCm: number | undefined;
1308
+ }
1309
+ declare function resolveDocumentPresentation(presentation?: DocumentPresentation): ResolvedDocumentPresentation | undefined;
1310
+ declare function documentPresentationStyleParts(tag: string, resolved: ResolvedDocumentPresentation | undefined): string[];
1311
+
1312
+ /**
1313
+ * Simple Table HTML presentation options for deltaToHtml (clipboard, export).
1314
+ * Structural data stays in Delta (table-row, table-col-align); this only affects inline styles.
1315
+ */
1316
+ /** Column/cell horizontal alignment (GFM subset). */
1317
+ type TableCellAlign = 'left' | 'center' | 'right';
1318
+ /** Optional styling when serializing Simple Tables to HTML. */
1319
+ interface TablePresentation {
1320
+ /** Full 1px border on all cell sides. When true, `line` is ignored. */
1321
+ grid?: boolean;
1322
+ /** Bottom border only (DeepSeek / ChatGPT). Used when `grid` is not true. */
1323
+ line?: boolean;
1324
+ /** Border color as explicit hex (e.g. `#e7e7e7`). */
1325
+ borderColor?: string;
1326
+ /** Background on header cells (`th`). */
1327
+ headerShade?: boolean;
1328
+ /** Background on even table rows in the body (see `isZebraBodyRow`). */
1329
+ zebraRows?: boolean;
1330
+ /** `font-weight: bold` on `th`. */
1331
+ headerBold?: boolean;
1332
+ /** `text-align: center` on `th` (GitHub-style header). */
1333
+ headerCenter?: boolean;
1334
+ /**
1335
+ * Alignment for cells without `table-col-align` in Delta. Never overrides GFM column align.
1336
+ * @default 'left'
1337
+ */
1338
+ defaultCellAlign?: TableCellAlign;
1339
+ }
1340
+ interface ResolvedTablePresentation {
1341
+ grid: boolean;
1342
+ line: boolean;
1343
+ borderColor: string;
1344
+ headerShade: boolean;
1345
+ zebraRows: boolean;
1346
+ headerBold: boolean;
1347
+ headerCenter: boolean;
1348
+ defaultCellAlign: TableCellAlign;
1349
+ }
1350
+ declare function resolveTablePresentation(presentation?: TablePresentation): ResolvedTablePresentation;
1351
+ /** Match CSS `tr:nth-child(even) td` when header rows precede body in `<table>`. */
1352
+ declare function isZebraBodyRow(headerRowCount: number, bodyRowIndex: number): boolean;
1353
+
1295
1354
  /**
1296
1355
  * Delta → HTML Conversion
1297
1356
  *
@@ -1351,6 +1410,16 @@ interface DeltaToHtmlOptions {
1351
1410
  * This enables extensibility without modifying converter internals.
1352
1411
  */
1353
1412
  registry?: Registry;
1413
+ /**
1414
+ * Simple Table presentation (borders, shades, header style) as inline CSS for
1415
+ * Office/HTML export and clipboard. Does not change Delta; omitted = legacy bare `<table>`.
1416
+ */
1417
+ tablePresentation?: TablePresentation;
1418
+ /**
1419
+ * Document-level paragraph styles (line spacing, first-line indent) as inline CSS for
1420
+ * Office/HTML export and clipboard. Does not change Delta.
1421
+ */
1422
+ documentPresentation?: DocumentPresentation;
1354
1423
  }
1355
1424
  /**
1356
1425
  * Convert a Delta to an HTML string
@@ -1816,4 +1885,4 @@ declare function isTableNewlineOp(op: Op | undefined): boolean;
1816
1885
  */
1817
1886
  declare function extractTableRegion(ops: readonly Op[], hintOpIdx: number): TableRegion | null;
1818
1887
 
1819
- export { ALERT_TYPES, type AlertBlockData, type AlertType, type AlignType, BOX_FLOAT_VALUES, BOX_OVERFLOW_VALUES, type BlockContext, type BlockHandler, BlockHandlerRegistry, type BlockRenderOptions, type BoxBlockData, type BoxFloat, type BoxOpAttributes, type BoxOverflow, BrowserDOMAdapter, type CellAlign, type CellData, type ColumnsBlockData, type DOMAdapter, type DOMDocument, type DOMDocumentFragment, type DOMElement, type DOMNode, type DOMNodeList, type DeltaToHtmlOptions, type DeltaToMarkdownOptions, type FootnotesBlockData, type Format, type FormatDefinition, type FormatMatchResult, type FormatScope, type HtmlToDeltaOptions, type ListType, type MarkdownToDeltaOptions, NODE_TYPE, NodeDOMAdapter, Registry, type SanitizeOptions, type TableBlockData, type TableColAlignType, type TableRegion, alertBlockHandler, alignFormat, backgroundFormat, blockFormat, blockquoteFormat, boldFormat, boxBlockHandler, browserAdapter, cloneDelta, codeBlockFormat, codeFormat, colorFormat, columnsBlockHandler, createDefaultBlockHandlers, createDefaultRegistry, defaultBlockFormats, defaultEmbedFormats, defaultFormats, defaultInlineFormats, deltaToHtml, deltaToMarkdown, dividerFormat, escapeHtml, extractBoxOpAttributes, extractTableRegion, fontFormat, footnoteRefFormat, footnotesBlockHandler, formulaFormat, getAdapter, getNamedColors, headerFormat, headerIdFormat, htmlToDelta, imageFormat, indentFormat, isAdapterAvailable, isElement, isRemarkAvailable, isTableNewlineOp, isTextNode, isValidColor, isValidHexColor, italicFormat, kbdFormat, linkFormat, listFormat, markFormat, markdownToDelta, markdownToDeltaSync, nodeAdapter, normalizeDelta, preloadRemark, sanitizeDelta, sizeFormat, slugify, slugifyWithDedup, softBreakFormat, strikeFormat, subscriptFormat, superscriptFormat, tableBlockHandler, tableColAlignFormat, tableColFormat, tableHeaderFormat, tableRowFormat, toHexColor, underlineFormat, unescapeHtml, validateDelta, videoFormat };
1888
+ export { ALERT_TYPES, type AlertBlockData, type AlertType, type AlignType, BOX_FLOAT_VALUES, BOX_OVERFLOW_VALUES, type BlockContext, type BlockHandler, BlockHandlerRegistry, type BlockRenderOptions, type BoxBlockData, type BoxFloat, type BoxOpAttributes, type BoxOverflow, BrowserDOMAdapter, type CellAlign, type CellData, type ColumnsBlockData, type DOMAdapter, type DOMDocument, type DOMDocumentFragment, type DOMElement, type DOMNode, type DOMNodeList, type DeltaToHtmlOptions, type DeltaToMarkdownOptions, type DocumentPresentation, type FootnotesBlockData, type Format, type FormatDefinition, type FormatMatchResult, type FormatScope, type HtmlToDeltaOptions, type ListType, type MarkdownToDeltaOptions, NODE_TYPE, NodeDOMAdapter, Registry, type ResolvedDocumentPresentation, type ResolvedTablePresentation, type SanitizeOptions, type TableBlockData, type TableCellAlign, type TableColAlignType, type TablePresentation, type TableRegion, alertBlockHandler, alignFormat, backgroundFormat, blockFormat, blockquoteFormat, boldFormat, boxBlockHandler, browserAdapter, cloneDelta, codeBlockFormat, codeFormat, colorFormat, columnsBlockHandler, createDefaultBlockHandlers, createDefaultRegistry, defaultBlockFormats, defaultEmbedFormats, defaultFormats, defaultInlineFormats, deltaToHtml, deltaToMarkdown, dividerFormat, documentPresentationStyleParts, escapeHtml, extractBoxOpAttributes, extractTableRegion, fontFormat, footnoteRefFormat, footnotesBlockHandler, formulaFormat, getAdapter, getNamedColors, headerFormat, headerIdFormat, htmlToDelta, imageFormat, indentFormat, isAdapterAvailable, isElement, isRemarkAvailable, isTableNewlineOp, isTextNode, isValidColor, isValidHexColor, isZebraBodyRow, italicFormat, kbdFormat, linkFormat, listFormat, markFormat, markdownToDelta, markdownToDeltaSync, nodeAdapter, normalizeDelta, preloadRemark, resolveDocumentPresentation, resolveTablePresentation, sanitizeDelta, sizeFormat, slugify, slugifyWithDedup, softBreakFormat, strikeFormat, subscriptFormat, superscriptFormat, tableBlockHandler, tableColAlignFormat, tableColFormat, tableHeaderFormat, tableRowFormat, toHexColor, underlineFormat, unescapeHtml, validateDelta, videoFormat };
package/dist/index.js CHANGED
@@ -2493,6 +2493,94 @@ function slugifyWithDedup(text, usedSlugs) {
2493
2493
  return `${base}-${count}`;
2494
2494
  }
2495
2495
 
2496
+ // src/conversion/html/document-presentation.ts
2497
+ function resolveDocumentPresentation(presentation) {
2498
+ if (!presentation) return void 0;
2499
+ const lineSpacing = typeof presentation.lineSpacing === "number" && presentation.lineSpacing > 0 ? presentation.lineSpacing : void 0;
2500
+ const textIndentCm = typeof presentation.textIndentCm === "number" && presentation.textIndentCm > 0 ? presentation.textIndentCm : void 0;
2501
+ if (lineSpacing === void 0 && textIndentCm === void 0) return void 0;
2502
+ return { lineSpacing, textIndentCm };
2503
+ }
2504
+ var LINE_HEIGHT_TAGS = /* @__PURE__ */ new Set(["p", "li", "blockquote"]);
2505
+ function documentPresentationStyleParts(tag, resolved) {
2506
+ if (!resolved) return [];
2507
+ const parts = [];
2508
+ if (resolved.lineSpacing !== void 0 && LINE_HEIGHT_TAGS.has(tag)) {
2509
+ const pct = Math.round(resolved.lineSpacing * 100);
2510
+ parts.push(`line-height:${resolved.lineSpacing}`);
2511
+ parts.push(`mso-line-height-alt:${pct}%`);
2512
+ }
2513
+ if (resolved.textIndentCm !== void 0 && tag === "p") {
2514
+ parts.push(`text-indent:${resolved.textIndentCm}cm`);
2515
+ }
2516
+ return parts;
2517
+ }
2518
+ function joinStyleParts(parts) {
2519
+ return parts.length > 0 ? ` style="${parts.join("; ")}"` : "";
2520
+ }
2521
+
2522
+ // src/conversion/html/table-presentation.ts
2523
+ var DEFAULT_BORDER_COLOR = "#e7e7e7";
2524
+ var DEFAULT_HEADER_BG = "#f5f5f5";
2525
+ var DEFAULT_ZEBRA_BG = "#fafafa";
2526
+ var CELL_PADDING = "6px 13px";
2527
+ function resolveTablePresentation(presentation) {
2528
+ return {
2529
+ grid: presentation?.grid === true,
2530
+ line: presentation?.line === true && presentation?.grid !== true,
2531
+ borderColor: presentation?.borderColor ?? DEFAULT_BORDER_COLOR,
2532
+ headerShade: presentation?.headerShade === true,
2533
+ zebraRows: presentation?.zebraRows === true,
2534
+ headerBold: presentation?.headerBold === true,
2535
+ headerCenter: presentation?.headerCenter === true,
2536
+ defaultCellAlign: presentation?.defaultCellAlign ?? "left"
2537
+ };
2538
+ }
2539
+ function isZebraBodyRow(headerRowCount, bodyRowIndex) {
2540
+ return (headerRowCount + bodyRowIndex + 1) % 2 === 0;
2541
+ }
2542
+ function isTableCellAlign(value) {
2543
+ return value === "left" || value === "center" || value === "right";
2544
+ }
2545
+ function tableOpenTag(presentation) {
2546
+ if (!presentation.grid && !presentation.line) {
2547
+ return "<table>";
2548
+ }
2549
+ return `<table style="border-collapse: collapse">`;
2550
+ }
2551
+ function buildTableCellStyleAttr(params) {
2552
+ const { presentation, cellTag, colAlign, headerRowCount, bodyRowIndex } = params;
2553
+ const parts = [];
2554
+ parts.push(`padding: ${CELL_PADDING}`);
2555
+ const color = presentation.borderColor;
2556
+ if (presentation.grid) {
2557
+ parts.push(`border: 1px solid ${color}`);
2558
+ } else if (presentation.line) {
2559
+ const width = cellTag === "th" ? "1px" : "0.5px";
2560
+ parts.push(`border-bottom: ${width} solid ${color}`);
2561
+ }
2562
+ let textAlign;
2563
+ if (cellTag === "th" && presentation.headerCenter) {
2564
+ textAlign = "center";
2565
+ } else if (isTableCellAlign(colAlign)) {
2566
+ textAlign = colAlign;
2567
+ } else if (colAlign == null || colAlign === "left") {
2568
+ textAlign = presentation.defaultCellAlign;
2569
+ }
2570
+ if (textAlign && textAlign !== "left") {
2571
+ parts.push(`text-align: ${textAlign}`);
2572
+ }
2573
+ if (cellTag === "th" && presentation.headerBold) {
2574
+ parts.push("font-weight: bold");
2575
+ }
2576
+ if (cellTag === "th" && presentation.headerShade) {
2577
+ parts.push(`background-color: ${DEFAULT_HEADER_BG}`);
2578
+ } else if (cellTag === "td" && presentation.zebraRows && bodyRowIndex !== void 0 && isZebraBodyRow(headerRowCount, bodyRowIndex)) {
2579
+ parts.push(`background-color: ${DEFAULT_ZEBRA_BG}`);
2580
+ }
2581
+ return ` style="${parts.join("; ")}"`;
2582
+ }
2583
+
2496
2584
  // src/conversion/html/delta-to-html.ts
2497
2585
  function deltaToHtml(delta, options = {}) {
2498
2586
  const lines = splitIntoLines(delta);
@@ -2501,6 +2589,7 @@ function deltaToHtml(delta, options = {}) {
2501
2589
  const hierarchicalNumbers = options.hierarchicalNumbers ?? false;
2502
2590
  const blockHandlers = options.blockHandlers;
2503
2591
  const anchorLinks = options.anchorLinks ?? false;
2592
+ const resolvedDocumentPresentation = resolveDocumentPresentation(options.documentPresentation);
2504
2593
  let html = "";
2505
2594
  let listStack = [];
2506
2595
  let counters = [];
@@ -2563,7 +2652,14 @@ function deltaToHtml(delta, options = {}) {
2563
2652
  if (hierarchicalNumbers && listType === "ordered") {
2564
2653
  hierarchicalNumber = counters.slice(0, indent + 1).join(".");
2565
2654
  }
2566
- html += renderListItem(content, listItemAttrs, pretty, indentLevel, hierarchicalNumber);
2655
+ html += renderListItem(
2656
+ content,
2657
+ listItemAttrs,
2658
+ pretty,
2659
+ indentLevel,
2660
+ hierarchicalNumber,
2661
+ resolvedDocumentPresentation
2662
+ );
2567
2663
  } else {
2568
2664
  let headingId;
2569
2665
  if (line.attributes?.header) {
@@ -2575,7 +2671,14 @@ function deltaToHtml(delta, options = {}) {
2575
2671
  headingId = slugifyWithDedup(plainText, slugUsageMap);
2576
2672
  }
2577
2673
  }
2578
- html += renderBlock(content, tag, line.attributes, pretty, headingId);
2674
+ html += renderBlock(
2675
+ content,
2676
+ tag,
2677
+ line.attributes,
2678
+ pretty,
2679
+ headingId,
2680
+ resolvedDocumentPresentation
2681
+ );
2579
2682
  }
2580
2683
  }
2581
2684
  html += closeAllLists(listStack, pretty);
@@ -2676,7 +2779,10 @@ function renderTable(tableLines, embedRenderers, pretty, blockHandlers, options)
2676
2779
  const bodyRows = sortedRows.filter(([, r]) => !r.isHeader);
2677
2780
  const indent = pretty ? " " : "";
2678
2781
  const nl = pretty ? "\n" : "";
2679
- let html = `<table>${nl}`;
2782
+ const usePresentation = options?.tablePresentation !== void 0;
2783
+ const presentation = usePresentation ? resolveTablePresentation(options.tablePresentation) : null;
2784
+ const headerRowCount = headerRows.length;
2785
+ let html = usePresentation && presentation ? `${tableOpenTag(presentation)}${nl}` : `<table>${nl}`;
2680
2786
  if (headerRows.length > 0) {
2681
2787
  html += `${indent}<thead>${nl}`;
2682
2788
  for (const [, row] of headerRows) {
@@ -2688,13 +2794,16 @@ function renderTable(tableLines, embedRenderers, pretty, blockHandlers, options)
2688
2794
  pretty,
2689
2795
  2,
2690
2796
  blockHandlers,
2691
- options
2797
+ options,
2798
+ presentation,
2799
+ headerRowCount
2692
2800
  );
2693
2801
  }
2694
2802
  html += `${indent}</thead>${nl}`;
2695
2803
  }
2696
2804
  if (bodyRows.length > 0) {
2697
2805
  html += `${indent}<tbody>${nl}`;
2806
+ let bodyRowIndex = 0;
2698
2807
  for (const [, row] of bodyRows) {
2699
2808
  html += renderTableRow(
2700
2809
  row.cells,
@@ -2704,8 +2813,12 @@ function renderTable(tableLines, embedRenderers, pretty, blockHandlers, options)
2704
2813
  pretty,
2705
2814
  2,
2706
2815
  blockHandlers,
2707
- options
2816
+ options,
2817
+ presentation,
2818
+ headerRowCount,
2819
+ bodyRowIndex
2708
2820
  );
2821
+ bodyRowIndex += 1;
2709
2822
  }
2710
2823
  html += `${indent}</tbody>${nl}`;
2711
2824
  }
@@ -2713,7 +2826,7 @@ function renderTable(tableLines, embedRenderers, pretty, blockHandlers, options)
2713
2826
  if (pretty) html += "\n";
2714
2827
  return html;
2715
2828
  }
2716
- function renderTableRow(cells, maxCol, cellTag, embedRenderers, pretty, depth, blockHandlers, options) {
2829
+ function renderTableRow(cells, maxCol, cellTag, embedRenderers, pretty, depth, blockHandlers, options, presentation, headerRowCount = 0, bodyRowIndex) {
2717
2830
  const indent = pretty ? " ".repeat(depth) : "";
2718
2831
  const cellIndent = pretty ? " ".repeat(depth + 1) : "";
2719
2832
  const nl = pretty ? "\n" : "";
@@ -2721,8 +2834,19 @@ function renderTableRow(cells, maxCol, cellTag, embedRenderers, pretty, depth, b
2721
2834
  for (let col = 0; col <= maxCol; col++) {
2722
2835
  const cell = cells.get(col);
2723
2836
  const content = cell ? renderLineContent(cell.ops, embedRenderers, blockHandlers, options) : "";
2724
- const alignStyle = cell?.colAlign && cell.colAlign !== "left" ? ` style="text-align: ${cell.colAlign}"` : "";
2725
- html += `${cellIndent}<${cellTag}${alignStyle}>${content}</${cellTag}>${nl}`;
2837
+ let styleAttr = "";
2838
+ if (presentation) {
2839
+ styleAttr = buildTableCellStyleAttr({
2840
+ presentation,
2841
+ cellTag,
2842
+ colAlign: cell?.colAlign,
2843
+ headerRowCount,
2844
+ bodyRowIndex: cellTag === "td" ? bodyRowIndex : void 0
2845
+ });
2846
+ } else {
2847
+ styleAttr = cell?.colAlign && cell.colAlign !== "left" ? ` style="text-align: ${cell.colAlign}"` : "";
2848
+ }
2849
+ html += `${cellIndent}<${cellTag}${styleAttr}>${content}</${cellTag}>${nl}`;
2726
2850
  }
2727
2851
  html += `${indent}</tr>${nl}`;
2728
2852
  return html;
@@ -2846,36 +2970,41 @@ function getListItemAttributes(attributes) {
2846
2970
  }
2847
2971
  return "";
2848
2972
  }
2849
- function renderListItem(content, attrs, pretty, indentLevel, hierarchicalNumber) {
2973
+ function renderListItem(content, attrs, pretty, indentLevel, hierarchicalNumber, resolvedDocumentPresentation) {
2850
2974
  const indent = pretty ? getIndent(indentLevel) : "";
2851
2975
  const innerContent = content || "<br>";
2852
2976
  let fullAttrs = attrs;
2853
2977
  if (hierarchicalNumber) {
2854
2978
  fullAttrs += ` data-number="${hierarchicalNumber}"`;
2855
2979
  }
2980
+ const styleAttr = joinStyleParts(
2981
+ documentPresentationStyleParts("li", resolvedDocumentPresentation)
2982
+ );
2983
+ fullAttrs += styleAttr;
2856
2984
  const html = `${indent}<li${fullAttrs}>${innerContent}</li>`;
2857
2985
  return pretty ? html + "\n" : html;
2858
2986
  }
2859
- function renderBlock(content, tag, attributes, pretty, id) {
2987
+ function renderBlock(content, tag, attributes, pretty, id, resolvedDocumentPresentation) {
2860
2988
  const idAttr = id ? ` id="${escapeHtml(id)}"` : "";
2861
- const styleAttr = getBlockStyleAttribute(attributes);
2989
+ const styleAttr = getBlockStyleAttribute(tag, attributes, resolvedDocumentPresentation);
2862
2990
  const innerContent = content || "<br>";
2863
2991
  const html = `<${tag}${idAttr}${styleAttr}>${innerContent}</${tag}>`;
2864
2992
  return pretty ? html + "\n" : html;
2865
2993
  }
2866
- function getBlockStyleAttribute(attributes) {
2867
- if (!attributes) return "";
2868
- const styles = [];
2869
- const alignVal = attributes.align;
2870
- if (alignVal && typeof alignVal === "string" && alignVal !== "left") {
2871
- styles.push(`text-align: ${alignVal}`);
2872
- }
2873
- if (attributes.indent && typeof attributes.indent === "number") {
2874
- if (!attributes.list) {
2875
- styles.push(`margin-left: ${attributes.indent * 2}em`);
2994
+ function getBlockStyleAttribute(tag, attributes, resolvedDocumentPresentation) {
2995
+ const styles = documentPresentationStyleParts(tag, resolvedDocumentPresentation);
2996
+ if (attributes) {
2997
+ const alignVal = attributes.align;
2998
+ if (alignVal && typeof alignVal === "string" && alignVal !== "left") {
2999
+ styles.push(`text-align: ${alignVal}`);
3000
+ }
3001
+ if (attributes.indent && typeof attributes.indent === "number") {
3002
+ if (!attributes.list) {
3003
+ styles.push(`margin-left: ${attributes.indent * 2}em`);
3004
+ }
2876
3005
  }
2877
3006
  }
2878
- return styles.length > 0 ? ` style="${styles.join("; ")}"` : "";
3007
+ return joinStyleParts(styles);
2879
3008
  }
2880
3009
  function extractPlainText(ops) {
2881
3010
  let text = "";
@@ -5027,6 +5156,7 @@ export {
5027
5156
  deltaToHtml,
5028
5157
  deltaToMarkdown,
5029
5158
  dividerFormat,
5159
+ documentPresentationStyleParts,
5030
5160
  escapeHtml,
5031
5161
  extractBoxOpAttributes,
5032
5162
  extractTableRegion,
@@ -5048,6 +5178,7 @@ export {
5048
5178
  isTextNode,
5049
5179
  isValidColor,
5050
5180
  isValidHexColor,
5181
+ isZebraBodyRow,
5051
5182
  italicFormat,
5052
5183
  kbdFormat,
5053
5184
  linkFormat,
@@ -5058,6 +5189,8 @@ export {
5058
5189
  nodeAdapter,
5059
5190
  normalizeDelta,
5060
5191
  preloadRemark,
5192
+ resolveDocumentPresentation,
5193
+ resolveTablePresentation,
5061
5194
  sanitizeDelta,
5062
5195
  sizeFormat,
5063
5196
  slugify,