@odoo/o-spreadsheet 18.2.13 → 18.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.
- package/dist/o-spreadsheet.cjs.js +206 -122
- package/dist/o-spreadsheet.esm.js +206 -122
- package/dist/o-spreadsheet.iife.js +206 -122
- package/dist/o-spreadsheet.iife.min.js +378 -378
- package/dist/o_spreadsheet.xml +6 -6
- package/package.json +1 -1
|
@@ -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 18.2.
|
|
6
|
-
* @date 2025-05-
|
|
7
|
-
* @hash
|
|
5
|
+
* @version 18.2.15
|
|
6
|
+
* @date 2025-05-30T08:45:53.952Z
|
|
7
|
+
* @hash 607492d
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
import { useEnv, useSubEnv, onWillUnmount, useComponent, status, Component, useRef, onMounted, useEffect, App, blockDom, useState, onPatched, onWillPatch, onWillUpdateProps, useExternalListener, onWillStart, xml, useChildSubEnv, markRaw, toRaw } from '@odoo/owl';
|
|
@@ -4149,6 +4149,113 @@ function transposeMatrix(matrix) {
|
|
|
4149
4149
|
}
|
|
4150
4150
|
return generateMatrix(matrix[0].length, matrix.length, (i, j) => matrix[j][i]);
|
|
4151
4151
|
}
|
|
4152
|
+
/**
|
|
4153
|
+
* Enables a formula function to accept matrix or vector inputs instead of simple value, computing results across multiple dimensions.
|
|
4154
|
+
*
|
|
4155
|
+
* ```
|
|
4156
|
+
* / |‾ ‾| \ |‾ ‾|
|
|
4157
|
+
* | | [A] | | | compute(A, D, E), compute(A, D, F), compute(A, D, G) |
|
|
4158
|
+
* applyVectorization| compute, | [B], D, [E, F, G] | | <=> | compute(B, D, E), compute(B, D, F), compute(B, D, G) |
|
|
4159
|
+
* | | [C] | | | compute(C, D, E), compute(C, D, F), compute(C, D, G) |
|
|
4160
|
+
* \ |_ _| / |_ _|
|
|
4161
|
+
* ```
|
|
4162
|
+
*
|
|
4163
|
+
* By default, all arguments are vectorized. To control which arguments are vectorized,
|
|
4164
|
+
* pass an `acceptToVectorize` boolean array of the same length as `args`:
|
|
4165
|
+
* - `true` enables vectorization for that argument
|
|
4166
|
+
* - `false` disables vectorization for that argument
|
|
4167
|
+
*
|
|
4168
|
+
* For example, with `[true, true, false]` on previous example you get:
|
|
4169
|
+
*
|
|
4170
|
+
* ```
|
|
4171
|
+
* |‾ ‾|
|
|
4172
|
+
* | compute(A, D, [E, F, G]) |
|
|
4173
|
+
* | compute(B, D, [E, F, G]) |
|
|
4174
|
+
* | compute(C, D, [E, F, G]) |
|
|
4175
|
+
* |_ _|
|
|
4176
|
+
* ```
|
|
4177
|
+
*
|
|
4178
|
+
* @remarks
|
|
4179
|
+
* This helper is automatically applied (by default) to **all** `compute` functions
|
|
4180
|
+
* across the various spreadsheet formula modules:
|
|
4181
|
+
* - If an argument is declared **scalar** (not `"range"`), it is vectorized.
|
|
4182
|
+
* - If **all** arguments are declared **ranges**, no vectorization occurs.
|
|
4183
|
+
* - e.g. `SUM(A1:B2)` returns a 1×1 sum over the range.
|
|
4184
|
+
* - e.g. `COS(A1:B2)` over `A1:B2` returns a 2×2 element-wise result.
|
|
4185
|
+
* - For special behaviors (e.g. the `IF` function), you may declare all arguments
|
|
4186
|
+
* as ranges and invoke this helper directly within your `compute` implementation.
|
|
4187
|
+
*/
|
|
4188
|
+
function applyVectorization(formula, args, acceptToVectorize = undefined) {
|
|
4189
|
+
let countVectorizedCol = 1;
|
|
4190
|
+
let countVectorizedRow = 1;
|
|
4191
|
+
let vectorizedColLimit = Infinity;
|
|
4192
|
+
let vectorizedRowLimit = Infinity;
|
|
4193
|
+
let vectorArgsType = undefined;
|
|
4194
|
+
for (let i = 0; i < args.length; i++) {
|
|
4195
|
+
const arg = args[i];
|
|
4196
|
+
if (isMatrix(arg) && (acceptToVectorize === undefined || acceptToVectorize[i])) {
|
|
4197
|
+
const nColumns = arg.length;
|
|
4198
|
+
const nRows = arg[0].length;
|
|
4199
|
+
if (nColumns !== 1 || nRows !== 1) {
|
|
4200
|
+
vectorArgsType ??= new Array(args.length);
|
|
4201
|
+
if (nColumns !== 1 && nRows !== 1) {
|
|
4202
|
+
vectorArgsType[i] = "matrix";
|
|
4203
|
+
countVectorizedCol = Math.max(countVectorizedCol, nColumns);
|
|
4204
|
+
countVectorizedRow = Math.max(countVectorizedRow, nRows);
|
|
4205
|
+
vectorizedColLimit = Math.min(vectorizedColLimit, nColumns);
|
|
4206
|
+
vectorizedRowLimit = Math.min(vectorizedRowLimit, nRows);
|
|
4207
|
+
}
|
|
4208
|
+
else if (nColumns !== 1) {
|
|
4209
|
+
vectorArgsType[i] = "horizontal";
|
|
4210
|
+
countVectorizedCol = Math.max(countVectorizedCol, nColumns);
|
|
4211
|
+
vectorizedColLimit = Math.min(vectorizedColLimit, nColumns);
|
|
4212
|
+
}
|
|
4213
|
+
else if (nRows !== 1) {
|
|
4214
|
+
vectorArgsType[i] = "vertical";
|
|
4215
|
+
countVectorizedRow = Math.max(countVectorizedRow, nRows);
|
|
4216
|
+
vectorizedRowLimit = Math.min(vectorizedRowLimit, nRows);
|
|
4217
|
+
}
|
|
4218
|
+
}
|
|
4219
|
+
else {
|
|
4220
|
+
args[i] = arg[0][0];
|
|
4221
|
+
}
|
|
4222
|
+
}
|
|
4223
|
+
}
|
|
4224
|
+
if (countVectorizedCol === 1 && countVectorizedRow === 1) {
|
|
4225
|
+
// either this function is not vectorized or it ends up with a 1x1 dimension
|
|
4226
|
+
return formula(...args);
|
|
4227
|
+
}
|
|
4228
|
+
const getArgOffset = (i, j) => args.map((arg, index) => {
|
|
4229
|
+
switch (vectorArgsType?.[index]) {
|
|
4230
|
+
case "matrix":
|
|
4231
|
+
return arg[i][j];
|
|
4232
|
+
case "horizontal":
|
|
4233
|
+
return arg[i][0];
|
|
4234
|
+
case "vertical":
|
|
4235
|
+
return arg[0][j];
|
|
4236
|
+
case undefined:
|
|
4237
|
+
return arg;
|
|
4238
|
+
}
|
|
4239
|
+
});
|
|
4240
|
+
return generateMatrix(countVectorizedCol, countVectorizedRow, (col, row) => {
|
|
4241
|
+
if (col > vectorizedColLimit - 1 || row > vectorizedRowLimit - 1) {
|
|
4242
|
+
return new NotAvailableError(_t("Array arguments to [[FUNCTION_NAME]] are of different size."));
|
|
4243
|
+
}
|
|
4244
|
+
const singleCellComputeResult = formula(...getArgOffset(col, row));
|
|
4245
|
+
// In the case where the user tries to vectorize arguments of an array formula, we will get an
|
|
4246
|
+
// array for every combination of the vectorized arguments, which will lead to a 3D matrix and
|
|
4247
|
+
// we won't be able to return the values.
|
|
4248
|
+
// In this case, we keep the first element of each spreading part, just as Excel does, and
|
|
4249
|
+
// create an array with these parts.
|
|
4250
|
+
// For exemple, we have MUNIT(x) that return an unitary matrix of x*x. If we use it with a
|
|
4251
|
+
// range, like MUNIT(A1:A2), we will get two unitary matrices (one for the value in A1 and one
|
|
4252
|
+
// for the value in A2). In this case, we will simply take the first value of each matrix and
|
|
4253
|
+
// return the array [First value of MUNIT(A1), First value of MUNIT(A2)].
|
|
4254
|
+
return isMatrix(singleCellComputeResult)
|
|
4255
|
+
? singleCellComputeResult[0][0]
|
|
4256
|
+
: singleCellComputeResult;
|
|
4257
|
+
});
|
|
4258
|
+
}
|
|
4152
4259
|
// -----------------------------------------------------------------------------
|
|
4153
4260
|
// CONDITIONAL EXPLORE FUNCTIONS
|
|
4154
4261
|
// -----------------------------------------------------------------------------
|
|
@@ -7440,14 +7547,20 @@ function multiplyMatrices(matrix1, matrix2) {
|
|
|
7440
7547
|
/**
|
|
7441
7548
|
* Return the input if it's a scalar or the first element of the input if it's a matrix.
|
|
7442
7549
|
*/
|
|
7443
|
-
function toScalar(
|
|
7444
|
-
if (!isMatrix(
|
|
7445
|
-
return
|
|
7550
|
+
function toScalar(arg) {
|
|
7551
|
+
if (!isMatrix(arg)) {
|
|
7552
|
+
return arg;
|
|
7446
7553
|
}
|
|
7447
|
-
if (
|
|
7554
|
+
if (!isSingleElementMatrix(arg)) {
|
|
7448
7555
|
throw new EvaluationError(_t("The value should be a scalar or a 1x1 matrix"));
|
|
7449
7556
|
}
|
|
7450
|
-
return
|
|
7557
|
+
return arg[0][0];
|
|
7558
|
+
}
|
|
7559
|
+
function isSingleElementMatrix(matrix) {
|
|
7560
|
+
return matrix.length === 1 && matrix[0].length === 1;
|
|
7561
|
+
}
|
|
7562
|
+
function isMultipleElementMatrix(arg) {
|
|
7563
|
+
return isMatrix(arg) && !isSingleElementMatrix(arg);
|
|
7451
7564
|
}
|
|
7452
7565
|
|
|
7453
7566
|
function assertSameNumberOfElements(...args) {
|
|
@@ -8189,9 +8302,10 @@ const AGGREGATOR_NAMES = {
|
|
|
8189
8302
|
avg: _t("Average"),
|
|
8190
8303
|
sum: _t("Sum"),
|
|
8191
8304
|
};
|
|
8305
|
+
const NUMBER_CHAR_AGGREGATORS = ["max", "min", "avg", "sum", "count_distinct", "count"];
|
|
8192
8306
|
const AGGREGATORS_BY_FIELD_TYPE = {
|
|
8193
|
-
integer:
|
|
8194
|
-
char:
|
|
8307
|
+
integer: NUMBER_CHAR_AGGREGATORS,
|
|
8308
|
+
char: NUMBER_CHAR_AGGREGATORS,
|
|
8195
8309
|
boolean: ["count_distinct", "count", "bool_and", "bool_or"],
|
|
8196
8310
|
datetime: ["max", "min", "count_distinct", "count"],
|
|
8197
8311
|
};
|
|
@@ -15455,7 +15569,7 @@ const FILTER = {
|
|
|
15455
15569
|
}
|
|
15456
15570
|
return mode === "row" ? transposeMatrix(result) : result;
|
|
15457
15571
|
},
|
|
15458
|
-
isExported:
|
|
15572
|
+
isExported: false,
|
|
15459
15573
|
};
|
|
15460
15574
|
// -----------------------------------------------------------------------------
|
|
15461
15575
|
// SORT
|
|
@@ -18586,16 +18700,23 @@ const FALSE = {
|
|
|
18586
18700
|
const IF = {
|
|
18587
18701
|
description: _t("Returns value depending on logical expression."),
|
|
18588
18702
|
args: [
|
|
18589
|
-
arg("logical_expression (boolean)", _t("An expression or reference to a cell containing an expression that represents some logical value, i.e. TRUE or FALSE.")),
|
|
18590
|
-
arg("value_if_true (any)", _t("The value the function returns if logical_expression is TRUE.")),
|
|
18591
|
-
arg("value_if_false (any, default=FALSE)", _t("The value the function returns if logical_expression is FALSE.")),
|
|
18703
|
+
arg("logical_expression (boolean, range<boolean>)", _t("An expression or reference to a cell containing an expression that represents some logical value, i.e. TRUE or FALSE.")),
|
|
18704
|
+
arg("value_if_true (any, range)", _t("The value the function returns if logical_expression is TRUE.")),
|
|
18705
|
+
arg("value_if_false (any, range, default=FALSE)", _t("The value the function returns if logical_expression is FALSE.")),
|
|
18592
18706
|
],
|
|
18593
18707
|
compute: function (logicalExpression, valueIfTrue, valueIfFalse) {
|
|
18594
|
-
|
|
18708
|
+
if (isMultipleElementMatrix(logicalExpression)) {
|
|
18709
|
+
return applyVectorization(IF.compute, [logicalExpression, valueIfTrue, valueIfFalse]);
|
|
18710
|
+
}
|
|
18711
|
+
let result = toBoolean(toScalar(logicalExpression)) ? valueIfTrue : valueIfFalse;
|
|
18712
|
+
// useful for interpreting empty cell references as empty strings. But must be removed to make empty cell references equal to zero
|
|
18713
|
+
if (!isMultipleElementMatrix(result)) {
|
|
18714
|
+
result = toScalar(result);
|
|
18715
|
+
}
|
|
18595
18716
|
if (result === undefined) {
|
|
18596
18717
|
return { value: "" };
|
|
18597
18718
|
}
|
|
18598
|
-
if (result.value === null) {
|
|
18719
|
+
if (!isMatrix(result) && result.value === null) {
|
|
18599
18720
|
return { ...result, value: "" };
|
|
18600
18721
|
}
|
|
18601
18722
|
return result;
|
|
@@ -18608,15 +18729,22 @@ const IF = {
|
|
|
18608
18729
|
const IFERROR = {
|
|
18609
18730
|
description: _t("Value if it is not an error, otherwise 2nd argument."),
|
|
18610
18731
|
args: [
|
|
18611
|
-
arg("value (any)", _t("The value to return if value itself is not an error.")),
|
|
18612
|
-
arg(`value_if_error (any, default="empty")`, _t("The value the function returns if value is an error.")),
|
|
18732
|
+
arg("value (any, range)", _t("The value to return if value itself is not an error.")),
|
|
18733
|
+
arg(`value_if_error (any, range, default="empty")`, _t("The value the function returns if value is an error.")),
|
|
18613
18734
|
],
|
|
18614
|
-
compute: function (value, valueIfError
|
|
18615
|
-
|
|
18735
|
+
compute: function (value, valueIfError) {
|
|
18736
|
+
if (isMultipleElementMatrix(value)) {
|
|
18737
|
+
return applyVectorization(IFERROR.compute, [value, valueIfError]);
|
|
18738
|
+
}
|
|
18739
|
+
let result = isEvaluationError(toScalar(value)?.value) ? valueIfError : value;
|
|
18740
|
+
// useful for interpreting empty cell references as empty strings. But must be removed to make empty cell references equal to zero
|
|
18741
|
+
if (!isMultipleElementMatrix(result)) {
|
|
18742
|
+
result = toScalar(result);
|
|
18743
|
+
}
|
|
18616
18744
|
if (result === undefined) {
|
|
18617
18745
|
return { value: "" };
|
|
18618
18746
|
}
|
|
18619
|
-
if (result.value === null) {
|
|
18747
|
+
if (!isMatrix(result) && result.value === null) {
|
|
18620
18748
|
return { ...result, value: "" };
|
|
18621
18749
|
}
|
|
18622
18750
|
return result;
|
|
@@ -18629,15 +18757,22 @@ const IFERROR = {
|
|
|
18629
18757
|
const IFNA = {
|
|
18630
18758
|
description: _t("Value if it is not an #N/A error, otherwise 2nd argument."),
|
|
18631
18759
|
args: [
|
|
18632
|
-
arg("value (any)", _t("The value to return if value itself is not #N/A an error.")),
|
|
18633
|
-
arg(`value_if_error (any, default="empty")`, _t("The value the function returns if value is an #N/A error.")),
|
|
18760
|
+
arg("value (any, range)", _t("The value to return if value itself is not #N/A an error.")),
|
|
18761
|
+
arg(`value_if_error (any, range, default="empty")`, _t("The value the function returns if value is an #N/A error.")),
|
|
18634
18762
|
],
|
|
18635
|
-
compute: function (value, valueIfError
|
|
18636
|
-
|
|
18763
|
+
compute: function (value, valueIfError) {
|
|
18764
|
+
if (isMultipleElementMatrix(value)) {
|
|
18765
|
+
return applyVectorization(IFNA.compute, [value, valueIfError]);
|
|
18766
|
+
}
|
|
18767
|
+
let result = toScalar(value)?.value === CellErrorType.NotAvailable ? valueIfError : value;
|
|
18768
|
+
// useful for interpreting empty cell references as empty strings. But must be removed to make empty cell references equal to zero
|
|
18769
|
+
if (!isMultipleElementMatrix(result)) {
|
|
18770
|
+
result = toScalar(result);
|
|
18771
|
+
}
|
|
18637
18772
|
if (result === undefined) {
|
|
18638
18773
|
return { value: "" };
|
|
18639
18774
|
}
|
|
18640
|
-
if (result.value === null) {
|
|
18775
|
+
if (!isMatrix(result) && result.value === null) {
|
|
18641
18776
|
return { ...result, value: "" };
|
|
18642
18777
|
}
|
|
18643
18778
|
return result;
|
|
@@ -18650,23 +18785,31 @@ const IFNA = {
|
|
|
18650
18785
|
const IFS = {
|
|
18651
18786
|
description: _t("Returns a value depending on multiple logical expressions."),
|
|
18652
18787
|
args: [
|
|
18653
|
-
arg("condition1 (boolean)", _t("The first condition to be evaluated. This can be a boolean, a number, an array, or a reference to any of those.")),
|
|
18654
|
-
arg("value1 (any)", _t("The returned value if condition1 is TRUE.")),
|
|
18655
|
-
arg("condition2 (boolean, any, repeating)", _t("Additional conditions to be evaluated if the previous ones are FALSE.")),
|
|
18656
|
-
arg("value2 (any, repeating)", _t("Additional values to be returned if their corresponding conditions are TRUE.")),
|
|
18788
|
+
arg("condition1 (boolean, range<boolean>)", _t("The first condition to be evaluated. This can be a boolean, a number, an array, or a reference to any of those.")),
|
|
18789
|
+
arg("value1 (any, range)", _t("The returned value if condition1 is TRUE.")),
|
|
18790
|
+
arg("condition2 (boolean, any, range, repeating)", _t("Additional conditions to be evaluated if the previous ones are FALSE.")),
|
|
18791
|
+
arg("value2 (any, range, repeating)", _t("Additional values to be returned if their corresponding conditions are TRUE.")),
|
|
18657
18792
|
],
|
|
18658
18793
|
compute: function (...values) {
|
|
18659
18794
|
assert(() => values.length % 2 === 0, _t("Wrong number of arguments. Expected an even number of arguments."));
|
|
18660
|
-
|
|
18661
|
-
if (
|
|
18662
|
-
|
|
18663
|
-
|
|
18795
|
+
while (values.length > 0) {
|
|
18796
|
+
if (isMultipleElementMatrix(values[0])) {
|
|
18797
|
+
return applyVectorization(IFS.compute, values);
|
|
18798
|
+
}
|
|
18799
|
+
const condition = toBoolean(toScalar(values.shift()));
|
|
18800
|
+
let valueIfTrue = values.shift();
|
|
18801
|
+
if (condition) {
|
|
18802
|
+
// useful for interpreting empty cell references as empty strings. But must be removed to make empty cell references equal to zero
|
|
18803
|
+
if (!isMultipleElementMatrix(valueIfTrue)) {
|
|
18804
|
+
valueIfTrue = toScalar(valueIfTrue);
|
|
18805
|
+
}
|
|
18806
|
+
if (valueIfTrue === undefined) {
|
|
18664
18807
|
return { value: "" };
|
|
18665
18808
|
}
|
|
18666
|
-
if (
|
|
18667
|
-
return { ...
|
|
18809
|
+
if (!isMatrix(valueIfTrue) && valueIfTrue.value === null) {
|
|
18810
|
+
return { ...valueIfTrue, value: "" };
|
|
18668
18811
|
}
|
|
18669
|
-
return
|
|
18812
|
+
return valueIfTrue;
|
|
18670
18813
|
}
|
|
18671
18814
|
}
|
|
18672
18815
|
return new EvaluationError(_t("No match."));
|
|
@@ -20328,7 +20471,7 @@ const SPLIT = {
|
|
|
20328
20471
|
}
|
|
20329
20472
|
return transposeMatrix([result]);
|
|
20330
20473
|
},
|
|
20331
|
-
isExported:
|
|
20474
|
+
isExported: false,
|
|
20332
20475
|
};
|
|
20333
20476
|
// -----------------------------------------------------------------------------
|
|
20334
20477
|
// SUBSTITUTE
|
|
@@ -20521,86 +20664,21 @@ for (let category of categories) {
|
|
|
20521
20664
|
functionRegistry.add(name, { isExported: false, ...addDescr });
|
|
20522
20665
|
}
|
|
20523
20666
|
}
|
|
20524
|
-
|
|
20667
|
+
//------------------------------------------------------------------------------
|
|
20668
|
+
// CREATE COMPUTE FUNCTION
|
|
20669
|
+
//------------------------------------------------------------------------------
|
|
20525
20670
|
function createComputeFunction(descr, functionName) {
|
|
20526
20671
|
function vectorizedCompute(...args) {
|
|
20527
|
-
|
|
20528
|
-
let countVectorizableRow = 1;
|
|
20529
|
-
let vectorizableColLimit = Infinity;
|
|
20530
|
-
let vectorizableRowLimit = Infinity;
|
|
20531
|
-
let vectorArgsType = undefined;
|
|
20532
|
-
//#region Compute vectorisation limits
|
|
20672
|
+
const acceptToVectorize = [];
|
|
20533
20673
|
for (let i = 0; i < args.length; i++) {
|
|
20534
20674
|
const argDefinition = descr.args[descr.getArgToFocus(i + 1) - 1];
|
|
20535
20675
|
const arg = args[i];
|
|
20536
|
-
if (isMatrix(arg) && !argDefinition.acceptMatrix) {
|
|
20537
|
-
// if argDefinition does not accept a matrix but arg is still a matrix
|
|
20538
|
-
// --> triggers the arguments vectorization
|
|
20539
|
-
const nColumns = arg.length;
|
|
20540
|
-
const nRows = arg[0].length;
|
|
20541
|
-
if (nColumns !== 1 || nRows !== 1) {
|
|
20542
|
-
vectorArgsType ??= new Array(args.length);
|
|
20543
|
-
if (nColumns !== 1 && nRows !== 1) {
|
|
20544
|
-
vectorArgsType[i] = "matrix";
|
|
20545
|
-
countVectorizableCol = Math.max(countVectorizableCol, nColumns);
|
|
20546
|
-
countVectorizableRow = Math.max(countVectorizableRow, nRows);
|
|
20547
|
-
vectorizableColLimit = Math.min(vectorizableColLimit, nColumns);
|
|
20548
|
-
vectorizableRowLimit = Math.min(vectorizableRowLimit, nRows);
|
|
20549
|
-
}
|
|
20550
|
-
else if (nColumns !== 1) {
|
|
20551
|
-
vectorArgsType[i] = "horizontal";
|
|
20552
|
-
countVectorizableCol = Math.max(countVectorizableCol, nColumns);
|
|
20553
|
-
vectorizableColLimit = Math.min(vectorizableColLimit, nColumns);
|
|
20554
|
-
}
|
|
20555
|
-
else if (nRows !== 1) {
|
|
20556
|
-
vectorArgsType[i] = "vertical";
|
|
20557
|
-
countVectorizableRow = Math.max(countVectorizableRow, nRows);
|
|
20558
|
-
vectorizableRowLimit = Math.min(vectorizableRowLimit, nRows);
|
|
20559
|
-
}
|
|
20560
|
-
}
|
|
20561
|
-
else {
|
|
20562
|
-
args[i] = arg[0][0];
|
|
20563
|
-
}
|
|
20564
|
-
}
|
|
20565
20676
|
if (!isMatrix(arg) && argDefinition.acceptMatrixOnly) {
|
|
20566
20677
|
throw new BadExpressionError(_t("Function %s expects the parameter '%s' to be reference to a cell or range.", functionName, (i + 1).toString()));
|
|
20567
20678
|
}
|
|
20679
|
+
acceptToVectorize.push(!argDefinition.acceptMatrix);
|
|
20568
20680
|
}
|
|
20569
|
-
|
|
20570
|
-
if (countVectorizableCol === 1 && countVectorizableRow === 1) {
|
|
20571
|
-
// either this function is not vectorized or it ends up with a 1x1 dimension
|
|
20572
|
-
return errorHandlingCompute.apply(this, args);
|
|
20573
|
-
}
|
|
20574
|
-
const getArgOffset = (i, j) => args.map((arg, index) => {
|
|
20575
|
-
switch (vectorArgsType?.[index]) {
|
|
20576
|
-
case "matrix":
|
|
20577
|
-
return arg[i][j];
|
|
20578
|
-
case "horizontal":
|
|
20579
|
-
return arg[i][0];
|
|
20580
|
-
case "vertical":
|
|
20581
|
-
return arg[0][j];
|
|
20582
|
-
case undefined:
|
|
20583
|
-
return arg;
|
|
20584
|
-
}
|
|
20585
|
-
});
|
|
20586
|
-
return generateMatrix(countVectorizableCol, countVectorizableRow, (col, row) => {
|
|
20587
|
-
if (col > vectorizableColLimit - 1 || row > vectorizableRowLimit - 1) {
|
|
20588
|
-
return notAvailableError;
|
|
20589
|
-
}
|
|
20590
|
-
const singleCellComputeResult = errorHandlingCompute.apply(this, getArgOffset(col, row));
|
|
20591
|
-
// In the case where the user tries to vectorize arguments of an array formula, we will get an
|
|
20592
|
-
// array for every combination of the vectorized arguments, which will lead to a 3D matrix and
|
|
20593
|
-
// we won't be able to return the values.
|
|
20594
|
-
// In this case, we keep the first element of each spreading part, just as Excel does, and
|
|
20595
|
-
// create an array with these parts.
|
|
20596
|
-
// For exemple, we have MUNIT(x) that return an unitary matrix of x*x. If we use it with a
|
|
20597
|
-
// range, like MUNIT(A1:A2), we will get two unitary matrices (one for the value in A1 and one
|
|
20598
|
-
// for the value in A2). In this case, we will simply take the first value of each matrix and
|
|
20599
|
-
// return the array [First value of MUNIT(A1), First value of MUNIT(A2)].
|
|
20600
|
-
return isMatrix(singleCellComputeResult)
|
|
20601
|
-
? singleCellComputeResult[0][0]
|
|
20602
|
-
: singleCellComputeResult;
|
|
20603
|
-
});
|
|
20681
|
+
return applyVectorization(errorHandlingCompute.bind(this), args, acceptToVectorize);
|
|
20604
20682
|
}
|
|
20605
20683
|
function errorHandlingCompute(...args) {
|
|
20606
20684
|
for (let i = 0; i < args.length; i++) {
|
|
@@ -21445,7 +21523,7 @@ class AbstractComposerStore extends SpreadsheetStore {
|
|
|
21445
21523
|
proposals &&
|
|
21446
21524
|
!["ARG_SEPARATOR", "LEFT_PAREN", "OPERATOR"].includes(tokenAtCursor.type)) {
|
|
21447
21525
|
const filteredProposals = fuzzyLookup(searchTerm, proposals, (p) => p.fuzzySearchKey || p.text);
|
|
21448
|
-
if (!exactMatch || filteredProposals.length
|
|
21526
|
+
if (!exactMatch || filteredProposals.length) {
|
|
21449
21527
|
proposals = filteredProposals;
|
|
21450
21528
|
}
|
|
21451
21529
|
}
|
|
@@ -46481,7 +46559,9 @@ function compareDimensionValues(dimension, a, b) {
|
|
|
46481
46559
|
return dimension.order === "asc" ? -1 : 1;
|
|
46482
46560
|
}
|
|
46483
46561
|
if (dimension.type === "integer" || dimension.type === "datetime") {
|
|
46484
|
-
return dimension.order === "asc"
|
|
46562
|
+
return dimension.order === "asc"
|
|
46563
|
+
? toNumber(a, DEFAULT_LOCALE) - toNumber(b, DEFAULT_LOCALE)
|
|
46564
|
+
: toNumber(b, DEFAULT_LOCALE) - toNumber(a, DEFAULT_LOCALE);
|
|
46485
46565
|
}
|
|
46486
46566
|
return dimension.order === "asc" ? a.localeCompare(b) : b.localeCompare(a);
|
|
46487
46567
|
}
|
|
@@ -47015,12 +47095,7 @@ class SpreadsheetPivot {
|
|
|
47015
47095
|
entry[field.name] = { value: null, type: CellValueType.empty, formattedValue: "" };
|
|
47016
47096
|
}
|
|
47017
47097
|
else {
|
|
47018
|
-
|
|
47019
|
-
entry[field.name] = { ...cell, value: cell.formattedValue || null };
|
|
47020
|
-
}
|
|
47021
|
-
else {
|
|
47022
|
-
entry[field.name] = cell;
|
|
47023
|
-
}
|
|
47098
|
+
entry[field.name] = cell;
|
|
47024
47099
|
}
|
|
47025
47100
|
}
|
|
47026
47101
|
entry["__count"] = { value: 1, type: CellValueType.number, formattedValue: "1" };
|
|
@@ -49244,8 +49319,7 @@ class CellComposerStore extends AbstractComposerStore {
|
|
|
49244
49319
|
if (!spreader) {
|
|
49245
49320
|
return undefined;
|
|
49246
49321
|
}
|
|
49247
|
-
|
|
49248
|
-
return cell?.content;
|
|
49322
|
+
return this.getters.getCellText(spreader, { showFormula: true });
|
|
49249
49323
|
}
|
|
49250
49324
|
get currentEditedCell() {
|
|
49251
49325
|
return {
|
|
@@ -52166,6 +52240,7 @@ function useGridDrawing(refName, model, canvasSize) {
|
|
|
52166
52240
|
const friction = 0.95;
|
|
52167
52241
|
const verticalScrollFactor = 1;
|
|
52168
52242
|
const horizontalScrollFactor = 1;
|
|
52243
|
+
const resetTimeoutDuration = 100;
|
|
52169
52244
|
function useTouchScroll(ref, updateScroll, canMoveUp) {
|
|
52170
52245
|
let lastX = 0;
|
|
52171
52246
|
let lastY = 0;
|
|
@@ -52173,6 +52248,7 @@ function useTouchScroll(ref, updateScroll, canMoveUp) {
|
|
|
52173
52248
|
let velocityY = 0;
|
|
52174
52249
|
let isMouseDown = false;
|
|
52175
52250
|
let lastTime = 0;
|
|
52251
|
+
let resetTimeout = null;
|
|
52176
52252
|
useRefListener(ref, "touchstart", onTouchStart, { capture: false });
|
|
52177
52253
|
useRefListener(ref, "touchmove", onTouchMove, { capture: false });
|
|
52178
52254
|
useRefListener(ref, "touchend", onTouchEnd, { capture: false });
|
|
@@ -52185,6 +52261,10 @@ function useTouchScroll(ref, updateScroll, canMoveUp) {
|
|
|
52185
52261
|
function onTouchMove(event) {
|
|
52186
52262
|
if (!isMouseDown)
|
|
52187
52263
|
return;
|
|
52264
|
+
if (resetTimeout) {
|
|
52265
|
+
clearTimeout(resetTimeout);
|
|
52266
|
+
resetTimeout = null;
|
|
52267
|
+
}
|
|
52188
52268
|
const currentTime = Date.now();
|
|
52189
52269
|
const { clientX, clientY } = event.touches[0];
|
|
52190
52270
|
let deltaX = lastX - clientX;
|
|
@@ -52201,6 +52281,10 @@ function useTouchScroll(ref, updateScroll, canMoveUp) {
|
|
|
52201
52281
|
}
|
|
52202
52282
|
event.stopPropagation();
|
|
52203
52283
|
}
|
|
52284
|
+
resetTimeout = setTimeout(() => {
|
|
52285
|
+
velocityX = 0;
|
|
52286
|
+
velocityY = 0;
|
|
52287
|
+
}, resetTimeoutDuration);
|
|
52204
52288
|
updateScroll(deltaX * horizontalScrollFactor, deltaY * verticalScrollFactor);
|
|
52205
52289
|
}
|
|
52206
52290
|
function onTouchEnd(ev) {
|
|
@@ -76780,6 +76864,6 @@ const chartHelpers = { ...CHART_HELPERS, ...CHART_RUNTIME_HELPERS };
|
|
|
76780
76864
|
export { AbstractCellClipboardHandler, AbstractChart, AbstractFigureClipboardHandler, CellErrorType, CommandResult, CorePlugin, CoreViewPlugin, DispatchResult, EvaluationError, Model, PivotRuntimeDefinition, Registry, Revision, SPREADSHEET_DIMENSIONS, Spreadsheet, SpreadsheetPivotTable, UIPlugin, __info__, addFunction, addRenderingLayer, astToFormula, chartHelpers, compile, compileTokens, components, constants, convertAstNodes, coreTypes, findCellInNewZone, functionCache, helpers, hooks, invalidateCFEvaluationCommands, invalidateDependenciesCommands, invalidateEvaluationCommands, iterateAstNodes, links, load, parse, parseTokens, readonlyAllowedCommands, registries, setDefaultSheetViewSize, setTranslationMethod, stores, tokenColors, tokenize };
|
|
76781
76865
|
|
|
76782
76866
|
|
|
76783
|
-
__info__.version = "18.2.
|
|
76784
|
-
__info__.date = "2025-05-
|
|
76785
|
-
__info__.hash = "
|
|
76867
|
+
__info__.version = "18.2.15";
|
|
76868
|
+
__info__.date = "2025-05-30T08:45:53.952Z";
|
|
76869
|
+
__info__.hash = "607492d";
|