@odoo/o-spreadsheet 17.2.7 → 17.2.9
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 +367 -217
- package/dist/o-spreadsheet.d.ts +90 -85
- package/dist/o-spreadsheet.esm.js +368 -218
- package/dist/o-spreadsheet.iife.js +367 -217
- package/dist/o-spreadsheet.iife.min.js +286 -286
- package/dist/o_spreadsheet.xml +3 -3
- package/package.json +2 -2
|
@@ -3,9 +3,9 @@
|
|
|
3
3
|
/**
|
|
4
4
|
* This file is generated by o-spreadsheet build tools. Do not edit it.
|
|
5
5
|
* @see https://github.com/odoo/o-spreadsheet
|
|
6
|
-
* @version 17.2.
|
|
7
|
-
* @date 2024-
|
|
8
|
-
* @hash
|
|
6
|
+
* @version 17.2.9
|
|
7
|
+
* @date 2024-06-03T14:56:21.684Z
|
|
8
|
+
* @hash 086af6d
|
|
9
9
|
*/
|
|
10
10
|
|
|
11
11
|
(function (exports, owl) {
|
|
@@ -503,6 +503,26 @@
|
|
|
503
503
|
};
|
|
504
504
|
return debounced;
|
|
505
505
|
}
|
|
506
|
+
/**
|
|
507
|
+
* Creates a batched version of a callback so that all calls to it in the same
|
|
508
|
+
* microtick will only call the original callback once.
|
|
509
|
+
*
|
|
510
|
+
* @param callback the callback to batch
|
|
511
|
+
* @returns a batched version of the original callback
|
|
512
|
+
*
|
|
513
|
+
* Copied from odoo/owl repo.
|
|
514
|
+
*/
|
|
515
|
+
function batched(callback) {
|
|
516
|
+
let scheduled = false;
|
|
517
|
+
return async (...args) => {
|
|
518
|
+
if (!scheduled) {
|
|
519
|
+
scheduled = true;
|
|
520
|
+
await Promise.resolve();
|
|
521
|
+
scheduled = false;
|
|
522
|
+
callback(...args);
|
|
523
|
+
}
|
|
524
|
+
};
|
|
525
|
+
}
|
|
506
526
|
/*
|
|
507
527
|
* Concatenate an array of strings.
|
|
508
528
|
*/
|
|
@@ -577,8 +597,9 @@
|
|
|
577
597
|
return false;
|
|
578
598
|
}
|
|
579
599
|
else {
|
|
580
|
-
if (ignoreFunctions && typeOfO1Key === "function")
|
|
581
|
-
|
|
600
|
+
if (ignoreFunctions && typeOfO1Key === "function") {
|
|
601
|
+
continue;
|
|
602
|
+
}
|
|
582
603
|
if (o1[key] !== o2[key])
|
|
583
604
|
return false;
|
|
584
605
|
}
|
|
@@ -1829,7 +1850,7 @@
|
|
|
1829
1850
|
}
|
|
1830
1851
|
valueOf() {
|
|
1831
1852
|
const str = super.valueOf();
|
|
1832
|
-
return _loaded() ? sprintf(_translate(str), ...this.values) : str;
|
|
1853
|
+
return _loaded() ? sprintf(_translate(str), ...this.values) : sprintf(str, ...this.values);
|
|
1833
1854
|
}
|
|
1834
1855
|
toString() {
|
|
1835
1856
|
return this.valueOf();
|
|
@@ -2638,7 +2659,7 @@
|
|
|
2638
2659
|
return false;
|
|
2639
2660
|
}
|
|
2640
2661
|
if (typeof operand === "number" && operator === "=") {
|
|
2641
|
-
return toString(
|
|
2662
|
+
return value.toString() === operand.toString();
|
|
2642
2663
|
}
|
|
2643
2664
|
if (operator === "<>" || operator === "=") {
|
|
2644
2665
|
let result;
|
|
@@ -2698,14 +2719,13 @@
|
|
|
2698
2719
|
if (countArg % 2 === 1) {
|
|
2699
2720
|
throw new EvaluationError(_t("Function [[FUNCTION_NAME]] expects criteria_range and criterion to be in pairs."));
|
|
2700
2721
|
}
|
|
2701
|
-
const
|
|
2702
|
-
const
|
|
2722
|
+
const firstArg = toMatrix(args[0]);
|
|
2723
|
+
const dimRow = firstArg.length;
|
|
2724
|
+
const dimCol = firstArg[0].length;
|
|
2703
2725
|
let predicates = [];
|
|
2704
2726
|
for (let i = 0; i < countArg - 1; i += 2) {
|
|
2705
|
-
const criteriaRange = args[i];
|
|
2706
|
-
if (
|
|
2707
|
-
criteriaRange.length !== dimRow ||
|
|
2708
|
-
criteriaRange[0].length !== dimCol) {
|
|
2727
|
+
const criteriaRange = toMatrix(args[i]);
|
|
2728
|
+
if (criteriaRange.length !== dimRow || criteriaRange[0].length !== dimCol) {
|
|
2709
2729
|
throw new EvaluationError(_t("Function [[FUNCTION_NAME]] expects criteria_range to have the same dimension"));
|
|
2710
2730
|
}
|
|
2711
2731
|
const description = toString(args[i + 1]);
|
|
@@ -2719,7 +2739,7 @@
|
|
|
2719
2739
|
for (let j = 0; j < dimCol; j++) {
|
|
2720
2740
|
let validatedPredicates = true;
|
|
2721
2741
|
for (let k = 0; k < countArg - 1; k += 2) {
|
|
2722
|
-
const criteriaValue = args[k][i][j].value;
|
|
2742
|
+
const criteriaValue = toMatrix(args[k])[i][j].value;
|
|
2723
2743
|
const criterion = predicates[k / 2];
|
|
2724
2744
|
validatedPredicates = evaluatePredicate(criteriaValue ?? undefined, criterion);
|
|
2725
2745
|
if (!validatedPredicates) {
|
|
@@ -4436,8 +4456,11 @@
|
|
|
4436
4456
|
/**
|
|
4437
4457
|
* Create a range from a xc. If the xc is empty, this function returns undefined.
|
|
4438
4458
|
*/
|
|
4439
|
-
function
|
|
4440
|
-
|
|
4459
|
+
function createValidRange(getters, sheetId, xc) {
|
|
4460
|
+
if (!xc)
|
|
4461
|
+
return;
|
|
4462
|
+
const range = getters.getRangeFromSheetXC(sheetId, xc);
|
|
4463
|
+
return !(range.invalidSheetName || range.invalidXc) ? range : undefined;
|
|
4441
4464
|
}
|
|
4442
4465
|
/**
|
|
4443
4466
|
* Spread multiple colrows zone to one row/col zone and add a many new input range as needed.
|
|
@@ -8013,10 +8036,66 @@
|
|
|
8013
8036
|
});
|
|
8014
8037
|
}
|
|
8015
8038
|
|
|
8039
|
+
/**
|
|
8040
|
+
* This is a generic event bus based on the Owl event bus.
|
|
8041
|
+
* This bus however ensures type safety across events and subscription callbacks.
|
|
8042
|
+
*/
|
|
8043
|
+
class EventBus {
|
|
8044
|
+
subscriptions = {};
|
|
8045
|
+
/**
|
|
8046
|
+
* Add a listener for the 'eventType' events.
|
|
8047
|
+
*
|
|
8048
|
+
* Note that the 'owner' of this event can be anything, but will more likely
|
|
8049
|
+
* be a component or a class. The idea is that the callback will be called with
|
|
8050
|
+
* the proper owner bound.
|
|
8051
|
+
*
|
|
8052
|
+
* Also, the owner should be kind of unique. This will be used to remove the
|
|
8053
|
+
* listener.
|
|
8054
|
+
*/
|
|
8055
|
+
on(type, owner, callback) {
|
|
8056
|
+
if (!callback) {
|
|
8057
|
+
throw new Error("Missing callback");
|
|
8058
|
+
}
|
|
8059
|
+
if (!this.subscriptions[type]) {
|
|
8060
|
+
this.subscriptions[type] = [];
|
|
8061
|
+
}
|
|
8062
|
+
this.subscriptions[type].push({
|
|
8063
|
+
owner,
|
|
8064
|
+
callback,
|
|
8065
|
+
});
|
|
8066
|
+
}
|
|
8067
|
+
/**
|
|
8068
|
+
* Emit an event of type 'eventType'. Any extra arguments will be passed to
|
|
8069
|
+
* the listeners callback.
|
|
8070
|
+
*/
|
|
8071
|
+
trigger(type, payload) {
|
|
8072
|
+
const subs = this.subscriptions[type] || [];
|
|
8073
|
+
for (let i = 0, iLen = subs.length; i < iLen; i++) {
|
|
8074
|
+
const sub = subs[i];
|
|
8075
|
+
sub.callback.call(sub.owner, payload);
|
|
8076
|
+
}
|
|
8077
|
+
}
|
|
8078
|
+
/**
|
|
8079
|
+
* Remove a listener
|
|
8080
|
+
*/
|
|
8081
|
+
off(eventType, owner) {
|
|
8082
|
+
const subs = this.subscriptions[eventType];
|
|
8083
|
+
if (subs) {
|
|
8084
|
+
this.subscriptions[eventType] = subs.filter((s) => s.owner !== owner);
|
|
8085
|
+
}
|
|
8086
|
+
}
|
|
8087
|
+
/**
|
|
8088
|
+
* Remove all subscriptions.
|
|
8089
|
+
*/
|
|
8090
|
+
clear() {
|
|
8091
|
+
this.subscriptions = {};
|
|
8092
|
+
}
|
|
8093
|
+
}
|
|
8094
|
+
|
|
8016
8095
|
/**
|
|
8017
8096
|
* A type-safe dependency container
|
|
8018
8097
|
*/
|
|
8019
|
-
class DependencyContainer {
|
|
8098
|
+
class DependencyContainer extends EventBus {
|
|
8020
8099
|
dependencies = new Map();
|
|
8021
8100
|
factory = new StoreFactory(this.get.bind(this));
|
|
8022
8101
|
/**
|
|
@@ -8093,15 +8172,12 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8093
8172
|
}
|
|
8094
8173
|
return MetaStore;
|
|
8095
8174
|
}
|
|
8096
|
-
class
|
|
8175
|
+
class DisposableStore {
|
|
8097
8176
|
get;
|
|
8177
|
+
disposeCallbacks = [];
|
|
8098
8178
|
constructor(get) {
|
|
8099
8179
|
this.get = get;
|
|
8100
|
-
return owl.reactive(this);
|
|
8101
8180
|
}
|
|
8102
|
-
}
|
|
8103
|
-
class DisposableStore extends ReactiveStore {
|
|
8104
|
-
disposeCallbacks = [];
|
|
8105
8181
|
onDispose(callback) {
|
|
8106
8182
|
this.disposeCallbacks.push(callback);
|
|
8107
8183
|
}
|
|
@@ -8121,7 +8197,10 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8121
8197
|
const container = new DependencyContainer();
|
|
8122
8198
|
owl.useSubEnv({
|
|
8123
8199
|
__spreadsheet_stores__: container,
|
|
8124
|
-
getStore:
|
|
8200
|
+
getStore: (Store) => {
|
|
8201
|
+
const store = container.get(Store);
|
|
8202
|
+
return proxifyStoreMutation(store, () => container.trigger("store-updated"));
|
|
8203
|
+
},
|
|
8125
8204
|
});
|
|
8126
8205
|
return container;
|
|
8127
8206
|
}
|
|
@@ -8131,14 +8210,57 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8131
8210
|
function useStore(Store) {
|
|
8132
8211
|
const env = owl.useEnv();
|
|
8133
8212
|
const container = getDependencyContainer(env);
|
|
8134
|
-
|
|
8213
|
+
const store = container.get(Store);
|
|
8214
|
+
return useStoreRenderProxy(container, store);
|
|
8135
8215
|
}
|
|
8136
8216
|
function useLocalStore(Store, ...args) {
|
|
8137
8217
|
const env = owl.useEnv();
|
|
8138
8218
|
const container = getDependencyContainer(env);
|
|
8139
|
-
const store =
|
|
8219
|
+
const store = container.instantiate(Store, ...args);
|
|
8140
8220
|
owl.onWillUnmount(() => store.dispose());
|
|
8141
|
-
return store;
|
|
8221
|
+
return useStoreRenderProxy(container, store);
|
|
8222
|
+
}
|
|
8223
|
+
/**
|
|
8224
|
+
* Trigger an event to re-render the app (deep render) when
|
|
8225
|
+
* a store is mutated by invoking one of its mutator methods.
|
|
8226
|
+
*/
|
|
8227
|
+
function useStoreRenderProxy(container, store) {
|
|
8228
|
+
const component = owl.useComponent();
|
|
8229
|
+
const proxy = proxifyStoreMutation(store, () => {
|
|
8230
|
+
if (owl.status(component) === "mounted") {
|
|
8231
|
+
container.trigger("store-updated");
|
|
8232
|
+
}
|
|
8233
|
+
});
|
|
8234
|
+
return proxy;
|
|
8235
|
+
}
|
|
8236
|
+
/**
|
|
8237
|
+
* Creates a proxied version of a store object with mutation tracking.
|
|
8238
|
+
* Whenever a mutator method of the store is called, the provided callback function is invoked.
|
|
8239
|
+
*/
|
|
8240
|
+
function proxifyStoreMutation(store, callback) {
|
|
8241
|
+
const proxy = new Proxy(store, {
|
|
8242
|
+
get(target, property, receiver) {
|
|
8243
|
+
const thisStore = target;
|
|
8244
|
+
// The third argument is `thisStore` (target) instead of `receiver`.
|
|
8245
|
+
// The goal is to always have the same `this` value in getter functions
|
|
8246
|
+
// (when `target[property]` is an accessor property).
|
|
8247
|
+
// `thisStore` is always the same object reference. `receiver` however is the
|
|
8248
|
+
// object on which the property is called, which is the Proxy object which is different for each component.
|
|
8249
|
+
const value = Reflect.get(target, property, thisStore);
|
|
8250
|
+
if (store.mutators.includes(property)) {
|
|
8251
|
+
const functionProxy = new Proxy(value, {
|
|
8252
|
+
// trap the function call
|
|
8253
|
+
apply(target, thisArg, argArray) {
|
|
8254
|
+
Reflect.apply(target, thisStore, argArray);
|
|
8255
|
+
callback();
|
|
8256
|
+
},
|
|
8257
|
+
});
|
|
8258
|
+
return functionProxy;
|
|
8259
|
+
}
|
|
8260
|
+
return value;
|
|
8261
|
+
},
|
|
8262
|
+
});
|
|
8263
|
+
return proxy;
|
|
8142
8264
|
}
|
|
8143
8265
|
function getDependencyContainer(env) {
|
|
8144
8266
|
const container = env.__spreadsheet_stores__;
|
|
@@ -8150,7 +8272,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8150
8272
|
|
|
8151
8273
|
const ModelStore = createAbstractStore("Model");
|
|
8152
8274
|
|
|
8153
|
-
class RendererStore
|
|
8275
|
+
class RendererStore {
|
|
8276
|
+
mutators = ["register", "unRegister"];
|
|
8154
8277
|
renderers = {};
|
|
8155
8278
|
register(renderer) {
|
|
8156
8279
|
if (!renderer.renderingLayers.length) {
|
|
@@ -8184,7 +8307,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8184
8307
|
class SpreadsheetStore extends DisposableStore {
|
|
8185
8308
|
// cast the model store as Model to allow model.dispatch to return the DispatchResult
|
|
8186
8309
|
model = this.get(ModelStore);
|
|
8187
|
-
getters =
|
|
8310
|
+
getters = this.model.getters;
|
|
8188
8311
|
renderer = this.get(RendererStore);
|
|
8189
8312
|
constructor(get) {
|
|
8190
8313
|
super(get);
|
|
@@ -8231,6 +8354,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8231
8354
|
}
|
|
8232
8355
|
|
|
8233
8356
|
class HighlightStore extends SpreadsheetStore {
|
|
8357
|
+
mutators = ["register", "unRegister"];
|
|
8234
8358
|
providers = [];
|
|
8235
8359
|
constructor(get) {
|
|
8236
8360
|
super(get);
|
|
@@ -8261,7 +8385,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8261
8385
|
this.providers.push(highlightProvider);
|
|
8262
8386
|
}
|
|
8263
8387
|
unRegister(highlightProvider) {
|
|
8264
|
-
this.providers = this.providers.filter((h) =>
|
|
8388
|
+
this.providers = this.providers.filter((h) => h !== highlightProvider);
|
|
8265
8389
|
}
|
|
8266
8390
|
drawLayer(ctx, layer) {
|
|
8267
8391
|
if (layer === "Highlights") {
|
|
@@ -8277,6 +8401,16 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8277
8401
|
|
|
8278
8402
|
const CELL_DELETED_MESSAGE = _t("The cell you are trying to edit has been deleted.");
|
|
8279
8403
|
class ComposerStore extends SpreadsheetStore {
|
|
8404
|
+
mutators = [
|
|
8405
|
+
"startEdition",
|
|
8406
|
+
"setCurrentContent",
|
|
8407
|
+
"stopEdition",
|
|
8408
|
+
"stopComposerRangeSelection",
|
|
8409
|
+
"cancelEdition",
|
|
8410
|
+
"cycleReferences",
|
|
8411
|
+
"changeComposerCursorSelection",
|
|
8412
|
+
"replaceComposerCursorSelection",
|
|
8413
|
+
];
|
|
8280
8414
|
col = 0;
|
|
8281
8415
|
row = 0;
|
|
8282
8416
|
editionMode = "inactive";
|
|
@@ -8291,9 +8425,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8291
8425
|
highlightStore = this.get(HighlightStore);
|
|
8292
8426
|
constructor(get) {
|
|
8293
8427
|
super(get);
|
|
8294
|
-
this.highlightStore.register(
|
|
8428
|
+
this.highlightStore.register(this);
|
|
8295
8429
|
this.onDispose(() => {
|
|
8296
|
-
this.highlightStore.unRegister(
|
|
8430
|
+
this.highlightStore.unRegister(this);
|
|
8297
8431
|
});
|
|
8298
8432
|
}
|
|
8299
8433
|
canStopEdition() {
|
|
@@ -8420,7 +8554,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8420
8554
|
if (this.isSelectingRange) {
|
|
8421
8555
|
this.editionMode = "editing";
|
|
8422
8556
|
}
|
|
8423
|
-
this.model.selection.resetAnchor(
|
|
8557
|
+
this.model.selection.resetAnchor(this, {
|
|
8424
8558
|
cell: { col: left, row: top },
|
|
8425
8559
|
zone: cmd.zone,
|
|
8426
8560
|
});
|
|
@@ -8438,7 +8572,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8438
8572
|
row: activePosition.row,
|
|
8439
8573
|
});
|
|
8440
8574
|
const zone = this.getters.expandZone(cmd.sheetIdTo, positionToZone({ col, row }));
|
|
8441
|
-
this.model.selection.resetAnchor(
|
|
8575
|
+
this.model.selection.resetAnchor(this, { cell: { col, row }, zone });
|
|
8442
8576
|
}
|
|
8443
8577
|
break;
|
|
8444
8578
|
case "DELETE_SHEET":
|
|
@@ -8537,7 +8671,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8537
8671
|
startComposerRangeSelection() {
|
|
8538
8672
|
if (this.sheetId === this.getters.getActiveSheetId()) {
|
|
8539
8673
|
const zone = positionToZone({ col: this.col, row: this.row });
|
|
8540
|
-
this.model.selection.resetAnchor(
|
|
8674
|
+
this.model.selection.resetAnchor(this, {
|
|
8541
8675
|
cell: { col: this.col, row: this.row },
|
|
8542
8676
|
zone,
|
|
8543
8677
|
});
|
|
@@ -8566,7 +8700,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8566
8700
|
this.setContent(str || this.initialContent, selection);
|
|
8567
8701
|
this.colorIndexByRange = {};
|
|
8568
8702
|
const zone = positionToZone({ col: this.col, row: this.row });
|
|
8569
|
-
this.model.selection.capture(
|
|
8703
|
+
this.model.selection.capture(this, { cell: { col: this.col, row: this.row }, zone }, {
|
|
8570
8704
|
handleEvent: this.handleEvent.bind(this),
|
|
8571
8705
|
release: () => {
|
|
8572
8706
|
this._stopEdition();
|
|
@@ -8674,7 +8808,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8674
8808
|
return;
|
|
8675
8809
|
}
|
|
8676
8810
|
this.editionMode = "inactive";
|
|
8677
|
-
this.model.selection.release(
|
|
8811
|
+
this.model.selection.release(this);
|
|
8678
8812
|
}
|
|
8679
8813
|
/**
|
|
8680
8814
|
* Reset the current content to the active cell content
|
|
@@ -8996,6 +9130,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
8996
9130
|
}
|
|
8997
9131
|
|
|
8998
9132
|
class ComposerFocusStore extends SpreadsheetStore {
|
|
9133
|
+
mutators = ["focusTopBarComposer", "focusGridComposerContent", "focusGridComposerCell"];
|
|
8999
9134
|
composerStore = this.get(ComposerStore);
|
|
9000
9135
|
topBarFocus = "inactive";
|
|
9001
9136
|
gridFocusMode = "inactive";
|
|
@@ -9512,8 +9647,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
9512
9647
|
type = "scorecard";
|
|
9513
9648
|
constructor(definition, sheetId, getters) {
|
|
9514
9649
|
super(definition, sheetId, getters);
|
|
9515
|
-
this.keyValue =
|
|
9516
|
-
this.baseline =
|
|
9650
|
+
this.keyValue = createValidRange(getters, sheetId, definition.keyValue);
|
|
9651
|
+
this.baseline = createValidRange(getters, sheetId, definition.baseline);
|
|
9517
9652
|
this.baselineMode = definition.baselineMode;
|
|
9518
9653
|
this.baselineDescr = definition.baselineDescr;
|
|
9519
9654
|
this.background = definition.background;
|
|
@@ -10083,6 +10218,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
10083
10218
|
if (types.some((t) => t.startsWith("RANGE"))) {
|
|
10084
10219
|
result.acceptMatrix = true;
|
|
10085
10220
|
}
|
|
10221
|
+
if (types.every((t) => t.startsWith("RANGE"))) {
|
|
10222
|
+
result.acceptMatrixOnly = true;
|
|
10223
|
+
}
|
|
10086
10224
|
return result;
|
|
10087
10225
|
}
|
|
10088
10226
|
/**
|
|
@@ -10364,11 +10502,16 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
10364
10502
|
compute: function (array, ...columns) {
|
|
10365
10503
|
const _array = toMatrix(array);
|
|
10366
10504
|
const _columns = flattenRowFirst(columns, (item) => toInteger(item?.value, this.locale));
|
|
10367
|
-
|
|
10505
|
+
const argOutOfRange = _columns.filter((col) => col === 0 || _array.length < Math.abs(col));
|
|
10506
|
+
assert(() => argOutOfRange.length === 0, _t("The columns arguments must be between -%s and %s (got %s), excluding 0.", _array.length.toString(), _array.length.toString(), argOutOfRange.join(",")));
|
|
10368
10507
|
const result = Array(_columns.length);
|
|
10369
10508
|
for (let col = 0; col < _columns.length; col++) {
|
|
10370
|
-
|
|
10371
|
-
|
|
10509
|
+
if (_columns[col] > 0) {
|
|
10510
|
+
result[col] = _array[_columns[col] - 1]; // -1 because columns arguments are 1-indexed
|
|
10511
|
+
}
|
|
10512
|
+
else {
|
|
10513
|
+
result[col] = _array[_array.length + _columns[col]];
|
|
10514
|
+
}
|
|
10372
10515
|
}
|
|
10373
10516
|
return result;
|
|
10374
10517
|
},
|
|
@@ -10389,8 +10532,14 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
10389
10532
|
const _array = toMatrix(array);
|
|
10390
10533
|
const _rows = flattenRowFirst(rows, (item) => toInteger(item?.value, this.locale));
|
|
10391
10534
|
const _nbColumns = _array.length;
|
|
10392
|
-
|
|
10393
|
-
|
|
10535
|
+
const argOutOfRange = _rows.filter((row) => row === 0 || _array[0].length < Math.abs(row));
|
|
10536
|
+
assert(() => argOutOfRange.length === 0, _t("The rows arguments must be between -%s and %s (got %s), excluding 0.", _array[0].length.toString(), _array[0].length.toString(), argOutOfRange.join(",")));
|
|
10537
|
+
return generateMatrix(_nbColumns, _rows.length, (col, row) => {
|
|
10538
|
+
if (_rows[row] > 0) {
|
|
10539
|
+
return _array[col][_rows[row] - 1]; // -1 because columns arguments are 1-indexed
|
|
10540
|
+
}
|
|
10541
|
+
return _array[col][_array[col].length + _rows[row]];
|
|
10542
|
+
});
|
|
10394
10543
|
},
|
|
10395
10544
|
isExported: true,
|
|
10396
10545
|
};
|
|
@@ -11298,7 +11447,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
11298
11447
|
compute: function (range, ...args) {
|
|
11299
11448
|
let uniqueValues = new Set();
|
|
11300
11449
|
visitMatchingRanges(args, (i, j) => {
|
|
11301
|
-
const data = range[i][j];
|
|
11450
|
+
const data = range[i]?.[j];
|
|
11302
11451
|
if (isDefined(data)) {
|
|
11303
11452
|
uniqueValues.add(data.value);
|
|
11304
11453
|
}
|
|
@@ -11928,7 +12077,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
11928
12077
|
}
|
|
11929
12078
|
let sum = 0;
|
|
11930
12079
|
visitMatchingRanges([criteriaRange, criterion], (i, j) => {
|
|
11931
|
-
const value = sumRange[i][j]
|
|
12080
|
+
const value = sumRange[i]?.[j]?.value;
|
|
11932
12081
|
if (typeof value === "number") {
|
|
11933
12082
|
sum += value;
|
|
11934
12083
|
}
|
|
@@ -11953,7 +12102,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
11953
12102
|
compute: function (sumRange, ...criters) {
|
|
11954
12103
|
let sum = 0;
|
|
11955
12104
|
visitMatchingRanges(criters, (i, j) => {
|
|
11956
|
-
const value = sumRange[i][j]
|
|
12105
|
+
const value = sumRange[i]?.[j]?.value;
|
|
11957
12106
|
if (typeof value === "number") {
|
|
11958
12107
|
sum += value;
|
|
11959
12108
|
}
|
|
@@ -12500,7 +12649,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
12500
12649
|
let count = 0;
|
|
12501
12650
|
let sum = 0;
|
|
12502
12651
|
visitMatchingRanges([criteriaRange, criterion], (i, j) => {
|
|
12503
|
-
const value = _averageRange[i][j]
|
|
12652
|
+
const value = _averageRange[i]?.[j]?.value;
|
|
12504
12653
|
if (typeof value === "number") {
|
|
12505
12654
|
count += 1;
|
|
12506
12655
|
sum += value;
|
|
@@ -12529,7 +12678,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
12529
12678
|
let count = 0;
|
|
12530
12679
|
let sum = 0;
|
|
12531
12680
|
visitMatchingRanges(args, (i, j) => {
|
|
12532
|
-
const value = _averageRange[i][j]
|
|
12681
|
+
const value = _averageRange[i]?.[j]?.value;
|
|
12533
12682
|
if (typeof value === "number") {
|
|
12534
12683
|
count += 1;
|
|
12535
12684
|
sum += value;
|
|
@@ -12834,7 +12983,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
12834
12983
|
compute: function (range, ...args) {
|
|
12835
12984
|
let result = -Infinity;
|
|
12836
12985
|
visitMatchingRanges(args, (i, j) => {
|
|
12837
|
-
const value = range[i][j]
|
|
12986
|
+
const value = range[i]?.[j]?.value;
|
|
12838
12987
|
if (typeof value === "number") {
|
|
12839
12988
|
result = result < value ? value : result;
|
|
12840
12989
|
}
|
|
@@ -12917,7 +13066,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
12917
13066
|
compute: function (range, ...args) {
|
|
12918
13067
|
let result = Infinity;
|
|
12919
13068
|
visitMatchingRanges(args, (i, j) => {
|
|
12920
|
-
const value = range[i][j]
|
|
13069
|
+
const value = range[i]?.[j]?.value;
|
|
12921
13070
|
if (typeof value === "number") {
|
|
12922
13071
|
result = result > value ? value : result;
|
|
12923
13072
|
}
|
|
@@ -18669,6 +18818,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
18669
18818
|
}
|
|
18670
18819
|
args[i] = arg[0][0];
|
|
18671
18820
|
}
|
|
18821
|
+
if (!isMatrix(arg) && argDefinition.acceptMatrixOnly) {
|
|
18822
|
+
throw new BadExpressionError(_t("Function [[FUNCTION_NAME]] expects the parameter '%s' to be reference to a cell or range.", (i + 1).toString()));
|
|
18823
|
+
}
|
|
18672
18824
|
}
|
|
18673
18825
|
return descr.compute.apply(this, args);
|
|
18674
18826
|
}
|
|
@@ -19671,7 +19823,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
19671
19823
|
constructor(definition, sheetId, getters) {
|
|
19672
19824
|
super(definition, sheetId, getters);
|
|
19673
19825
|
this.dataSets = createDataSets(getters, definition.dataSets, sheetId, definition.dataSetsHaveTitle);
|
|
19674
|
-
this.labelRange =
|
|
19826
|
+
this.labelRange = createValidRange(getters, sheetId, definition.labelRange);
|
|
19675
19827
|
this.background = definition.background;
|
|
19676
19828
|
this.verticalAxisPosition = definition.verticalAxisPosition;
|
|
19677
19829
|
this.legendPosition = definition.legendPosition;
|
|
@@ -19915,7 +20067,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
19915
20067
|
type = "gauge";
|
|
19916
20068
|
constructor(definition, sheetId, getters) {
|
|
19917
20069
|
super(definition, sheetId, getters);
|
|
19918
|
-
this.dataRange =
|
|
20070
|
+
this.dataRange = createValidRange(this.getters, this.sheetId, definition.dataRange);
|
|
19919
20071
|
this.sectionRule = definition.sectionRule;
|
|
19920
20072
|
this.background = definition.background;
|
|
19921
20073
|
}
|
|
@@ -20436,7 +20588,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
20436
20588
|
constructor(definition, sheetId, getters) {
|
|
20437
20589
|
super(definition, sheetId, getters);
|
|
20438
20590
|
this.dataSets = createDataSets(this.getters, definition.dataSets, sheetId, definition.dataSetsHaveTitle);
|
|
20439
|
-
this.labelRange =
|
|
20591
|
+
this.labelRange = createValidRange(this.getters, sheetId, definition.labelRange);
|
|
20440
20592
|
this.background = definition.background;
|
|
20441
20593
|
this.verticalAxisPosition = definition.verticalAxisPosition;
|
|
20442
20594
|
this.legendPosition = definition.legendPosition;
|
|
@@ -20551,7 +20703,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
20551
20703
|
constructor(definition, sheetId, getters) {
|
|
20552
20704
|
super(definition, sheetId, getters);
|
|
20553
20705
|
this.dataSets = createDataSets(getters, definition.dataSets, sheetId, definition.dataSetsHaveTitle);
|
|
20554
|
-
this.labelRange =
|
|
20706
|
+
this.labelRange = createValidRange(getters, sheetId, definition.labelRange);
|
|
20555
20707
|
this.background = definition.background;
|
|
20556
20708
|
this.legendPosition = definition.legendPosition;
|
|
20557
20709
|
this.aggregated = definition.aggregated;
|
|
@@ -20753,7 +20905,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
20753
20905
|
constructor(definition, sheetId, getters) {
|
|
20754
20906
|
super(definition, sheetId, getters);
|
|
20755
20907
|
this.dataSets = createDataSets(this.getters, definition.dataSets, sheetId, definition.dataSetsHaveTitle);
|
|
20756
|
-
this.labelRange =
|
|
20908
|
+
this.labelRange = createValidRange(this.getters, sheetId, definition.labelRange);
|
|
20757
20909
|
this.background = definition.background;
|
|
20758
20910
|
this.verticalAxisPosition = definition.verticalAxisPosition;
|
|
20759
20911
|
this.legendPosition = definition.legendPosition;
|
|
@@ -20839,13 +20991,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
20839
20991
|
// have less options than the line chart (it only works with linear labels)
|
|
20840
20992
|
chartJsConfig.type = "line";
|
|
20841
20993
|
const configOptions = chartJsConfig.options;
|
|
20842
|
-
configOptions.elements = {
|
|
20843
|
-
point: {
|
|
20844
|
-
radius: 3,
|
|
20845
|
-
hoverRadius: 3,
|
|
20846
|
-
hitRadius: 8,
|
|
20847
|
-
},
|
|
20848
|
-
};
|
|
20849
20994
|
const locale = getters.getLocale();
|
|
20850
20995
|
configOptions.plugins.tooltip.callbacks.title = () => "";
|
|
20851
20996
|
configOptions.plugins.tooltip.callbacks.label = (tooltipItem) => {
|
|
@@ -21452,6 +21597,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
21452
21597
|
}
|
|
21453
21598
|
|
|
21454
21599
|
class HoveredCellStore extends SpreadsheetStore {
|
|
21600
|
+
mutators = ["clear", "hover"];
|
|
21455
21601
|
col;
|
|
21456
21602
|
row;
|
|
21457
21603
|
handle(cmd) {
|
|
@@ -21471,6 +21617,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
21471
21617
|
}
|
|
21472
21618
|
|
|
21473
21619
|
class CellPopoverStore extends SpreadsheetStore {
|
|
21620
|
+
mutators = ["open", "close"];
|
|
21474
21621
|
persistentPopover;
|
|
21475
21622
|
hoveredCell = this.get(HoveredCellStore);
|
|
21476
21623
|
handle(cmd) {
|
|
@@ -25962,12 +26109,13 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
25962
26109
|
|
|
25963
26110
|
// The name is misleading and can be confused with the DOM focus.
|
|
25964
26111
|
class FocusStore {
|
|
26112
|
+
mutators = ["focus", "unfocus"];
|
|
25965
26113
|
focusedElement = null;
|
|
25966
26114
|
focus(element) {
|
|
25967
26115
|
this.focusedElement = element;
|
|
25968
26116
|
}
|
|
25969
26117
|
unfocus(element) {
|
|
25970
|
-
if (this.focusedElement &&
|
|
26118
|
+
if (this.focusedElement && this.focusedElement === element) {
|
|
25971
26119
|
this.focusedElement = null;
|
|
25972
26120
|
}
|
|
25973
26121
|
}
|
|
@@ -25983,6 +26131,16 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
25983
26131
|
class SelectionInputStore extends SpreadsheetStore {
|
|
25984
26132
|
initialRanges;
|
|
25985
26133
|
inputHasSingleRange;
|
|
26134
|
+
mutators = [
|
|
26135
|
+
"resetWithRanges",
|
|
26136
|
+
"focusById",
|
|
26137
|
+
"unfocus",
|
|
26138
|
+
"addEmptyRange",
|
|
26139
|
+
"removeRange",
|
|
26140
|
+
"changeRange",
|
|
26141
|
+
"reset",
|
|
26142
|
+
"confirm",
|
|
26143
|
+
];
|
|
25986
26144
|
ranges = [];
|
|
25987
26145
|
focusedRangeIndex = null;
|
|
25988
26146
|
inputSheetId;
|
|
@@ -26042,7 +26200,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26042
26200
|
row: 0,
|
|
26043
26201
|
});
|
|
26044
26202
|
const zone = this.getters.expandZone(cmd.sheetIdTo, positionToZone({ col, row }));
|
|
26045
|
-
this.model.selection.resetAnchor(
|
|
26203
|
+
this.model.selection.resetAnchor(this, { cell: { col, row }, zone });
|
|
26046
26204
|
}
|
|
26047
26205
|
break;
|
|
26048
26206
|
}
|
|
@@ -26061,7 +26219,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26061
26219
|
if (focusIndex !== -1) {
|
|
26062
26220
|
this.focus(focusIndex);
|
|
26063
26221
|
const { left, top } = newZone;
|
|
26064
|
-
this.model.selection.resetAnchor(
|
|
26222
|
+
this.model.selection.resetAnchor(this, {
|
|
26065
26223
|
cell: { col: left, row: top },
|
|
26066
26224
|
zone: newZone,
|
|
26067
26225
|
});
|
|
@@ -26152,7 +26310,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26152
26310
|
}
|
|
26153
26311
|
get hasMainFocus() {
|
|
26154
26312
|
const focusedElement = this.focusStore.focusedElement;
|
|
26155
|
-
return !!focusedElement &&
|
|
26313
|
+
return !!focusedElement && focusedElement === this;
|
|
26156
26314
|
}
|
|
26157
26315
|
get highlights() {
|
|
26158
26316
|
if (!this.hasMainFocus) {
|
|
@@ -26181,7 +26339,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26181
26339
|
unfocus() {
|
|
26182
26340
|
this.focusedRangeIndex = null;
|
|
26183
26341
|
this.focusStore.unfocus(this);
|
|
26184
|
-
this.model.selection.release(
|
|
26342
|
+
this.model.selection.release(this);
|
|
26185
26343
|
}
|
|
26186
26344
|
captureSelection() {
|
|
26187
26345
|
if (this.focusedRangeIndex === null) {
|
|
@@ -26190,7 +26348,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26190
26348
|
const range = this.ranges[this.focusedRangeIndex];
|
|
26191
26349
|
const sheetId = this.getters.getActiveSheetId();
|
|
26192
26350
|
const zone = this.getters.getRangeFromSheetXC(sheetId, range?.xc || "A1").zone;
|
|
26193
|
-
this.model.selection.capture(
|
|
26351
|
+
this.model.selection.capture(this, { cell: { col: zone.left, row: zone.top }, zone }, {
|
|
26194
26352
|
handleEvent: this.handleEvent.bind(this),
|
|
26195
26353
|
release: this.unfocus.bind(this),
|
|
26196
26354
|
});
|
|
@@ -26666,7 +26824,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26666
26824
|
}
|
|
26667
26825
|
const getters = this.env.model.getters;
|
|
26668
26826
|
const sheetId = getters.getActiveSheetId();
|
|
26669
|
-
const labelRange =
|
|
26827
|
+
const labelRange = createValidRange(getters, sheetId, this.labelRange);
|
|
26670
26828
|
const dataSets = createDataSets(getters, this.dataSeriesRanges, sheetId, this.props.definition.dataSetsHaveTitle);
|
|
26671
26829
|
if (dataSets.length) {
|
|
26672
26830
|
return dataSets[0].dataRange.zone.top + 1;
|
|
@@ -26695,15 +26853,23 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26695
26853
|
}
|
|
26696
26854
|
}
|
|
26697
26855
|
|
|
26856
|
+
/**
|
|
26857
|
+
* Start listening to pointer events and apply the given callbacks.
|
|
26858
|
+
*
|
|
26859
|
+
* @returns A function to remove the listeners.
|
|
26860
|
+
*/
|
|
26698
26861
|
function startDnd(onMouseMove, onMouseUp, onMouseDown = () => { }) {
|
|
26699
|
-
const
|
|
26700
|
-
onMouseUp(ev);
|
|
26862
|
+
const removeListeners = () => {
|
|
26701
26863
|
window.removeEventListener("pointerdown", onMouseDown);
|
|
26702
26864
|
window.removeEventListener("pointerup", _onMouseUp);
|
|
26703
26865
|
window.removeEventListener("dragstart", _onDragStart);
|
|
26704
26866
|
window.removeEventListener("pointermove", onMouseMove);
|
|
26705
26867
|
window.removeEventListener("wheel", onMouseMove);
|
|
26706
26868
|
};
|
|
26869
|
+
const _onMouseUp = (ev) => {
|
|
26870
|
+
onMouseUp(ev);
|
|
26871
|
+
removeListeners();
|
|
26872
|
+
};
|
|
26707
26873
|
function _onDragStart(ev) {
|
|
26708
26874
|
ev.preventDefault();
|
|
26709
26875
|
}
|
|
@@ -26715,6 +26881,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
26715
26881
|
// preventDefault() is not allowed in passive event handler.
|
|
26716
26882
|
// https://chromestatus.com/feature/6662647093133312
|
|
26717
26883
|
window.addEventListener("wheel", onMouseMove, { passive: false });
|
|
26884
|
+
return removeListeners;
|
|
26718
26885
|
}
|
|
26719
26886
|
/**
|
|
26720
26887
|
* Function to be used during a pointerdown event, this function allows to
|
|
@@ -27658,6 +27825,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
27658
27825
|
});
|
|
27659
27826
|
|
|
27660
27827
|
class MainChartPanelStore extends SpreadsheetStore {
|
|
27828
|
+
mutators = ["activatePanel"];
|
|
27661
27829
|
panel = "configuration";
|
|
27662
27830
|
activatePanel(panel) {
|
|
27663
27831
|
this.panel = panel;
|
|
@@ -27908,6 +28076,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
27908
28076
|
state.itemsStyle = {};
|
|
27909
28077
|
document.body.style.cursor = previousCursor;
|
|
27910
28078
|
args.onCancel?.();
|
|
28079
|
+
cleanUp();
|
|
27911
28080
|
};
|
|
27912
28081
|
const onDragEnd = (itemId, indexAtEnd) => {
|
|
27913
28082
|
state.draggedItemId = undefined;
|
|
@@ -27928,7 +28097,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
27928
28097
|
onDragEnd,
|
|
27929
28098
|
onCancel: state.cancel,
|
|
27930
28099
|
});
|
|
27931
|
-
startDnd(dndHelper.onMouseMove.bind(dndHelper), dndHelper.onMouseUp.bind(dndHelper));
|
|
28100
|
+
const stopListening = startDnd(dndHelper.onMouseMove.bind(dndHelper), dndHelper.onMouseUp.bind(dndHelper));
|
|
28101
|
+
cleanupFns.push(stopListening);
|
|
27932
28102
|
const onScroll = dndHelper.onScroll.bind(dndHelper);
|
|
27933
28103
|
args.containerEl.addEventListener("scroll", onScroll);
|
|
27934
28104
|
cleanupFns.push(() => args.containerEl.removeEventListener("scroll", onScroll));
|
|
@@ -28005,7 +28175,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
28005
28175
|
this.moveDraggedItemToPosition(this.currentMousePosition + this.scrollOffset);
|
|
28006
28176
|
}
|
|
28007
28177
|
onMouseMove(ev) {
|
|
28008
|
-
if (ev.button
|
|
28178
|
+
if (ev.button > 1) {
|
|
28009
28179
|
this.onCancel();
|
|
28010
28180
|
return;
|
|
28011
28181
|
}
|
|
@@ -28196,14 +28366,14 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
28196
28366
|
|
|
28197
28367
|
function useHighlightsOnHover(ref, highlightProvider) {
|
|
28198
28368
|
const hoverState = useHoveredElement(ref);
|
|
28199
|
-
const
|
|
28369
|
+
const stores = useStoreProvider();
|
|
28200
28370
|
useHighlights({
|
|
28201
28371
|
get highlights() {
|
|
28202
28372
|
return hoverState.hovered ? highlightProvider.highlights : [];
|
|
28203
28373
|
},
|
|
28204
28374
|
});
|
|
28205
28375
|
owl.useEffect(() => {
|
|
28206
|
-
|
|
28376
|
+
stores.trigger("store-updated");
|
|
28207
28377
|
}, () => [hoverState.hovered]);
|
|
28208
28378
|
}
|
|
28209
28379
|
function useHighlights(highlightProvider) {
|
|
@@ -29659,6 +29829,14 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
29659
29829
|
Direction[Direction["next"] = 1] = "next";
|
|
29660
29830
|
})(Direction || (Direction = {}));
|
|
29661
29831
|
class FindAndReplaceStore extends SpreadsheetStore {
|
|
29832
|
+
mutators = [
|
|
29833
|
+
"updateSearchOptions",
|
|
29834
|
+
"updateSearchContent",
|
|
29835
|
+
"searchFormulas",
|
|
29836
|
+
"selectPreviousMatch",
|
|
29837
|
+
"selectNextMatch",
|
|
29838
|
+
"replace",
|
|
29839
|
+
];
|
|
29662
29840
|
allSheetsMatches = [];
|
|
29663
29841
|
activeSheetMatches = [];
|
|
29664
29842
|
specificRangeMatches = [];
|
|
@@ -29683,11 +29861,11 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
29683
29861
|
this.initialShowFormulaState = this.model.getters.shouldShowFormulas();
|
|
29684
29862
|
this.searchOptions.searchFormulas = this.initialShowFormulaState;
|
|
29685
29863
|
const highlightStore = get(HighlightStore);
|
|
29686
|
-
highlightStore.register(
|
|
29864
|
+
highlightStore.register(this);
|
|
29687
29865
|
this.onDispose(() => {
|
|
29688
29866
|
this.model.dispatch("SET_FORMULA_VISIBILITY", { show: this.initialShowFormulaState });
|
|
29689
29867
|
this.updateSearchContent.stopDebounce();
|
|
29690
|
-
highlightStore.unRegister(
|
|
29868
|
+
highlightStore.unRegister(this);
|
|
29691
29869
|
});
|
|
29692
29870
|
}
|
|
29693
29871
|
get searchMatches() {
|
|
@@ -31167,14 +31345,14 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
31167
31345
|
}
|
|
31168
31346
|
onKeyDown(ev) {
|
|
31169
31347
|
const figure = this.props.figure;
|
|
31170
|
-
|
|
31348
|
+
const keyDownShortcut = keyboardEventToShortcutString(ev);
|
|
31349
|
+
switch (keyDownShortcut) {
|
|
31171
31350
|
case "Delete":
|
|
31172
31351
|
this.env.model.dispatch("DELETE_FIGURE", {
|
|
31173
31352
|
sheetId: this.env.model.getters.getActiveSheetId(),
|
|
31174
31353
|
id: figure.id,
|
|
31175
31354
|
});
|
|
31176
31355
|
this.props.onFigureDeleted();
|
|
31177
|
-
ev.stopPropagation();
|
|
31178
31356
|
ev.preventDefault();
|
|
31179
31357
|
ev.stopPropagation();
|
|
31180
31358
|
break;
|
|
@@ -31195,7 +31373,22 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
31195
31373
|
x: figure.x + delta[0],
|
|
31196
31374
|
y: figure.y + delta[1],
|
|
31197
31375
|
});
|
|
31376
|
+
ev.preventDefault();
|
|
31377
|
+
ev.stopPropagation();
|
|
31378
|
+
break;
|
|
31379
|
+
case "Ctrl+A":
|
|
31380
|
+
// Maybe in the future we will implement a way to select all figures
|
|
31381
|
+
ev.preventDefault();
|
|
31198
31382
|
ev.stopPropagation();
|
|
31383
|
+
break;
|
|
31384
|
+
case "Ctrl+Y":
|
|
31385
|
+
case "Ctrl+Z":
|
|
31386
|
+
if (keyDownShortcut === "Ctrl+Y") {
|
|
31387
|
+
this.env.model.dispatch("REQUEST_REDO");
|
|
31388
|
+
}
|
|
31389
|
+
else if (keyDownShortcut === "Ctrl+Z") {
|
|
31390
|
+
this.env.model.dispatch("REQUEST_UNDO");
|
|
31391
|
+
}
|
|
31199
31392
|
ev.preventDefault();
|
|
31200
31393
|
ev.stopPropagation();
|
|
31201
31394
|
break;
|
|
@@ -31330,6 +31523,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
31330
31523
|
});
|
|
31331
31524
|
|
|
31332
31525
|
class DOMFocusableElementStore {
|
|
31526
|
+
mutators = ["setFocusableElement", "focus"];
|
|
31333
31527
|
focusableElement = undefined;
|
|
31334
31528
|
setFocusableElement(element) {
|
|
31335
31529
|
this.focusableElement = element;
|
|
@@ -32066,7 +32260,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
32066
32260
|
"Ctrl+Enter": this.processNewLineEvent,
|
|
32067
32261
|
Escape: this.processEscapeKey,
|
|
32068
32262
|
F2: () => console.warn("Not implemented"),
|
|
32069
|
-
F4: this.processF4Key,
|
|
32263
|
+
F4: (ev) => this.processF4Key(ev),
|
|
32070
32264
|
Tab: (ev) => this.processTabKey(ev, "right"),
|
|
32071
32265
|
"Shift+Tab": (ev) => this.processTabKey(ev, "left"),
|
|
32072
32266
|
};
|
|
@@ -32188,7 +32382,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
32188
32382
|
processEscapeKey() {
|
|
32189
32383
|
this.composerStore.cancelEdition();
|
|
32190
32384
|
}
|
|
32191
|
-
processF4Key() {
|
|
32385
|
+
processF4Key(ev) {
|
|
32386
|
+
ev.stopPropagation();
|
|
32192
32387
|
this.composerStore.cycleReferences();
|
|
32193
32388
|
this.processContent();
|
|
32194
32389
|
}
|
|
@@ -34391,13 +34586,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
34391
34586
|
this.getters = get(ModelStore).getters;
|
|
34392
34587
|
this.renderer = get(RendererStore);
|
|
34393
34588
|
this.renderer.register(this);
|
|
34394
|
-
/**
|
|
34395
|
-
* Mark the instance as raw to avoid reactivity as this class is instanciated
|
|
34396
|
-
* as a Store by `useGridDrawing` (which casts it as reactive).
|
|
34397
|
-
*
|
|
34398
|
-
* Calling `this.` on a reactive instance is significantly slower than on a raw object.
|
|
34399
|
-
*/
|
|
34400
|
-
owl.markRaw(this);
|
|
34401
34589
|
}
|
|
34402
34590
|
get renderingLayers() {
|
|
34403
34591
|
return ["Background", "Headers"];
|
|
@@ -35027,7 +35215,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
35027
35215
|
function useGridDrawing(refName, model, canvasSize) {
|
|
35028
35216
|
const canvasRef = owl.useRef(refName);
|
|
35029
35217
|
owl.useEffect(drawGrid);
|
|
35030
|
-
const
|
|
35218
|
+
const rendererStore = useStore(RendererStore);
|
|
35031
35219
|
useStore(GridRenderer);
|
|
35032
35220
|
function drawGrid() {
|
|
35033
35221
|
const canvas = canvasRef.el;
|
|
@@ -35055,7 +35243,11 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
35055
35243
|
ctx.scale(dpr, dpr);
|
|
35056
35244
|
for (const layer of OrderedLayers()) {
|
|
35057
35245
|
model.drawLayer(renderingContext, layer);
|
|
35058
|
-
|
|
35246
|
+
// @ts-ignore 'drawLayer' is not declated as a mutator because:
|
|
35247
|
+
// it does not mutate anything. Most importantly it's used
|
|
35248
|
+
// during rendering. Invoking a mutator during rendering would
|
|
35249
|
+
// trigger another rendering, ultimately resulting in an infinite loop.
|
|
35250
|
+
rendererStore.drawLayer(renderingContext, layer);
|
|
35059
35251
|
}
|
|
35060
35252
|
}
|
|
35061
35253
|
}
|
|
@@ -35457,6 +35649,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
35457
35649
|
}
|
|
35458
35650
|
|
|
35459
35651
|
class SidePanelStore extends SpreadsheetStore {
|
|
35652
|
+
mutators = ["open", "toggle", "close"];
|
|
35460
35653
|
initialPanelProps = {};
|
|
35461
35654
|
componentTag = "";
|
|
35462
35655
|
get isOpen() {
|
|
@@ -40983,12 +41176,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
40983
41176
|
// detect when an argument need to be evaluated as a meta argument
|
|
40984
41177
|
const isMeta = argTypes.includes("META");
|
|
40985
41178
|
const hasRange = argTypes.some((t) => isRangeType(t));
|
|
40986
|
-
const isRangeOnly = argTypes.every((t) => isRangeType(t));
|
|
40987
|
-
if (isRangeOnly) {
|
|
40988
|
-
if (!isRangeInput(currentArg)) {
|
|
40989
|
-
throw new BadExpressionError(_t("Function %s expects the parameter %s to be reference to a cell or range, not a %s.", functionName, (i + 1).toString(), currentArg.type.toLowerCase()));
|
|
40990
|
-
}
|
|
40991
|
-
}
|
|
40992
41179
|
compiledArgs.push(compileAST(currentArg, isMeta, hasRange, {
|
|
40993
41180
|
functionName,
|
|
40994
41181
|
paramIndex: i + 1,
|
|
@@ -41159,16 +41346,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
41159
41346
|
function isRangeType(type) {
|
|
41160
41347
|
return type.startsWith("RANGE");
|
|
41161
41348
|
}
|
|
41162
|
-
function isRangeInput(arg) {
|
|
41163
|
-
if (arg.type === "REFERENCE") {
|
|
41164
|
-
return true;
|
|
41165
|
-
}
|
|
41166
|
-
if (arg.type === "FUNCALL") {
|
|
41167
|
-
const fnDef = functions$1[arg.value.toUpperCase()];
|
|
41168
|
-
return fnDef && isRangeType(fnDef.returns[0]);
|
|
41169
|
-
}
|
|
41170
|
-
return false;
|
|
41171
|
-
}
|
|
41172
41349
|
|
|
41173
41350
|
const functions = functionRegistry.content;
|
|
41174
41351
|
function isExportableToExcel(tokens) {
|
|
@@ -43285,7 +43462,12 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
43285
43462
|
* if they have at least a common cell
|
|
43286
43463
|
*/
|
|
43287
43464
|
doesIntersectMerge(sheetId, zone) {
|
|
43288
|
-
|
|
43465
|
+
for (const merge of this.getMerges(sheetId)) {
|
|
43466
|
+
if (overlap(zone, merge)) {
|
|
43467
|
+
return true;
|
|
43468
|
+
}
|
|
43469
|
+
}
|
|
43470
|
+
return false;
|
|
43289
43471
|
}
|
|
43290
43472
|
/**
|
|
43291
43473
|
* Returns true if two columns have at least one merge in common
|
|
@@ -43901,6 +44083,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
43901
44083
|
if (range.invalidXc) {
|
|
43902
44084
|
return range.invalidXc;
|
|
43903
44085
|
}
|
|
44086
|
+
if (!this.getters.tryGetSheet(range.sheetId)) {
|
|
44087
|
+
return CellErrorType.InvalidReference;
|
|
44088
|
+
}
|
|
43904
44089
|
if (range.zone.bottom - range.zone.top < 0 || range.zone.right - range.zone.left < 0) {
|
|
43905
44090
|
return CellErrorType.InvalidReference;
|
|
43906
44091
|
}
|
|
@@ -47285,7 +47470,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47285
47470
|
*
|
|
47286
47471
|
*/
|
|
47287
47472
|
class SpreadingRelation {
|
|
47288
|
-
createEmptyPositionSet;
|
|
47289
47473
|
/**
|
|
47290
47474
|
* Internal structure:
|
|
47291
47475
|
* For something like
|
|
@@ -47316,9 +47500,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47316
47500
|
*/
|
|
47317
47501
|
resultsToArrayFormulas = new PositionMap();
|
|
47318
47502
|
arrayFormulasToResults = new PositionMap();
|
|
47319
|
-
constructor(createEmptyPositionSet) {
|
|
47320
|
-
this.createEmptyPositionSet = createEmptyPositionSet;
|
|
47321
|
-
}
|
|
47322
47503
|
getFormulaPositionsSpreadingOn(resultPosition) {
|
|
47323
47504
|
return this.resultsToArrayFormulas.get(resultPosition) || EMPTY_ARRAY;
|
|
47324
47505
|
}
|
|
@@ -47337,13 +47518,13 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47337
47518
|
*/
|
|
47338
47519
|
addRelation({ arrayFormulaPosition, resultPosition, }) {
|
|
47339
47520
|
if (!this.resultsToArrayFormulas.has(resultPosition)) {
|
|
47340
|
-
this.resultsToArrayFormulas.set(resultPosition,
|
|
47521
|
+
this.resultsToArrayFormulas.set(resultPosition, []);
|
|
47341
47522
|
}
|
|
47342
|
-
this.resultsToArrayFormulas.get(resultPosition)?.
|
|
47523
|
+
this.resultsToArrayFormulas.get(resultPosition)?.push(arrayFormulaPosition);
|
|
47343
47524
|
if (!this.arrayFormulasToResults.has(arrayFormulaPosition)) {
|
|
47344
|
-
this.arrayFormulasToResults.set(arrayFormulaPosition,
|
|
47525
|
+
this.arrayFormulasToResults.set(arrayFormulaPosition, []);
|
|
47345
47526
|
}
|
|
47346
|
-
this.arrayFormulasToResults.get(arrayFormulaPosition)?.
|
|
47527
|
+
this.arrayFormulasToResults.get(arrayFormulaPosition)?.push(resultPosition);
|
|
47347
47528
|
}
|
|
47348
47529
|
hasArrayFormulaResult(position) {
|
|
47349
47530
|
return this.resultsToArrayFormulas.has(position);
|
|
@@ -47364,7 +47545,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47364
47545
|
evaluatedCells = new PositionMap();
|
|
47365
47546
|
formulaDependencies = lazy(new FormulaDependencyGraph(this.createEmptyPositionSet.bind(this)));
|
|
47366
47547
|
blockedArrayFormulas = new PositionSet({});
|
|
47367
|
-
spreadingRelations = new SpreadingRelation(
|
|
47548
|
+
spreadingRelations = new SpreadingRelation();
|
|
47368
47549
|
constructor(context, getters) {
|
|
47369
47550
|
this.context = context;
|
|
47370
47551
|
this.getters = getters;
|
|
@@ -47441,7 +47622,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47441
47622
|
}
|
|
47442
47623
|
buildDependencyGraph() {
|
|
47443
47624
|
this.blockedArrayFormulas = this.createEmptyPositionSet();
|
|
47444
|
-
this.spreadingRelations = new SpreadingRelation(
|
|
47625
|
+
this.spreadingRelations = new SpreadingRelation();
|
|
47445
47626
|
this.formulaDependencies = lazy(() => {
|
|
47446
47627
|
const dependencies = [...this.getAllCells()].flatMap((position) => this.getDirectDependencies(position)
|
|
47447
47628
|
.filter((range) => !range.invalidSheetName && !range.invalidXc)
|
|
@@ -47930,16 +48111,22 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
47930
48111
|
let newContent = undefined;
|
|
47931
48112
|
let newFormat = undefined;
|
|
47932
48113
|
let isExported = true;
|
|
48114
|
+
const exportedSheetData = data.sheets.find((sheet) => sheet.id === position.sheetId);
|
|
47933
48115
|
const formulaCell = this.getCorrespondingFormulaCell(position);
|
|
47934
48116
|
if (formulaCell) {
|
|
47935
48117
|
isExported = isExportableToExcel(formulaCell.compiledFormula.tokens);
|
|
47936
48118
|
isFormula = isExported;
|
|
47937
48119
|
if (!isExported) {
|
|
47938
|
-
|
|
47939
|
-
|
|
48120
|
+
// If the cell contains a non-exported formula and that is evaluates to
|
|
48121
|
+
// nothing* ,we don't export it.
|
|
48122
|
+
// * non-falsy value are relevant and so are 0 and FALSE, which only leaves
|
|
48123
|
+
// the empty string.
|
|
48124
|
+
if (value !== "") {
|
|
48125
|
+
newContent = (value ?? "").toString();
|
|
48126
|
+
newFormat = evaluatedCell.format;
|
|
48127
|
+
}
|
|
47940
48128
|
}
|
|
47941
48129
|
}
|
|
47942
|
-
const exportedSheetData = data.sheets.find((sheet) => sheet.id === position.sheetId);
|
|
47943
48130
|
const exportedCellData = exportedSheetData.cells[xc] || {};
|
|
47944
48131
|
const format = newFormat
|
|
47945
48132
|
? getItemId(newFormat, data.formats)
|
|
@@ -49605,62 +49792,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
49605
49792
|
}
|
|
49606
49793
|
}
|
|
49607
49794
|
|
|
49608
|
-
/**
|
|
49609
|
-
* This is a generic event bus based on the Owl event bus.
|
|
49610
|
-
* This bus however ensures type safety across events and subscription callbacks.
|
|
49611
|
-
*/
|
|
49612
|
-
class EventBus {
|
|
49613
|
-
subscriptions = {};
|
|
49614
|
-
/**
|
|
49615
|
-
* Add a listener for the 'eventType' events.
|
|
49616
|
-
*
|
|
49617
|
-
* Note that the 'owner' of this event can be anything, but will more likely
|
|
49618
|
-
* be a component or a class. The idea is that the callback will be called with
|
|
49619
|
-
* the proper owner bound.
|
|
49620
|
-
*
|
|
49621
|
-
* Also, the owner should be kind of unique. This will be used to remove the
|
|
49622
|
-
* listener.
|
|
49623
|
-
*/
|
|
49624
|
-
on(type, owner, callback) {
|
|
49625
|
-
if (!callback) {
|
|
49626
|
-
throw new Error("Missing callback");
|
|
49627
|
-
}
|
|
49628
|
-
if (!this.subscriptions[type]) {
|
|
49629
|
-
this.subscriptions[type] = [];
|
|
49630
|
-
}
|
|
49631
|
-
this.subscriptions[type].push({
|
|
49632
|
-
owner,
|
|
49633
|
-
callback,
|
|
49634
|
-
});
|
|
49635
|
-
}
|
|
49636
|
-
/**
|
|
49637
|
-
* Emit an event of type 'eventType'. Any extra arguments will be passed to
|
|
49638
|
-
* the listeners callback.
|
|
49639
|
-
*/
|
|
49640
|
-
trigger(type, payload) {
|
|
49641
|
-
const subs = this.subscriptions[type] || [];
|
|
49642
|
-
for (let i = 0, iLen = subs.length; i < iLen; i++) {
|
|
49643
|
-
const sub = subs[i];
|
|
49644
|
-
sub.callback.call(sub.owner, payload);
|
|
49645
|
-
}
|
|
49646
|
-
}
|
|
49647
|
-
/**
|
|
49648
|
-
* Remove a listener
|
|
49649
|
-
*/
|
|
49650
|
-
off(eventType, owner) {
|
|
49651
|
-
const subs = this.subscriptions[eventType];
|
|
49652
|
-
if (subs) {
|
|
49653
|
-
this.subscriptions[eventType] = subs.filter((s) => s.owner !== owner);
|
|
49654
|
-
}
|
|
49655
|
-
}
|
|
49656
|
-
/**
|
|
49657
|
-
* Remove all subscriptions.
|
|
49658
|
-
*/
|
|
49659
|
-
clear() {
|
|
49660
|
-
this.subscriptions = {};
|
|
49661
|
-
}
|
|
49662
|
-
}
|
|
49663
|
-
|
|
49664
49795
|
/*
|
|
49665
49796
|
* This file contains the specifics transformations
|
|
49666
49797
|
*/
|
|
@@ -51985,7 +52116,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
51985
52116
|
paintFormatStatus = "inactive";
|
|
51986
52117
|
originSheetId;
|
|
51987
52118
|
copiedData;
|
|
51988
|
-
_isCutOperation;
|
|
52119
|
+
_isCutOperation = false;
|
|
51989
52120
|
// ---------------------------------------------------------------------------
|
|
51990
52121
|
// Command Handling
|
|
51991
52122
|
// ---------------------------------------------------------------------------
|
|
@@ -51997,14 +52128,17 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
51997
52128
|
case "PASTE_FROM_OS_CLIPBOARD": {
|
|
51998
52129
|
const copiedData = this.convertOSClipboardData(cmd.text);
|
|
51999
52130
|
const pasteOption = cmd.pasteOption || (this.paintFormatStatus !== "inactive" ? "onlyFormat" : undefined);
|
|
52000
|
-
return this.isPasteAllowed(cmd.target, copiedData, { pasteOption });
|
|
52131
|
+
return this.isPasteAllowed(cmd.target, copiedData, { pasteOption, isCutOperation: false });
|
|
52001
52132
|
}
|
|
52002
52133
|
case "PASTE": {
|
|
52003
52134
|
if (!this.copiedData) {
|
|
52004
52135
|
return "EmptyClipboard" /* CommandResult.EmptyClipboard */;
|
|
52005
52136
|
}
|
|
52006
52137
|
const pasteOption = cmd.pasteOption || (this.paintFormatStatus !== "inactive" ? "onlyFormat" : undefined);
|
|
52007
|
-
return this.isPasteAllowed(cmd.target, this.copiedData, {
|
|
52138
|
+
return this.isPasteAllowed(cmd.target, this.copiedData, {
|
|
52139
|
+
pasteOption: pasteOption,
|
|
52140
|
+
isCutOperation: this._isCutOperation,
|
|
52141
|
+
});
|
|
52008
52142
|
}
|
|
52009
52143
|
case "COPY_PASTE_CELLS_ABOVE": {
|
|
52010
52144
|
const zones = this.getters.getSelectedZones();
|
|
@@ -52022,13 +52156,13 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52022
52156
|
}
|
|
52023
52157
|
case "INSERT_CELL": {
|
|
52024
52158
|
const { cut, paste } = this.getInsertCellsTargets(cmd.zone, cmd.shiftDimension);
|
|
52025
|
-
const copiedData = this.copy(
|
|
52026
|
-
return this.isPasteAllowed(paste, copiedData, {});
|
|
52159
|
+
const copiedData = this.copy(cut);
|
|
52160
|
+
return this.isPasteAllowed(paste, copiedData, { isCutOperation: true });
|
|
52027
52161
|
}
|
|
52028
52162
|
case "DELETE_CELL": {
|
|
52029
52163
|
const { cut, paste } = this.getDeleteCellsTargets(cmd.zone, cmd.shiftDimension);
|
|
52030
|
-
const copiedData = this.copy(
|
|
52031
|
-
return this.isPasteAllowed(paste, copiedData, {});
|
|
52164
|
+
const copiedData = this.copy(cut);
|
|
52165
|
+
return this.isPasteAllowed(paste, copiedData, { isCutOperation: true });
|
|
52032
52166
|
}
|
|
52033
52167
|
case "ACTIVATE_PAINT_FORMAT": {
|
|
52034
52168
|
if (this.paintFormatStatus !== "inactive") {
|
|
@@ -52046,23 +52180,27 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52046
52180
|
const zones = this.getters.getSelectedZones();
|
|
52047
52181
|
this.status = "visible";
|
|
52048
52182
|
this.originSheetId = this.getters.getActiveSheetId();
|
|
52049
|
-
this.copiedData = this.copy(
|
|
52183
|
+
this.copiedData = this.copy(zones);
|
|
52184
|
+
this._isCutOperation = cmd.type === "CUT";
|
|
52050
52185
|
break;
|
|
52051
52186
|
case "PASTE_FROM_OS_CLIPBOARD": {
|
|
52187
|
+
this._isCutOperation = false;
|
|
52052
52188
|
this.copiedData = this.convertOSClipboardData(cmd.text);
|
|
52053
52189
|
const pasteOption = cmd.pasteOption || (this.paintFormatStatus !== "inactive" ? "onlyFormat" : undefined);
|
|
52054
|
-
this.paste(cmd.target, {
|
|
52190
|
+
this.paste(cmd.target, this.copiedData, {
|
|
52055
52191
|
pasteOption,
|
|
52056
52192
|
selectTarget: true,
|
|
52193
|
+
isCutOperation: false,
|
|
52057
52194
|
});
|
|
52058
52195
|
this.status = "invisible";
|
|
52059
52196
|
break;
|
|
52060
52197
|
}
|
|
52061
52198
|
case "PASTE": {
|
|
52062
52199
|
const pasteOption = cmd.pasteOption || (this.paintFormatStatus !== "inactive" ? "onlyFormat" : undefined);
|
|
52063
|
-
this.paste(cmd.target, {
|
|
52200
|
+
this.paste(cmd.target, this.copiedData, {
|
|
52064
52201
|
pasteOption,
|
|
52065
52202
|
selectTarget: true,
|
|
52203
|
+
isCutOperation: this._isCutOperation,
|
|
52066
52204
|
});
|
|
52067
52205
|
if (this.paintFormatStatus === "oneOff") {
|
|
52068
52206
|
this.paintFormatStatus = "inactive";
|
|
@@ -52083,9 +52221,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52083
52221
|
top: multipleRowsInSelection ? zone.top : zone.top - 1,
|
|
52084
52222
|
};
|
|
52085
52223
|
this.originSheetId = this.getters.getActiveSheetId();
|
|
52086
|
-
|
|
52087
|
-
this.paste([zone], {
|
|
52088
|
-
|
|
52224
|
+
const copiedData = this.copy([copyTarget]);
|
|
52225
|
+
this.paste([zone], copiedData, {
|
|
52226
|
+
isCutOperation: false,
|
|
52089
52227
|
selectTarget: true,
|
|
52090
52228
|
});
|
|
52091
52229
|
}
|
|
@@ -52100,9 +52238,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52100
52238
|
left: multipleColsInSelection ? zone.left : zone.left - 1,
|
|
52101
52239
|
};
|
|
52102
52240
|
this.originSheetId = this.getters.getActiveSheetId();
|
|
52103
|
-
|
|
52104
|
-
this.paste([zone], {
|
|
52105
|
-
|
|
52241
|
+
const copiedData = this.copy([copyTarget]);
|
|
52242
|
+
this.paste([zone], copiedData, {
|
|
52243
|
+
isCutOperation: false,
|
|
52106
52244
|
selectTarget: true,
|
|
52107
52245
|
});
|
|
52108
52246
|
}
|
|
@@ -52118,20 +52256,20 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52118
52256
|
}
|
|
52119
52257
|
break;
|
|
52120
52258
|
}
|
|
52121
|
-
|
|
52122
|
-
this.paste(paste, {});
|
|
52259
|
+
const copiedData = this.copy(cut);
|
|
52260
|
+
this.paste(paste, copiedData, { isCutOperation: true });
|
|
52123
52261
|
break;
|
|
52124
52262
|
}
|
|
52125
52263
|
case "INSERT_CELL": {
|
|
52126
52264
|
const { cut, paste } = this.getInsertCellsTargets(cmd.zone, cmd.shiftDimension);
|
|
52127
|
-
|
|
52128
|
-
this.paste(paste, {});
|
|
52265
|
+
const copiedData = this.copy(cut);
|
|
52266
|
+
this.paste(paste, copiedData, { isCutOperation: true });
|
|
52129
52267
|
break;
|
|
52130
52268
|
}
|
|
52131
52269
|
case "ADD_COLUMNS_ROWS": {
|
|
52132
52270
|
this.status = "invisible";
|
|
52133
52271
|
// If we add a col/row inside or before the cut area, we invalidate the clipboard
|
|
52134
|
-
if (this._isCutOperation !== true) {
|
|
52272
|
+
if (this._isCutOperation !== true || cmd.sheetId !== this.copiedData?.sheetId) {
|
|
52135
52273
|
return;
|
|
52136
52274
|
}
|
|
52137
52275
|
const isClipboardDirty = this.isColRowDirtyingClipboard(cmd.position === "before" ? cmd.base : cmd.base + 1, cmd.dimension);
|
|
@@ -52143,7 +52281,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52143
52281
|
case "REMOVE_COLUMNS_ROWS": {
|
|
52144
52282
|
this.status = "invisible";
|
|
52145
52283
|
// If we remove a col/row inside or before the cut area, we invalidate the clipboard
|
|
52146
|
-
if (this._isCutOperation !== true) {
|
|
52284
|
+
if (this._isCutOperation !== true || cmd.sheetId !== this.copiedData?.sheetId) {
|
|
52147
52285
|
return;
|
|
52148
52286
|
}
|
|
52149
52287
|
for (let el of cmd.elements) {
|
|
@@ -52157,7 +52295,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52157
52295
|
break;
|
|
52158
52296
|
}
|
|
52159
52297
|
case "REPEAT_PASTE": {
|
|
52160
|
-
this.paste(cmd.target, {
|
|
52298
|
+
this.paste(cmd.target, this.copiedData, {
|
|
52299
|
+
isCutOperation: false,
|
|
52161
52300
|
pasteOption: cmd.pasteOption,
|
|
52162
52301
|
selectTarget: true,
|
|
52163
52302
|
});
|
|
@@ -52165,7 +52304,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52165
52304
|
}
|
|
52166
52305
|
case "ACTIVATE_PAINT_FORMAT": {
|
|
52167
52306
|
const zones = this.getters.getSelectedZones();
|
|
52168
|
-
this.copiedData = this.copy(
|
|
52307
|
+
this.copiedData = this.copy(zones);
|
|
52169
52308
|
this.status = "visible";
|
|
52170
52309
|
if (cmd.persistent) {
|
|
52171
52310
|
this.paintFormatStatus = "persistent";
|
|
@@ -52196,7 +52335,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52196
52335
|
}
|
|
52197
52336
|
}
|
|
52198
52337
|
convertOSClipboardData(clipboardData) {
|
|
52199
|
-
this._isCutOperation = false;
|
|
52200
52338
|
const handlers = clipboardHandlersRegistries.figureHandlers
|
|
52201
52339
|
.getAll()
|
|
52202
52340
|
.map((handler) => new handler(this.getters, this.dispatch));
|
|
@@ -52234,7 +52372,6 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52234
52372
|
for (const handler of this.selectClipboardHandlers(copiedData)) {
|
|
52235
52373
|
const result = handler.isPasteAllowed(this.getters.getActiveSheetId(), target, copiedData, {
|
|
52236
52374
|
...options,
|
|
52237
|
-
isCutOperation: this.isCutOperation(),
|
|
52238
52375
|
});
|
|
52239
52376
|
if (result !== "Success" /* CommandResult.Success */) {
|
|
52240
52377
|
return result;
|
|
@@ -52257,9 +52394,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52257
52394
|
}
|
|
52258
52395
|
return false;
|
|
52259
52396
|
}
|
|
52260
|
-
copy(
|
|
52397
|
+
copy(zones) {
|
|
52261
52398
|
let copiedData = {};
|
|
52262
|
-
this._isCutOperation = operation === "CUT";
|
|
52263
52399
|
const clipboardData = this.getClipboardData(zones);
|
|
52264
52400
|
for (const handler of this.selectClipboardHandlers(clipboardData)) {
|
|
52265
52401
|
const data = handler.copy(clipboardData);
|
|
@@ -52267,8 +52403,8 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52267
52403
|
}
|
|
52268
52404
|
return copiedData;
|
|
52269
52405
|
}
|
|
52270
|
-
paste(zones, options) {
|
|
52271
|
-
if (!
|
|
52406
|
+
paste(zones, copiedData, options) {
|
|
52407
|
+
if (!copiedData) {
|
|
52272
52408
|
return;
|
|
52273
52409
|
}
|
|
52274
52410
|
let zone = undefined;
|
|
@@ -52276,12 +52412,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52276
52412
|
let target = {
|
|
52277
52413
|
zones,
|
|
52278
52414
|
};
|
|
52279
|
-
const handlers = this.selectClipboardHandlers(
|
|
52415
|
+
const handlers = this.selectClipboardHandlers(copiedData);
|
|
52280
52416
|
for (const handler of handlers) {
|
|
52281
|
-
const currentTarget = handler.getPasteTarget(zones,
|
|
52282
|
-
...options,
|
|
52283
|
-
isCutOperation: this.isCutOperation(),
|
|
52284
|
-
});
|
|
52417
|
+
const currentTarget = handler.getPasteTarget(zones, copiedData, options);
|
|
52285
52418
|
if (currentTarget.figureId) {
|
|
52286
52419
|
target.figureId = currentTarget.figureId;
|
|
52287
52420
|
}
|
|
@@ -52297,7 +52430,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
52297
52430
|
if (zone !== undefined) {
|
|
52298
52431
|
this.addMissingDimensions(this.getters.getActiveSheetId(), zone.right - zone.left + 1, zone.bottom - zone.top + 1, zone.left, zone.top);
|
|
52299
52432
|
}
|
|
52300
|
-
handlers.forEach((handler) => handler.paste(target,
|
|
52433
|
+
handlers.forEach((handler) => handler.paste(target, copiedData, options));
|
|
52301
52434
|
if (!options?.selectTarget) {
|
|
52302
52435
|
return;
|
|
52303
52436
|
}
|
|
@@ -54767,6 +54900,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
54767
54900
|
sheetDivRef = owl.useRef("sheetDiv");
|
|
54768
54901
|
sheetNameRef = owl.useRef("sheetNameSpan");
|
|
54769
54902
|
editionState = "initializing";
|
|
54903
|
+
DOMFocusableElementStore;
|
|
54770
54904
|
setup() {
|
|
54771
54905
|
owl.onMounted(() => {
|
|
54772
54906
|
if (this.isSheetActive) {
|
|
@@ -54779,6 +54913,7 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
54779
54913
|
this.focusInputAndSelectContent();
|
|
54780
54914
|
}
|
|
54781
54915
|
});
|
|
54916
|
+
this.DOMFocusableElementStore = useStore(DOMFocusableElementStore);
|
|
54782
54917
|
}
|
|
54783
54918
|
focusInputAndSelectContent() {
|
|
54784
54919
|
if (!this.state.isEditing || !this.sheetNameRef.el)
|
|
@@ -54820,9 +54955,11 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
54820
54955
|
if (ev.key === "Enter") {
|
|
54821
54956
|
ev.preventDefault();
|
|
54822
54957
|
this.stopEdition();
|
|
54958
|
+
this.DOMFocusableElementStore.focus();
|
|
54823
54959
|
}
|
|
54824
54960
|
if (ev.key === "Escape") {
|
|
54825
54961
|
this.cancelEdition();
|
|
54962
|
+
this.DOMFocusableElementStore.focus();
|
|
54826
54963
|
}
|
|
54827
54964
|
}
|
|
54828
54965
|
onClickSheetName(ev) {
|
|
@@ -56778,16 +56915,25 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
56778
56915
|
}
|
|
56779
56916
|
}, () => [this.env.model.getters.getActiveSheetId()]);
|
|
56780
56917
|
owl.useExternalListener(window, "resize", () => this.render(true));
|
|
56918
|
+
// For some reason, the wheel event is not properly registered inside templates
|
|
56919
|
+
// in Chromium-based browsers based on chromium 125
|
|
56920
|
+
// This hack ensures the event declared in the template is properly registered/working
|
|
56921
|
+
owl.useExternalListener(document.body, "wheel", () => { });
|
|
56781
56922
|
this.bindModelEvents();
|
|
56782
56923
|
owl.onWillUpdateProps((nextProps) => {
|
|
56783
56924
|
if (nextProps.model !== this.props.model) {
|
|
56784
56925
|
throw new Error("Changing the props model is not supported at the moment.");
|
|
56785
56926
|
}
|
|
56786
56927
|
});
|
|
56928
|
+
const render = batched(this.render.bind(this, true));
|
|
56787
56929
|
owl.onMounted(() => {
|
|
56788
56930
|
this.checkViewportSize();
|
|
56931
|
+
stores.on("store-updated", this, render);
|
|
56932
|
+
});
|
|
56933
|
+
owl.onWillUnmount(() => {
|
|
56934
|
+
this.unbindModelEvents();
|
|
56935
|
+
stores.off("store-updated", this);
|
|
56789
56936
|
});
|
|
56790
|
-
owl.onWillUnmount(() => this.unbindModelEvents());
|
|
56791
56937
|
owl.onPatched(() => {
|
|
56792
56938
|
this.checkViewportSize();
|
|
56793
56939
|
});
|
|
@@ -59536,7 +59682,11 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
59536
59682
|
let cellNode = escapeXml ``;
|
|
59537
59683
|
// Either formula or static value inside the cell
|
|
59538
59684
|
if (cell.isFormula) {
|
|
59539
|
-
|
|
59685
|
+
const res = addFormula(cell);
|
|
59686
|
+
if (!res) {
|
|
59687
|
+
continue;
|
|
59688
|
+
}
|
|
59689
|
+
({ attrs: additionalAttrs, node: cellNode } = res);
|
|
59540
59690
|
}
|
|
59541
59691
|
else if (cell.content && isMarkdownLink(cell.content)) {
|
|
59542
59692
|
const { label } = parseMarkdownLink(cell.content);
|
|
@@ -60616,9 +60766,9 @@ stores.inject(MyMetaStore, storeInstance);
|
|
|
60616
60766
|
exports.tokenize = tokenize;
|
|
60617
60767
|
|
|
60618
60768
|
|
|
60619
|
-
__info__.version = "17.2.
|
|
60620
|
-
__info__.date = "2024-
|
|
60621
|
-
__info__.hash = "
|
|
60769
|
+
__info__.version = "17.2.9";
|
|
60770
|
+
__info__.date = "2024-06-03T14:56:21.684Z";
|
|
60771
|
+
__info__.hash = "086af6d";
|
|
60622
60772
|
|
|
60623
60773
|
|
|
60624
60774
|
})(this.o_spreadsheet = this.o_spreadsheet || {}, owl);
|