@silurus/ooxml 0.57.0 → 0.58.0

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.
@@ -251,6 +251,8 @@ declare type CfRule = {
251
251
  } | {
252
252
  type: 'aboveAverage';
253
253
  aboveAverage: boolean;
254
+ equalAverage?: boolean;
255
+ stdDev?: number;
254
256
  dxfId: number | null;
255
257
  priority: number;
256
258
  } | {
@@ -848,6 +850,28 @@ declare interface DataPointOverride {
848
850
  markerLine?: string;
849
851
  }
850
852
 
853
+ /** One `<dataValidation>` rule (ECMA-376 §18.3.1.33). `type` is the constraint
854
+ * class (`list` | `whole` | `decimal` | `date` | `time` | `textLength` |
855
+ * `custom`); `operator` qualifies it (`between` | `notBetween` | `equal` | …).
856
+ * `formula1` / `formula2` are the operands (for `list`, `formula1` is the
857
+ * comma-separated literal list or a range/named reference). 1:1 with the Rust
858
+ * `DataValidation` (serde camelCase). */
859
+ declare interface DataValidation {
860
+ /** Affected cell ranges, verbatim from `@sqref` (space-separated A1 refs). */
861
+ sqref: string;
862
+ /** Constraint class. Absent means the spec default (`none`, no constraint). */
863
+ validationType?: string;
864
+ operator?: string;
865
+ formula1?: string;
866
+ formula2?: string;
867
+ /** `@allowBlank` — empty input is permitted. */
868
+ allowBlank?: boolean;
869
+ promptTitle?: string;
870
+ prompt?: string;
871
+ errorTitle?: string;
872
+ errorMessage?: string;
873
+ }
874
+
851
875
  declare interface DefinedName {
852
876
  name: string;
853
877
  formula: string;
@@ -863,7 +887,12 @@ declare interface DocComment {
863
887
 
864
888
  declare interface DocNote {
865
889
  id: string;
866
- text: string;
890
+ /** ECMA-376 §17.11.2 / §17.11.10 — the note's block-level content
891
+ * (paragraphs / nested tables), parsed with the document's styles +
892
+ * numbering. The leading run is the `<w:footnoteRef/>` auto-number marker
893
+ * (carries a {@link DocxTextRun.noteRef}). Use {@link noteText} to extract
894
+ * the plain-text body without the marker. */
895
+ content: BodyElement[];
867
896
  }
868
897
 
869
898
  declare interface DocParagraph {
@@ -905,10 +934,21 @@ declare interface DocParagraph {
905
934
  defaultFontFamily?: string | null;
906
935
  /**
907
936
  * ECMA-376 §17.3.1.6 `<w:bidi>` — right-to-left paragraph. `true` = RTL,
908
- * `false` = explicitly LTR, absent = unspecified (inherit). Phase 0 of RTL
909
- * support: recorded only; alignment/column-order resolution is deferred.
937
+ * `false` = explicitly LTR, absent = unspecified (inherit). The renderer uses
938
+ * this as the paragraph base direction: it seeds the UAX#9 reordering pass
939
+ * (`computeLineVisualOrder`), swaps the left/right indents, resolves the
940
+ * `w:jc` start/end edges (`resolveAlignEdge`), and lays out lines from the
941
+ * right.
910
942
  */
911
943
  bidi?: boolean;
944
+ /**
945
+ * ECMA-376 §17.3.1.32 `<w:snapToGrid>` — when `false`, this paragraph opts out
946
+ * of the section's document grid (`w:docGrid`): its lines use natural font
947
+ * metrics / the line-spacing multiplier directly instead of snapping to the
948
+ * grid pitch. `undefined` = inherit (default on). Set on Word's "Footnote
949
+ * Text" style, so footnote bodies use compact natural line height.
950
+ */
951
+ snapToGrid?: boolean;
912
952
  }
913
953
 
914
954
  declare interface DocRevision {
@@ -973,8 +1013,8 @@ declare interface DocTable {
973
1013
  /**
974
1014
  * ECMA-376 §17.4.1 `<w:bidiVisual>` — render columns in right-to-left
975
1015
  * (visual) order. `true` = RTL columns, `false` = explicitly LTR, absent =
976
- * unspecified. Phase 0 of RTL support: recorded only; column-order
977
- * resolution is deferred.
1016
+ * unspecified. When `true` the renderer mirrors the grid so logical column 0
1017
+ * is placed rightmost, and flips per-cell left/right borders accordingly.
978
1018
  */
979
1019
  bidiVisual?: boolean;
980
1020
  }
@@ -1019,6 +1059,7 @@ export declare namespace docx {
1019
1059
  DocxViewerOptions,
1020
1060
  autoResize,
1021
1061
  AutoResizeOptions,
1062
+ noteText,
1022
1063
  DocxDocumentModel,
1023
1064
  DocSettings,
1024
1065
  SectionProps,
@@ -1039,6 +1080,7 @@ export declare namespace docx {
1039
1080
  DocRevision,
1040
1081
  DocComment,
1041
1082
  DocNote,
1083
+ NoteRef,
1042
1084
  LineSpacing,
1043
1085
  TabStop_2 as TabStop,
1044
1086
  ParagraphBorders,
@@ -1067,6 +1109,29 @@ declare class DocxDocument {
1067
1109
  destroy(): void;
1068
1110
  get pageCount(): number;
1069
1111
  get document(): DocxDocumentModel;
1112
+ /**
1113
+ * ECMA-376 §17.13.4 — the document's comments (`word/comments.xml`), each with
1114
+ * id / author / initials / date / plain-text body. Comments are a data-only
1115
+ * API: they are NOT drawn on the page (Word renders them in a margin pane /
1116
+ * balloons, which this viewer does not reproduce). Use this to build a review
1117
+ * panel, export an annotation list, etc. Returns `[]` when the document has no
1118
+ * comments part. The same data is also reachable via `document.comments`.
1119
+ */
1120
+ get comments(): DocComment[];
1121
+ /**
1122
+ * ECMA-376 §17.11.10 — the document's footnotes (`word/footnotes.xml`),
1123
+ * excluding the reserved separator entries. Each note carries its `id` and
1124
+ * block-level `content`; use {@link noteText} for the plain-text body. These
1125
+ * ARE drawn at the bottom of the page that holds their reference; this getter
1126
+ * additionally exposes them as data. Returns `[]` when absent.
1127
+ */
1128
+ get footnotes(): DocNote[];
1129
+ /**
1130
+ * ECMA-376 §17.11.4 — the document's endnotes (`word/endnotes.xml`). Same
1131
+ * shape as {@link footnotes}; rendered at the end of the document. Returns
1132
+ * `[]` when absent.
1133
+ */
1134
+ get endnotes(): DocNote[];
1070
1135
  private _getPages;
1071
1136
  renderPage(target: HTMLCanvasElement | OffscreenCanvas, pageIndex: number, opts?: RenderPageOptions): Promise<void>;
1072
1137
  }
@@ -1137,8 +1202,10 @@ declare interface DocxTextRun {
1137
1202
  * tracked changes appear inline. */
1138
1203
  revision?: RunRevision;
1139
1204
  /** ECMA-376 §17.3.2.30 `<w:rtl>` — complex-script / right-to-left run.
1140
- * `true` = RTL, `false` = explicitly LTR, absent = unspecified.
1141
- * Phase 0: recorded only; glyph-order resolution is deferred. */
1205
+ * `true` = RTL, `false` = explicitly LTR, absent = unspecified. The renderer
1206
+ * treats a `true` run as RTL for the UAX#9 pass (it forces complex-script
1207
+ * shaping and marks the segment so `computeLineVisualOrder` reorders it), and
1208
+ * draws the slice with `ctx.direction = 'rtl'` so Canvas mirrors the glyphs. */
1142
1209
  rtl?: boolean;
1143
1210
  /** ECMA-376 §17.3.2.7 `<w:cs/>` — complex-script run toggle: cs formatting
1144
1211
  * applies to ALL characters of the run (§17.3.2.26). Distinct from
@@ -1157,6 +1224,12 @@ declare interface DocxTextRun {
1157
1224
  /** ECMA-376 §17.3.2.20 `<w:lang w:bidi>` — complex-script (RTL) language tag,
1158
1225
  * lower-cased (e.g. "ar-sa", "ae-ar"). Drives Word's AN digit ordering. */
1159
1226
  langBidi?: string;
1227
+ /** ECMA-376 §17.11.6/.7/.16/.17 — set when this run is a footnote/endnote
1228
+ * reference marker (`<w:footnoteReference>` in the body, `<w:footnoteRef>` at
1229
+ * the start of the note's content, and the endnote equivalents). `text` holds
1230
+ * the raw `@w:id`; the renderer overrides the displayed glyph with the note's
1231
+ * sequential number. */
1232
+ noteRef?: NoteRef;
1160
1233
  }
1161
1234
 
1162
1235
  /** Information about a rendered text segment for building a transparent selection overlay. */
@@ -1280,7 +1353,20 @@ declare interface FieldRun {
1280
1353
  highlight?: string | null;
1281
1354
  }
1282
1355
 
1283
- declare type Fill = SolidFill | NoFill | GradientFill | PatternFill;
1356
+ declare type Fill = SolidFill | NoFill | GradientFill | PatternFill | ImageFill;
1357
+
1358
+ /**
1359
+ * ECMA-376 §20.1.8.30 (CT_RelativeRect) — the destination rectangle a stretched
1360
+ * blip is mapped into, as edge insets relative to the fill region. Values are
1361
+ * fractions (ST_Percentage / 100000); **negative values let the image bleed
1362
+ * past the box (overscan)**. Absent edges default to 0.
1363
+ */
1364
+ declare interface FillRect {
1365
+ l?: number;
1366
+ t?: number;
1367
+ r?: number;
1368
+ b?: number;
1369
+ }
1284
1370
 
1285
1371
  /** ECMA-376 §20.1.8.17 (CT_GlowEffect) — coloured halo with blur radius. */
1286
1372
  declare interface Glow {
@@ -1369,6 +1455,30 @@ declare interface ImageAnchor {
1369
1455
  dataUrl: string;
1370
1456
  }
1371
1457
 
1458
+ /**
1459
+ * Image fill — ECMA-376 §20.1.8.14 (CT_BlipFillProperties). The embedded blip
1460
+ * is resolved to a base64 data URL at parse time. Both fill-modes are modelled
1461
+ * and mutually exclusive: `stretch` (§20.1.8.56) carries {@link ImageFill.fillRect};
1462
+ * `tile` (§20.1.8.58) carries {@link ImageFill.tile}.
1463
+ */
1464
+ declare interface ImageFill {
1465
+ fillType: 'image';
1466
+ /** `data:<mime>;base64,…` of the embedded blip. */
1467
+ dataUrl: string;
1468
+ /**
1469
+ * `<a:stretch><a:fillRect>` insets. Absent → fills the whole box (or the
1470
+ * fill is tiled — see {@link ImageFill.tile}).
1471
+ */
1472
+ fillRect?: FillRect;
1473
+ /**
1474
+ * `<a:tile>` descriptor. Present only when the blipFill is tiled; mutually
1475
+ * exclusive with {@link ImageFill.fillRect}.
1476
+ */
1477
+ tile?: TileInfo;
1478
+ /** `a:blip > a:alphaModFix@amt` as a fraction (0.0–1.0). Absent = opaque. */
1479
+ alpha?: number;
1480
+ }
1481
+
1372
1482
  declare interface ImageRun {
1373
1483
  dataUrl: string;
1374
1484
  widthPt: number;
@@ -1435,8 +1545,8 @@ declare interface LegendManualLayout_2 {
1435
1545
  }
1436
1546
 
1437
1547
  /**
1438
- * `<a:lightRig>` — ECMA-376 §20.1.5.9 (`CT_LightRig`). Parsed for Phase B
1439
- * (lighting/bevel shading); the Phase A camera renderer ignores it.
1548
+ * `<a:lightRig>` — ECMA-376 §20.1.5.9 (`CT_LightRig`). Drives the bevel-lip
1549
+ * lighting (Phase B): `dir` selects the key-light octant.
1440
1550
  */
1441
1551
  declare interface LightRig {
1442
1552
  /** Light-rig preset (`ST_LightRigType`), e.g. "threePt". */
@@ -1693,6 +1803,20 @@ declare interface NoFill {
1693
1803
  fillType: 'none';
1694
1804
  }
1695
1805
 
1806
+ /** A footnote / endnote reference marker (ECMA-376 §17.11). */
1807
+ declare interface NoteRef {
1808
+ /** "footnote" | "endnote" */
1809
+ kind: 'footnote' | 'endnote' | string;
1810
+ /** `@w:id` linking the marker to its note. Empty for the in-note
1811
+ * `<w:footnoteRef/>` placeholder (the renderer uses the enclosing note). */
1812
+ id: string;
1813
+ }
1814
+
1815
+ /** Flatten a footnote/endnote's content to its plain-text body, excluding the
1816
+ * auto-number reference marker. Convenience for data-only consumers
1817
+ * (the renderer draws {@link DocNote.content} directly). */
1818
+ declare function noteText(note: DocNote): string;
1819
+
1696
1820
  declare interface NumberingInfo {
1697
1821
  numId: number;
1698
1822
  level: number;
@@ -1961,6 +2085,7 @@ export declare namespace pptx {
1961
2085
  AutoResizeOptions,
1962
2086
  Presentation,
1963
2087
  Slide,
2088
+ PptxComment,
1964
2089
  SlideElement,
1965
2090
  ShapeElement,
1966
2091
  PictureElement,
@@ -1981,6 +2106,9 @@ export declare namespace pptx {
1981
2106
  NoFill,
1982
2107
  GradientFill,
1983
2108
  GradientStop,
2109
+ ImageFill,
2110
+ FillRect,
2111
+ TileInfo,
1984
2112
  Stroke,
1985
2113
  Shadow,
1986
2114
  Glow,
@@ -2000,6 +2128,17 @@ export declare namespace pptx {
2000
2128
  }
2001
2129
  }
2002
2130
 
2131
+ /** A single legacy slide comment (`<p:cm>` in `ppt/comments/commentN.xml`). */
2132
+ declare interface PptxComment {
2133
+ /** Resolved author name from `ppt/commentAuthors.xml`. Absent when the
2134
+ * authors file is missing or the `authorId` is out of range. */
2135
+ author?: string;
2136
+ /** `<p:cm @dt>` — ISO-8601 timestamp the comment was authored. */
2137
+ date?: string;
2138
+ /** Plain-text comment body (`<p:text>`). */
2139
+ text: string;
2140
+ }
2141
+
2003
2142
  /**
2004
2143
  * Headless PPTX rendering engine.
2005
2144
  *
@@ -2037,6 +2176,26 @@ declare class PptxPresentation {
2037
2176
  get slideWidth(): number;
2038
2177
  /** Slide height in EMU. */
2039
2178
  get slideHeight(): number;
2179
+ /**
2180
+ * Speaker-notes text for a slide (`ppt/notesSlides/notesSlideN.xml`,
2181
+ * ECMA-376 §13.3.5 — Notes Slide). Returns the notes-body text as a single
2182
+ * string (paragraphs joined with `\n`), or `null` when the slide has no
2183
+ * notes part. The notes are parsed at {@link load} time, so this is a
2184
+ * synchronous lookup.
2185
+ *
2186
+ * `slideIndex` is 0-based. Unlike navigation methods it is *not* clamped:
2187
+ * an out-of-range or non-integer index returns `null` rather than the notes
2188
+ * of the nearest slide (so a tool iterating by index gets an honest "no
2189
+ * notes" instead of a duplicated neighbour).
2190
+ *
2191
+ * @example
2192
+ * const pres = await PptxPresentation.load(buffer);
2193
+ * for (let i = 0; i < pres.slideCount; i++) {
2194
+ * const notes = pres.getNotes(i);
2195
+ * if (notes) console.log(`Slide ${i + 1} notes:`, notes);
2196
+ * }
2197
+ */
2198
+ getNotes(slideIndex: number): string | null;
2040
2199
  /** Render a slide onto the given canvas. */
2041
2200
  renderSlide(canvas: HTMLCanvasElement, slideIndex: number, opts?: RenderSlideOptions): Promise<void>;
2042
2201
  /**
@@ -2121,6 +2280,13 @@ declare class PptxViewer {
2121
2280
  prevSlide(): Promise<void>;
2122
2281
  get slideIndex(): number;
2123
2282
  get slideCount(): number;
2283
+ /**
2284
+ * Speaker-notes text for a slide (`ppt/notesSlides/notesSlideN.xml`,
2285
+ * ECMA-376 §13.3.5). Passthrough to {@link PptxPresentation.getNotes}:
2286
+ * 0-based index, returns `null` when the slide has no notes part, the index
2287
+ * is out of range, or nothing is loaded yet.
2288
+ */
2289
+ getNotes(slideIndex: number): string | null;
2124
2290
  /** The underlying <canvas> element. */
2125
2291
  get canvasElement(): HTMLCanvasElement;
2126
2292
  private renderCurrentSlide;
@@ -2297,6 +2463,20 @@ declare interface RenderViewportOptions {
2297
2463
  } | null;
2298
2464
  }
2299
2465
 
2466
+ /**
2467
+ * Resolved allowed-value set for a list validation. Either concrete display
2468
+ * `values` (inline list or expanded range), or — when the operand is a defined
2469
+ * name / complex formula we cannot expand — the raw `formula` text so the panel
2470
+ * can disclose it instead of showing nothing.
2471
+ */
2472
+ declare type ResolvedList = {
2473
+ kind: 'values';
2474
+ values: string[];
2475
+ } | {
2476
+ kind: 'formula';
2477
+ formula: string;
2478
+ };
2479
+
2300
2480
  /**
2301
2481
  * 3D rotation in sphere coordinates — ECMA-376 §20.1.5.11 (`CT_SphereCoords`).
2302
2482
  * Angles are in **degrees** (the XML carries 60000ths of a degree; the parser
@@ -2698,6 +2878,20 @@ declare interface Slide {
2698
2878
  slideNumber: number;
2699
2879
  background: Fill | null;
2700
2880
  elements: SlideElement[];
2881
+ /**
2882
+ * Speaker-notes pane text from `ppt/notesSlides/notesSlideN.xml`
2883
+ * (ECMA-376 §13.3.5 — Notes Slide). The full notes-body text as a single
2884
+ * string, paragraphs joined with `\n`. Absent (`undefined`) when the slide
2885
+ * has no notes part. The renderer ignores this — it is surfaced for tools;
2886
+ * read it via {@link PptxPresentation.getNotes}.
2887
+ */
2888
+ notes?: string;
2889
+ /**
2890
+ * Legacy slide comments (`ppt/comments/commentN.xml`, ECMA-376 §13.3.4).
2891
+ * Modern Office 365 threaded comments are not parsed. Omitted from the JSON
2892
+ * when the slide has no comments.
2893
+ */
2894
+ comments?: PptxComment[];
2701
2895
  }
2702
2896
 
2703
2897
  declare type SlideElement = ShapeElement | PictureElement | TableElement | ChartElement | MediaElement;
@@ -2723,9 +2917,10 @@ declare interface SolidFill {
2723
2917
  }
2724
2918
 
2725
2919
  /**
2726
- * `<a:sp3d>` — ECMA-376 §20.1.5.12 (`CT_Shape3D`). Parsed in full but **not
2727
- * rendered in Phase A** (camera-only). bevel/contour/extrusion are Phase B.
2728
- * Numeric fields are omitted from JSON when zero.
2920
+ * `<a:sp3d>` — ECMA-376 §20.1.5.12 (`CT_Shape3D`). Rendered in Phase B: bevelT/
2921
+ * bevelB are shaded as a lit lip (distance-field + lightRig), extrusionH as a
2922
+ * swept side wall, and contour as a flat outline approximation. Numeric fields
2923
+ * are omitted from JSON when zero.
2729
2924
  */
2730
2925
  declare interface Sp3d {
2731
2926
  /** Z position of the front face in EMU (default 0). */
@@ -3092,6 +3287,29 @@ declare interface TextRunData {
3092
3287
  outline?: TextOutline;
3093
3288
  }
3094
3289
 
3290
+ /**
3291
+ * ECMA-376 §20.1.8.58 (CT_TileInfoProperties) — tiled blip-fill placement.
3292
+ * The blip repeats at its native size (scaled by sx/sy) across the fill box.
3293
+ * Mutually exclusive with {@link ImageFill.fillRect} (the `stretch` mode).
3294
+ */
3295
+ declare interface TileInfo {
3296
+ /** Horizontal offset of the first tile, in EMU (`tx`). Default 0. */
3297
+ tx: number;
3298
+ /** Vertical offset of the first tile, in EMU (`ty`). Default 0. */
3299
+ ty: number;
3300
+ /** Horizontal tile scale as a fraction (`sx` / 100000). Default 1.0. */
3301
+ sx: number;
3302
+ /** Vertical tile scale as a fraction (`sy` / 100000). Default 1.0. */
3303
+ sy: number;
3304
+ /** Mirror mode: `'none' | 'x' | 'y' | 'xy'` (`flip`). Default `'none'`. */
3305
+ flip: string;
3306
+ /**
3307
+ * Anchor corner the tile grid registers against:
3308
+ * `tl|t|tr|l|ctr|r|bl|b|br` (`algn`). Default `'tl'`.
3309
+ */
3310
+ algn: string;
3311
+ }
3312
+
3095
3313
  declare interface ViewportRange {
3096
3314
  row: number;
3097
3315
  col: number;
@@ -3139,6 +3357,17 @@ declare interface Worksheet {
3139
3357
  /** A1-style cell refs of commented cells (ECMA-376 §18.7.3). Rendered as a
3140
3358
  * small red triangle in each cell's top-right corner. */
3141
3359
  commentRefs?: string[];
3360
+ /** Full-fidelity comment bodies (cell ref + author + plain text) for every
3361
+ * `<comment>` in `xl/commentsN.xml` (ECMA-376 §18.7). Parallel to
3362
+ * {@link commentRefs} (one entry per ref). Consume this to read the note
3363
+ * text; the renderer uses {@link commentRefs} for the red indicator and the
3364
+ * viewer surfaces these bodies in an Excel-style hover popup. */
3365
+ comments?: XlsxComment[];
3366
+ /** Data-validation rules on this sheet (ECMA-376 §18.3.1.32–33). Exposed for
3367
+ * tooling. The viewer draws a list-dropdown arrow on the active cell when the
3368
+ * selection intersects a `list`-type rule's `sqref` (display only — opening
3369
+ * the list / picking a value is out of scope for a viewer). */
3370
+ dataValidations?: DataValidation[];
3142
3371
  /** Defined names in scope for this sheet (ECMA-376 §18.2.5). Used by
3143
3372
  * conditional-formatting `expression` rules that call named ranges
3144
3373
  * (e.g. `task_start`, `today`). */
@@ -3169,6 +3398,7 @@ export declare namespace xlsx {
3169
3398
  XlsxWorkbook,
3170
3399
  LoadOptions_3 as LoadOptions,
3171
3400
  XlsxViewer,
3401
+ ResolvedList,
3172
3402
  XlsxViewerOptions,
3173
3403
  CellAddress,
3174
3404
  CellRange_2 as CellRange,
@@ -3205,6 +3435,8 @@ export declare namespace xlsx {
3205
3435
  CfIcon,
3206
3436
  DefinedName,
3207
3437
  Hyperlink,
3438
+ XlsxComment,
3439
+ DataValidation,
3208
3440
  TableInfo,
3209
3441
  TableColumnInfo,
3210
3442
  SlicerAnchor,
@@ -3279,6 +3511,24 @@ declare interface XlsxChartSeries {
3279
3511
  errBars?: ErrBars[];
3280
3512
  }
3281
3513
 
3514
+ /** One cell comment. Sourced from the classic notes file `xl/commentsN.xml`
3515
+ * (ECMA-376 §18.7) when present, otherwise from the Office-365 threaded
3516
+ * comments part `xl/threadedComments/` (MS-XLSX schema
3517
+ * `…/spreadsheetml/2018/threadedcomments`, `personId` resolved via
3518
+ * `xl/persons/`). `text` is the joined plain text — every `<r><t>` run for
3519
+ * classic notes, every reply in the thread (newline-joined) for threaded
3520
+ * comments; rich-text formatting is dropped. 1:1 with the Rust `XlsxComment`
3521
+ * (serde camelCase). */
3522
+ declare interface XlsxComment {
3523
+ /** A1-style cell reference (`@ref` on the comment element). */
3524
+ cellRef: string;
3525
+ /** Resolved author name — the `<authors>` entry (classic) or the `<person>`
3526
+ * `displayName` (threaded). Absent when unresolved. */
3527
+ author?: string;
3528
+ /** Concatenated plain text of every run / threaded reply. */
3529
+ text: string;
3530
+ }
3531
+
3282
3532
  /** Emitted once per cell that has text, with the cell's canvas-pixel bounds. */
3283
3533
  declare interface XlsxTextRunInfo {
3284
3534
  text: string;
@@ -3332,6 +3582,32 @@ declare class XlsxViewer {
3332
3582
  private selectionOverlay;
3333
3583
  private keydownHandler;
3334
3584
  private pendingTap;
3585
+ /** DOM overlay element that shows the hovered cell's comment. Lives in
3586
+ * canvasArea above the scrollHost; `pointer-events:none` so it never blocks
3587
+ * cell interaction. */
3588
+ private commentPopup;
3589
+ /** `"row:col"` → comment for the current sheet, rebuilt on every showSheet. */
3590
+ private commentMap;
3591
+ /** `"row:col"` of the cell whose popup is currently shown (or pending), so a
3592
+ * pointermove within the same cell doesn't restart the show timer. */
3593
+ private commentPopupKey;
3594
+ /** Pending show timer (see {@link COMMENT_POPUP_DELAY_MS}). */
3595
+ private commentPopupTimer;
3596
+ /** DOM overlay listing a list-validated cell's allowed values. Lives in
3597
+ * canvasArea above the scrollHost; unlike the comment popup this is a click
3598
+ * target (`pointer-events:auto`). Read-only: hovering an item highlights it
3599
+ * but selecting does NOT change the cell. */
3600
+ private validationPanel;
3601
+ /** `"row:col"` of the cell whose panel is currently open, or null. Lets a
3602
+ * re-click on the same arrow toggle the panel closed. */
3603
+ private validationPanelKey;
3604
+ /** Screen rect (canvasArea CSS px) of the dropdown arrow button last drawn by
3605
+ * {@link maybeDrawValidationDropdown}, so pointerdown can hit-test it. Null
3606
+ * when no arrow is currently visible. */
3607
+ private validationArrowRect;
3608
+ /** Document-level pointerdown listener that closes the panel on an outside
3609
+ * click; installed only while the panel is open. */
3610
+ private validationOutsideHandler;
3335
3611
  constructor(container: HTMLElement, opts?: XlsxViewerOptions);
3336
3612
  /**
3337
3613
  * Load an XLSX from URL or ArrayBuffer and render the first sheet.
@@ -3406,6 +3682,14 @@ declare class XlsxViewer {
3406
3682
  private getCellRect;
3407
3683
  /** Returns the current selection, including mode. */
3408
3684
  get selection(): CellRange_2 | null;
3685
+ /**
3686
+ * Programmatically select a single cell by A1 reference (e.g. `"B2"`), as if
3687
+ * the user had clicked it: updates the active/anchor cell, redraws the
3688
+ * selection overlay (including any list-validation dropdown arrow), and fires
3689
+ * `onSelectionChange`. A no-op for malformed refs. Closes any open validation
3690
+ * panel, matching the click path.
3691
+ */
3692
+ select(ref: string): void;
3409
3693
  /**
3410
3694
  * Returns what the header area contains at the given client coordinates.
3411
3695
  * Returns null when the point is in the cell grid (not a header).
@@ -3414,6 +3698,49 @@ declare class XlsxViewer {
3414
3698
  /** Copy the selected cell range as tab-separated text to the clipboard. */
3415
3699
  private copySelection;
3416
3700
  private updateSelectionOverlay;
3701
+ /** Draw the Excel list-validation dropdown button just outside the
3702
+ * bottom-right corner of the *active* cell when that cell is covered by a
3703
+ * `list` data-validation rule. Anchored to the single active cell (not the
3704
+ * whole range) to mirror Excel, which attaches the button to the active
3705
+ * cell of the selection. */
3706
+ private maybeDrawValidationDropdown;
3707
+ /** Toggle the dropdown panel for the active cell's list validation. Called
3708
+ * from pointerdown when the arrow rect is hit. Re-clicking the same arrow
3709
+ * closes it. */
3710
+ private toggleValidationPanel;
3711
+ /** Resolve the allowed values for `formula1` (relative to the current sheet)
3712
+ * and render them in the panel anchored below the active cell. Async because
3713
+ * cross-sheet range references may need a lazily-parsed worksheet. */
3714
+ private openValidationPanel;
3715
+ /** Build the panel's children. Uses textContent throughout (no HTML injection
3716
+ * from cell values). Items highlight on hover but are NOT selectable —
3717
+ * this is a read-only viewer, so clicking a value must not change the cell. */
3718
+ private renderValidationPanel;
3719
+ /** Position the (already-populated, visible-or-becoming-visible) panel below
3720
+ * the dropdown arrow / active cell using the pure geometry calculator. */
3721
+ private positionValidationPanel;
3722
+ /** Install a document-level pointerdown listener that closes the panel on a
3723
+ * click outside it (and outside the arrow, which toggles via its own path).
3724
+ * Removed by {@link hideValidationPanel}. */
3725
+ private installValidationOutsideHandler;
3726
+ /** Hide the panel and detach its outside-click listener. Called on re-click,
3727
+ * outside click, Esc, scroll, selection change, sheet switch and destroy. */
3728
+ private hideValidationPanel;
3729
+ /** Build the `"row:col"` → comment index for the given sheet. Parses each
3730
+ * `XlsxComment.cellRef` with the shared {@link parseA1}; later refs win on a
3731
+ * collision (Excel allows at most one note per cell, so this is moot in
3732
+ * practice). */
3733
+ private buildCommentMap;
3734
+ /** Show the popup for the comment on `cell` after the hover dwell, anchored to
3735
+ * the cell's current on-screen rect. No-op when the cell carries no comment.
3736
+ * Re-hovering the same cell does not restart the timer. */
3737
+ private scheduleCommentPopup;
3738
+ /** Immediately render the popup for `comment` anchored to `cell` (used by the
3739
+ * hover-dwell timer and by touch selection, which has no hover). */
3740
+ private renderCommentPopup;
3741
+ /** Hide the popup and cancel any pending show. Called on cell-out, scroll,
3742
+ * sheet switch and destroy. */
3743
+ private hideCommentPopup;
3417
3744
  private applyPointerSelection;
3418
3745
  private setupSelectionEvents;
3419
3746
  private buildTabs;
@@ -3515,6 +3842,22 @@ declare class XlsxWorkbook {
3515
3842
  * `null` for sheets that declare no tab color. */
3516
3843
  get tabColors(): (string | null)[];
3517
3844
  getWorksheet(sheetIndex: number): Promise<Worksheet>;
3845
+ /**
3846
+ * Resolve a `list`-type data-validation `formula1` (ECMA-376 §18.3.1.32) into
3847
+ * the set of allowed values to display, evaluated relative to `sheetIndex`
3848
+ * (the sheet that owns the validation, used to resolve unqualified ranges):
3849
+ *
3850
+ * - Inline quoted list `"A,B,C"` → the literal values.
3851
+ * - Range ref `$B$2:$B$5` → each non-empty cell's *display
3852
+ * string* (the same formatted text the grid shows, via {@link formatCellValue}),
3853
+ * walked row-major. `Sheet2!$A$1:$A$9` resolves against the named sheet
3854
+ * (lazily parsed via {@link getWorksheet}, hence async).
3855
+ * - Named range / complex formula → `{ kind: 'formula' }` carrying the
3856
+ * raw text so the caller can disclose it rather than blanking it.
3857
+ *
3858
+ * Read-only: this only reads cell values for display; it never writes.
3859
+ */
3860
+ resolveValidationList(sheetIndex: number, formula1: string | undefined): Promise<ResolvedList>;
3518
3861
  renderViewport(target: HTMLCanvasElement | OffscreenCanvas, sheetIndex: number, viewport: ViewportRange, opts?: RenderViewportOptions): Promise<void>;
3519
3862
  destroy(): void;
3520
3863
  }