@odoo/o-spreadsheet 17.0.20 → 17.0.21

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 17.0.20
6
- * @date 2024-04-26T07:37:04.503Z
7
- * @hash 065ac98
5
+ * @version 17.0.21
6
+ * @date 2024-05-07T10:39:36.750Z
7
+ * @hash 998bea0
8
8
  */
9
9
 
10
10
  'use strict';
@@ -642,7 +642,7 @@ function getAddHeaderStartIndex(position, base) {
642
642
  /**
643
643
  * Compares two objects.
644
644
  */
645
- function deepEquals(o1, o2) {
645
+ function deepEquals(o1, o2, ignoreFunctions) {
646
646
  if (o1 === o2)
647
647
  return true;
648
648
  if ((o1 && !o2) || (o2 && !o1))
@@ -658,13 +658,16 @@ function deepEquals(o1, o2) {
658
658
  }
659
659
  }
660
660
  for (const key in o1) {
661
- if (typeof o1[key] !== typeof o2[key])
661
+ const typeOfO1Key = typeof o1[key];
662
+ if (typeOfO1Key !== typeof o2[key])
662
663
  return false;
663
- if (typeof o1[key] === "object") {
664
- if (!deepEquals(o1[key], o2[key]))
664
+ if (typeOfO1Key === "object") {
665
+ if (!deepEquals(o1[key], o2[key], ignoreFunctions))
665
666
  return false;
666
667
  }
667
668
  else {
669
+ if (ignoreFunctions && typeOfO1Key === "function")
670
+ return true;
668
671
  if (o1[key] !== o2[key])
669
672
  return false;
670
673
  }
@@ -3559,21 +3562,22 @@ function toZoneWithoutBoundaryChanges(xc) {
3559
3562
  xc = xc.split("!").at(-1);
3560
3563
  }
3561
3564
  if (xc.includes("$")) {
3562
- xc = xc.replace(/\$/g, "");
3565
+ xc = xc.replaceAll("$", "");
3563
3566
  }
3564
- let ranges;
3567
+ let firstRangePart = "";
3568
+ let secondRangePart;
3565
3569
  if (xc.includes(":")) {
3566
- ranges = xc.split(":").map((x) => x.trim());
3570
+ [firstRangePart, secondRangePart] = xc.split(":");
3571
+ firstRangePart = firstRangePart.trim();
3572
+ secondRangePart = secondRangePart.trim();
3567
3573
  }
3568
3574
  else {
3569
- ranges = [xc.trim()];
3575
+ firstRangePart = xc.trim();
3570
3576
  }
3571
3577
  let top, bottom, left, right;
3572
3578
  let fullCol = false;
3573
3579
  let fullRow = false;
3574
3580
  let hasHeader = false;
3575
- const firstRangePart = ranges[0];
3576
- const secondRangePart = ranges[1] && ranges[1];
3577
3581
  if (isColReference(firstRangePart)) {
3578
3582
  left = right = lettersToNumber(firstRangePart);
3579
3583
  top = bottom = 0;
@@ -3590,7 +3594,7 @@ function toZoneWithoutBoundaryChanges(xc) {
3590
3594
  top = bottom = c.row;
3591
3595
  hasHeader = true;
3592
3596
  }
3593
- if (ranges.length === 2) {
3597
+ if (secondRangePart) {
3594
3598
  if (isColReference(secondRangePart)) {
3595
3599
  right = lettersToNumber(secondRangePart);
3596
3600
  fullCol = true;
@@ -4759,6 +4763,7 @@ class ChartJsComponent extends owl.Component {
4759
4763
  static template = "o-spreadsheet-ChartJsComponent";
4760
4764
  canvas = owl.useRef("graphContainer");
4761
4765
  chart;
4766
+ currentRuntime;
4762
4767
  get background() {
4763
4768
  return this.chartRuntime.background;
4764
4769
  }
@@ -4775,9 +4780,17 @@ class ChartJsComponent extends owl.Component {
4775
4780
  setup() {
4776
4781
  owl.onMounted(() => {
4777
4782
  const runtime = this.chartRuntime;
4778
- this.createChart(runtime.chartJsConfig);
4783
+ this.currentRuntime = runtime;
4784
+ // Note: chartJS modify the runtime in place, so it's important to give it a copy
4785
+ this.createChart(deepCopy(runtime.chartJsConfig));
4786
+ });
4787
+ owl.useEffect(() => {
4788
+ const runtime = this.chartRuntime;
4789
+ if (!deepEquals(runtime, this.currentRuntime, "ignoreFunctions")) {
4790
+ this.currentRuntime = runtime;
4791
+ this.updateChartJs(deepCopy(runtime));
4792
+ }
4779
4793
  });
4780
- owl.useEffect(() => this.updateChartJs(this.chartRuntime), () => [this.chartRuntime]);
4781
4794
  }
4782
4795
  createChart(chartData) {
4783
4796
  const canvas = this.canvas.el;
@@ -4805,8 +4818,7 @@ class ChartJsComponent extends owl.Component {
4805
4818
  this.chart.config.options.plugins.tooltip = chartData.options.plugins.tooltip;
4806
4819
  this.chart.config.options.plugins.legend = chartData.options.plugins.legend;
4807
4820
  this.chart.config.options.scales = chartData.options?.scales;
4808
- // ?
4809
- this.chart.update("active");
4821
+ this.chart.update();
4810
4822
  }
4811
4823
  }
4812
4824
  ChartJsComponent.props = {
@@ -8375,7 +8387,7 @@ function truncateLabel(label) {
8375
8387
  /**
8376
8388
  * Get a default chart js configuration
8377
8389
  */
8378
- function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale }) {
8390
+ function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale, truncateLabels }) {
8379
8391
  const options = {
8380
8392
  // https://www.chartjs.org/docs/latest/general/responsive.html
8381
8393
  responsive: true,
@@ -8422,7 +8434,7 @@ function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale })
8422
8434
  type: chart.type,
8423
8435
  options,
8424
8436
  data: {
8425
- labels: labels.map(truncateLabel),
8437
+ labels: truncateLabels ? labels.map(truncateLabel) : labels,
8426
8438
  datasets: [],
8427
8439
  },
8428
8440
  plugins: [],
@@ -9304,9 +9316,9 @@ function canBeLinearChart(labelRange, getters) {
9304
9316
  }
9305
9317
  return true;
9306
9318
  }
9307
- function getLineConfiguration(chart, labels, localeFormat) {
9319
+ function getLineConfiguration(chart, labels, options) {
9308
9320
  const fontColor = chartFontColor(chart.background);
9309
- const config = getDefaultChartJsRuntime(chart, labels, fontColor, localeFormat);
9321
+ const config = getDefaultChartJsRuntime(chart, labels, fontColor, options);
9310
9322
  const legend = {
9311
9323
  labels: {
9312
9324
  color: fontColor,
@@ -9349,7 +9361,7 @@ function getLineConfiguration(chart, labels, localeFormat) {
9349
9361
  value = Number(value);
9350
9362
  if (isNaN(value))
9351
9363
  return value;
9352
- const { locale, format } = localeFormat;
9364
+ const { locale, format } = options;
9353
9365
  return formatValue(value, {
9354
9366
  locale,
9355
9367
  format: !format && Math.abs(value) >= 1000 ? "#,##" : format,
@@ -9382,9 +9394,10 @@ function createLineChartRuntime(chart, getters) {
9382
9394
  ({ labels, dataSetsValues } = aggregateDataForLabels(labels, dataSetsValues));
9383
9395
  }
9384
9396
  const locale = getters.getLocale();
9397
+ const truncateLabels = axisType === "category";
9385
9398
  const dataSetFormat = getChartDatasetFormat(getters, chart.dataSets);
9386
- const localeFormat = { format: dataSetFormat, locale };
9387
- const config = getLineConfiguration(chart, labels, localeFormat);
9399
+ const options = { format: dataSetFormat, locale, truncateLabels };
9400
+ const config = getLineConfiguration(chart, labels, options);
9388
9401
  const labelFormat = getChartLabelFormat(getters, chart.labelRange);
9389
9402
  if (axisType === "time") {
9390
9403
  const axis = {
@@ -27544,7 +27557,8 @@ class DataValidationOverlay extends owl.Component {
27544
27557
  get checkBoxCellPositions() {
27545
27558
  return this.env.model.getters
27546
27559
  .getVisibleCellPositions()
27547
- .filter(this.env.model.getters.isCellValidCheckbox);
27560
+ .filter((position) => this.env.model.getters.isCellValidCheckbox(position) &&
27561
+ !this.env.model.getters.isFilterHeader(position));
27548
27562
  }
27549
27563
  get listIconsCellPositions() {
27550
27564
  if (this.env.model.getters.isReadonly()) {
@@ -27552,7 +27566,8 @@ class DataValidationOverlay extends owl.Component {
27552
27566
  }
27553
27567
  return this.env.model.getters
27554
27568
  .getVisibleCellPositions()
27555
- .filter(this.env.model.getters.cellHasListDataValidationIcon);
27569
+ .filter((position) => this.env.model.getters.cellHasListDataValidationIcon(position) &&
27570
+ !this.env.model.getters.isFilterHeader(position));
27556
27571
  }
27557
27572
  }
27558
27573
  DataValidationOverlay.props = {};
@@ -42019,7 +42034,7 @@ class EvaluationPlugin extends UIPlugin {
42019
42034
  ? getItemId(newFormat, data.formats)
42020
42035
  : exportedCellData.format;
42021
42036
  let content;
42022
- if (isFormula && formulaCell instanceof FormulaCellWithDependencies) {
42037
+ if (isExported && isFormula && formulaCell?.compiledFormula.dependencies.length) {
42023
42038
  content = this.getters.getFormulaCellContent(exportedSheetData.id, formulaCell.compiledFormula, formulaCell.compiledFormula.dependencies, true);
42024
42039
  }
42025
42040
  else {
@@ -57392,6 +57407,6 @@ exports.setTranslationMethod = setTranslationMethod;
57392
57407
  exports.tokenize = tokenize;
57393
57408
 
57394
57409
 
57395
- __info__.version = "17.0.20";
57396
- __info__.date = "2024-04-26T07:37:04.503Z";
57397
- __info__.hash = "065ac98";
57410
+ __info__.version = "17.0.21";
57411
+ __info__.date = "2024-05-07T10:39:36.750Z";
57412
+ __info__.hash = "998bea0";
@@ -5952,6 +5952,7 @@ declare class ChartJsComponent extends Component<Props$B, SpreadsheetChildEnv> {
5952
5952
  static template: string;
5953
5953
  private canvas;
5954
5954
  private chart?;
5955
+ private currentRuntime;
5955
5956
  get background(): string;
5956
5957
  get canvasStyle(): string;
5957
5958
  get chartRuntime(): ChartJSRuntime;
@@ -7793,7 +7794,9 @@ declare function chartFontColor(backgroundColor: Color | undefined): Color;
7793
7794
  /**
7794
7795
  * Get a default chart js configuration
7795
7796
  */
7796
- declare function getDefaultChartJsRuntime(chart: AbstractChart, labels: string[], fontColor: Color, { format, locale }: LocaleFormat): Required<ChartConfiguration>;
7797
+ declare function getDefaultChartJsRuntime(chart: AbstractChart, labels: string[], fontColor: Color, { format, locale, truncateLabels }: LocaleFormat & {
7798
+ truncateLabels?: boolean;
7799
+ }): Required<ChartConfiguration>;
7797
7800
  /** See https://www.chartjs.org/docs/latest/charts/area.html#filling-modes */
7798
7801
  declare function getFillingMode(index: number): "origin" | number;
7799
7802
 
@@ -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 17.0.20
6
- * @date 2024-04-26T07:37:04.503Z
7
- * @hash 065ac98
5
+ * @version 17.0.21
6
+ * @date 2024-05-07T10:39:36.750Z
7
+ * @hash 998bea0
8
8
  */
9
9
 
10
10
  import { Component, useRef, onMounted, useEffect, onWillPatch, useState, onWillUpdateProps, onPatched, useComponent, useExternalListener, onWillUnmount, onWillStart, xml, useChildSubEnv, useSubEnv, markRaw } from '@odoo/owl';
@@ -640,7 +640,7 @@ function getAddHeaderStartIndex(position, base) {
640
640
  /**
641
641
  * Compares two objects.
642
642
  */
643
- function deepEquals(o1, o2) {
643
+ function deepEquals(o1, o2, ignoreFunctions) {
644
644
  if (o1 === o2)
645
645
  return true;
646
646
  if ((o1 && !o2) || (o2 && !o1))
@@ -656,13 +656,16 @@ function deepEquals(o1, o2) {
656
656
  }
657
657
  }
658
658
  for (const key in o1) {
659
- if (typeof o1[key] !== typeof o2[key])
659
+ const typeOfO1Key = typeof o1[key];
660
+ if (typeOfO1Key !== typeof o2[key])
660
661
  return false;
661
- if (typeof o1[key] === "object") {
662
- if (!deepEquals(o1[key], o2[key]))
662
+ if (typeOfO1Key === "object") {
663
+ if (!deepEquals(o1[key], o2[key], ignoreFunctions))
663
664
  return false;
664
665
  }
665
666
  else {
667
+ if (ignoreFunctions && typeOfO1Key === "function")
668
+ return true;
666
669
  if (o1[key] !== o2[key])
667
670
  return false;
668
671
  }
@@ -3557,21 +3560,22 @@ function toZoneWithoutBoundaryChanges(xc) {
3557
3560
  xc = xc.split("!").at(-1);
3558
3561
  }
3559
3562
  if (xc.includes("$")) {
3560
- xc = xc.replace(/\$/g, "");
3563
+ xc = xc.replaceAll("$", "");
3561
3564
  }
3562
- let ranges;
3565
+ let firstRangePart = "";
3566
+ let secondRangePart;
3563
3567
  if (xc.includes(":")) {
3564
- ranges = xc.split(":").map((x) => x.trim());
3568
+ [firstRangePart, secondRangePart] = xc.split(":");
3569
+ firstRangePart = firstRangePart.trim();
3570
+ secondRangePart = secondRangePart.trim();
3565
3571
  }
3566
3572
  else {
3567
- ranges = [xc.trim()];
3573
+ firstRangePart = xc.trim();
3568
3574
  }
3569
3575
  let top, bottom, left, right;
3570
3576
  let fullCol = false;
3571
3577
  let fullRow = false;
3572
3578
  let hasHeader = false;
3573
- const firstRangePart = ranges[0];
3574
- const secondRangePart = ranges[1] && ranges[1];
3575
3579
  if (isColReference(firstRangePart)) {
3576
3580
  left = right = lettersToNumber(firstRangePart);
3577
3581
  top = bottom = 0;
@@ -3588,7 +3592,7 @@ function toZoneWithoutBoundaryChanges(xc) {
3588
3592
  top = bottom = c.row;
3589
3593
  hasHeader = true;
3590
3594
  }
3591
- if (ranges.length === 2) {
3595
+ if (secondRangePart) {
3592
3596
  if (isColReference(secondRangePart)) {
3593
3597
  right = lettersToNumber(secondRangePart);
3594
3598
  fullCol = true;
@@ -4757,6 +4761,7 @@ class ChartJsComponent extends Component {
4757
4761
  static template = "o-spreadsheet-ChartJsComponent";
4758
4762
  canvas = useRef("graphContainer");
4759
4763
  chart;
4764
+ currentRuntime;
4760
4765
  get background() {
4761
4766
  return this.chartRuntime.background;
4762
4767
  }
@@ -4773,9 +4778,17 @@ class ChartJsComponent extends Component {
4773
4778
  setup() {
4774
4779
  onMounted(() => {
4775
4780
  const runtime = this.chartRuntime;
4776
- this.createChart(runtime.chartJsConfig);
4781
+ this.currentRuntime = runtime;
4782
+ // Note: chartJS modify the runtime in place, so it's important to give it a copy
4783
+ this.createChart(deepCopy(runtime.chartJsConfig));
4784
+ });
4785
+ useEffect(() => {
4786
+ const runtime = this.chartRuntime;
4787
+ if (!deepEquals(runtime, this.currentRuntime, "ignoreFunctions")) {
4788
+ this.currentRuntime = runtime;
4789
+ this.updateChartJs(deepCopy(runtime));
4790
+ }
4777
4791
  });
4778
- useEffect(() => this.updateChartJs(this.chartRuntime), () => [this.chartRuntime]);
4779
4792
  }
4780
4793
  createChart(chartData) {
4781
4794
  const canvas = this.canvas.el;
@@ -4803,8 +4816,7 @@ class ChartJsComponent extends Component {
4803
4816
  this.chart.config.options.plugins.tooltip = chartData.options.plugins.tooltip;
4804
4817
  this.chart.config.options.plugins.legend = chartData.options.plugins.legend;
4805
4818
  this.chart.config.options.scales = chartData.options?.scales;
4806
- // ?
4807
- this.chart.update("active");
4819
+ this.chart.update();
4808
4820
  }
4809
4821
  }
4810
4822
  ChartJsComponent.props = {
@@ -8373,7 +8385,7 @@ function truncateLabel(label) {
8373
8385
  /**
8374
8386
  * Get a default chart js configuration
8375
8387
  */
8376
- function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale }) {
8388
+ function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale, truncateLabels }) {
8377
8389
  const options = {
8378
8390
  // https://www.chartjs.org/docs/latest/general/responsive.html
8379
8391
  responsive: true,
@@ -8420,7 +8432,7 @@ function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale })
8420
8432
  type: chart.type,
8421
8433
  options,
8422
8434
  data: {
8423
- labels: labels.map(truncateLabel),
8435
+ labels: truncateLabels ? labels.map(truncateLabel) : labels,
8424
8436
  datasets: [],
8425
8437
  },
8426
8438
  plugins: [],
@@ -9302,9 +9314,9 @@ function canBeLinearChart(labelRange, getters) {
9302
9314
  }
9303
9315
  return true;
9304
9316
  }
9305
- function getLineConfiguration(chart, labels, localeFormat) {
9317
+ function getLineConfiguration(chart, labels, options) {
9306
9318
  const fontColor = chartFontColor(chart.background);
9307
- const config = getDefaultChartJsRuntime(chart, labels, fontColor, localeFormat);
9319
+ const config = getDefaultChartJsRuntime(chart, labels, fontColor, options);
9308
9320
  const legend = {
9309
9321
  labels: {
9310
9322
  color: fontColor,
@@ -9347,7 +9359,7 @@ function getLineConfiguration(chart, labels, localeFormat) {
9347
9359
  value = Number(value);
9348
9360
  if (isNaN(value))
9349
9361
  return value;
9350
- const { locale, format } = localeFormat;
9362
+ const { locale, format } = options;
9351
9363
  return formatValue(value, {
9352
9364
  locale,
9353
9365
  format: !format && Math.abs(value) >= 1000 ? "#,##" : format,
@@ -9380,9 +9392,10 @@ function createLineChartRuntime(chart, getters) {
9380
9392
  ({ labels, dataSetsValues } = aggregateDataForLabels(labels, dataSetsValues));
9381
9393
  }
9382
9394
  const locale = getters.getLocale();
9395
+ const truncateLabels = axisType === "category";
9383
9396
  const dataSetFormat = getChartDatasetFormat(getters, chart.dataSets);
9384
- const localeFormat = { format: dataSetFormat, locale };
9385
- const config = getLineConfiguration(chart, labels, localeFormat);
9397
+ const options = { format: dataSetFormat, locale, truncateLabels };
9398
+ const config = getLineConfiguration(chart, labels, options);
9386
9399
  const labelFormat = getChartLabelFormat(getters, chart.labelRange);
9387
9400
  if (axisType === "time") {
9388
9401
  const axis = {
@@ -27542,7 +27555,8 @@ class DataValidationOverlay extends Component {
27542
27555
  get checkBoxCellPositions() {
27543
27556
  return this.env.model.getters
27544
27557
  .getVisibleCellPositions()
27545
- .filter(this.env.model.getters.isCellValidCheckbox);
27558
+ .filter((position) => this.env.model.getters.isCellValidCheckbox(position) &&
27559
+ !this.env.model.getters.isFilterHeader(position));
27546
27560
  }
27547
27561
  get listIconsCellPositions() {
27548
27562
  if (this.env.model.getters.isReadonly()) {
@@ -27550,7 +27564,8 @@ class DataValidationOverlay extends Component {
27550
27564
  }
27551
27565
  return this.env.model.getters
27552
27566
  .getVisibleCellPositions()
27553
- .filter(this.env.model.getters.cellHasListDataValidationIcon);
27567
+ .filter((position) => this.env.model.getters.cellHasListDataValidationIcon(position) &&
27568
+ !this.env.model.getters.isFilterHeader(position));
27554
27569
  }
27555
27570
  }
27556
27571
  DataValidationOverlay.props = {};
@@ -42017,7 +42032,7 @@ class EvaluationPlugin extends UIPlugin {
42017
42032
  ? getItemId(newFormat, data.formats)
42018
42033
  : exportedCellData.format;
42019
42034
  let content;
42020
- if (isFormula && formulaCell instanceof FormulaCellWithDependencies) {
42035
+ if (isExported && isFormula && formulaCell?.compiledFormula.dependencies.length) {
42021
42036
  content = this.getters.getFormulaCellContent(exportedSheetData.id, formulaCell.compiledFormula, formulaCell.compiledFormula.dependencies, true);
42022
42037
  }
42023
42038
  else {
@@ -57355,6 +57370,6 @@ const constants = {
57355
57370
  export { AbstractChart, CommandResult, CorePlugin, DispatchResult, EvaluationError, Model, Registry, Revision, SPREADSHEET_DIMENSIONS, Spreadsheet, UIPlugin, __info__, addFunction, astToFormula, compile, compileTokens, components, constants, convertAstNodes, coreTypes, findCellInNewZone, functionCache, helpers, hooks, invalidateCFEvaluationCommands, invalidateDependenciesCommands, invalidateEvaluationCommands, iterateAstNodes, links, load, parse, parseTokens, readonlyAllowedCommands, registries, setDefaultSheetViewSize, setTranslationMethod, tokenize };
57356
57371
 
57357
57372
 
57358
- __info__.version = "17.0.20";
57359
- __info__.date = "2024-04-26T07:37:04.503Z";
57360
- __info__.hash = "065ac98";
57373
+ __info__.version = "17.0.21";
57374
+ __info__.date = "2024-05-07T10:39:36.750Z";
57375
+ __info__.hash = "998bea0";
@@ -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 17.0.20
6
- * @date 2024-04-26T07:37:04.503Z
7
- * @hash 065ac98
5
+ * @version 17.0.21
6
+ * @date 2024-05-07T10:39:36.750Z
7
+ * @hash 998bea0
8
8
  */
9
9
 
10
10
  (function (exports, owl) {
@@ -641,7 +641,7 @@
641
641
  /**
642
642
  * Compares two objects.
643
643
  */
644
- function deepEquals(o1, o2) {
644
+ function deepEquals(o1, o2, ignoreFunctions) {
645
645
  if (o1 === o2)
646
646
  return true;
647
647
  if ((o1 && !o2) || (o2 && !o1))
@@ -657,13 +657,16 @@
657
657
  }
658
658
  }
659
659
  for (const key in o1) {
660
- if (typeof o1[key] !== typeof o2[key])
660
+ const typeOfO1Key = typeof o1[key];
661
+ if (typeOfO1Key !== typeof o2[key])
661
662
  return false;
662
- if (typeof o1[key] === "object") {
663
- if (!deepEquals(o1[key], o2[key]))
663
+ if (typeOfO1Key === "object") {
664
+ if (!deepEquals(o1[key], o2[key], ignoreFunctions))
664
665
  return false;
665
666
  }
666
667
  else {
668
+ if (ignoreFunctions && typeOfO1Key === "function")
669
+ return true;
667
670
  if (o1[key] !== o2[key])
668
671
  return false;
669
672
  }
@@ -3558,21 +3561,22 @@
3558
3561
  xc = xc.split("!").at(-1);
3559
3562
  }
3560
3563
  if (xc.includes("$")) {
3561
- xc = xc.replace(/\$/g, "");
3564
+ xc = xc.replaceAll("$", "");
3562
3565
  }
3563
- let ranges;
3566
+ let firstRangePart = "";
3567
+ let secondRangePart;
3564
3568
  if (xc.includes(":")) {
3565
- ranges = xc.split(":").map((x) => x.trim());
3569
+ [firstRangePart, secondRangePart] = xc.split(":");
3570
+ firstRangePart = firstRangePart.trim();
3571
+ secondRangePart = secondRangePart.trim();
3566
3572
  }
3567
3573
  else {
3568
- ranges = [xc.trim()];
3574
+ firstRangePart = xc.trim();
3569
3575
  }
3570
3576
  let top, bottom, left, right;
3571
3577
  let fullCol = false;
3572
3578
  let fullRow = false;
3573
3579
  let hasHeader = false;
3574
- const firstRangePart = ranges[0];
3575
- const secondRangePart = ranges[1] && ranges[1];
3576
3580
  if (isColReference(firstRangePart)) {
3577
3581
  left = right = lettersToNumber(firstRangePart);
3578
3582
  top = bottom = 0;
@@ -3589,7 +3593,7 @@
3589
3593
  top = bottom = c.row;
3590
3594
  hasHeader = true;
3591
3595
  }
3592
- if (ranges.length === 2) {
3596
+ if (secondRangePart) {
3593
3597
  if (isColReference(secondRangePart)) {
3594
3598
  right = lettersToNumber(secondRangePart);
3595
3599
  fullCol = true;
@@ -4758,6 +4762,7 @@
4758
4762
  static template = "o-spreadsheet-ChartJsComponent";
4759
4763
  canvas = owl.useRef("graphContainer");
4760
4764
  chart;
4765
+ currentRuntime;
4761
4766
  get background() {
4762
4767
  return this.chartRuntime.background;
4763
4768
  }
@@ -4774,9 +4779,17 @@
4774
4779
  setup() {
4775
4780
  owl.onMounted(() => {
4776
4781
  const runtime = this.chartRuntime;
4777
- this.createChart(runtime.chartJsConfig);
4782
+ this.currentRuntime = runtime;
4783
+ // Note: chartJS modify the runtime in place, so it's important to give it a copy
4784
+ this.createChart(deepCopy(runtime.chartJsConfig));
4785
+ });
4786
+ owl.useEffect(() => {
4787
+ const runtime = this.chartRuntime;
4788
+ if (!deepEquals(runtime, this.currentRuntime, "ignoreFunctions")) {
4789
+ this.currentRuntime = runtime;
4790
+ this.updateChartJs(deepCopy(runtime));
4791
+ }
4778
4792
  });
4779
- owl.useEffect(() => this.updateChartJs(this.chartRuntime), () => [this.chartRuntime]);
4780
4793
  }
4781
4794
  createChart(chartData) {
4782
4795
  const canvas = this.canvas.el;
@@ -4804,8 +4817,7 @@
4804
4817
  this.chart.config.options.plugins.tooltip = chartData.options.plugins.tooltip;
4805
4818
  this.chart.config.options.plugins.legend = chartData.options.plugins.legend;
4806
4819
  this.chart.config.options.scales = chartData.options?.scales;
4807
- // ?
4808
- this.chart.update("active");
4820
+ this.chart.update();
4809
4821
  }
4810
4822
  }
4811
4823
  ChartJsComponent.props = {
@@ -8374,7 +8386,7 @@
8374
8386
  /**
8375
8387
  * Get a default chart js configuration
8376
8388
  */
8377
- function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale }) {
8389
+ function getDefaultChartJsRuntime(chart, labels, fontColor, { format, locale, truncateLabels }) {
8378
8390
  const options = {
8379
8391
  // https://www.chartjs.org/docs/latest/general/responsive.html
8380
8392
  responsive: true,
@@ -8421,7 +8433,7 @@
8421
8433
  type: chart.type,
8422
8434
  options,
8423
8435
  data: {
8424
- labels: labels.map(truncateLabel),
8436
+ labels: truncateLabels ? labels.map(truncateLabel) : labels,
8425
8437
  datasets: [],
8426
8438
  },
8427
8439
  plugins: [],
@@ -9303,9 +9315,9 @@
9303
9315
  }
9304
9316
  return true;
9305
9317
  }
9306
- function getLineConfiguration(chart, labels, localeFormat) {
9318
+ function getLineConfiguration(chart, labels, options) {
9307
9319
  const fontColor = chartFontColor(chart.background);
9308
- const config = getDefaultChartJsRuntime(chart, labels, fontColor, localeFormat);
9320
+ const config = getDefaultChartJsRuntime(chart, labels, fontColor, options);
9309
9321
  const legend = {
9310
9322
  labels: {
9311
9323
  color: fontColor,
@@ -9348,7 +9360,7 @@
9348
9360
  value = Number(value);
9349
9361
  if (isNaN(value))
9350
9362
  return value;
9351
- const { locale, format } = localeFormat;
9363
+ const { locale, format } = options;
9352
9364
  return formatValue(value, {
9353
9365
  locale,
9354
9366
  format: !format && Math.abs(value) >= 1000 ? "#,##" : format,
@@ -9381,9 +9393,10 @@
9381
9393
  ({ labels, dataSetsValues } = aggregateDataForLabels(labels, dataSetsValues));
9382
9394
  }
9383
9395
  const locale = getters.getLocale();
9396
+ const truncateLabels = axisType === "category";
9384
9397
  const dataSetFormat = getChartDatasetFormat(getters, chart.dataSets);
9385
- const localeFormat = { format: dataSetFormat, locale };
9386
- const config = getLineConfiguration(chart, labels, localeFormat);
9398
+ const options = { format: dataSetFormat, locale, truncateLabels };
9399
+ const config = getLineConfiguration(chart, labels, options);
9387
9400
  const labelFormat = getChartLabelFormat(getters, chart.labelRange);
9388
9401
  if (axisType === "time") {
9389
9402
  const axis = {
@@ -27543,7 +27556,8 @@
27543
27556
  get checkBoxCellPositions() {
27544
27557
  return this.env.model.getters
27545
27558
  .getVisibleCellPositions()
27546
- .filter(this.env.model.getters.isCellValidCheckbox);
27559
+ .filter((position) => this.env.model.getters.isCellValidCheckbox(position) &&
27560
+ !this.env.model.getters.isFilterHeader(position));
27547
27561
  }
27548
27562
  get listIconsCellPositions() {
27549
27563
  if (this.env.model.getters.isReadonly()) {
@@ -27551,7 +27565,8 @@
27551
27565
  }
27552
27566
  return this.env.model.getters
27553
27567
  .getVisibleCellPositions()
27554
- .filter(this.env.model.getters.cellHasListDataValidationIcon);
27568
+ .filter((position) => this.env.model.getters.cellHasListDataValidationIcon(position) &&
27569
+ !this.env.model.getters.isFilterHeader(position));
27555
27570
  }
27556
27571
  }
27557
27572
  DataValidationOverlay.props = {};
@@ -42018,7 +42033,7 @@
42018
42033
  ? getItemId(newFormat, data.formats)
42019
42034
  : exportedCellData.format;
42020
42035
  let content;
42021
- if (isFormula && formulaCell instanceof FormulaCellWithDependencies) {
42036
+ if (isExported && isFormula && formulaCell?.compiledFormula.dependencies.length) {
42022
42037
  content = this.getters.getFormulaCellContent(exportedSheetData.id, formulaCell.compiledFormula, formulaCell.compiledFormula.dependencies, true);
42023
42038
  }
42024
42039
  else {
@@ -57391,9 +57406,9 @@
57391
57406
  exports.tokenize = tokenize;
57392
57407
 
57393
57408
 
57394
- __info__.version = "17.0.20";
57395
- __info__.date = "2024-04-26T07:37:04.503Z";
57396
- __info__.hash = "065ac98";
57409
+ __info__.version = "17.0.21";
57410
+ __info__.date = "2024-05-07T10:39:36.750Z";
57411
+ __info__.hash = "998bea0";
57397
57412
 
57398
57413
 
57399
57414
  })(this.o_spreadsheet = this.o_spreadsheet || {}, owl);