@cj-tech-master/excelts 2.0.1 → 3.0.0-canary.20251228183403.d3eb98d

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.
Files changed (58) hide show
  1. package/dist/browser/excelts.esm.js +181 -133
  2. package/dist/browser/excelts.esm.js.map +1 -1
  3. package/dist/browser/excelts.esm.min.js +30 -24
  4. package/dist/browser/excelts.iife.js +181 -133
  5. package/dist/browser/excelts.iife.js.map +1 -1
  6. package/dist/browser/excelts.iife.min.js +30 -24
  7. package/dist/cjs/doc/pivot-table.js +47 -6
  8. package/dist/cjs/doc/worksheet.js +0 -1
  9. package/dist/cjs/stream/xlsx/worksheet-writer.js +0 -1
  10. package/dist/cjs/xlsx/xform/book/sheet-xform.js +3 -2
  11. package/dist/cjs/xlsx/xform/book/workbook-properties-xform.js +1 -1
  12. package/dist/cjs/xlsx/xform/core/content-types-xform.js +12 -6
  13. package/dist/cjs/xlsx/xform/pivot-table/cache-field-xform.js +17 -21
  14. package/dist/cjs/xlsx/xform/pivot-table/cache-field.js +43 -7
  15. package/dist/cjs/xlsx/xform/pivot-table/pivot-cache-definition-xform.js +1 -10
  16. package/dist/cjs/xlsx/xform/pivot-table/pivot-cache-records-xform.js +1 -1
  17. package/dist/cjs/xlsx/xform/pivot-table/pivot-table-xform.js +51 -30
  18. package/dist/cjs/xlsx/xform/sheet/page-setup-xform.js +4 -3
  19. package/dist/cjs/xlsx/xform/sheet/row-xform.js +1 -1
  20. package/dist/cjs/xlsx/xform/sheet/sheet-format-properties-xform.js +6 -3
  21. package/dist/cjs/xlsx/xform/sheet/sheet-view-xform.js +8 -4
  22. package/dist/cjs/xlsx/xform/sheet/worksheet-xform.js +2 -2
  23. package/dist/cjs/xlsx/xform/style/font-xform.js +36 -23
  24. package/dist/cjs/xlsx/xform/table/auto-filter-xform.js +3 -1
  25. package/dist/cjs/xlsx/xform/table/table-column-xform.js +2 -1
  26. package/dist/cjs/xlsx/xform/table/table-xform.js +5 -9
  27. package/dist/esm/doc/pivot-table.js +47 -6
  28. package/dist/esm/doc/worksheet.js +0 -1
  29. package/dist/esm/stream/xlsx/worksheet-writer.js +0 -1
  30. package/dist/esm/xlsx/xform/book/sheet-xform.js +3 -2
  31. package/dist/esm/xlsx/xform/book/workbook-properties-xform.js +1 -1
  32. package/dist/esm/xlsx/xform/core/content-types-xform.js +12 -6
  33. package/dist/esm/xlsx/xform/pivot-table/cache-field-xform.js +17 -21
  34. package/dist/esm/xlsx/xform/pivot-table/cache-field.js +43 -7
  35. package/dist/esm/xlsx/xform/pivot-table/pivot-cache-definition-xform.js +1 -10
  36. package/dist/esm/xlsx/xform/pivot-table/pivot-cache-records-xform.js +1 -1
  37. package/dist/esm/xlsx/xform/pivot-table/pivot-table-xform.js +51 -30
  38. package/dist/esm/xlsx/xform/sheet/page-setup-xform.js +4 -3
  39. package/dist/esm/xlsx/xform/sheet/row-xform.js +1 -1
  40. package/dist/esm/xlsx/xform/sheet/sheet-format-properties-xform.js +6 -3
  41. package/dist/esm/xlsx/xform/sheet/sheet-view-xform.js +8 -4
  42. package/dist/esm/xlsx/xform/sheet/worksheet-xform.js +2 -2
  43. package/dist/esm/xlsx/xform/style/font-xform.js +36 -23
  44. package/dist/esm/xlsx/xform/table/auto-filter-xform.js +3 -1
  45. package/dist/esm/xlsx/xform/table/table-column-xform.js +2 -1
  46. package/dist/esm/xlsx/xform/table/table-xform.js +5 -9
  47. package/dist/types/doc/pivot-table.d.ts +5 -1
  48. package/dist/types/stream/xlsx/worksheet-writer.d.ts +1 -1
  49. package/dist/types/types.d.ts +1 -1
  50. package/dist/types/xlsx/xform/pivot-table/cache-field-xform.d.ts +1 -1
  51. package/dist/types/xlsx/xform/pivot-table/cache-field.d.ts +6 -2
  52. package/dist/types/xlsx/xform/pivot-table/pivot-cache-definition-xform.d.ts +0 -5
  53. package/dist/types/xlsx/xform/pivot-table/pivot-table-xform.d.ts +0 -3
  54. package/dist/types/xlsx/xform/sheet/sheet-format-properties-xform.d.ts +1 -1
  55. package/dist/types/xlsx/xform/sheet/worksheet-xform.d.ts +1 -1
  56. package/dist/types/xlsx/xform/style/font-xform.d.ts +1 -0
  57. package/dist/types/xlsx/xform/table/table-xform.d.ts +0 -4
  58. package/package.json +1 -1
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * @cj-tech-master/excelts v2.0.1
2
+ * @cj-tech-master/excelts v3.0.0-canary.20251228183403.d3eb98d
3
3
  * TypeScript Excel Workbook Manager - Read and Write xlsx and csv Files.
