@odoo/o-spreadsheet 18.2.6 → 18.2.8
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 +257 -136
- package/dist/o-spreadsheet.d.ts +33 -16
- package/dist/o-spreadsheet.esm.js +257 -136
- package/dist/o-spreadsheet.iife.js +257 -136
- package/dist/o-spreadsheet.iife.min.js +378 -377
- package/dist/o_spreadsheet.xml +38 -36
- 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-04-
|
|
7
|
-
* @hash
|
|
5
|
+
* @version 18.2.8
|
|
6
|
+
* @date 2025-04-18T16:26:20.673Z
|
|
7
|
+
* @hash 5da9ddc
|
|
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';
|
|
@@ -3573,6 +3573,7 @@ const coreTypes = new Set([
|
|
|
3573
3573
|
"CLEAR_FORMATTING",
|
|
3574
3574
|
"SET_BORDER",
|
|
3575
3575
|
"SET_ZONE_BORDERS",
|
|
3576
|
+
"SET_BORDERS_ON_TARGET",
|
|
3576
3577
|
/** CHART */
|
|
3577
3578
|
"CREATE_CHART",
|
|
3578
3579
|
"UPDATE_CHART",
|
|
@@ -6722,6 +6723,7 @@ class AbstractCellClipboardHandler extends ClipboardHandler {
|
|
|
6722
6723
|
}
|
|
6723
6724
|
|
|
6724
6725
|
class BorderClipboardHandler extends AbstractCellClipboardHandler {
|
|
6726
|
+
queuedBordersToAdd = {};
|
|
6725
6727
|
copy(data) {
|
|
6726
6728
|
const sheetId = data.sheetId;
|
|
6727
6729
|
if (data.zones.length === 0) {
|
|
@@ -6752,6 +6754,7 @@ class BorderClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
6752
6754
|
const { left, top } = zones[0];
|
|
6753
6755
|
this.pasteZone(sheetId, left, top, content.borders);
|
|
6754
6756
|
}
|
|
6757
|
+
this.executeQueuedChanges(sheetId);
|
|
6755
6758
|
}
|
|
6756
6759
|
pasteZone(sheetId, col, row, borders) {
|
|
6757
6760
|
for (const [r, rowBorders] of borders.entries()) {
|
|
@@ -6770,7 +6773,20 @@ class BorderClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
6770
6773
|
...targetBorders,
|
|
6771
6774
|
...originBorders,
|
|
6772
6775
|
};
|
|
6773
|
-
|
|
6776
|
+
const borderKey = JSON.stringify(border);
|
|
6777
|
+
if (!this.queuedBordersToAdd[borderKey]) {
|
|
6778
|
+
this.queuedBordersToAdd[borderKey] = [];
|
|
6779
|
+
}
|
|
6780
|
+
this.queuedBordersToAdd[borderKey].push(positionToZone(target));
|
|
6781
|
+
}
|
|
6782
|
+
executeQueuedChanges(pasteSheetTarget) {
|
|
6783
|
+
for (const borderKey in this.queuedBordersToAdd) {
|
|
6784
|
+
const zones = this.queuedBordersToAdd[borderKey];
|
|
6785
|
+
const border = JSON.parse(borderKey);
|
|
6786
|
+
const target = recomputeZones(zones, []);
|
|
6787
|
+
this.dispatch("SET_BORDERS_ON_TARGET", { sheetId: pasteSheetTarget, target, border });
|
|
6788
|
+
}
|
|
6789
|
+
this.queuedBordersToAdd = {};
|
|
6774
6790
|
}
|
|
6775
6791
|
}
|
|
6776
6792
|
|
|
@@ -6882,6 +6898,12 @@ function tokenizeString(chars) {
|
|
|
6882
6898
|
}
|
|
6883
6899
|
return null;
|
|
6884
6900
|
}
|
|
6901
|
+
/**
|
|
6902
|
+
- \p{L} is for any letter (from any language)
|
|
6903
|
+
- \p{N} is for any number
|
|
6904
|
+
- the u flag at the end is for unicode, which enables the `\p{...}` syntax
|
|
6905
|
+
*/
|
|
6906
|
+
const unicodeSymbolCharRegexp = /\p{L}|\p{N}|_|\.|!|\$/u;
|
|
6885
6907
|
const SYMBOL_CHARS = new Set("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_.!$");
|
|
6886
6908
|
/**
|
|
6887
6909
|
* A "Symbol" is just basically any word-like element that can appear in a
|
|
@@ -6922,7 +6944,8 @@ function tokenizeSymbol(chars) {
|
|
|
6922
6944
|
};
|
|
6923
6945
|
}
|
|
6924
6946
|
}
|
|
6925
|
-
while (chars.current &&
|
|
6947
|
+
while (chars.current &&
|
|
6948
|
+
(SYMBOL_CHARS.has(chars.current) || chars.current.match(unicodeSymbolCharRegexp))) {
|
|
6926
6949
|
result += chars.shift();
|
|
6927
6950
|
}
|
|
6928
6951
|
if (result.length) {
|
|
@@ -8710,12 +8733,13 @@ class ConditionalFormatClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
8710
8733
|
}
|
|
8711
8734
|
pasteCf(origin, target, isCutOperation) {
|
|
8712
8735
|
if (origin?.rules && origin.rules.length > 0) {
|
|
8736
|
+
const originZone = positionToZone(origin.position);
|
|
8713
8737
|
const zone = positionToZone(target);
|
|
8714
8738
|
for (const rule of origin.rules) {
|
|
8715
8739
|
const toRemoveZones = [];
|
|
8716
8740
|
if (isCutOperation) {
|
|
8717
8741
|
//remove from current rule
|
|
8718
|
-
toRemoveZones.push(
|
|
8742
|
+
toRemoveZones.push(originZone);
|
|
8719
8743
|
}
|
|
8720
8744
|
if (origin.position.sheetId === target.sheetId) {
|
|
8721
8745
|
this.adaptCFRules(origin.position.sheetId, rule, [zone], toRemoveZones);
|
|
@@ -8829,6 +8853,7 @@ class DataValidationClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
8829
8853
|
pasteDataValidation(origin, target, isCutOperation) {
|
|
8830
8854
|
if (origin) {
|
|
8831
8855
|
const zone = positionToZone(target);
|
|
8856
|
+
const originZone = positionToZone(origin.position);
|
|
8832
8857
|
const rule = origin.rule;
|
|
8833
8858
|
if (!rule) {
|
|
8834
8859
|
const targetRule = this.getters.getValidationRuleForCell(target);
|
|
@@ -8840,7 +8865,7 @@ class DataValidationClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
8840
8865
|
}
|
|
8841
8866
|
const toRemoveZone = [];
|
|
8842
8867
|
if (isCutOperation) {
|
|
8843
|
-
toRemoveZone.push(
|
|
8868
|
+
toRemoveZone.push(originZone);
|
|
8844
8869
|
}
|
|
8845
8870
|
if (origin.position.sheetId === target.sheetId) {
|
|
8846
8871
|
const copyToRule = this.getDataValidationRuleToCopyTo(target.sheetId, rule, false);
|
|
@@ -8900,7 +8925,7 @@ class DataValidationClipboardHandler extends AbstractCellClipboardHandler {
|
|
|
8900
8925
|
continue;
|
|
8901
8926
|
}
|
|
8902
8927
|
this.dispatch("ADD_DATA_VALIDATION_RULE", {
|
|
8903
|
-
rule: dv,
|
|
8928
|
+
rule: { id: dv.id, criterion: dv.criterion, isBlocking: dv.isBlocking },
|
|
8904
8929
|
ranges: newDvZones.map((zone) => this.getters.getRangeDataFromZone(sheetId, zone)),
|
|
8905
8930
|
sheetId,
|
|
8906
8931
|
});
|
|
@@ -9227,7 +9252,7 @@ function transformZone(zone, executed) {
|
|
|
9227
9252
|
if (executed.type === "ADD_COLUMNS_ROWS") {
|
|
9228
9253
|
return expandZoneOnInsertion(zone, executed.dimension === "COL" ? "left" : "top", executed.base, executed.position, executed.quantity);
|
|
9229
9254
|
}
|
|
9230
|
-
return
|
|
9255
|
+
return zone;
|
|
9231
9256
|
}
|
|
9232
9257
|
function transformRangeData(range, executed) {
|
|
9233
9258
|
const deletedSheet = executed.type === "DELETE_SHEET" && executed.sheetId;
|
|
@@ -33618,6 +33643,12 @@ function isMacOS() {
|
|
|
33618
33643
|
function isCtrlKey(ev) {
|
|
33619
33644
|
return isMacOS() ? ev.metaKey : ev.ctrlKey;
|
|
33620
33645
|
}
|
|
33646
|
+
/**
|
|
33647
|
+
* Detects if the current browser is Firefox
|
|
33648
|
+
*/
|
|
33649
|
+
function isBrowserFirefox() {
|
|
33650
|
+
return /Firefox/i.test(navigator.userAgent);
|
|
33651
|
+
}
|
|
33621
33652
|
|
|
33622
33653
|
/**
|
|
33623
33654
|
* Repeatedly calls a callback function with a time delay between calls.
|
|
@@ -50413,39 +50444,6 @@ function useCellHovered(env, gridRef, callback) {
|
|
|
50413
50444
|
}
|
|
50414
50445
|
return hoveredPosition;
|
|
50415
50446
|
}
|
|
50416
|
-
function useTouchMove(gridRef, handler, canMoveUp) {
|
|
50417
|
-
let x = null;
|
|
50418
|
-
let y = null;
|
|
50419
|
-
function onTouchStart(ev) {
|
|
50420
|
-
if (ev.touches.length !== 1)
|
|
50421
|
-
return;
|
|
50422
|
-
x = ev.touches[0].clientX;
|
|
50423
|
-
y = ev.touches[0].clientY;
|
|
50424
|
-
}
|
|
50425
|
-
function onTouchEnd() {
|
|
50426
|
-
x = null;
|
|
50427
|
-
y = null;
|
|
50428
|
-
}
|
|
50429
|
-
function onTouchMove(ev) {
|
|
50430
|
-
if (ev.touches.length !== 1)
|
|
50431
|
-
return;
|
|
50432
|
-
// On mobile browsers, swiping down is often associated with "pull to refresh".
|
|
50433
|
-
// We only want this behavior if the grid is already at the top.
|
|
50434
|
-
// Otherwise we only want to move the canvas up, without triggering any refresh.
|
|
50435
|
-
if (canMoveUp()) {
|
|
50436
|
-
ev.preventDefault();
|
|
50437
|
-
ev.stopPropagation();
|
|
50438
|
-
}
|
|
50439
|
-
const currentX = ev.touches[0].clientX;
|
|
50440
|
-
const currentY = ev.touches[0].clientY;
|
|
50441
|
-
handler(x - currentX, y - currentY);
|
|
50442
|
-
x = currentX;
|
|
50443
|
-
y = currentY;
|
|
50444
|
-
}
|
|
50445
|
-
useRefListener(gridRef, "touchstart", onTouchStart);
|
|
50446
|
-
useRefListener(gridRef, "touchend", onTouchEnd);
|
|
50447
|
-
useRefListener(gridRef, "touchmove", onTouchMove);
|
|
50448
|
-
}
|
|
50449
50447
|
class GridOverlay extends Component {
|
|
50450
50448
|
static template = "o-spreadsheet-GridOverlay";
|
|
50451
50449
|
static props = {
|
|
@@ -50493,10 +50491,6 @@ class GridOverlay extends Component {
|
|
|
50493
50491
|
onWillUnmount(() => {
|
|
50494
50492
|
resizeObserver.disconnect();
|
|
50495
50493
|
});
|
|
50496
|
-
useTouchMove(this.gridOverlay, this.props.onGridMoved, () => {
|
|
50497
|
-
const { scrollY } = this.env.model.getters.getActiveSheetScrollInfo();
|
|
50498
|
-
return scrollY > 0;
|
|
50499
|
-
});
|
|
50500
50494
|
this.cellPopovers = useStore(CellPopoverStore);
|
|
50501
50495
|
this.paintFormatStore = useStore(PaintFormatStore);
|
|
50502
50496
|
}
|
|
@@ -51968,6 +51962,73 @@ function useGridDrawing(refName, model, canvasSize) {
|
|
|
51968
51962
|
}
|
|
51969
51963
|
}
|
|
51970
51964
|
|
|
51965
|
+
const friction = 0.95;
|
|
51966
|
+
const verticalScrollFactor = 1;
|
|
51967
|
+
const horizontalScrollFactor = 1;
|
|
51968
|
+
function useTouchScroll(ref, updateScroll, canMoveUp) {
|
|
51969
|
+
let lastX = 0;
|
|
51970
|
+
let lastY = 0;
|
|
51971
|
+
let velocityX = 0;
|
|
51972
|
+
let velocityY = 0;
|
|
51973
|
+
let isMouseDown = false;
|
|
51974
|
+
let lastTime = 0;
|
|
51975
|
+
useRefListener(ref, "touchstart", onTouchStart, { capture: false });
|
|
51976
|
+
useRefListener(ref, "touchmove", onTouchMove, { capture: false });
|
|
51977
|
+
useRefListener(ref, "touchend", onTouchEnd, { capture: false });
|
|
51978
|
+
function onTouchStart(event) {
|
|
51979
|
+
isMouseDown = true;
|
|
51980
|
+
({ clientX: lastX, clientY: lastY } = event.touches[0]);
|
|
51981
|
+
velocityX = 0;
|
|
51982
|
+
velocityY = 0;
|
|
51983
|
+
}
|
|
51984
|
+
function onTouchMove(event) {
|
|
51985
|
+
if (!isMouseDown)
|
|
51986
|
+
return;
|
|
51987
|
+
const currentTime = Date.now();
|
|
51988
|
+
const { clientX, clientY } = event.touches[0];
|
|
51989
|
+
let deltaX = lastX - clientX;
|
|
51990
|
+
let deltaY = lastY - clientY;
|
|
51991
|
+
const elapsedTime = currentTime - lastTime;
|
|
51992
|
+
velocityX = deltaX / elapsedTime;
|
|
51993
|
+
velocityY = deltaY / elapsedTime;
|
|
51994
|
+
lastX = clientX;
|
|
51995
|
+
lastY = clientY;
|
|
51996
|
+
lastTime = currentTime;
|
|
51997
|
+
if (canMoveUp()) {
|
|
51998
|
+
if (event.cancelable) {
|
|
51999
|
+
event.preventDefault();
|
|
52000
|
+
}
|
|
52001
|
+
event.stopPropagation();
|
|
52002
|
+
}
|
|
52003
|
+
updateScroll(deltaX * horizontalScrollFactor, deltaY * verticalScrollFactor);
|
|
52004
|
+
}
|
|
52005
|
+
function onTouchEnd(ev) {
|
|
52006
|
+
isMouseDown = false;
|
|
52007
|
+
lastX = lastY = 0;
|
|
52008
|
+
requestAnimationFrame(scroll);
|
|
52009
|
+
}
|
|
52010
|
+
function scroll() {
|
|
52011
|
+
if (Math.abs(velocityX) < 0.05) {
|
|
52012
|
+
velocityX = 0;
|
|
52013
|
+
}
|
|
52014
|
+
if (Math.abs(velocityY) < 0.05) {
|
|
52015
|
+
velocityY = 0;
|
|
52016
|
+
}
|
|
52017
|
+
if (!velocityX && !velocityY) {
|
|
52018
|
+
return;
|
|
52019
|
+
}
|
|
52020
|
+
const currentTime = Date.now();
|
|
52021
|
+
const elapsedTime = Math.abs(currentTime - lastTime);
|
|
52022
|
+
const deltaX = velocityX * elapsedTime;
|
|
52023
|
+
const deltaY = velocityY * elapsedTime;
|
|
52024
|
+
updateScroll(deltaX * horizontalScrollFactor, deltaY * verticalScrollFactor);
|
|
52025
|
+
lastTime = currentTime;
|
|
52026
|
+
velocityX *= friction;
|
|
52027
|
+
velocityY *= friction;
|
|
52028
|
+
requestAnimationFrame(scroll);
|
|
52029
|
+
}
|
|
52030
|
+
}
|
|
52031
|
+
|
|
51971
52032
|
function useWheelHandler(handler) {
|
|
51972
52033
|
function normalize(val, deltaMode) {
|
|
51973
52034
|
return val * (deltaMode === 0 ? 1 : DEFAULT_CELL_HEIGHT);
|
|
@@ -52308,7 +52369,7 @@ class HorizontalScrollBar extends Component {
|
|
|
52308
52369
|
left: `${this.props.leftOffset + x}px`,
|
|
52309
52370
|
bottom: "0px",
|
|
52310
52371
|
height: `${SCROLLBAR_WIDTH}px`,
|
|
52311
|
-
right: `
|
|
52372
|
+
right: isBrowserFirefox() ? `${SCROLLBAR_WIDTH}px` : "0",
|
|
52312
52373
|
};
|
|
52313
52374
|
}
|
|
52314
52375
|
onScroll(offset) {
|
|
@@ -52353,7 +52414,7 @@ class VerticalScrollBar extends Component {
|
|
|
52353
52414
|
top: `${this.props.topOffset + y}px`,
|
|
52354
52415
|
right: "0px",
|
|
52355
52416
|
width: `${SCROLLBAR_WIDTH}px`,
|
|
52356
|
-
bottom: `
|
|
52417
|
+
bottom: isBrowserFirefox() ? `${SCROLLBAR_WIDTH}px` : "0",
|
|
52357
52418
|
};
|
|
52358
52419
|
}
|
|
52359
52420
|
onScroll(offset) {
|
|
@@ -52589,6 +52650,10 @@ class Grid extends Component {
|
|
|
52589
52650
|
this.DOMFocusableElementStore.focusableElement?.focus();
|
|
52590
52651
|
}
|
|
52591
52652
|
}, () => [this.sidePanel.isOpen]);
|
|
52653
|
+
useTouchScroll(this.gridRef, this.moveCanvas.bind(this), () => {
|
|
52654
|
+
const { scrollY } = this.env.model.getters.getActiveSheetScrollInfo();
|
|
52655
|
+
return scrollY > 0;
|
|
52656
|
+
});
|
|
52592
52657
|
}
|
|
52593
52658
|
onCellHovered({ col, row }) {
|
|
52594
52659
|
this.hoveredCell.hover({ col, row });
|
|
@@ -53311,6 +53376,15 @@ class BordersPlugin extends CorePlugin {
|
|
|
53311
53376
|
case "SET_BORDER":
|
|
53312
53377
|
this.setBorder(cmd.sheetId, cmd.col, cmd.row, cmd.border);
|
|
53313
53378
|
break;
|
|
53379
|
+
case "SET_BORDERS_ON_TARGET":
|
|
53380
|
+
for (const zone of cmd.target) {
|
|
53381
|
+
for (let row = zone.top; row <= zone.bottom; row++) {
|
|
53382
|
+
for (let col = zone.left; col <= zone.right; col++) {
|
|
53383
|
+
this.setBorder(cmd.sheetId, col, row, cmd.border);
|
|
53384
|
+
}
|
|
53385
|
+
}
|
|
53386
|
+
}
|
|
53387
|
+
break;
|
|
53314
53388
|
case "SET_ZONE_BORDERS":
|
|
53315
53389
|
if (cmd.border) {
|
|
53316
53390
|
const target = cmd.target.map((zone) => this.getters.expandZone(cmd.sheetId, zone));
|
|
@@ -63073,25 +63147,6 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63073
63147
|
case "AUTOFILL_AUTO":
|
|
63074
63148
|
this.autofillAuto();
|
|
63075
63149
|
break;
|
|
63076
|
-
case "AUTOFILL_CELL":
|
|
63077
|
-
this.autoFillMerge(cmd.originCol, cmd.originRow, cmd.col, cmd.row);
|
|
63078
|
-
const sheetId = this.getters.getActiveSheetId();
|
|
63079
|
-
this.dispatch("UPDATE_CELL", {
|
|
63080
|
-
sheetId,
|
|
63081
|
-
col: cmd.col,
|
|
63082
|
-
row: cmd.row,
|
|
63083
|
-
style: cmd.style || null,
|
|
63084
|
-
content: cmd.content || "",
|
|
63085
|
-
format: cmd.format || "",
|
|
63086
|
-
});
|
|
63087
|
-
this.dispatch("SET_BORDER", {
|
|
63088
|
-
sheetId,
|
|
63089
|
-
col: cmd.col,
|
|
63090
|
-
row: cmd.row,
|
|
63091
|
-
border: cmd.border,
|
|
63092
|
-
});
|
|
63093
|
-
this.autofillCF(cmd.originCol, cmd.originRow, cmd.col, cmd.row);
|
|
63094
|
-
this.autofillDV(cmd.originCol, cmd.originRow, cmd.col, cmd.row);
|
|
63095
63150
|
}
|
|
63096
63151
|
}
|
|
63097
63152
|
// ---------------------------------------------------------------------------
|
|
@@ -63115,6 +63170,7 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63115
63170
|
}
|
|
63116
63171
|
const source = this.getters.getSelectedZone();
|
|
63117
63172
|
const target = this.autofillZone;
|
|
63173
|
+
const autofillCellsData = [];
|
|
63118
63174
|
switch (this.direction) {
|
|
63119
63175
|
case "down" /* DIRECTION.DOWN */:
|
|
63120
63176
|
for (let col = source.left; col <= source.right; col++) {
|
|
@@ -63124,7 +63180,7 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63124
63180
|
}
|
|
63125
63181
|
const generator = this.createGenerator(xcs);
|
|
63126
63182
|
for (let row = target.top; row <= target.bottom; row++) {
|
|
63127
|
-
this.computeNewCell(generator, col, row
|
|
63183
|
+
autofillCellsData.push(this.computeNewCell(generator, col, row));
|
|
63128
63184
|
}
|
|
63129
63185
|
}
|
|
63130
63186
|
break;
|
|
@@ -63136,7 +63192,7 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63136
63192
|
}
|
|
63137
63193
|
const generator = this.createGenerator(xcs);
|
|
63138
63194
|
for (let row = target.bottom; row >= target.top; row--) {
|
|
63139
|
-
this.computeNewCell(generator, col, row
|
|
63195
|
+
autofillCellsData.push(this.computeNewCell(generator, col, row));
|
|
63140
63196
|
}
|
|
63141
63197
|
}
|
|
63142
63198
|
break;
|
|
@@ -63148,7 +63204,7 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63148
63204
|
}
|
|
63149
63205
|
const generator = this.createGenerator(xcs);
|
|
63150
63206
|
for (let col = target.right; col >= target.left; col--) {
|
|
63151
|
-
this.computeNewCell(generator, col, row
|
|
63207
|
+
autofillCellsData.push(this.computeNewCell(generator, col, row));
|
|
63152
63208
|
}
|
|
63153
63209
|
}
|
|
63154
63210
|
break;
|
|
@@ -63160,12 +63216,26 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63160
63216
|
}
|
|
63161
63217
|
const generator = this.createGenerator(xcs);
|
|
63162
63218
|
for (let col = target.left; col <= target.right; col++) {
|
|
63163
|
-
this.computeNewCell(generator, col, row
|
|
63219
|
+
autofillCellsData.push(this.computeNewCell(generator, col, row));
|
|
63164
63220
|
}
|
|
63165
63221
|
}
|
|
63166
63222
|
break;
|
|
63167
63223
|
}
|
|
63168
63224
|
if (apply) {
|
|
63225
|
+
const bordersZones = {};
|
|
63226
|
+
const cfNewRanges = {};
|
|
63227
|
+
const dvNewZones = {};
|
|
63228
|
+
const sheetId = this.getters.getActiveSheetId();
|
|
63229
|
+
for (const data of autofillCellsData) {
|
|
63230
|
+
this.collectBordersData(data, bordersZones);
|
|
63231
|
+
this.autofillMerge(sheetId, data);
|
|
63232
|
+
this.autofillCell(sheetId, data);
|
|
63233
|
+
this.collectConditionalFormatsData(sheetId, data, cfNewRanges);
|
|
63234
|
+
this.collectDataValidationsData(sheetId, data, dvNewZones);
|
|
63235
|
+
}
|
|
63236
|
+
this.autofillBorders(sheetId, bordersZones);
|
|
63237
|
+
this.autofillConditionalFormats(sheetId, cfNewRanges);
|
|
63238
|
+
this.autofillDataValidations(sheetId, dvNewZones);
|
|
63169
63239
|
this.autofillZone = undefined;
|
|
63170
63240
|
this.selection.resizeAnchorZone(this.direction, this.steps);
|
|
63171
63241
|
this.lastCellSelected = {};
|
|
@@ -63174,6 +63244,95 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63174
63244
|
this.tooltip = undefined;
|
|
63175
63245
|
}
|
|
63176
63246
|
}
|
|
63247
|
+
collectBordersData(data, bordersPositions) {
|
|
63248
|
+
const key = JSON.stringify(data.border);
|
|
63249
|
+
if (!(key in bordersPositions)) {
|
|
63250
|
+
bordersPositions[key] = [];
|
|
63251
|
+
}
|
|
63252
|
+
bordersPositions[key].push(positionToZone({ col: data.col, row: data.row }));
|
|
63253
|
+
}
|
|
63254
|
+
collectConditionalFormatsData(sheetId, data, cfNewRanges) {
|
|
63255
|
+
const { originCol, originRow, col, row } = data;
|
|
63256
|
+
const cfsAtOrigin = this.getters.getRulesByCell(sheetId, originCol, originRow);
|
|
63257
|
+
const xc = toXC(col, row);
|
|
63258
|
+
for (const cf of cfsAtOrigin) {
|
|
63259
|
+
if (!(cf.id in cfNewRanges)) {
|
|
63260
|
+
cfNewRanges[cf.id] = [];
|
|
63261
|
+
}
|
|
63262
|
+
cfNewRanges[cf.id].push(xc);
|
|
63263
|
+
}
|
|
63264
|
+
}
|
|
63265
|
+
collectDataValidationsData(sheetId, data, dvNewZones) {
|
|
63266
|
+
const { originCol, originRow, col, row } = data;
|
|
63267
|
+
const cellPosition = { sheetId, col: originCol, row: originRow };
|
|
63268
|
+
const dvsAtOrigin = this.getters.getValidationRuleForCell(cellPosition);
|
|
63269
|
+
if (!dvsAtOrigin) {
|
|
63270
|
+
return;
|
|
63271
|
+
}
|
|
63272
|
+
if (!(dvsAtOrigin.id in dvNewZones)) {
|
|
63273
|
+
dvNewZones[dvsAtOrigin.id] = [];
|
|
63274
|
+
}
|
|
63275
|
+
dvNewZones[dvsAtOrigin.id].push(positionToZone({ col, row }));
|
|
63276
|
+
}
|
|
63277
|
+
autofillCell(sheetId, data) {
|
|
63278
|
+
this.dispatch("UPDATE_CELL", {
|
|
63279
|
+
sheetId,
|
|
63280
|
+
col: data.col,
|
|
63281
|
+
row: data.row,
|
|
63282
|
+
content: data.content || "",
|
|
63283
|
+
style: data.style || null,
|
|
63284
|
+
format: data.format || "",
|
|
63285
|
+
});
|
|
63286
|
+
// Still usefull in odoo ATM to autofill field sync
|
|
63287
|
+
this.dispatch("AUTOFILL_CELL", data);
|
|
63288
|
+
}
|
|
63289
|
+
autofillBorders(sheetId, bordersPositions) {
|
|
63290
|
+
for (const stringifiedBorder in bordersPositions) {
|
|
63291
|
+
const border = stringifiedBorder === "undefined" ? undefined : JSON.parse(stringifiedBorder);
|
|
63292
|
+
this.dispatch("SET_BORDERS_ON_TARGET", {
|
|
63293
|
+
sheetId,
|
|
63294
|
+
border,
|
|
63295
|
+
target: recomputeZones(bordersPositions[stringifiedBorder]),
|
|
63296
|
+
});
|
|
63297
|
+
}
|
|
63298
|
+
}
|
|
63299
|
+
autofillConditionalFormats(sheetId, cfNewRanges) {
|
|
63300
|
+
for (const cfId in cfNewRanges) {
|
|
63301
|
+
const changes = cfNewRanges[cfId];
|
|
63302
|
+
const cf = this.getters.getConditionalFormats(sheetId).find((cf) => cf.id === cfId);
|
|
63303
|
+
if (!cf) {
|
|
63304
|
+
continue;
|
|
63305
|
+
}
|
|
63306
|
+
const newCfRanges = this.getters.getAdaptedCfRanges(sheetId, cf, changes.map(toZone), []);
|
|
63307
|
+
if (newCfRanges) {
|
|
63308
|
+
this.dispatch("ADD_CONDITIONAL_FORMAT", {
|
|
63309
|
+
cf: {
|
|
63310
|
+
id: cf.id,
|
|
63311
|
+
rule: cf.rule,
|
|
63312
|
+
stopIfTrue: cf.stopIfTrue,
|
|
63313
|
+
},
|
|
63314
|
+
ranges: newCfRanges,
|
|
63315
|
+
sheetId,
|
|
63316
|
+
});
|
|
63317
|
+
}
|
|
63318
|
+
}
|
|
63319
|
+
}
|
|
63320
|
+
autofillDataValidations(sheetId, dvNewZones) {
|
|
63321
|
+
for (const dvId in dvNewZones) {
|
|
63322
|
+
const changes = dvNewZones[dvId];
|
|
63323
|
+
const dvOrigin = this.getters.getDataValidationRule(sheetId, dvId);
|
|
63324
|
+
if (!dvOrigin) {
|
|
63325
|
+
continue;
|
|
63326
|
+
}
|
|
63327
|
+
const dvRangesXcs = dvOrigin.ranges.map((range) => range.zone);
|
|
63328
|
+
const newDvRanges = recomputeZones(dvRangesXcs.concat(changes), []);
|
|
63329
|
+
this.dispatch("ADD_DATA_VALIDATION_RULE", {
|
|
63330
|
+
rule: dvOrigin,
|
|
63331
|
+
ranges: newDvRanges.map((zone) => this.getters.getRangeDataFromZone(sheetId, zone)),
|
|
63332
|
+
sheetId,
|
|
63333
|
+
});
|
|
63334
|
+
}
|
|
63335
|
+
}
|
|
63177
63336
|
/**
|
|
63178
63337
|
* Select a cell which becomes the last cell of the autofillZone
|
|
63179
63338
|
*/
|
|
@@ -63252,22 +63411,20 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63252
63411
|
/**
|
|
63253
63412
|
* Generate the next cell
|
|
63254
63413
|
*/
|
|
63255
|
-
computeNewCell(generator, col, row
|
|
63414
|
+
computeNewCell(generator, col, row) {
|
|
63256
63415
|
const { cellData, tooltip, origin } = generator.next();
|
|
63257
63416
|
const { content, style, border, format } = cellData;
|
|
63258
63417
|
this.tooltip = tooltip;
|
|
63259
|
-
|
|
63260
|
-
|
|
63261
|
-
|
|
63262
|
-
|
|
63263
|
-
|
|
63264
|
-
|
|
63265
|
-
|
|
63266
|
-
|
|
63267
|
-
|
|
63268
|
-
|
|
63269
|
-
});
|
|
63270
|
-
}
|
|
63418
|
+
return {
|
|
63419
|
+
originCol: origin.col,
|
|
63420
|
+
originRow: origin.row,
|
|
63421
|
+
col,
|
|
63422
|
+
row,
|
|
63423
|
+
content,
|
|
63424
|
+
style,
|
|
63425
|
+
border,
|
|
63426
|
+
format,
|
|
63427
|
+
};
|
|
63271
63428
|
}
|
|
63272
63429
|
/**
|
|
63273
63430
|
* Get the rule associated to the current cell
|
|
@@ -63335,8 +63492,8 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63335
63492
|
? position[first].value
|
|
63336
63493
|
: position[second].value;
|
|
63337
63494
|
}
|
|
63338
|
-
|
|
63339
|
-
const
|
|
63495
|
+
autofillMerge(sheetId, data) {
|
|
63496
|
+
const { originCol, originRow, col, row } = data;
|
|
63340
63497
|
const position = { sheetId, col, row };
|
|
63341
63498
|
const originPosition = { sheetId, col: originCol, row: originRow };
|
|
63342
63499
|
if (this.getters.isInMerge(position) && !this.getters.isInMerge(originPosition)) {
|
|
@@ -63363,35 +63520,6 @@ class AutofillPlugin extends UIPlugin {
|
|
|
63363
63520
|
});
|
|
63364
63521
|
}
|
|
63365
63522
|
}
|
|
63366
|
-
autofillCF(originCol, originRow, col, row) {
|
|
63367
|
-
const sheetId = this.getters.getActiveSheetId();
|
|
63368
|
-
const cfOrigin = this.getters.getRulesByCell(sheetId, originCol, originRow);
|
|
63369
|
-
for (const cf of cfOrigin) {
|
|
63370
|
-
const newCfRanges = this.getters.getAdaptedCfRanges(sheetId, cf, [positionToZone({ col, row })], []);
|
|
63371
|
-
if (newCfRanges) {
|
|
63372
|
-
this.dispatch("ADD_CONDITIONAL_FORMAT", {
|
|
63373
|
-
cf: deepCopy(cf),
|
|
63374
|
-
ranges: newCfRanges,
|
|
63375
|
-
sheetId,
|
|
63376
|
-
});
|
|
63377
|
-
}
|
|
63378
|
-
}
|
|
63379
|
-
}
|
|
63380
|
-
autofillDV(originCol, originRow, col, row) {
|
|
63381
|
-
const sheetId = this.getters.getActiveSheetId();
|
|
63382
|
-
const cellPosition = { sheetId, col: originCol, row: originRow };
|
|
63383
|
-
const dvOrigin = this.getters.getValidationRuleForCell(cellPosition);
|
|
63384
|
-
if (!dvOrigin) {
|
|
63385
|
-
return;
|
|
63386
|
-
}
|
|
63387
|
-
const dvRangesZones = dvOrigin.ranges.map((range) => range.zone);
|
|
63388
|
-
const newDvRanges = recomputeZones(dvRangesZones.concat(positionToZone({ col, row })), []);
|
|
63389
|
-
this.dispatch("ADD_DATA_VALIDATION_RULE", {
|
|
63390
|
-
rule: dvOrigin,
|
|
63391
|
-
ranges: newDvRanges.map((zone) => this.getters.getRangeDataFromZone(sheetId, zone)),
|
|
63392
|
-
sheetId,
|
|
63393
|
-
});
|
|
63394
|
-
}
|
|
63395
63523
|
// ---------------------------------------------------------------------------
|
|
63396
63524
|
// Grid rendering
|
|
63397
63525
|
// ---------------------------------------------------------------------------
|
|
@@ -63771,10 +63899,8 @@ function mergeTransformation(toTransform, executed) {
|
|
|
63771
63899
|
}
|
|
63772
63900
|
const target = [];
|
|
63773
63901
|
for (const zone1 of toTransform.target) {
|
|
63774
|
-
|
|
63775
|
-
|
|
63776
|
-
target.push({ ...zone1 });
|
|
63777
|
-
}
|
|
63902
|
+
if (executed.target.every((zone2) => !overlap(zone1, zone2))) {
|
|
63903
|
+
target.push(zone1);
|
|
63778
63904
|
}
|
|
63779
63905
|
}
|
|
63780
63906
|
if (target.length) {
|
|
@@ -67906,24 +68032,14 @@ class InternalViewport {
|
|
|
67906
68032
|
first: this.boundaries.top,
|
|
67907
68033
|
last: this.boundaries.bottom,
|
|
67908
68034
|
});
|
|
67909
|
-
const { end: lastColEnd
|
|
67910
|
-
const { end: lastRowEnd
|
|
67911
|
-
const leftColIndex = this.searchHeaderIndex("COL", lastColEnd - this.viewportWidth, 0);
|
|
67912
|
-
const leftColSize = this.getters.getColSize(this.sheetId, leftColIndex);
|
|
67913
|
-
const leftRowIndex = this.searchHeaderIndex("ROW", lastRowEnd - this.viewportHeight, 0);
|
|
67914
|
-
const topRowSize = this.getters.getRowSize(this.sheetId, leftRowIndex);
|
|
68035
|
+
const { end: lastColEnd } = this.getters.getColDimensions(this.sheetId, lastCol);
|
|
68036
|
+
const { end: lastRowEnd } = this.getters.getRowDimensions(this.sheetId, lastRow);
|
|
67915
68037
|
let width = lastColEnd - this.offsetCorrectionX;
|
|
67916
68038
|
if (this.canScrollHorizontally) {
|
|
67917
|
-
width += Math.max(DEFAULT_CELL_WIDTH, // leave some minimal space to let the user know they scrolled all the way
|
|
67918
|
-
Math.min(leftColSize, this.viewportWidth - lastColSize) // Add pixels that allows the snapping at maximum horizontal scroll
|
|
67919
|
-
);
|
|
67920
68039
|
width = Math.max(width, this.viewportWidth); // if the viewport grid size is smaller than its client width, return client width
|
|
67921
68040
|
}
|
|
67922
68041
|
let height = lastRowEnd - this.offsetCorrectionY;
|
|
67923
68042
|
if (this.canScrollVertically) {
|
|
67924
|
-
height += Math.max(DEFAULT_CELL_HEIGHT + 5, // leave some space to let the user know they scrolled all the way
|
|
67925
|
-
Math.min(topRowSize, this.viewportHeight - lastRowSize) // Add pixels that allows the snapping at maximum vertical scroll
|
|
67926
|
-
);
|
|
67927
68043
|
height = Math.max(height, this.viewportHeight); // if the viewport grid size is smaller than its client height, return client height
|
|
67928
68044
|
if (lastRowEnd + FOOTER_HEIGHT > height && !this.getters.isReadonly()) {
|
|
67929
68045
|
height += FOOTER_HEIGHT;
|
|
@@ -68488,8 +68604,8 @@ class SheetViewPlugin extends UIPlugin {
|
|
|
68488
68604
|
const { width, height } = this.getMainViewportRect();
|
|
68489
68605
|
const viewport = this.getMainInternalViewport(sheetId);
|
|
68490
68606
|
return {
|
|
68491
|
-
maxOffsetX: Math.max(0, width - viewport.viewportWidth
|
|
68492
|
-
maxOffsetY: Math.max(0, height - viewport.viewportHeight
|
|
68607
|
+
maxOffsetX: Math.max(0, width - viewport.viewportWidth),
|
|
68608
|
+
maxOffsetY: Math.max(0, height - viewport.viewportHeight),
|
|
68493
68609
|
};
|
|
68494
68610
|
}
|
|
68495
68611
|
getColRowOffsetInViewport(dimension, referenceHeaderIndex, targetHeaderIndex) {
|
|
@@ -70011,6 +70127,10 @@ class SpreadsheetDashboard extends Component {
|
|
|
70011
70127
|
this.hoveredCell.clear();
|
|
70012
70128
|
});
|
|
70013
70129
|
this.cellPopovers = useStore(CellPopoverStore);
|
|
70130
|
+
useTouchScroll(gridRef, this.moveCanvas.bind(this), () => {
|
|
70131
|
+
const { scrollY } = this.env.model.getters.getActiveSheetScrollInfo();
|
|
70132
|
+
return scrollY > 0;
|
|
70133
|
+
});
|
|
70014
70134
|
}
|
|
70015
70135
|
onCellHovered({ col, row }) {
|
|
70016
70136
|
this.hoveredCell.hover({ col, row });
|
|
@@ -71401,6 +71521,7 @@ css /* scss */ `
|
|
|
71401
71521
|
> canvas {
|
|
71402
71522
|
box-sizing: content-box;
|
|
71403
71523
|
border-bottom: 1px solid #e2e3e3;
|
|
71524
|
+
border-right: 1px solid #e2e3e3;
|
|
71404
71525
|
}
|
|
71405
71526
|
|
|
71406
71527
|
.o-grid-overlay {
|
|
@@ -76062,6 +76183,6 @@ const chartHelpers = { ...CHART_HELPERS, ...CHART_RUNTIME_HELPERS };
|
|
|
76062
76183
|
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 };
|
|
76063
76184
|
|
|
76064
76185
|
|
|
76065
|
-
__info__.version = "18.2.
|
|
76066
|
-
__info__.date = "2025-04-
|
|
76067
|
-
__info__.hash = "
|
|
76186
|
+
__info__.version = "18.2.8";
|
|
76187
|
+
__info__.date = "2025-04-18T16:26:20.673Z";
|
|
76188
|
+
__info__.hash = "5da9ddc";
|