@odoo/o-spreadsheet 16.4.8 → 16.4.10

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.
@@ -1197,7 +1197,17 @@ const timeRegexp = /((\d+(:\d+)?(:\d+)?\s*(AM|PM))|(\d+:\d+(:\d+)?))$/;
1197
1197
  function isDateTime(str, locale) {
1198
1198
  return parseDateTime(str, locale) !== null;
1199
1199
  }
1200
+ const CACHE = new Map();
1200
1201
  function parseDateTime(str, locale) {
1202
+ if (!CACHE.has(locale)) {
1203
+ CACHE.set(locale, new Map());
1204
+ }
1205
+ if (!CACHE.get(locale).has(str)) {
1206
+ CACHE.get(locale).set(str, _parseDateTime(str, locale));
1207
+ }
1208
+ return CACHE.get(locale).get(str);
1209
+ }
1210
+ function _parseDateTime(str, locale) {
1201
1211
  str = str.trim();
1202
1212
  let time = null;
1203
1213
  const timeMatch = str.match(timeRegexp);
@@ -3016,8 +3026,9 @@ class RangeImpl {
3016
3026
  }
3017
3027
  get zone() {
3018
3028
  const { left, top, bottom, right } = this._zone;
3019
- if (right !== undefined && bottom !== undefined)
3020
- return { left, top, right, bottom };
3029
+ if (right !== undefined && bottom !== undefined) {
3030
+ return this._zone;
3031
+ }
3021
3032
  else if (bottom === undefined && right !== undefined) {
3022
3033
  return { right, top, left, bottom: this.getSheetSize(this.sheetId).numberOfRows - 1 };
3023
3034
  }
@@ -4287,7 +4298,7 @@ var LAYERS;
4287
4298
  const SORT_TYPES_ORDER = ["number", "string", "boolean", "undefined"];
4288
4299
  function assert(condition, message) {
4289
4300
  if (!condition()) {
4290
- throw new Error(message);
4301
+ throw new EvaluationError(CellErrorType.GenericError, message);
4291
4302
  }
4292
4303
  }
4293
4304
  // -----------------------------------------------------------------------------
@@ -4932,7 +4943,7 @@ function _createEvaluatedCell(value, localeFormat) {
4932
4943
  return textCell((value || "").toString(), localeFormat);
4933
4944
  }
4934
4945
  catch (error) {
4935
- return errorCell((value || "").toString(), new EvaluationError(CellErrorType.GenericError, error.message || DEFAULT_ERROR_MESSAGE));
4946
+ return errorCell(new EvaluationError(CellErrorType.GenericError, error.message || DEFAULT_ERROR_MESSAGE));
4936
4947
  }
4937
4948
  }
4938
4949
  function textCell(value, localeFormat) {
@@ -4999,7 +5010,7 @@ function booleanCell(value, localeFormat) {
4999
5010
  formattedValue,
5000
5011
  };
5001
5012
  }
5002
- function errorCell(content, error) {
5013
+ function errorCell(error) {
5003
5014
  return {
5004
5015
  type: CellValueType.error,
5005
5016
  value: error.errorType,
@@ -13036,6 +13047,35 @@ const HLOOKUP = {
13036
13047
  isExported: true,
13037
13048
  };
13038
13049
  // -----------------------------------------------------------------------------
13050
+ // INDEX
13051
+ // -----------------------------------------------------------------------------
13052
+ const INDEX = {
13053
+ description: _lt(`Returns the content of a cell, specified by row and column offset.`),
13054
+ args: [
13055
+ arg("reference (any, range)", _lt("The range of cells from which the values are returned.")),
13056
+ arg("row (number)", _lt("The index of the row to be returned from within the reference range of cells.")),
13057
+ arg("column (number)", _lt("The index of the column to be returned from within the reference range of cells.")),
13058
+ ],
13059
+ returns: ["ANY"],
13060
+ computeFormat: function (reference, row, column) {
13061
+ const _row = toNumber(row.value, this.locale);
13062
+ const _column = toNumber(column.value, this.locale);
13063
+ return reference.format[_column - 1][_row - 1];
13064
+ },
13065
+ compute: function (reference, row, column) {
13066
+ const _reference = isMatrix(reference) ? reference : [[reference]];
13067
+ const _row = toNumber(row, this.locale);
13068
+ const _column = toNumber(column, this.locale);
13069
+ assert(() => _column >= 0 &&
13070
+ _column - 1 < _reference.length &&
13071
+ _row >= 0 &&
13072
+ _row - 1 < _reference[0].length, _lt("Index out of range."));
13073
+ assert(() => row !== 0 && column !== 0, _lt("This function can only return a single cell value, not an array. Provide valid row and column indices."));
13074
+ return _reference[_column - 1][_row - 1];
13075
+ },
13076
+ isExported: true,
13077
+ };
13078
+ // -----------------------------------------------------------------------------
13039
13079
  // LOOKUP
13040
13080
  // -----------------------------------------------------------------------------
13041
13081
  const LOOKUP = {
@@ -13233,6 +13273,7 @@ var lookup = /*#__PURE__*/Object.freeze({
13233
13273
  COLUMN: COLUMN,
13234
13274
  COLUMNS: COLUMNS,
13235
13275
  HLOOKUP: HLOOKUP,
13276
+ INDEX: INDEX,
13236
13277
  LOOKUP: LOOKUP,
13237
13278
  MATCH: MATCH,
13238
13279
  ROW: ROW,
@@ -21804,7 +21845,7 @@ class ChartPanel extends owl.Component {
21804
21845
  });
21805
21846
  }
21806
21847
  canUpdateChart(figureId, updateDefinition) {
21807
- if (figureId !== this.figureId) {
21848
+ if (figureId !== this.figureId || !this.env.model.getters.isChartDefined(figureId)) {
21808
21849
  return;
21809
21850
  }
21810
21851
  const definition = {
@@ -25672,7 +25713,14 @@ class AbstractResizer extends owl.Component {
25672
25713
  return;
25673
25714
  }
25674
25715
  if (this.state.waitingForMove === true) {
25675
- this.startMovement(ev);
25716
+ if (!this.env.model.getters.isGridSelectionActive()) {
25717
+ this._selectElement(index, false);
25718
+ }
25719
+ else {
25720
+ // FIXME: Consider reintroducing this feature for all type of selection if we find
25721
+ // a way to have the grid selection follow the other selections evolution
25722
+ this.startMovement(ev);
25723
+ }
25676
25724
  return;
25677
25725
  }
25678
25726
  if (this.env.model.getters.getEditionMode() === "editing") {
@@ -29098,12 +29146,15 @@ function createXMLFile(doc, path, contentType) {
29098
29146
  };
29099
29147
  }
29100
29148
  function xmlEscape(str) {
29101
- return String(str)
29149
+ return (String(str)
29102
29150
  .replace(/\&/g, "&amp;")
29103
29151
  .replace(/\</g, "&lt;")
29104
29152
  .replace(/\>/g, "&gt;")
29105
29153
  .replace(/\"/g, "&quot;")
29106
- .replace(/\'/g, "&apos;");
29154
+ .replace(/\'/g, "&apos;")
29155
+ // Delete all ASCII control characters except for TAB (\x09), LF (\x0A) and CR (\x0D)
29156
+ // They are not valid at all in XML 1.0 (even escaped)
29157
+ .replace(/[\x00-\x08\x0B\x0C\x0E-\x1F]/g, ""));
29107
29158
  }
29108
29159
  function formatAttributes(attrs) {
29109
29160
  return new XMLString(attrs.map(([key, val]) => `${key}="${xmlEscape(val)}"`).join(" "));
@@ -31821,10 +31872,11 @@ class CellPlugin extends CorePlugin {
31821
31872
  * Reconstructs the original formula string based on a normalized form and its dependencies
31822
31873
  */
31823
31874
  buildFormulaContent(sheetId, cell, dependencies) {
31824
- const ranges = dependencies || [...cell.dependencies];
31875
+ const ranges = dependencies || cell.dependencies;
31876
+ let rangeIndex = 0;
31825
31877
  return concat(cell.compiledFormula.tokens.map((token) => {
31826
31878
  if (token.type === "REFERENCE") {
31827
- const range = ranges.shift();
31879
+ const range = ranges[rangeIndex++];
31828
31880
  return this.getters.getRangeString(range, sheetId);
31829
31881
  }
31830
31882
  return token.value;
@@ -35432,7 +35484,7 @@ class CompilationParametersBuilder {
35432
35484
  const evaluatedCell = this.getEvaluatedCell(position);
35433
35485
  if (evaluatedCell.type === CellValueType.empty) {
35434
35486
  const cell = this.getters.getCell(position);
35435
- if (!cell || cell.content === "") {
35487
+ if (!cell || (!cell.isFormula && cell.content === "")) {
35436
35488
  return undefined;
35437
35489
  }
35438
35490
  }
@@ -35652,7 +35704,7 @@ class Evaluator {
35652
35704
  constructor(context, getters) {
35653
35705
  this.context = context;
35654
35706
  this.getters = getters;
35655
- this.compilationParams = buildCompilationParameters(context, getters, (position) => this.computeCell(this.encodePosition(position)));
35707
+ this.compilationParams = buildCompilationParameters(this.context, this.getters, this.computeAndSave.bind(this));
35656
35708
  }
35657
35709
  getEvaluatedCell(position) {
35658
35710
  return (this.evaluatedCells.get(this.encodePosition(position)) ||
@@ -35680,7 +35732,7 @@ class Evaluator {
35680
35732
  this.formulaDependencies().addDependencies(positionId, dependencies);
35681
35733
  }
35682
35734
  updateCompilationParameters() {
35683
- this.compilationParams = buildCompilationParameters(this.context, this.getters, (position) => this.computeCell(this.encodePosition(position)));
35735
+ this.compilationParams = buildCompilationParameters(this.context, this.getters, this.computeAndSave.bind(this));
35684
35736
  }
35685
35737
  evaluateCells(positions) {
35686
35738
  const cells = positions.map(this.encodePosition.bind(this));
@@ -35796,15 +35848,21 @@ class Evaluator {
35796
35848
  this.cellsBeingComputed.delete(cellId);
35797
35849
  }
35798
35850
  }
35851
+ computeAndSave(position) {
35852
+ const positionId = this.encodePosition(position);
35853
+ const evaluatedCell = this.computeCell(positionId);
35854
+ if (!this.evaluatedCells.has(positionId)) {
35855
+ this.setEvaluatedCell(positionId, evaluatedCell);
35856
+ }
35857
+ return evaluatedCell;
35858
+ }
35799
35859
  handleError(e, cell) {
35800
- if (!(e instanceof Error)) {
35801
- e = new Error(e);
35860
+ if (!(e instanceof EvaluationError)) {
35861
+ e = new EvaluationError(CellErrorType.GenericError, e.message);
35802
35862
  }
35803
- const msg = e?.errorType || CellErrorType.GenericError;
35804
- // apply function name
35805
35863
  const __lastFnCalled = this.compilationParams[2].__lastFnCalled || "";
35806
- const error = new EvaluationError(msg, e.message.replace("[[FUNCTION_NAME]]", __lastFnCalled), e.logLevel !== undefined ? e.logLevel : CellErrorLevel.error);
35807
- return errorCell(cell.content, error);
35864
+ e.message = e.message.replace("[[FUNCTION_NAME]]", __lastFnCalled);
35865
+ return errorCell(e);
35808
35866
  }
35809
35867
  computeFormulaCell(cellData) {
35810
35868
  const cellId = cellData.id;
@@ -41696,6 +41754,10 @@ class ClipboardCellsState extends ClipboardCellsAbstractState {
41696
41754
  if (!newRangesXC) {
41697
41755
  return;
41698
41756
  }
41757
+ if (newRangesXC.length === 0) {
41758
+ this.dispatch("REMOVE_CONDITIONAL_FORMAT", { id: cf.id, sheetId });
41759
+ return;
41760
+ }
41699
41761
  this.dispatch("ADD_CONDITIONAL_FORMAT", {
41700
41762
  cf: {
41701
41763
  id: cf.id,
@@ -43201,6 +43263,7 @@ class GridSelectionPlugin extends UIPlugin {
43201
43263
  "isSingleColSelected",
43202
43264
  "getElementsFromSelection",
43203
43265
  "tryGetActiveSheetId",
43266
+ "isGridSelectionActive",
43204
43267
  ];
43205
43268
  gridSelection = {
43206
43269
  anchor: {
@@ -43410,6 +43473,9 @@ class GridSelectionPlugin extends UIPlugin {
43410
43473
  // ---------------------------------------------------------------------------
43411
43474
  // Getters
43412
43475
  // ---------------------------------------------------------------------------
43476
+ isGridSelectionActive() {
43477
+ return this.selection.isListening(this);
43478
+ }
43413
43479
  getActiveSheet() {
43414
43480
  return this.activeSheet;
43415
43481
  }
@@ -48225,6 +48291,9 @@ class SelectionStreamProcessorImpl {
48225
48291
  },
48226
48292
  });
48227
48293
  }
48294
+ isListening(owner) {
48295
+ return this.stream.isListening(owner);
48296
+ }
48228
48297
  /**
48229
48298
  * Process a new anchor selection event. If the new anchor is inside
48230
48299
  * the sheet boundaries, the event is pushed to the event stream to
@@ -50693,6 +50762,6 @@ exports.setTranslationMethod = setTranslationMethod;
50693
50762
  exports.tokenize = tokenize;
50694
50763
 
50695
50764
 
50696
- __info__.version = '16.4.8';
50697
- __info__.date = '2023-10-03T12:45:33.807Z';
50698
- __info__.hash = 'c614d64';
50765
+ __info__.version = '16.4.10';
50766
+ __info__.date = '2023-10-19T14:23:58.054Z';
50767
+ __info__.hash = 'bc7546f';
@@ -962,7 +962,7 @@ declare class RangeImpl implements Range {
962
962
  constructor(args: ConstructorArgs, getSheetSize: (sheetId: UID) => ZoneDimension);
963
963
  static fromRange(range: Range, getters: CoreGetters): RangeImpl;
964
964
  get unboundedZone(): UnboundedZone;
965
- get zone(): Zone;
965
+ get zone(): Readonly<Zone>;
966
966
  static getRangeParts(xc: string, zone: UnboundedZone): RangePart[];
967
967
  get isFullCol(): boolean;
968
968
  get isFullRow(): boolean;
@@ -1057,6 +1057,7 @@ interface SelectionProcessor {
1057
1057
  selectAll(): DispatchResult;
1058
1058
  loopSelection(): DispatchResult;
1059
1059
  selectTableAroundSelection(): DispatchResult;
1060
+ isListening(owner: unknown): boolean;
1060
1061
  }
1061
1062
  type SelectionStreamProcessor = SelectionProcessor & StatefulStream<SelectionEvent, AnchorZone>;
1062
1063
 
@@ -4508,7 +4509,7 @@ declare class FilterEvaluationPlugin extends UIPlugin {
4508
4509
  */
4509
4510
  declare class GridSelectionPlugin extends UIPlugin {
4510
4511
  static layers: LAYERS[];
4511
- static getters: readonly ["getActiveSheet", "getActiveSheetId", "getActiveCell", "getActiveCols", "getActiveRows", "getCurrentStyle", "getSelectedZones", "getSelectedZone", "getSelectedCells", "getStatisticFnResults", "getAggregate", "getSelectedFigureId", "getSelection", "getActivePosition", "getSheetPosition", "isSelected", "isSingleColSelected", "getElementsFromSelection", "tryGetActiveSheetId"];
4512
+ static getters: readonly ["getActiveSheet", "getActiveSheetId", "getActiveCell", "getActiveCols", "getActiveRows", "getCurrentStyle", "getSelectedZones", "getSelectedZone", "getSelectedCells", "getStatisticFnResults", "getAggregate", "getSelectedFigureId", "getSelection", "getActivePosition", "getSheetPosition", "isSelected", "isSingleColSelected", "getElementsFromSelection", "tryGetActiveSheetId", "isGridSelectionActive"];
4512
4513
  private gridSelection;
4513
4514
  private selectedFigureId;
4514
4515
  private sheetsData;
@@ -4518,6 +4519,7 @@ declare class GridSelectionPlugin extends UIPlugin {
4518
4519
  allowDispatch(cmd: LocalCommand): CommandResult;
4519
4520
  private handleEvent;
4520
4521
  handle(cmd: Command): void;
4522
+ isGridSelectionActive(): boolean;
4521
4523
  getActiveSheet(): Readonly<Sheet>;
4522
4524
  getActiveSheetId(): UID;
4523
4525
  tryGetActiveSheetId(): UID | undefined;
@@ -1193,7 +1193,17 @@ const timeRegexp = /((\d+(:\d+)?(:\d+)?\s*(AM|PM))|(\d+:\d+(:\d+)?))$/;
1193
1193
  function isDateTime(str, locale) {
1194
1194
  return parseDateTime(str, locale) !== null;
1195
1195
  }
1196
+ const CACHE = new Map();
1196
1197
  function parseDateTime(str, locale) {
1198
+ if (!CACHE.has(locale)) {
1199
+ CACHE.set(locale, new Map());
1200
+ }
1201
+ if (!CACHE.get(locale).has(str)) {
1202
+ CACHE.get(locale).set(str, _parseDateTime(str, locale));
1203
+ }
1204
+ return CACHE.get(locale).get(str);
1205
+ }
1206
+ function _parseDateTime(str, locale) {
1197
1207
  str = str.trim();
1198
1208
  let time = null;
1199
1209
  const timeMatch = str.match(timeRegexp);
@@ -3012,8 +3022,9 @@ class RangeImpl {
3012
3022
  }
3013
3023
  get zone() {
3014
3024
  const { left, top, bottom, right } = this._zone;
3015
- if (right !== undefined && bottom !== undefined)
3016
- return { left, top, right, bottom };
3025
+ if (right !== undefined && bottom !== undefined) {
3026
+ return this._zone;
3027
+ }
3017
3028
  else if (bottom === undefined && right !== undefined) {
3018
3029
  return { right, top, left, bottom: this.getSheetSize(this.sheetId).numberOfRows - 1 };
3019
3030
  }
@@ -4283,7 +4294,7 @@ var LAYERS;
4283
4294
  const SORT_TYPES_ORDER = ["number", "string", "boolean", "undefined"];
4284
4295
  function assert(condition, message) {
4285
4296
  if (!condition()) {
4286
- throw new Error(message);
4297
+ throw new EvaluationError(CellErrorType.GenericError, message);
4287
4298
  }
4288
4299
  }
4289
4300
  // -----------------------------------------------------------------------------
@@ -4928,7 +4939,7 @@ function _createEvaluatedCell(value, localeFormat) {
4928
4939
  return textCell((value || "").toString(), localeFormat);
4929
4940
  }
4930
4941
  catch (error) {
4931
- return errorCell((value || "").toString(), new EvaluationError(CellErrorType.GenericError, error.message || DEFAULT_ERROR_MESSAGE));
4942
+ return errorCell(new EvaluationError(CellErrorType.GenericError, error.message || DEFAULT_ERROR_MESSAGE));
4932
4943
  }
4933
4944
  }
4934
4945
  function textCell(value, localeFormat) {
@@ -4995,7 +5006,7 @@ function booleanCell(value, localeFormat) {
4995
5006
  formattedValue,
4996
5007
  };
4997
5008
  }
4998
- function errorCell(content, error) {
5009
+ function errorCell(error) {
4999
5010
  return {
5000
5011
  type: CellValueType.error,
5001
5012
  value: error.errorType,
@@ -13032,6 +13043,35 @@ const HLOOKUP = {
13032
13043
  isExported: true,
13033
13044
  };
13034
13045
  // -----------------------------------------------------------------------------
13046
+ // INDEX
13047
+ // -----------------------------------------------------------------------------
13048
+ const INDEX = {
13049
+ description: _lt(`Returns the content of a cell, specified by row and column offset.`),
13050
+ args: [
13051
+ arg("reference (any, range)", _lt("The range of cells from which the values are returned.")),
13052
+ arg("row (number)", _lt("The index of the row to be returned from within the reference range of cells.")),
13053
+ arg("column (number)", _lt("The index of the column to be returned from within the reference range of cells.")),
13054
+ ],
13055
+ returns: ["ANY"],
13056
+ computeFormat: function (reference, row, column) {
13057
+ const _row = toNumber(row.value, this.locale);
13058
+ const _column = toNumber(column.value, this.locale);
13059
+ return reference.format[_column - 1][_row - 1];
13060
+ },
13061
+ compute: function (reference, row, column) {
13062
+ const _reference = isMatrix(reference) ? reference : [[reference]];
13063
+ const _row = toNumber(row, this.locale);
13064
+ const _column = toNumber(column, this.locale);
13065
+ assert(() => _column >= 0 &&
13066
+ _column - 1 < _reference.length &&
13067
+ _row >= 0 &&
13068
+ _row - 1 < _reference[0].length, _lt("Index out of range."));
13069
+ assert(() => row !== 0 && column !== 0, _lt("This function can only return a single cell value, not an array. Provide valid row and column indices."));
13070
+ return _reference[_column - 1][_row - 1];
13071
+ },
13072
+ isExported: true,
13073
+ };
13074
+ // -----------------------------------------------------------------------------
13035
13075
  // LOOKUP
13036
13076
  // -----------------------------------------------------------------------------
13037
13077
  const LOOKUP = {
@@ -13229,6 +13269,7 @@ var lookup = /*#__PURE__*/Object.freeze({
13229
13269
  COLUMN: COLUMN,
13230
13270
  COLUMNS: COLUMNS,
13231
13271
  HLOOKUP: HLOOKUP,
13272
+ INDEX: INDEX,
13232
13273
  LOOKUP: LOOKUP,
13233
13274
  MATCH: MATCH,
13234
13275
  ROW: ROW,
@@ -21800,7 +21841,7 @@ class ChartPanel extends Component {
21800
21841
  });
21801
21842
  }
21802
21843
  canUpdateChart(figureId, updateDefinition) {
21803
- if (figureId !== this.figureId) {
21844
+ if (figureId !== this.figureId || !this.env.model.getters.isChartDefined(figureId)) {
21804
21845
  return;
21805
21846
  }
21806
21847
  const definition = {
@@ -25668,7 +25709,14 @@ class AbstractResizer extends Component {
25668
25709
  return;
25669
25710
  }
25670
25711
  if (this.state.waitingForMove === true) {
25671
- this.startMovement(ev);
25712
+ if (!this.env.model.getters.isGridSelectionActive()) {
25713
+ this._selectElement(index, false);
25714
+ }
25715
+ else {
25716
+ // FIXME: Consider reintroducing this feature for all type of selection if we find
25717
+ // a way to have the grid selection follow the other selections evolution
25718
+ this.startMovement(ev);
25719
+ }
25672
25720
  return;
25673
25721
  }
25674
25722
  if (this.env.model.getters.getEditionMode() === "editing") {
@@ -29094,12 +29142,15 @@ function createXMLFile(doc, path, contentType) {
29094
29142
  };
29095
29143
  }
29096
29144
  function xmlEscape(str) {
29097
- return String(str)
29145
+ return (String(str)
29098
29146
  .replace(/\&/g, "&amp;")
29099
29147
  .replace(/\</g, "&lt;")
29100
29148
  .replace(/\>/g, "&gt;")
29101
29149
  .replace(/\"/g, "&quot;")
29102
- .replace(/\'/g, "&apos;");
29150
+ .replace(/\'/g, "&apos;")
29151
+ // Delete all ASCII control characters except for TAB (\x09), LF (\x0A) and CR (\x0D)
29152
+ // They are not valid at all in XML 1.0 (even escaped)
29153
+ .replace(/[\x00-\x08\x0B\x0C\x0E-\x1F]/g, ""));
29103
29154
  }
29104
29155
  function formatAttributes(attrs) {
29105
29156
  return new XMLString(attrs.map(([key, val]) => `${key}="${xmlEscape(val)}"`).join(" "));
@@ -31817,10 +31868,11 @@ class CellPlugin extends CorePlugin {
31817
31868
  * Reconstructs the original formula string based on a normalized form and its dependencies
31818
31869
  */
31819
31870
  buildFormulaContent(sheetId, cell, dependencies) {
31820
- const ranges = dependencies || [...cell.dependencies];
31871
+ const ranges = dependencies || cell.dependencies;
31872
+ let rangeIndex = 0;
31821
31873
  return concat(cell.compiledFormula.tokens.map((token) => {
31822
31874
  if (token.type === "REFERENCE") {
31823
- const range = ranges.shift();
31875
+ const range = ranges[rangeIndex++];
31824
31876
  return this.getters.getRangeString(range, sheetId);
31825
31877
  }
31826
31878
  return token.value;
@@ -35428,7 +35480,7 @@ class CompilationParametersBuilder {
35428
35480
  const evaluatedCell = this.getEvaluatedCell(position);
35429
35481
  if (evaluatedCell.type === CellValueType.empty) {
35430
35482
  const cell = this.getters.getCell(position);
35431
- if (!cell || cell.content === "") {
35483
+ if (!cell || (!cell.isFormula && cell.content === "")) {
35432
35484
  return undefined;
35433
35485
  }
35434
35486
  }
@@ -35648,7 +35700,7 @@ class Evaluator {
35648
35700
  constructor(context, getters) {
35649
35701
  this.context = context;
35650
35702
  this.getters = getters;
35651
- this.compilationParams = buildCompilationParameters(context, getters, (position) => this.computeCell(this.encodePosition(position)));
35703
+ this.compilationParams = buildCompilationParameters(this.context, this.getters, this.computeAndSave.bind(this));
35652
35704
  }
35653
35705
  getEvaluatedCell(position) {
35654
35706
  return (this.evaluatedCells.get(this.encodePosition(position)) ||
@@ -35676,7 +35728,7 @@ class Evaluator {
35676
35728
  this.formulaDependencies().addDependencies(positionId, dependencies);
35677
35729
  }
35678
35730
  updateCompilationParameters() {
35679
- this.compilationParams = buildCompilationParameters(this.context, this.getters, (position) => this.computeCell(this.encodePosition(position)));
35731
+ this.compilationParams = buildCompilationParameters(this.context, this.getters, this.computeAndSave.bind(this));
35680
35732
  }
35681
35733
  evaluateCells(positions) {
35682
35734
  const cells = positions.map(this.encodePosition.bind(this));
@@ -35792,15 +35844,21 @@ class Evaluator {
35792
35844
  this.cellsBeingComputed.delete(cellId);
35793
35845
  }
35794
35846
  }
35847
+ computeAndSave(position) {
35848
+ const positionId = this.encodePosition(position);
35849
+ const evaluatedCell = this.computeCell(positionId);
35850
+ if (!this.evaluatedCells.has(positionId)) {
35851
+ this.setEvaluatedCell(positionId, evaluatedCell);
35852
+ }
35853
+ return evaluatedCell;
35854
+ }
35795
35855
  handleError(e, cell) {
35796
- if (!(e instanceof Error)) {
35797
- e = new Error(e);
35856
+ if (!(e instanceof EvaluationError)) {
35857
+ e = new EvaluationError(CellErrorType.GenericError, e.message);
35798
35858
  }
35799
- const msg = e?.errorType || CellErrorType.GenericError;
35800
- // apply function name
35801
35859
  const __lastFnCalled = this.compilationParams[2].__lastFnCalled || "";
35802
- const error = new EvaluationError(msg, e.message.replace("[[FUNCTION_NAME]]", __lastFnCalled), e.logLevel !== undefined ? e.logLevel : CellErrorLevel.error);
35803
- return errorCell(cell.content, error);
35860
+ e.message = e.message.replace("[[FUNCTION_NAME]]", __lastFnCalled);
35861
+ return errorCell(e);
35804
35862
  }
35805
35863
  computeFormulaCell(cellData) {
35806
35864
  const cellId = cellData.id;
@@ -41692,6 +41750,10 @@ class ClipboardCellsState extends ClipboardCellsAbstractState {
41692
41750
  if (!newRangesXC) {
41693
41751
  return;
41694
41752
  }
41753
+ if (newRangesXC.length === 0) {
41754
+ this.dispatch("REMOVE_CONDITIONAL_FORMAT", { id: cf.id, sheetId });
41755
+ return;
41756
+ }
41695
41757
  this.dispatch("ADD_CONDITIONAL_FORMAT", {
41696
41758
  cf: {
41697
41759
  id: cf.id,
@@ -43197,6 +43259,7 @@ class GridSelectionPlugin extends UIPlugin {
43197
43259
  "isSingleColSelected",
43198
43260
  "getElementsFromSelection",
43199
43261
  "tryGetActiveSheetId",
43262
+ "isGridSelectionActive",
43200
43263
  ];
43201
43264
  gridSelection = {
43202
43265
  anchor: {
@@ -43406,6 +43469,9 @@ class GridSelectionPlugin extends UIPlugin {
43406
43469
  // ---------------------------------------------------------------------------
43407
43470
  // Getters
43408
43471
  // ---------------------------------------------------------------------------
43472
+ isGridSelectionActive() {
43473
+ return this.selection.isListening(this);
43474
+ }
43409
43475
  getActiveSheet() {
43410
43476
  return this.activeSheet;
43411
43477
  }
@@ -48221,6 +48287,9 @@ class SelectionStreamProcessorImpl {
48221
48287
  },
48222
48288
  });
48223
48289
  }
48290
+ isListening(owner) {
48291
+ return this.stream.isListening(owner);
48292
+ }
48224
48293
  /**
48225
48294
  * Process a new anchor selection event. If the new anchor is inside
48226
48295
  * the sheet boundaries, the event is pushed to the event stream to
@@ -50657,6 +50726,6 @@ const constants = {
50657
50726
  export { AbstractChart, CommandResult, CorePlugin, DispatchResult, EvaluationError, Model, Registry, Revision, SPREADSHEET_DIMENSIONS, Spreadsheet, UIPlugin, __info__, addFunction, astToFormula, compile, components, constants, convertAstNodes, coreTypes, findCellInNewZone, functionCache, helpers, invalidateCFEvaluationCommands, invalidateDependenciesCommands, invalidateEvaluationCommands, iterateAstNodes, links, load, parse, readonlyAllowedCommands, registries, setDefaultSheetViewSize, setTranslationMethod, tokenize };
50658
50727
 
50659
50728
 
50660
- __info__.version = '16.4.8';
50661
- __info__.date = '2023-10-03T12:45:33.807Z';
50662
- __info__.hash = 'c614d64';
50729
+ __info__.version = '16.4.10';
50730
+ __info__.date = '2023-10-19T14:23:58.054Z';
50731
+ __info__.hash = 'bc7546f';