|
1 | | -import type { FlowMode, Fragment } from './index.js'; |
| 1 | +import type { FlowMode, Fragment, Line } from './index.js'; |
2 | 2 |
|
3 | 3 | /** A fully resolved layout ready for the next-generation paint pipeline. */ |
4 | 4 | export type ResolvedLayout = { |
@@ -69,4 +69,101 @@ export type ResolvedFragmentItem = { |
69 | 69 | blockId: string; |
70 | 70 | /** Index within page.fragments — bridge to legacy content rendering. */ |
71 | 71 | fragmentIndex: number; |
| 72 | + /** Pre-resolved paragraph content for non-table paragraph fragments. */ |
| 73 | + content?: ResolvedParagraphContent; |
| 74 | +}; |
| 75 | + |
| 76 | +/** Resolved paragraph content for non-table paragraph/list-item fragments. */ |
| 77 | +export type ResolvedParagraphContent = { |
| 78 | + /** The lines to render, with all layout data pre-resolved. */ |
| 79 | + lines: ResolvedTextLineItem[]; |
| 80 | + /** Drop cap rendering data. Only present on first fragment of a paragraph with a drop cap. */ |
| 81 | + dropCap?: ResolvedDropCapItem; |
| 82 | + /** List marker rendering data. Only present on first fragment of a list paragraph. */ |
| 83 | + marker?: ResolvedListMarkerItem; |
| 84 | + /** Whether this fragment continues from a previous page. */ |
| 85 | + continuesFromPrev?: boolean; |
| 86 | + /** Whether this fragment continues on the next page. */ |
| 87 | + continuesOnNext?: boolean; |
| 88 | + /** Whether the source paragraph ends with a lineBreak run. */ |
| 89 | + paragraphEndsWithLineBreak?: boolean; |
| 90 | +}; |
| 91 | + |
| 92 | +/** A single resolved text line with pre-computed rendering geometry. */ |
| 93 | +export type ResolvedTextLineItem = { |
| 94 | + /** The source Line data (segments, leaders, bars, dimensions, run indices). */ |
| 95 | + line: Line; |
| 96 | + /** Global line index within the paragraph (fragment.fromLine + localIndex). */ |
| 97 | + lineIndex: number; |
| 98 | + /** Pre-computed available width for justify calculations. */ |
| 99 | + availableWidth: number; |
| 100 | + /** Whether to skip justification for this line (last line of paragraph). */ |
| 101 | + skipJustify: boolean; |
| 102 | + /** Pre-computed CSS paddingLeft in pixels. */ |
| 103 | + paddingLeftPx: number; |
| 104 | + /** Pre-computed CSS paddingRight in pixels. */ |
| 105 | + paddingRightPx: number; |
| 106 | + /** Pre-computed CSS textIndent in pixels (0 when not applicable). */ |
| 107 | + textIndentPx: number; |
| 108 | + /** Whether this is a list first line (indent handled by marker, not CSS). */ |
| 109 | + isListFirstLine: boolean; |
| 110 | + /** Resolved text-start position for list first lines with explicit segment positioning. */ |
| 111 | + resolvedListTextStartPx?: number; |
| 112 | + /** Whether this line has explicit segment positioning (tabs). */ |
| 113 | + hasExplicitSegmentPositioning: boolean; |
| 114 | + /** Pre-computed indent offset for the segment positioning path in renderLine. */ |
| 115 | + indentOffset: number; |
| 116 | +}; |
| 117 | + |
| 118 | +/** Resolved drop cap rendering data. */ |
| 119 | +export type ResolvedDropCapItem = { |
| 120 | + /** Drop cap text content. */ |
| 121 | + text: string; |
| 122 | + /** Drop cap mode. */ |
| 123 | + mode: 'drop' | 'margin'; |
| 124 | + /** Font family. */ |
| 125 | + fontFamily: string; |
| 126 | + /** Font size in pixels. */ |
| 127 | + fontSize: number; |
| 128 | + /** Bold styling. */ |
| 129 | + bold?: boolean; |
| 130 | + /** Italic styling. */ |
| 131 | + italic?: boolean; |
| 132 | + /** Text color. */ |
| 133 | + color?: string; |
| 134 | + /** Vertical position offset in pixels. */ |
| 135 | + position?: number; |
| 136 | + /** Measured width in pixels. */ |
| 137 | + width?: number; |
| 138 | + /** Measured height in pixels. */ |
| 139 | + height?: number; |
| 140 | +}; |
| 141 | + |
| 142 | +/** Resolved list marker rendering data with pre-computed positioning. */ |
| 143 | +export type ResolvedListMarkerItem = { |
| 144 | + /** Marker text content (e.g., "1.", "a)", bullet). */ |
| 145 | + text: string; |
| 146 | + /** Horizontal justification. */ |
| 147 | + justification: 'left' | 'right' | 'center'; |
| 148 | + /** Suffix type after marker. */ |
| 149 | + suffix: 'tab' | 'space' | 'nothing'; |
| 150 | + /** Whether marker should be hidden (vanish property). */ |
| 151 | + vanish?: boolean; |
| 152 | + /** Pre-computed left position of marker container in pixels. */ |
| 153 | + markerStartPx: number; |
| 154 | + /** Pre-computed tab/space suffix width in pixels. */ |
| 155 | + suffixWidthPx: number; |
| 156 | + /** CSS paddingLeft for the first line when marker is present. */ |
| 157 | + firstLinePaddingLeftPx: number; |
| 158 | + /** Extra padding adjustment for center-justified markers. */ |
| 159 | + centerPaddingAdjustPx?: number; |
| 160 | + /** Marker run styling. */ |
| 161 | + run: { |
| 162 | + fontFamily: string; |
| 163 | + fontSize: number; |
| 164 | + bold?: boolean; |
| 165 | + italic?: boolean; |
| 166 | + color?: string; |
| 167 | + letterSpacing?: number; |
| 168 | + }; |
72 | 169 | }; |
0 commit comments