@odoo/o-spreadsheet 19.2.13 → 19.2.15

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.
@@ -2,9 +2,9 @@
2
2
  /**
3
3
  * This file is generated by o-spreadsheet build tools. Do not edit it.
4
4
  * @see https://github.com/odoo/o-spreadsheet
5
- * @version 19.2.13
6
- * @date 2026-05-15T07:07:37.391Z
7
- * @hash fece642
5
+ * @version 19.2.15
6
+ * @date 2026-06-06T06:23:14.723Z
7
+ * @hash d29528e
8
8
  */
9
9
 
10
10
  import { App, Component, blockDom, markRaw, onMounted, onPatched, onWillPatch, onWillStart, onWillUnmount, onWillUpdateProps, status, toRaw, useChildSubEnv, useComponent, useEffect, useEnv, useExternalListener, useRef, useState, useSubEnv, whenReady, xml } from "@odoo/owl";
@@ -4327,6 +4327,7 @@ const DEFAULT_LOCALE = DEFAULT_LOCALES[0];
4327
4327
  //#endregion
4328
4328
  //#region src/helpers/format/format_tokenizer.ts
4329
4329
  function tokenizeFormat(str) {
4330
+ str = str.replace(/\s/g, " ");
4330
4331
  const chars = new TokenizingChars(str);
4331
4332
  const result = [];
4332
4333
  let currentFormatPart = [];
@@ -5503,7 +5504,12 @@ const lockedSheetAllowedCommands = new Set([
5503
5504
  "SET_ZOOM",
5504
5505
  "UPDATE_CAROUSEL_ACTIVE_ITEM",
5505
5506
  "DUPLICATE_PIVOT_IN_NEW_SHEET",
5506
- "UPDATE_FILTER"
5507
+ "UPDATE_FILTER",
5508
+ "ACTIVATE_NEXT_SHEET",
5509
+ "ACTIVATE_PREVIOUS_SHEET",
5510
+ "SCROLL_TO_CELL",
5511
+ "SHIFT_VIEWPORT_DOWN",
5512
+ "SHIFT_VIEWPORT_UP"
5507
5513
  ]);
5508
5514
  const coreTypes = new Set([
5509
5515
  "UPDATE_CELL",
@@ -6483,8 +6489,13 @@ function getApplyRangeChangeAddColRow(cmd) {
6483
6489
  changeType: "NONE",
6484
6490
  range
6485
6491
  };
6492
+ const isUnboundedAtEnd = range.unboundedZone[end] === void 0;
6493
+ if (isUnboundedAtEnd && !range.unboundedZone.hasHeader) return {
6494
+ changeType: "RESIZE",
6495
+ range: createAdaptedRange(range, dimension, "RESIZE", cmd.quantity)
6496
+ };
6486
6497
  if (cmd.position === "after") {
6487
- if (range.zone[start] <= cmd.base && cmd.base < range.zone[end]) return {
6498
+ if (range.zone[start] <= cmd.base && (cmd.base < range.zone[end] || isUnboundedAtEnd)) return {
6488
6499
  changeType: "RESIZE",
6489
6500
  range: createAdaptedRange(range, dimension, "RESIZE", cmd.quantity)
6490
6501
  };
@@ -7077,40 +7088,9 @@ var UuidGenerator = class {
7077
7088
  }
7078
7089
  };
7079
7090
 
7080
- //#endregion
7081
- //#region src/registry.ts
7082
- var Registry$1 = class {
7083
- content = {};
7084
- add(key, value) {
7085
- if (key in this.content) throw new Error(`${key} is already present in this registry!`);
7086
- return this.replace(key, value);
7087
- }
7088
- replace(key, value) {
7089
- this.content[key] = value;
7090
- return this;
7091
- }
7092
- get(key) {
7093
- const content = this.content[key];
7094
- if (!content && !(key in this.content)) throw new Error(`Cannot find ${key} in this registry!`);
7095
- return content;
7096
- }
7097
- contains(key) {
7098
- return key in this.content;
7099
- }
7100
- getAll() {
7101
- return Object.values(this.content);
7102
- }
7103
- getKeys() {
7104
- return Object.keys(this.content);
7105
- }
7106
- remove(key) {
7107
- delete this.content[key];
7108
- }
7109
- };
7110
-
7111
7091
  //#endregion
7112
7092
  //#region src/helpers/figures/charts/chart_js_extension.ts
7113
- const chartJsExtensionRegistry = new Registry$1();
7093
+ const chartJsExtensionRegistry = new Registry();
7114
7094
  function areChartJSExtensionsLoaded() {
7115
7095
  return globalThis.Chart ? !!globalThis.Chart.registry.plugins.get("chartShowValuesPlugin") : true;
7116
7096
  }
@@ -7428,6 +7408,10 @@ const FORCE_DEFAULT_ARGS_FUNCTIONS = {
7428
7408
  ROUNDDOWN: [{
7429
7409
  type: "NUMBER",
7430
7410
  value: 0
7411
+ }],
7412
+ IFERROR: [{
7413
+ type: "NUMBER",
7414
+ value: 0
7431
7415
  }]
7432
7416
  };
7433
7417
  /**
@@ -25701,7 +25685,7 @@ const HYPERLINK = {
25701
25685
  //#endregion
25702
25686
  //#region src/functions/function_registry.ts
25703
25687
  const functionNameRegex = /^[A-Z0-9\_\.]+$/;
25704
- var FunctionRegistry = class extends Registry$1 {
25688
+ var FunctionRegistry = class extends Registry {
25705
25689
  mapping = {};
25706
25690
  add(name, addDescr) {
25707
25691
  name = name.toUpperCase();
@@ -30195,7 +30179,7 @@ const WEEK_START = {
30195
30179
 
30196
30180
  //#endregion
30197
30181
  //#region src/migrations/migration_steps.ts
30198
- const migrationStepRegistry = new Registry$1();
30182
+ const migrationStepRegistry = new Registry();
30199
30183
  migrationStepRegistry.add("0.1", { migrate(data) {
30200
30184
  if (data.sheets && data.sheets[0]) data.activeSheet = data.sheets[0].name;
30201
30185
  return data;
@@ -37518,11 +37502,10 @@ const INSERT_TABLE = (env) => {
37518
37502
  if (interactiveCreateTable(env, env.model.getters.getActiveSheetId()).isSuccessful) env.openSidePanel("TableSidePanel", {});
37519
37503
  };
37520
37504
  const DELETE_SELECTED_TABLE = (env) => {
37521
- const position = env.model.getters.getActivePosition();
37522
- const table = env.model.getters.getTable(position);
37505
+ const table = env.model.getters.getFirstTableInSelection();
37523
37506
  if (!table) return;
37524
37507
  env.model.dispatch("REMOVE_TABLE", {
37525
- sheetId: position.sheetId,
37508
+ sheetId: env.model.getters.getActiveSheetId(),
37526
37509
  target: [table.range.zone]
37527
37510
  });
37528
37511
  };
@@ -43305,7 +43288,7 @@ function getVisiblePivotCellPositions(getters, pivotId) {
43305
43288
  col,
43306
43289
  row
43307
43290
  };
43308
- if (pivotId === getters.getPivotIdFromPosition(position)) positions.push(position);
43291
+ if (getters.getPivotIdsFromPosition(position).includes(pivotId)) positions.push(position);
43309
43292
  }
43310
43293
  return positions;
43311
43294
  }
@@ -45729,7 +45712,7 @@ var SpreadsheetPivot = class {
45729
45712
 
45730
45713
  //#endregion
45731
45714
  //#region src/helpers/pivot/pivot_registry.ts
45732
- const pivotRegistry = new Registry$1();
45715
+ const pivotRegistry = new Registry();
45733
45716
  const dateGranularities = [
45734
45717
  "year",
45735
45718
  "quarter_number",
@@ -45793,6 +45776,9 @@ const PIVOT_FUNCTIONS = [
45793
45776
  function getFirstPivotFunction(compiledFormula, getters) {
45794
45777
  return compiledFormula.getFunctionsFromTokens(PIVOT_FUNCTIONS, getters)[0];
45795
45778
  }
45779
+ function getPivotFunctions(compiledFormula, getters) {
45780
+ return compiledFormula.getFunctionsFromTokens(PIVOT_FUNCTIONS, getters);
45781
+ }
45796
45782
  /**
45797
45783
  * Parse a spreadsheet formula and detect the number of PIVOT functions that are
45798
45784
  * present in the given formula.
@@ -63521,6 +63507,7 @@ var PivotUIPlugin = class extends CoreViewPlugin {
63521
63507
  "getFirstPivotFunction",
63522
63508
  "getPivotCellSortDirection",
63523
63509
  "getPivotIdFromPosition",
63510
+ "getPivotIdsFromPosition",
63524
63511
  "getPivotCellFromPosition",
63525
63512
  "generateNewCalculatedMeasureName",
63526
63513
  "isPivotUnused",
@@ -63547,9 +63534,11 @@ var PivotUIPlugin = class extends CoreViewPlugin {
63547
63534
  this.refreshPivot(cmd.id);
63548
63535
  break;
63549
63536
  case "ADD_PIVOT":
63537
+ this.unusedPivotsInFormulas?.push(cmd.pivotId);
63550
63538
  this.setupPivot(cmd.pivotId);
63551
63539
  break;
63552
63540
  case "DUPLICATE_PIVOT":
63541
+ this.unusedPivotsInFormulas?.push(cmd.newPivotId);
63553
63542
  this.setupPivot(cmd.newPivotId);
63554
63543
  break;
63555
63544
  case "UPDATE_PIVOT":
@@ -63580,37 +63569,52 @@ var PivotUIPlugin = class extends CoreViewPlugin {
63580
63569
  }
63581
63570
  }
63582
63571
  /**
63583
- * Get the id of the pivot at the given position. Returns undefined if there
63572
+ * Get the id of the first pivot in the formula at the given position. Returns undefined if there
63584
63573
  * is no pivot at this position
63585
63574
  */
63586
63575
  getPivotIdFromPosition(position) {
63576
+ return this.getPivotIdsFromPosition(position)[0];
63577
+ }
63578
+ /**
63579
+ * Get all of the ids of the pivot present in the formula at the given position.
63580
+ */
63581
+ getPivotIdsFromPosition(position) {
63587
63582
  const cell = this.getters.getCorrespondingFormulaCell(position);
63588
- if (cell && cell.isFormula) {
63589
- const pivotFunction = this.getFirstPivotFunction(position.sheetId, cell.compiledFormula);
63590
- if (pivotFunction) {
63591
- const pivotId = pivotFunction.args[0]?.toString();
63592
- return pivotId && this.getters.getPivotId(pivotId);
63593
- }
63594
- }
63583
+ if (cell && cell.isFormula) return this.getPivotIdsFromFormula(position.sheetId, cell.compiledFormula);
63584
+ return [];
63585
+ }
63586
+ getPivotIdsFromFormula(sheetId, formula) {
63587
+ return this.getPivotFunctions(sheetId, formula).map((pivotFunction) => {
63588
+ const pivotId = pivotFunction.args[0]?.toString();
63589
+ return pivotId && this.getters.getPivotId(pivotId);
63590
+ }).filter(isDefined);
63595
63591
  }
63596
63592
  isSpillPivotFormula(position) {
63597
63593
  const cell = this.getters.getCorrespondingFormulaCell(position);
63598
63594
  if (cell && cell.isFormula) return this.getFirstPivotFunction(position.sheetId, cell.compiledFormula)?.functionName === "PIVOT";
63599
63595
  return false;
63600
63596
  }
63601
- getFirstPivotFunction(sheetId, compiledFormula) {
63602
- const pivotFunction = getFirstPivotFunction(compiledFormula, this.getters);
63603
- if (!pivotFunction) return;
63604
- const { functionName, args } = pivotFunction;
63605
- return {
63606
- functionName,
63607
- args: args.map((argAst) => {
63597
+ getPivotFunctions(sheetId, formula) {
63598
+ const pivotFunctions = getPivotFunctions(formula, this.getters);
63599
+ if (!pivotFunctions.length) return [];
63600
+ const evaluatedPivotFunctions = [];
63601
+ for (const pivotFunction of pivotFunctions) {
63602
+ const { functionName, args } = pivotFunction;
63603
+ const evaluatedArgs = args.map((argAst) => {
63608
63604
  if (argAst.type === "EMPTY") return;
63609
63605
  else if (argAst.type === "STRING" || argAst.type === "BOOLEAN" || argAst.type === "NUMBER") return argAst.value;
63610
63606
  const argsString = astToFormula(argAst);
63611
63607
  return this.getters.evaluateFormula(sheetId, argsString);
63612
- })
63613
- };
63608
+ });
63609
+ evaluatedPivotFunctions.push({
63610
+ functionName,
63611
+ args: evaluatedArgs
63612
+ });
63613
+ }
63614
+ return evaluatedPivotFunctions;
63615
+ }
63616
+ getFirstPivotFunction(sheetId, formula) {
63617
+ return this.getPivotFunctions(sheetId, formula)[0];
63614
63618
  }
63615
63619
  /**
63616
63620
  * Returns the domain args of a pivot formula from a position.
@@ -63716,8 +63720,8 @@ var PivotUIPlugin = class extends CoreViewPlugin {
63716
63720
  const unusedPivots = new Set(this.getters.getPivotIds());
63717
63721
  for (const sheetId of this.getters.getSheetIds()) for (const cell of this.getters.getCells(sheetId)) {
63718
63722
  const position = this.getters.getCellPosition(cell.id);
63719
- const pivotId = this.getPivotIdFromPosition(position);
63720
- if (pivotId) {
63723
+ const pivotIds = this.getPivotIdsFromPosition(position);
63724
+ for (const pivotId of pivotIds) {
63721
63725
  unusedPivots.delete(pivotId);
63722
63726
  if (!unusedPivots.size) {
63723
63727
  this.unusedPivotsInFormulas = [];
@@ -63725,6 +63729,21 @@ var PivotUIPlugin = class extends CoreViewPlugin {
63725
63729
  }
63726
63730
  }
63727
63731
  }
63732
+ for (const pivotId of this.getters.getPivotIds()) {
63733
+ const pivot = this.getters.getPivotCoreDefinition(pivotId);
63734
+ for (const measure of pivot.measures) if (measure.computedBy) {
63735
+ const { sheetId } = measure.computedBy;
63736
+ const formula = this.getters.getMeasureCompiledFormula(pivotId, measure);
63737
+ const relatedPivotIds = this.getPivotIdsFromFormula(sheetId, formula);
63738
+ for (const relatedPivotId of relatedPivotIds) {
63739
+ unusedPivots.delete(relatedPivotId);
63740
+ if (!unusedPivots.size) {
63741
+ this.unusedPivotsInFormulas = [];
63742
+ return [];
63743
+ }
63744
+ }
63745
+ }
63746
+ }
63728
63747
  this.unusedPivotsInFormulas = [...unusedPivots];
63729
63748
  return this.unusedPivotsInFormulas;
63730
63749
  }
@@ -65452,7 +65471,8 @@ const invalidateTableStyleCommandsSet = new Set([
65452
65471
  "REMOVE_TABLE",
65453
65472
  "RESIZE_TABLE",
65454
65473
  "CREATE_TABLE_STYLE",
65455
- "REMOVE_TABLE_STYLE"
65474
+ "REMOVE_TABLE_STYLE",
65475
+ "DELETE_CONTENT"
65456
65476
  ]);
65457
65477
  function doesCommandInvalidatesTableStyle(cmd) {
65458
65478
  return invalidateTableStyleCommandsSet.has(cmd.type);
@@ -70737,10 +70757,10 @@ var SheetViewPlugin = class extends UIPlugin {
70737
70757
 
70738
70758
  //#endregion
70739
70759
  //#region src/plugins/index.ts
70740
- const corePluginRegistry = new Registry$1().add("settings", SettingsPlugin).add("sheet", SheetPlugin).add("header grouping", HeaderGroupingPlugin).add("header visibility", HeaderVisibilityPlugin).add("tables", TablePlugin).add("dataValidation", DataValidationPlugin).add("cell", CellPlugin).add("merge", MergePlugin).add("headerSize", HeaderSizePlugin).add("borders", BordersPlugin).add("conditional formatting", ConditionalFormatPlugin).add("figures", FigurePlugin).add("chart", ChartPlugin).add("carousel", CarouselPlugin).add("image", ImagePlugin).add("pivot_core", PivotCorePlugin).add("spreadsheet_pivot_core", SpreadsheetPivotCorePlugin).add("tableStyle", TableStylePlugin);
70741
- const featurePluginRegistry = new Registry$1().add("ui_sheet", SheetUIPlugin).add("ui_options", UIOptionsPlugin).add("autofill", AutofillPlugin).add("sort", SortPlugin).add("automatic_sum", AutomaticSumPlugin).add("format", FormatPlugin).add("insert_pivot", InsertPivotPlugin).add("pivot_presence", PivotPresencePlugin).add("split_to_columns", SplitToColumnsPlugin).add("subtotal_evaluation", SubtotalEvaluationPlugin).add("collaborative", CollaborativePlugin).add("history", HistoryPlugin).add("table_autofill", TableAutofillPlugin).add("table_ui_resize", TableResizeUI).add("datavalidation_insert", DataValidationInsertionPlugin).add("checkbox_toggle", CheckboxTogglePlugin).add("dynamic_translate", DynamicTranslate).add("geo_features", GeoFeaturePlugin).add("data_cleanup", DataCleanupPlugin);
70742
- const statefulUIPluginRegistry = new Registry$1().add("selection", GridSelectionPlugin).add("evaluation_filter", FilterEvaluationPlugin).add("header_visibility_ui", HeaderVisibilityUIPlugin).add("cell_computed_style", CellComputedStylePlugin).add("table_computed_style", TableComputedStylePlugin).add("header_positions", HeaderPositionsUIPlugin).add("viewport", SheetViewPlugin).add("clipboard", ClipboardPlugin).add("carousel_ui", CarouselUIPlugin).add("lock_sheet", LockSheetPlugin);
70743
- const coreViewsPluginRegistry = new Registry$1().add("evaluation", EvaluationPlugin).add("evaluation_chart", EvaluationChartPlugin).add("evaluation_cf", EvaluationConditionalFormatPlugin).add("row_size", HeaderSizeUIPlugin).add("data_validation_ui", EvaluationDataValidationPlugin).add("dynamic_tables", DynamicTablesPlugin).add("custom_colors", CustomColorsPlugin).add("pivot_ui", PivotUIPlugin).add("cell_icon", CellIconPlugin).add("formula_tracker", FormulaTrackerPlugin);
70760
+ const corePluginRegistry = new Registry().add("settings", SettingsPlugin).add("sheet", SheetPlugin).add("header grouping", HeaderGroupingPlugin).add("header visibility", HeaderVisibilityPlugin).add("tables", TablePlugin).add("dataValidation", DataValidationPlugin).add("cell", CellPlugin).add("merge", MergePlugin).add("headerSize", HeaderSizePlugin).add("borders", BordersPlugin).add("conditional formatting", ConditionalFormatPlugin).add("figures", FigurePlugin).add("chart", ChartPlugin).add("carousel", CarouselPlugin).add("image", ImagePlugin).add("pivot_core", PivotCorePlugin).add("spreadsheet_pivot_core", SpreadsheetPivotCorePlugin).add("tableStyle", TableStylePlugin);
70761
+ const featurePluginRegistry = new Registry().add("ui_sheet", SheetUIPlugin).add("ui_options", UIOptionsPlugin).add("autofill", AutofillPlugin).add("sort", SortPlugin).add("automatic_sum", AutomaticSumPlugin).add("format", FormatPlugin).add("insert_pivot", InsertPivotPlugin).add("pivot_presence", PivotPresencePlugin).add("split_to_columns", SplitToColumnsPlugin).add("subtotal_evaluation", SubtotalEvaluationPlugin).add("collaborative", CollaborativePlugin).add("history", HistoryPlugin).add("table_autofill", TableAutofillPlugin).add("table_ui_resize", TableResizeUI).add("datavalidation_insert", DataValidationInsertionPlugin).add("checkbox_toggle", CheckboxTogglePlugin).add("dynamic_translate", DynamicTranslate).add("geo_features", GeoFeaturePlugin).add("data_cleanup", DataCleanupPlugin);
70762
+ const statefulUIPluginRegistry = new Registry().add("selection", GridSelectionPlugin).add("evaluation_filter", FilterEvaluationPlugin).add("header_visibility_ui", HeaderVisibilityUIPlugin).add("cell_computed_style", CellComputedStylePlugin).add("table_computed_style", TableComputedStylePlugin).add("header_positions", HeaderPositionsUIPlugin).add("viewport", SheetViewPlugin).add("clipboard", ClipboardPlugin).add("carousel_ui", CarouselUIPlugin).add("lock_sheet", LockSheetPlugin);
70763
+ const coreViewsPluginRegistry = new Registry().add("evaluation", EvaluationPlugin).add("evaluation_chart", EvaluationChartPlugin).add("evaluation_cf", EvaluationConditionalFormatPlugin).add("row_size", HeaderSizeUIPlugin).add("data_validation_ui", EvaluationDataValidationPlugin).add("dynamic_tables", DynamicTablesPlugin).add("custom_colors", CustomColorsPlugin).add("pivot_ui", PivotUIPlugin).add("cell_icon", CellIconPlugin).add("formula_tracker", FormulaTrackerPlugin);
70744
70764
 
70745
70765
  //#endregion
70746
70766
  //#region src/registries/auto_completes/data_validation_auto_complete.ts
@@ -76624,6 +76644,11 @@ function lineAttributes(params) {
76624
76644
  `;
76625
76645
  }
76626
76646
  function insertText(text, fontColor = "000000", fontsize = 16, style = {}) {
76647
+ const textProperties = [
76648
+ ["b", style.bold ? "1" : "0"],
76649
+ ["i", style.italic ? "1" : "0"],
76650
+ ["sz", fontsize * 100]
76651
+ ];
76627
76652
  return escapeXml`
76628
76653
  <c:tx>
76629
76654
  <c:rich>
@@ -76631,13 +76656,13 @@ function insertText(text, fontColor = "000000", fontsize = 16, style = {}) {
76631
76656
  <a:lstStyle />
76632
76657
  <a:p>
76633
76658
  <a:pPr lvl="0">
76634
- <a:defRPr b="${style?.bold ? 1 : 0}" i="${style?.italic ? 1 : 0}">
76659
+ <a:defRPr ${formatAttributes(textProperties)}>
76635
76660
  ${solidFill(fontColor)}
76636
76661
  <a:latin typeface="+mn-lt"/>
76637
76662
  </a:defRPr>
76638
76663
  </a:pPr>
76639
76664
  <a:r> <!-- Runs -->
76640
- <a:rPr b="${style?.bold ? 1 : 0}" i="${style?.italic ? 1 : 0}" sz="${fontsize * 100}"/>
76665
+ <a:rPr ${formatAttributes(textProperties)}/>
76641
76666
  <a:t>${text}</a:t>
76642
76667
  </a:r>
76643
76668
  </a:p>
@@ -81603,6 +81628,6 @@ const chartHelpers = {
81603
81628
  //#endregion
81604
81629
  export { AbstractCellClipboardHandler, AbstractChart, AbstractFigureClipboardHandler, CellErrorType, ClientDisconnectedError, CommandResult, CompiledFormula, CorePlugin, CoreViewPlugin, DEFAULT_LOCALE, DEFAULT_LOCALES, DispatchResult, EvaluationError, LocalTransportService, Model, PivotRuntimeDefinition, Registry, Revision, SPREADSHEET_DIMENSIONS, Spreadsheet, SpreadsheetPivotTable, UIPlugin, __info__, addFunction, addRenderingLayer, astToFormula, canExecuteInReadonly, categories, chartHelpers, components, constants, convertAstNodes, coreTypes, createAutocompleteArgumentsProvider, findCellInNewZone, functionCache, getCaretDownSvg, getCaretUpSvg, helpers, hooks, invalidateCFEvaluationCommands, invalidateChartEvaluationCommands, invalidateDependenciesCommands, invalidateEvaluationCommands, isCoreCommand, isSheetDependent, iterateAstNodes, links, load, lockedSheetAllowedCommands, parse, parseTokens, readonlyAllowedCommands, registries, setDefaultSheetViewSize, setTranslationMethod, stores, tokenColors, tokenize };
81605
81630
 
81606
- __info__.version = "19.2.13";
81607
- __info__.date = "2026-05-15T07:07:37.391Z";
81608
- __info__.hash = "fece642";
81631
+ __info__.version = "19.2.15";
81632
+ __info__.date = "2026-06-06T06:23:14.723Z";
81633
+ __info__.hash = "d29528e";