4
4
  * (c) 2025 cjnoname
5
5
  * Released under the MIT License
@@ -2962,7 +2962,7 @@ function createTableSourceAdapter(table) {
2962
2962
  const endCol = startCol + columnNames.length - 1;
2963
2963
  const shortRange = colCache.encode(startRow, startCol, endRow, endCol);
2964
2964
  return {
2965
- name: tableModel.name,
2965
+ name: table.worksheet.name,
2966
2966
  getRow(rowNumber) {
2967
2967
  if (rowNumber === 1) return { values: headerRow };
2968
2968
  const dataIndex = rowNumber - 2;
@@ -2999,7 +2999,7 @@ function makePivotTable(worksheet, model) {
2999
2999
  validate(worksheet, model, source);
3000
3000
  const { rows, values } = model;
3001
3001
  const columns = model.columns ?? [];
3002
- const cacheFields = makeCacheFields(source, [...rows, ...columns]);
3002
+ const cacheFields = makeCacheFields(source, [...rows, ...columns], values);
3003
3003
  const nameToIndex = cacheFields.reduce((result, cacheField, index) => {
3004
3004
  result[cacheField.name] = index;
3005
3005
  return result;
@@ -3034,9 +3034,10 @@ function validate(_worksheet, model, source) {
3034
3034
  if (model.values.length < 1) throw new Error("Must have at least one value.");
3035
3035
  if (model.values.length > 1 && columns.length > 0) throw new Error("It is currently not possible to have multiple values when columns are specified. Please either supply an empty array for columns or a single value.");
3036
3036
  }
3037
- function makeCacheFields(source, fieldNamesWithSharedItems) {
3037
+ function makeCacheFields(source, fieldNamesWithSharedItems, valueFieldNames) {
3038
3038
  const names = source.getRow(1).values;
3039
3039
  const sharedItemsFields = new Set(fieldNamesWithSharedItems);
3040
+ const valueFields = new Set(valueFieldNames);
3040
3041
  const aggregate = (columnIndex) => {
3041
3042
  const columnValues = source.getColumn(columnIndex).values;
3042
3043
  const uniqueValues = /* @__PURE__ */ new Set();
@@ -3046,13 +3047,42 @@ function makeCacheFields(source, fieldNamesWithSharedItems) {
3046
3047
  }
3047
3048
  return toSortedArray(uniqueValues);
3048
3049
  };
3050
+ const getMinMax = (columnIndex) => {
3051
+ const columnValues = source.getColumn(columnIndex).values;
3052
+ let min = Infinity;
3053
+ let max = -Infinity;
3054
+ let hasNumeric = false;
3055
+ for (let i = 2; i < columnValues.length; i++) {
3056
+ const v = columnValues[i];
3057
+ if (typeof v === "number" && !isNaN(v)) {
3058
+ hasNumeric = true;
3059
+ if (v < min) min = v;
3060
+ if (v > max) max = v;
3061
+ }
3062
+ }
3063
+ return hasNumeric ? {
3064
+ minValue: min,
3065
+ maxValue: max
3066
+ } : null;
3067
+ };
3049
3068
  const result = [];
3050
3069
  for (const columnIndex of range(1, names.length)) {
3051
3070
  const name = names[columnIndex];
3052
- const sharedItems = sharedItemsFields.has(name) ? aggregate(columnIndex) : null;
3053
- result.push({
3071
+ if (sharedItemsFields.has(name)) result.push({
3054
3072
  name,
3055
- sharedItems
3073
+ sharedItems: aggregate(columnIndex)
3074
+ });
3075
+ else if (valueFields.has(name)) {
3076
+ const minMax = getMinMax(columnIndex);
3077
+ result.push({
3078
+ name,
3079
+ sharedItems: null,
3080
+ minValue: minMax?.minValue,
3081
+ maxValue: minMax?.maxValue
3082
+ });
3083
+ } else result.push({
3084
+ name,
3085
+ sharedItems: null
3056
3086
  });
3057
3087
  }
3058
3088
  return result;
@@ -3115,7 +3145,6 @@ var Worksheet = class {
3115
3145
  this.colBreaks = [];
3116
3146
  this.properties = Object.assign({}, {
3117
3147
  defaultRowHeight: 15,
3118
- dyDescent: 55,
3119
3148
  outlineLevelCol: 0,
3120
3149
  outlineLevelRow: 0
3121
3150
  }, options.properties);
@@ -7489,116 +7518,136 @@ var FontXform = class FontXform extends BaseXform {
7489
7518
  constructor(options) {
7490
7519
  super();
7491
7520
  this.options = options || FontXform.OPTIONS;
7492
- this.map = {
7493
- b: {
7521
+ const fontProperties = [
7522
+ {
7523
+ tag: "b",
7494
7524
  prop: "bold",
7495
7525
  xform: new BooleanXform({
7496
7526
  tag: "b",
7497
7527
  attr: "val"
7498
7528
  })
7499
7529
  },
7500
- i: {
7530
+ {
7531
+ tag: "i",
7501
7532
  prop: "italic",
7502
7533
  xform: new BooleanXform({
7503
7534
  tag: "i",
7504
7535
  attr: "val"
7505
7536
  })
7506
7537
  },
7507
- u: {
7538
+ {
7539
+ tag: "u",
7508
7540
  prop: "underline",
7509
7541
  xform: new UnderlineXform()
7510
7542
  },
7511
- charset: {
7512
- prop: "charset",
7513
- xform: new IntegerXform({
7514
- tag: "charset",
7543
+ {
7544
+ tag: "strike",
7545
+ prop: "strike",
7546
+ xform: new BooleanXform({
7547
+ tag: "strike",
7515
7548
  attr: "val"
7516
7549
  })
7517
7550
  },
7518
- color: {
7519
- prop: "color",
7520
- xform: new ColorXform()
7521
- },
7522
- condense: {
7551
+ {
7552
+ tag: "condense",
7523
7553
  prop: "condense",
7524
7554
  xform: new BooleanXform({
7525
7555
  tag: "condense",
7526
7556
  attr: "val"
7527
7557
  })
7528
7558
  },
7529
- extend: {
7559
+ {
7560
+ tag: "extend",
7530
7561
  prop: "extend",
7531
7562
  xform: new BooleanXform({
7532
7563
  tag: "extend",
7533
7564
  attr: "val"
7534
7565
  })
7535
7566
  },
7536
- family: {
7537
- prop: "family",
7538
- xform: new IntegerXform({
7539
- tag: "family",
7567
+ {
7568
+ tag: "outline",
7569
+ prop: "outline",
7570
+ xform: new BooleanXform({
7571
+ tag: "outline",
7540
7572
  attr: "val"
7541
7573
  })
7542
7574
  },
7543
- outline: {
7544
- prop: "outline",
7575
+ {
7576
+ tag: "shadow",
7577
+ prop: "shadow",
7545
7578
  xform: new BooleanXform({
7546
- tag: "outline",
7579
+ tag: "shadow",
7547
7580
  attr: "val"
7548
7581
  })
7549
7582
  },
7550
- vertAlign: {
7551
- prop: "vertAlign",
7552
- xform: new StringXform({
7553
- tag: "vertAlign",
7583
+ {
7584
+ tag: "sz",
7585
+ prop: "size",
7586
+ xform: new IntegerXform({
7587
+ tag: "sz",
7554
7588
  attr: "val"
7555
7589
  })
7556
7590
  },
7557
- scheme: {
7558
- prop: "scheme",
7591
+ {
7592
+ tag: "color",
7593
+ prop: "color",
7594
+ xform: new ColorXform()
7595
+ },
7596
+ {
7597
+ tag: this.options.fontNameTag,
7598
+ prop: "name",
7559
7599
  xform: new StringXform({
7560
- tag: "scheme",
7600
+ tag: this.options.fontNameTag,
7561
7601
  attr: "val"
7562
7602
  })
7563
7603
  },
7564
- shadow: {
7565
- prop: "shadow",
7566
- xform: new BooleanXform({
7567
- tag: "shadow",
7604
+ {
7605
+ tag: "family",
7606
+ prop: "family",
7607
+ xform: new IntegerXform({
7608
+ tag: "family",
7568
7609
  attr: "val"
7569
7610
  })
7570
7611
  },
7571
- strike: {
7572
- prop: "strike",
7573
- xform: new BooleanXform({
7574
- tag: "strike",
7612
+ {
7613
+ tag: "scheme",
7614
+ prop: "scheme",
7615
+ xform: new StringXform({
7616
+ tag: "scheme",
7575
7617
  attr: "val"
7576
7618
  })
7577
7619
  },
7578
- sz: {
7579
- prop: "size",
7620
+ {
7621
+ tag: "charset",
7622
+ prop: "charset",
7580
7623
  xform: new IntegerXform({
7581
- tag: "sz",
7624
+ tag: "charset",
7625
+ attr: "val"
7626
+ })
7627
+ },
7628
+ {
7629
+ tag: "vertAlign",
7630
+ prop: "vertAlign",
7631
+ xform: new StringXform({
7632
+ tag: "vertAlign",
7582
7633
  attr: "val"
7583
7634
  })
7584
7635
  }
7585
- };
7586
- this.map[this.options.fontNameTag] = {
7587
- prop: "name",
7588
- xform: new StringXform({
7589
- tag: this.options.fontNameTag,
7590
- attr: "val"
7591
- })
7592
- };
7636
+ ];
7637
+ this.map = Object.fromEntries(fontProperties.map((p) => [p.tag, {
7638
+ prop: p.prop,
7639
+ xform: p.xform
7640
+ }]));
7641
+ this.renderOrder = fontProperties.map((p) => p.tag);
7593
7642
  }
7594
7643
  get tag() {
7595
7644
  return this.options.tagName;
7596
7645
  }
7597
7646
  render(xmlStream, model) {
7598
- const { map } = this;
7647
+ const { map, renderOrder } = this;
7599
7648
  xmlStream.openNode(this.options.tagName);
7600
- Object.entries(this.map).forEach(([tag, defn]) => {
7601
- map[tag].xform.render(xmlStream, model[defn.prop]);
7649
+ renderOrder.forEach((tag) => {
7650
+ map[tag].xform.render(xmlStream, model[map[tag].prop]);
7602
7651
  });
7603
7652
  xmlStream.closeNode();
7604
7653
  }
@@ -9677,10 +9726,6 @@ var ContentTypesXform = class ContentTypesXform extends BaseXform {
9677
9726
  PartName: `/xl/pivotCache/pivotCacheRecords${n}.xml`,
9678
9727
  ContentType: "application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheRecords+xml"
9679
9728
  });
9680
- xmlStream.leafNode("Override", {
9681
- PartName: `/xl/pivotTables/pivotTable${n}.xml`,
9682
- ContentType: "application/vnd.openxmlformats-officedocument.spreadsheetml.pivotTable+xml"
9683
- });
9684
9729
  });
9685
9730
  xmlStream.leafNode("Override", {
9686
9731
  PartName: "/xl/theme/theme1.xml",
@@ -9700,13 +9745,20 @@ var ContentTypesXform = class ContentTypesXform extends BaseXform {
9700
9745
  ContentType: "application/vnd.openxmlformats-officedocument.spreadsheetml.table+xml"
9701
9746
  });
9702
9747
  });
9748
+ if ((model.pivotTables || []).length) (model.pivotTables || []).forEach((pivotTable) => {
9749
+ const n = pivotTable.tableNumber;
9750
+ xmlStream.leafNode("Override", {
9751
+ PartName: `/xl/pivotTables/pivotTable${n}.xml`,
9752
+ ContentType: "application/vnd.openxmlformats-officedocument.spreadsheetml.pivotTable+xml"
9753
+ });
9754
+ });
9703
9755
  if (model.drawings) model.drawings.forEach((drawing) => {
9704
9756
  xmlStream.leafNode("Override", {
9705
9757
  PartName: `/xl/drawings/${drawing.name}.xml`,
9706
9758
  ContentType: "application/vnd.openxmlformats-officedocument.drawing+xml"
9707
9759
  });
9708
9760
  });
9709
- if (model.commentRefs) {
9761
+ if (model.commentRefs && model.commentRefs.length) {
9710
9762
  xmlStream.leafNode("Default", {
9711
9763
  Extension: "vml",
9712
9764
  ContentType: "application/vnd.openxmlformats-officedocument.vmlDrawing"
@@ -9955,9 +10007,9 @@ function extractRanges(parsedText) {
9955
10007
  var WorksheetXform = class extends BaseXform {
9956
10008
  render(xmlStream, model) {
9957
10009
  xmlStream.leafNode("sheet", {
9958
- sheetId: model.id,
9959
10010
  name: model.name,
9960
- state: model.state,
10011
+ sheetId: model.id,
10012
+ state: model.state === "visible" ? void 0 : model.state,
9961
10013
  "r:id": model.rId
9962
10014
  });
9963
10015
  }
@@ -10027,7 +10079,6 @@ var WorkbookPropertiesXform = class extends BaseXform {
10027
10079
  render(xmlStream, model) {
10028
10080
  xmlStream.leafNode("workbookPr", {
10029
10081
  date1904: model.date1904 ? 1 : void 0,
10030
- defaultThemeVersion: 164011,
10031
10082
  filterPrivacy: 1
10032
10083
  });
10033
10084
  }
@@ -10724,7 +10775,6 @@ var RowXform = class extends BaseXform {
10724
10775
  xmlStream.addAttribute("s", model.styleId);
10725
10776
  xmlStream.addAttribute("customFormat", "1");
10726
10777
  }
10727
- xmlStream.addAttribute("x14ac:dyDescent", "0.25");
10728
10778
  if (model.outlineLevel) xmlStream.addAttribute("outlineLevel", model.outlineLevel);
10729
10779
  if (model.collapsed) xmlStream.addAttribute("collapsed", "1");
10730
10780
  const cellXform = this.map.c;
@@ -11257,9 +11307,9 @@ var SheetFormatPropertiesXform = class extends BaseXform {
11257
11307
  if (model) {
11258
11308
  const attributes = {
11259
11309
  defaultRowHeight: model.defaultRowHeight,
11260
- outlineLevelRow: model.outlineLevelRow,
11261
- outlineLevelCol: model.outlineLevelCol,
11262
- "x14ac:dyDescent": model.dyDescent
11310
+ outlineLevelRow: model.outlineLevelRow || void 0,
11311
+ outlineLevelCol: model.outlineLevelCol || void 0,
11312
+ "x14ac:dyDescent": model.dyDescent || void 0
11263
11313
  };
11264
11314
  if (model.defaultColWidth) attributes.defaultColWidth = model.defaultColWidth;
11265
11315
  if (!model.defaultRowHeight || model.defaultRowHeight !== 15) attributes.customHeight = "1";
@@ -11306,12 +11356,14 @@ var SheetViewXform = class extends BaseXform {
11306
11356
  }
11307
11357
  }
11308
11358
  render(xmlStream, model) {
11309
- xmlStream.openNode("sheetView", { workbookViewId: model.workbookViewId || 0 });
11359
+ const initialAttrs = {};
11360
+ if (model.tabSelected) initialAttrs.tabSelected = "1";
11361
+ initialAttrs.workbookViewId = model.workbookViewId || 0;
11362
+ xmlStream.openNode("sheetView", initialAttrs);
11310
11363
  const add = function(name, value, included) {
11311
11364
  if (included) xmlStream.addAttribute(name, value);
11312
11365
  };
11313
11366
  add("rightToLeft", "1", model.rightToLeft === true);
11314
- add("tabSelected", "1", model.tabSelected);
11315
11367
  add("showRuler", "0", model.showRuler === false);
11316
11368
  add("showRowColHeaders", "0", model.showRowColHeaders === false);
11317
11369
  add("showGridLines", "0", model.showGridLines === false);
@@ -11611,9 +11663,9 @@ var PageSetupXform = class extends BaseXform {
11611
11663
  draft: booleanToXml$1(model.draft),
11612
11664
  cellComments: cellCommentsToXml(model.cellComments),
11613
11665
  errors: errorsToXml(model.errors),
11614
- scale: model.scale,
11615
- fitToWidth: model.fitToWidth,
11616
- fitToHeight: model.fitToHeight,
11666
+ scale: model.scale !== 100 ? model.scale : void 0,
11667
+ fitToWidth: model.fitToWidth !== 1 ? model.fitToWidth : void 0,
11668
+ fitToHeight: model.fitToHeight !== 1 ? model.fitToHeight : void 0,
11617
11669
  firstPageNumber: model.firstPageNumber,
11618
11670
  useFirstPageNumber: booleanToXml$1(!!model.firstPageNumber),
11619
11671
  usePrinterDefaults: booleanToXml$1(model.usePrinterDefaults),
@@ -13005,8 +13057,8 @@ var WorkSheetXform = class WorkSheetXform extends BaseXform {
13005
13057
  xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main",
13006
13058
  "xmlns:r": "http://schemas.openxmlformats.org/officeDocument/2006/relationships",
13007
13059
  "xmlns:mc": "http://schemas.openxmlformats.org/markup-compatibility/2006",
13008
- "mc:Ignorable": "x14ac",
13009
- "xmlns:x14ac": "http://schemas.microsoft.com/office/spreadsheetml/2009/9/ac"
13060
+ "xmlns:x14ac": "http://schemas.microsoft.com/office/spreadsheetml/2009/9/ac",
13061
+ "mc:Ignorable": "x14ac"
13010
13062
  };
13011
13063
  }
13012
13064
  constructor(options) {
@@ -14273,7 +14325,7 @@ var TableColumnXform = class extends BaseXform {
14273
14325
  id: model.id.toString(),
14274
14326
  name: model.name,
14275
14327
  totalsRowLabel: model.totalsRowLabel,
14276
- totalsRowFunction: model.totalsRowFunction,
14328
+ totalsRowFunction: model.totalsRowFunction === "none" ? void 0 : model.totalsRowFunction,
14277
14329
  dxfId: model.dxfId
14278
14330
  });
14279
14331
  }
@@ -14379,8 +14431,7 @@ var TableXform = class TableXform extends BaseXform {
14379
14431
  displayName: model.displayName || model.name,
14380
14432
  ref: model.tableRef,
14381
14433
  totalsRowCount: model.totalsRow ? "1" : void 0,
14382
- totalsRowShown: model.totalsRow ? void 0 : "1",
14383
- headerRowCount: model.headerRow ? "1" : "0"
14434
+ headerRowCount: model.headerRow ? void 0 : "0"
14384
14435
  });
14385
14436
  this.map.autoFilter.render(xmlStream, model);
14386
14437
  this.map.tableColumns.render(xmlStream, model.columns);
@@ -14401,7 +14452,7 @@ var TableXform = class TableXform extends BaseXform {
14401
14452
  displayName: attributes.displayName || attributes.name,
14402
14453
  tableRef: attributes.ref,
14403
14454
  totalsRow: attributes.totalsRowCount === "1",
14404
- headerRow: attributes.headerRowCount === "1"
14455
+ headerRow: attributes.headerRowCount !== "0"
14405
14456
  };
14406
14457
  break;
14407
14458
  default:
@@ -14441,13 +14492,7 @@ var TableXform = class TableXform extends BaseXform {
14441
14492
  });
14442
14493
  }
14443
14494
  static {
14444
- this.TABLE_ATTRIBUTES = {
14445
- xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main",
14446
- "xmlns:mc": "http://schemas.openxmlformats.org/markup-compatibility/2006",
14447
- "mc:Ignorable": "xr xr3",
14448
- "xmlns:xr": "http://schemas.microsoft.com/office/spreadsheetml/2014/revision",
14449
- "xmlns:xr3": "http://schemas.microsoft.com/office/spreadsheetml/2016/revision3"
14450
- };
14495
+ this.TABLE_ATTRIBUTES = { xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main" };
14451
14496
  }
14452
14497
  };
14453
14498
 
@@ -14631,15 +14676,33 @@ var PivotCacheRecordsXform = class PivotCacheRecordsXform extends BaseXform {
14631
14676
  //#endregion
14632
14677
  //#region src/xlsx/xform/pivot-table/cache-field.ts
14633
14678
  var CacheField = class {
14634
- constructor({ name, sharedItems }) {
14679
+ constructor({ name, sharedItems, minValue, maxValue }) {
14635
14680
  this.name = name;
14636
14681
  this.sharedItems = sharedItems;
14682
+ this.minValue = minValue;
14683
+ this.maxValue = maxValue;
14637
14684
  }
14638
14685
  render() {
14639
14686
  const escapedName = xmlEncode(this.name);
14640
- if (this.sharedItems === null) return `<cacheField name="${escapedName}" numFmtId="0">
14641
- <sharedItems containsSemiMixedTypes="0" containsString="0" containsNumber="1" containsInteger="1" />
14687
+ if (this.sharedItems === null) {
14688
+ if (this.minValue === void 0 || this.maxValue === void 0) return `<cacheField name="${escapedName}" numFmtId="0">
14689
+ <sharedItems />
14690
+ </cacheField>`;
14691
+ return `<cacheField name="${escapedName}" numFmtId="0">
14692
+ <sharedItems containsSemiMixedTypes="0" containsString="0" containsNumber="1" containsInteger="1" minValue="${this.minValue}" maxValue="${this.maxValue}" />
14642
14693
  </cacheField>`;
14694
+ }
14695
+ const allNumeric = this.sharedItems.length > 0 && this.sharedItems.every((item) => typeof item === "number" && Number.isFinite(item));
14696
+ const allInteger = allNumeric && this.sharedItems.every((item) => Number.isInteger(item));
14697
+ if (allNumeric) {
14698
+ const minValue = Math.min(...this.sharedItems);
14699
+ const maxValue = Math.max(...this.sharedItems);
14700
+ return `<cacheField name="${escapedName}" numFmtId="0">
14701
+ <sharedItems containsSemiMixedTypes="0" containsString="0" containsNumber="1"${allInteger ? " containsInteger=\"1\"" : ""} minValue="${minValue}" maxValue="${maxValue}" count="${this.sharedItems.length}">
14702
+ ${this.sharedItems.map((item) => `<n v="${item}" />`).join("")}
14703
+ </sharedItems>
14704
+ </cacheField>`;
14705
+ }
14643
14706
  return `<cacheField name="${escapedName}" numFmtId="0">
14644
14707
  <sharedItems count="${this.sharedItems.length}">
14645
14708
  ${this.sharedItems.map((item) => `<s v="${xmlEncode(String(item))}" />`).join("")}
@@ -14693,16 +14756,13 @@ var CacheFieldXform = class extends BaseXform {
14693
14756
  break;
14694
14757
  case "sharedItems":
14695
14758
  this.inSharedItems = true;
14696
- if (attributes.containsNumber === "1" || attributes.containsInteger === "1") {
14697
- if (this.model) {
14698
- this.model.containsNumber = attributes.containsNumber === "1";
14699
- this.model.containsInteger = attributes.containsInteger === "1";
14700
- if (attributes.minValue !== void 0) this.model.minValue = parseFloat(attributes.minValue);
14701
- if (attributes.maxValue !== void 0) this.model.maxValue = parseFloat(attributes.maxValue);
14702
- this.model.sharedItems = null;
14703
- }
14704
- } else if (this.model) {
14759
+ if (this.model) {
14760
+ this.model.containsNumber = attributes.containsNumber === "1";
14761
+ this.model.containsInteger = attributes.containsInteger === "1";
14762
+ if (attributes.minValue !== void 0) this.model.minValue = parseFloat(attributes.minValue);
14763
+ if (attributes.maxValue !== void 0) this.model.maxValue = parseFloat(attributes.maxValue);
14705
14764
  if (parseInt(attributes.count || "0", 10) > 0) this.model.sharedItems = [];
14765
+ else this.model.sharedItems = null;
14706
14766
  }
14707
14767
  break;
14708
14768
  case "s":
@@ -14793,8 +14853,6 @@ var PivotCacheDefinitionXform = class PivotCacheDefinitionXform extends BaseXfor
14793
14853
  ...PivotCacheDefinitionXform.PIVOT_CACHE_DEFINITION_ATTRIBUTES,
14794
14854
  "r:id": "rId1",
14795
14855
  refreshOnLoad: "1",
14796
- refreshedBy: "Author",
14797
- refreshedDate: "45125.026046874998",
14798
14856
  createdVersion: "8",
14799
14857
  refreshedVersion: "8",
14800
14858
  minRefreshableVersion: "3",
@@ -14821,8 +14879,6 @@ var PivotCacheDefinitionXform = class PivotCacheDefinitionXform extends BaseXfor
14821
14879
  ...PivotCacheDefinitionXform.PIVOT_CACHE_DEFINITION_ATTRIBUTES,
14822
14880
  "r:id": model.rId || "rId1",
14823
14881
  refreshOnLoad: model.refreshOnLoad || "1",
14824
- refreshedBy: model.refreshedBy || "Author",
14825
- refreshedDate: model.refreshedDate || "45125.026046874998",
14826
14882
  createdVersion: model.createdVersion || "8",
14827
14883
  refreshedVersion: model.refreshedVersion || "8",
14828
14884
  minRefreshableVersion: model.minRefreshableVersion || "3",
@@ -14852,8 +14908,6 @@ var PivotCacheDefinitionXform = class PivotCacheDefinitionXform extends BaseXfor
14852
14908
  cacheFields: [],
14853
14909
  rId: attributes["r:id"],
14854
14910
  refreshOnLoad: attributes.refreshOnLoad,
14855
- refreshedBy: attributes.refreshedBy,
14856
- refreshedDate: attributes.refreshedDate,
14857
14911
  createdVersion: attributes.createdVersion,
14858
14912
  refreshedVersion: attributes.refreshedVersion,
14859
14913
  minRefreshableVersion: attributes.minRefreshableVersion,
@@ -14908,10 +14962,7 @@ var PivotCacheDefinitionXform = class PivotCacheDefinitionXform extends BaseXfor
14908
14962
  static {
14909
14963
  this.PIVOT_CACHE_DEFINITION_ATTRIBUTES = {
14910
14964
  xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main",
14911
- "xmlns:r": "http://schemas.openxmlformats.org/officeDocument/2006/relationships",
14912
- "xmlns:mc": "http://schemas.openxmlformats.org/markup-compatibility/2006",
14913
- "mc:Ignorable": "xr",
14914
- "xmlns:xr": "http://schemas.microsoft.com/office/spreadsheetml/2014/revision"
14965
+ "xmlns:r": "http://schemas.openxmlformats.org/officeDocument/2006/relationships"
14915
14966
  };
14916
14967
  }
14917
14968
  };
@@ -14964,18 +15015,16 @@ var PivotTableXform = class PivotTableXform extends BaseXform {
14964
15015
  */
14965
15016
  renderNew(xmlStream, model) {
14966
15017
  const { rows, columns, values, cacheFields, cacheId, applyWidthHeightFormats } = model;
14967
- const uniqueUid = `{${crypto.randomUUID().toUpperCase()}}`;
14968
15018
  const rowItems = buildRowItems(rows, cacheFields);
14969
15019
  const colItems = buildColItems(columns, cacheFields, values.length);
14970
15020
  const rowFieldItemCount = rows.length > 0 ? cacheFields[rows[0]]?.sharedItems?.length || 0 : 0;
14971
15021
  const colFieldItemCount = columns.length > 0 ? cacheFields[columns[0]]?.sharedItems?.length || 0 : 0;
14972
- const endRow = 3 + rowFieldItemCount + 1;
15022
+ const endRow = 4 + rowFieldItemCount + 1;
14973
15023
  const endCol = 1 + colFieldItemCount + 1;
14974
15024
  const locationRef = `A3:${String.fromCharCode(64 + endCol)}${endRow}`;
14975
15025
  xmlStream.openXml(XmlStream.StdDocAttributes);
14976
15026
  xmlStream.openNode(this.tag, {
14977
15027
  ...PivotTableXform.PIVOT_TABLE_ATTRIBUTES,
14978
- "xr:uid": uniqueUid,
14979
15028
  name: "PivotTable2",
14980
15029
  cacheId,
14981
15030
  applyNumberFormats: "0",
@@ -15050,11 +15099,9 @@ var PivotTableXform = class PivotTableXform extends BaseXform {
15050
15099
  * Render loaded pivot table (preserving original structure)
15051
15100
  */
15052
15101
  renderLoaded(xmlStream, model) {
15053
- const uniqueUid = model.uid || `{${crypto.randomUUID().toUpperCase()}}`;
15054
15102
  xmlStream.openXml(XmlStream.StdDocAttributes);
15055
15103
  xmlStream.openNode(this.tag, {
15056
15104
  ...PivotTableXform.PIVOT_TABLE_ATTRIBUTES,
15057
- "xr:uid": uniqueUid,
15058
15105
  name: model.name || "PivotTable1",
15059
15106
  cacheId: model.cacheId,
15060
15107
  applyNumberFormats: model.applyNumberFormats || "0",
@@ -15303,19 +15350,15 @@ var PivotTableXform = class PivotTableXform extends BaseXform {
15303
15350
  }
15304
15351
  reconcile(_model, _options) {}
15305
15352
  static {
15306
- this.PIVOT_TABLE_ATTRIBUTES = {
15307
- xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main",
15308
- "xmlns:mc": "http://schemas.openxmlformats.org/markup-compatibility/2006",
15309
- "mc:Ignorable": "xr",
15310
- "xmlns:xr": "http://schemas.microsoft.com/office/spreadsheetml/2014/revision"
15311
- };
15353
+ this.PIVOT_TABLE_ATTRIBUTES = { xmlns: "http://schemas.openxmlformats.org/spreadsheetml/2006/main" };
15312
15354
  }
15313
15355
  };
15314
15356
  /**
15315
15357
  * Build rowItems XML - one item for each unique value in row fields, plus grand total.
15316
15358
  * Each <i> represents a row in the pivot table.
15317
- * - Regular items: <i><x v="index"/></i> where index is the position in sharedItems
15359
+ * - Regular items: <i><x/></i> for index 0, <i><x v="index"/></i> for index > 0
15318
15360
  * - Grand total: <i t="grand"><x/></i>
15361
+ * Note: When v=0, the v attribute should be omitted (Excel convention)
15319
15362
  */
15320
15363
  function buildRowItems(rows, cacheFields) {
15321
15364
  if (rows.length === 0) return {
@@ -15324,7 +15367,8 @@ function buildRowItems(rows, cacheFields) {
15324
15367
  };
15325
15368
  const itemCount = (cacheFields[rows[0]]?.sharedItems || []).length;
15326
15369
  const items = [];
15327
- for (let i = 0; i < itemCount; i++) items.push(`<i><x v="${i}" /></i>`);
15370
+ for (let i = 0; i < itemCount; i++) if (i === 0) items.push("<i><x /></i>");
15371
+ else items.push(`<i><x v="${i}" /></i>`);
15328
15372
  items.push("<i t=\"grand\"><x /></i>");
15329
15373
  return {
15330
15374
  count: items.length,
@@ -15334,12 +15378,14 @@ function buildRowItems(rows, cacheFields) {
15334
15378
  /**
15335
15379
  * Build colItems XML - one item for each unique value in column fields, plus grand total.
15336
15380
  * When there are multiple data fields (values), each column value may have sub-columns.
15381
+ * Note: When v=0, the v attribute should be omitted (Excel convention)
15337
15382
  */
15338
15383
  function buildColItems(columns, cacheFields, valueCount) {
15339
15384
  if (columns.length === 0) {
15340
15385
  if (valueCount > 1) {
15341
15386
  const items$1 = [];
15342
- for (let i = 0; i < valueCount; i++) items$1.push(`<i><x v="${i}" /></i>`);
15387
+ for (let i = 0; i < valueCount; i++) if (i === 0) items$1.push("<i><x /></i>");
15388
+ else items$1.push(`<i><x v="${i}" /></i>`);
15343
15389
  items$1.push("<i t=\"grand\"><x /></i>");
15344
15390
  return {
15345
15391
  count: items$1.length,
@@ -15353,7 +15399,8 @@ function buildColItems(columns, cacheFields, valueCount) {
15353
15399
  }
15354
15400
  const itemCount = (cacheFields[columns[0]]?.sharedItems || []).length;
15355
15401
  const items = [];
15356
- for (let i = 0; i < itemCount; i++) items.push(`<i><x v="${i}" /></i>`);
15402
+ for (let i = 0; i < itemCount; i++) if (i === 0) items.push("<i><x /></i>");
15403
+ else items.push(`<i><x v="${i}" /></i>`);
15357
15404
  items.push("<i t=\"grand\"><x /></i>");
15358
15405
  return {
15359
15406
  count: items.length,
@@ -15379,16 +15426,17 @@ function renderPivotFields(pivotTable) {
15379
15426
  const colSet = new Set(pivotTable.columns);
15380
15427
  const valueSet = new Set(pivotTable.values);
15381
15428
  return pivotTable.cacheFields.map((cacheField, fieldIndex) => {
15382
- return renderPivotField(rowSet.has(fieldIndex) ? "row" : colSet.has(fieldIndex) ? "column" : valueSet.has(fieldIndex) ? "value" : null, cacheField.sharedItems);
15429
+ return renderPivotField(rowSet.has(fieldIndex), colSet.has(fieldIndex), valueSet.has(fieldIndex), cacheField.sharedItems);
15383
15430
  }).join("");
15384
15431
  }
15385
- function renderPivotField(fieldType, sharedItems) {
15386
- const defaultAttributes = "compact=\"0\" outline=\"0\" showAll=\"0\" defaultSubtotal=\"0\"";
15387
- if (fieldType === "row" || fieldType === "column") {
15388
- const axis = fieldType === "row" ? "axisRow" : "axisCol";
15432
+ function renderPivotField(isRow, isCol, isValue, sharedItems) {
15433
+ if (isRow || isCol) {
15434
+ const axis = isRow ? "axisRow" : "axisCol";
15435
+ let axisAttributes = "compact=\"0\" outline=\"0\" showAll=\"0\"";
15436
+ if (isValue) axisAttributes = `dataField="1" ${axisAttributes}`;
15389
15437
  const itemsXml = [...sharedItems.map((_item, index) => `<item x="${index}" />`), "<item t=\"default\" />"].join("\n ");
15390
15438
  return `
15391
- <pivotField axis="${axis}" ${defaultAttributes}>
15439
+ <pivotField axis="${axis}" ${axisAttributes}>
15392
15440
  <items count="${sharedItems.length + 1}">
15393
15441
  ${itemsXml}
15394
15442
  </items>
@@ -15397,8 +15445,8 @@ function renderPivotField(fieldType, sharedItems) {
15397
15445
  }
15398
15446
  return `
15399
15447
  <pivotField
15400
- ${fieldType === "value" ? "dataField=\"1\"" : ""}
15401
- ${defaultAttributes}
15448
+ ${isValue ? "dataField=\"1\"" : ""}
15449
+ compact="0" outline="0" showAll="0" defaultSubtotal="0"
15402
15450
  />
15403
15451
  `;
15404
15452
  }