@odoo/o-spreadsheet 18.5.0-alpha.11 → 18.5.0-alpha.12
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 +145 -42
- package/dist/o-spreadsheet.d.ts +167 -142
- package/dist/o-spreadsheet.esm.js +145 -42
- package/dist/o-spreadsheet.iife.js +145 -42
- package/dist/o-spreadsheet.iife.min.js +286 -286
- package/dist/o_spreadsheet.xml +18 -5
- 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.5.0-alpha.
|
|
6
|
-
* @date 2025-08-
|
|
7
|
-
* @hash
|
|
5
|
+
* @version 18.5.0-alpha.12
|
|
6
|
+
* @date 2025-08-29T08:05:09.767Z
|
|
7
|
+
* @hash 8ee7677
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
'use strict';
|
|
@@ -1347,6 +1347,18 @@ function hslaToHex(hsla) {
|
|
|
1347
1347
|
function hexToHSLA(hex) {
|
|
1348
1348
|
return rgbaToHSLA(colorToRGBA(hex));
|
|
1349
1349
|
}
|
|
1350
|
+
/**
|
|
1351
|
+
* Blend color2 on top of color1, with alpha blending.
|
|
1352
|
+
*/
|
|
1353
|
+
function blendColors(color1, color2) {
|
|
1354
|
+
const rgba2 = colorToRGBA(color2);
|
|
1355
|
+
const rgba1 = colorToRGBA(color1);
|
|
1356
|
+
const a = rgba2.a + rgba1.a * (1 - rgba2.a);
|
|
1357
|
+
const r = Math.round((rgba2.r * rgba2.a + rgba1.r * rgba1.a * (1 - rgba2.a)) / a);
|
|
1358
|
+
const g = Math.round((rgba2.g * rgba2.a + rgba1.g * rgba1.a * (1 - rgba2.a)) / a);
|
|
1359
|
+
const b = Math.round((rgba2.b * rgba2.a + rgba1.b * rgba1.a * (1 - rgba2.a)) / a);
|
|
1360
|
+
return rgbaToHex({ r, g, b, a });
|
|
1361
|
+
}
|
|
1350
1362
|
function colorOrNumberToRGBA(color) {
|
|
1351
1363
|
if (typeof color === "number") {
|
|
1352
1364
|
return colorToRGBA(colorNumberToHex(color));
|
|
@@ -2661,6 +2673,7 @@ const invalidateBordersCommands = new Set([
|
|
|
2661
2673
|
"AUTOFILL_CELL",
|
|
2662
2674
|
"SET_BORDER",
|
|
2663
2675
|
"SET_ZONE_BORDERS",
|
|
2676
|
+
"SET_BORDERS_ON_TARGET",
|
|
2664
2677
|
]);
|
|
2665
2678
|
const invalidSubtotalFormulasCommands = new Set([
|
|
2666
2679
|
"UNHIDE_COLUMNS_ROWS",
|
|
@@ -2688,6 +2701,7 @@ const readonlyAllowedCommands = new Set([
|
|
|
2688
2701
|
"UPDATE_FILTER",
|
|
2689
2702
|
"UPDATE_CHART",
|
|
2690
2703
|
"UPDATE_CAROUSEL_ACTIVE_ITEM",
|
|
2704
|
+
"UPDATE_PIVOT",
|
|
2691
2705
|
]);
|
|
2692
2706
|
const coreTypes = new Set([
|
|
2693
2707
|
/** CELLS */
|
|
@@ -46926,18 +46940,18 @@ const pivotProperties = {
|
|
|
46926
46940
|
};
|
|
46927
46941
|
const pivotSortingAsc = {
|
|
46928
46942
|
name: _t("Ascending"),
|
|
46929
|
-
execute: (env) => sortPivot(env, "asc"),
|
|
46930
|
-
isActive: (env) =>
|
|
46943
|
+
execute: (env) => sortPivot(env, env.model.getters.getActivePosition(), "asc"),
|
|
46944
|
+
isActive: (env) => env.model.getters.getPivotCellSortDirection(env.model.getters.getActivePosition()) === "asc",
|
|
46931
46945
|
};
|
|
46932
46946
|
const pivotSortingDesc = {
|
|
46933
46947
|
name: _t("Descending"),
|
|
46934
|
-
execute: (env) => sortPivot(env, "desc"),
|
|
46935
|
-
isActive: (env) =>
|
|
46948
|
+
execute: (env) => sortPivot(env, env.model.getters.getActivePosition(), "desc"),
|
|
46949
|
+
isActive: (env) => env.model.getters.getPivotCellSortDirection(env.model.getters.getActivePosition()) === "desc",
|
|
46936
46950
|
};
|
|
46937
46951
|
const noPivotSorting = {
|
|
46938
46952
|
name: _t("No sorting"),
|
|
46939
|
-
execute: (env) => sortPivot(env, "none"),
|
|
46940
|
-
isActive: (env) =>
|
|
46953
|
+
execute: (env) => sortPivot(env, env.model.getters.getActivePosition(), "none"),
|
|
46954
|
+
isActive: (env) => env.model.getters.getPivotCellSortDirection(env.model.getters.getActivePosition()) === "none",
|
|
46941
46955
|
};
|
|
46942
46956
|
const FIX_FORMULAS = {
|
|
46943
46957
|
name: _t("Convert to individual formulas"),
|
|
@@ -47073,23 +47087,19 @@ const ungroupPivotHeadersAction = {
|
|
|
47073
47087
|
return areFieldValuesInGroups(definition, values, field, pivot.getFields());
|
|
47074
47088
|
},
|
|
47075
47089
|
};
|
|
47076
|
-
function canSortPivot(
|
|
47077
|
-
const
|
|
47078
|
-
|
|
47079
|
-
if (!pivotId ||
|
|
47080
|
-
!env.model.getters.isExistingPivot(pivotId) ||
|
|
47081
|
-
!env.model.getters.isSpillPivotFormula(position)) {
|
|
47090
|
+
function canSortPivot(getters, position) {
|
|
47091
|
+
const pivotId = getters.getPivotIdFromPosition(position);
|
|
47092
|
+
if (!pivotId || !getters.isExistingPivot(pivotId) || !getters.isSpillPivotFormula(position)) {
|
|
47082
47093
|
return false;
|
|
47083
47094
|
}
|
|
47084
|
-
const pivot =
|
|
47095
|
+
const pivot = getters.getPivot(pivotId);
|
|
47085
47096
|
if (!pivot.isValid()) {
|
|
47086
47097
|
return false;
|
|
47087
47098
|
}
|
|
47088
|
-
const pivotCell =
|
|
47099
|
+
const pivotCell = getters.getPivotCellFromPosition(position);
|
|
47089
47100
|
return pivotCell.type === "VALUE" || pivotCell.type === "MEASURE_HEADER";
|
|
47090
47101
|
}
|
|
47091
|
-
function sortPivot(env, order) {
|
|
47092
|
-
const position = env.model.getters.getActivePosition();
|
|
47102
|
+
function sortPivot(env, position, order) {
|
|
47093
47103
|
const pivotId = env.model.getters.getPivotIdFromPosition(position);
|
|
47094
47104
|
const pivotCell = env.model.getters.getPivotCellFromPosition(position);
|
|
47095
47105
|
if (pivotCell.type === "EMPTY" || pivotCell.type === "HEADER" || !pivotId) {
|
|
@@ -47115,24 +47125,6 @@ function sortPivot(env, order) {
|
|
|
47115
47125
|
},
|
|
47116
47126
|
});
|
|
47117
47127
|
}
|
|
47118
|
-
function isPivotSortMenuItemActive(env, order) {
|
|
47119
|
-
const position = env.model.getters.getActivePosition();
|
|
47120
|
-
const pivotId = env.model.getters.getPivotIdFromPosition(position);
|
|
47121
|
-
const pivotCell = env.model.getters.getPivotCellFromPosition(position);
|
|
47122
|
-
if (pivotCell.type === "EMPTY" || pivotCell.type === "HEADER" || !pivotId) {
|
|
47123
|
-
return false;
|
|
47124
|
-
}
|
|
47125
|
-
const pivot = env.model.getters.getPivot(pivotId);
|
|
47126
|
-
const colDomain = domainToColRowDomain(pivot, pivotCell.domain).colDomain;
|
|
47127
|
-
const sortedColumn = pivot.definition.sortedColumn;
|
|
47128
|
-
if (order === "none") {
|
|
47129
|
-
return !sortedColumn;
|
|
47130
|
-
}
|
|
47131
|
-
if (!sortedColumn || sortedColumn.order !== order) {
|
|
47132
|
-
return false;
|
|
47133
|
-
}
|
|
47134
|
-
return sortedColumn.measure === pivotCell.measure && deepEquals(sortedColumn.domain, colDomain);
|
|
47135
|
-
}
|
|
47136
47128
|
/*
|
|
47137
47129
|
* Get the values of the pivot headers in the current selection, if all the pivot headers on the selection belong
|
|
47138
47130
|
* to the same pivot, the same field and that the pivot formula is a dynamic pivot. Otherwise return undefined.
|
|
@@ -47435,7 +47427,10 @@ cellMenuRegistry
|
|
|
47435
47427
|
name: _t("Sort pivot"),
|
|
47436
47428
|
sequence: 155,
|
|
47437
47429
|
icon: "o-spreadsheet-Icon.SORT_RANGE",
|
|
47438
|
-
isVisible:
|
|
47430
|
+
isVisible: (env) => {
|
|
47431
|
+
const position = env.model.getters.getActivePosition();
|
|
47432
|
+
return canSortPivot(env.model.getters, position);
|
|
47433
|
+
},
|
|
47439
47434
|
})
|
|
47440
47435
|
.add("pivot_fix_formulas", {
|
|
47441
47436
|
...FIX_FORMULAS,
|
|
@@ -60701,6 +60696,42 @@ class Grid extends owl.Component {
|
|
|
60701
60696
|
const supportedPivotPositionalFormulaRegistry = new Registry();
|
|
60702
60697
|
supportedPivotPositionalFormulaRegistry.add("SPREADSHEET", false);
|
|
60703
60698
|
|
|
60699
|
+
class ClickableCellSortIcon extends owl.Component {
|
|
60700
|
+
static template = "o-spreadsheet-ClickableCellSortIcon";
|
|
60701
|
+
static props = {
|
|
60702
|
+
position: Object,
|
|
60703
|
+
sortDirection: String,
|
|
60704
|
+
};
|
|
60705
|
+
hoveredTableStore;
|
|
60706
|
+
setup() {
|
|
60707
|
+
this.hoveredTableStore = useStore(HoveredTableStore);
|
|
60708
|
+
}
|
|
60709
|
+
get style() {
|
|
60710
|
+
const cellStyle = this.env.model.getters.getCellComputedStyle(this.props.position);
|
|
60711
|
+
return cssPropertiesToCss({
|
|
60712
|
+
color: cellStyle.textColor || TEXT_BODY_MUTED,
|
|
60713
|
+
"background-color": this.getBackgroundColor(cellStyle),
|
|
60714
|
+
});
|
|
60715
|
+
}
|
|
60716
|
+
get icon() {
|
|
60717
|
+
switch (this.props.sortDirection) {
|
|
60718
|
+
case "asc":
|
|
60719
|
+
return "fa-sort-asc";
|
|
60720
|
+
case "desc":
|
|
60721
|
+
return "fa-sort-desc";
|
|
60722
|
+
default:
|
|
60723
|
+
return "fa-sort";
|
|
60724
|
+
}
|
|
60725
|
+
}
|
|
60726
|
+
getBackgroundColor(cellStyle) {
|
|
60727
|
+
const overlayColor = this.hoveredTableStore.overlayColors.get(this.props.position);
|
|
60728
|
+
if (overlayColor) {
|
|
60729
|
+
return blendColors(cellStyle.fillColor || "#FFFFFF", overlayColor);
|
|
60730
|
+
}
|
|
60731
|
+
return cellStyle.fillColor || "#FFFFFF";
|
|
60732
|
+
}
|
|
60733
|
+
}
|
|
60734
|
+
|
|
60704
60735
|
class FullScreenChart extends owl.Component {
|
|
60705
60736
|
static template = "o-spreadsheet-FullScreenChart";
|
|
60706
60737
|
static props = {};
|
|
@@ -71057,6 +71088,7 @@ class PivotUIPlugin extends CoreViewPlugin {
|
|
|
71057
71088
|
static getters = [
|
|
71058
71089
|
"getPivot",
|
|
71059
71090
|
"getFirstPivotFunction",
|
|
71091
|
+
"getPivotCellSortDirection",
|
|
71060
71092
|
"getPivotIdFromPosition",
|
|
71061
71093
|
"getPivotCellFromPosition",
|
|
71062
71094
|
"generateNewCalculatedMeasureName",
|
|
@@ -71277,6 +71309,20 @@ class PivotUIPlugin extends CoreViewPlugin {
|
|
|
71277
71309
|
isPivotUnused(pivotId) {
|
|
71278
71310
|
return this._getUnusedPivots().includes(pivotId);
|
|
71279
71311
|
}
|
|
71312
|
+
getPivotCellSortDirection(position) {
|
|
71313
|
+
const pivotId = this.getters.getPivotIdFromPosition(position);
|
|
71314
|
+
const pivotCell = this.getters.getPivotCellFromPosition(position);
|
|
71315
|
+
if (pivotCell.type === "EMPTY" || pivotCell.type === "HEADER" || !pivotId) {
|
|
71316
|
+
return undefined;
|
|
71317
|
+
}
|
|
71318
|
+
const pivot = this.getters.getPivot(pivotId);
|
|
71319
|
+
const colDomain = domainToColRowDomain(pivot, pivotCell.domain).colDomain;
|
|
71320
|
+
const sortedColumn = pivot.definition.sortedColumn;
|
|
71321
|
+
if (sortedColumn?.measure === pivotCell.measure && deepEquals(sortedColumn.domain, colDomain)) {
|
|
71322
|
+
return sortedColumn.order;
|
|
71323
|
+
}
|
|
71324
|
+
return "none";
|
|
71325
|
+
}
|
|
71280
71326
|
// ---------------------------------------------------------------------
|
|
71281
71327
|
// Private
|
|
71282
71328
|
// ---------------------------------------------------------------------
|
|
@@ -78969,6 +79015,34 @@ clickableCellRegistry.add("link", {
|
|
|
78969
79015
|
},
|
|
78970
79016
|
sequence: 5,
|
|
78971
79017
|
});
|
|
79018
|
+
clickableCellRegistry.add("dashboard_pivot_sorting", {
|
|
79019
|
+
condition: (position, getters) => {
|
|
79020
|
+
if (!getters.isDashboard()) {
|
|
79021
|
+
return false;
|
|
79022
|
+
}
|
|
79023
|
+
const pivotCell = getters.getPivotCellFromPosition(position);
|
|
79024
|
+
return canSortPivot(getters, position) && pivotCell.type === "MEASURE_HEADER";
|
|
79025
|
+
},
|
|
79026
|
+
execute: (position, env) => {
|
|
79027
|
+
sortPivot(env, position, getNextSortDirection(env.model.getters, position));
|
|
79028
|
+
},
|
|
79029
|
+
component: ClickableCellSortIcon,
|
|
79030
|
+
componentProps: (position, getters) => {
|
|
79031
|
+
return {
|
|
79032
|
+
position,
|
|
79033
|
+
sortDirection: getters.getPivotCellSortDirection(position),
|
|
79034
|
+
};
|
|
79035
|
+
},
|
|
79036
|
+
sequence: 2,
|
|
79037
|
+
});
|
|
79038
|
+
const NEXT_SORT_DIRECTION = {
|
|
79039
|
+
none: "asc",
|
|
79040
|
+
asc: "desc",
|
|
79041
|
+
desc: "none",
|
|
79042
|
+
};
|
|
79043
|
+
function getNextSortDirection(getters, position) {
|
|
79044
|
+
return NEXT_SORT_DIRECTION[getters.getPivotCellSortDirection(position) ?? "none"];
|
|
79045
|
+
}
|
|
78972
79046
|
|
|
78973
79047
|
const inverseCommandRegistry = new Registry()
|
|
78974
79048
|
.add("ADD_COLUMNS_ROWS", inverseAddColumnsRows)
|
|
@@ -80685,6 +80759,8 @@ class ClickableCellsStore extends SpreadsheetStore {
|
|
|
80685
80759
|
position,
|
|
80686
80760
|
action: item.execute,
|
|
80687
80761
|
title: title || "",
|
|
80762
|
+
component: item.component,
|
|
80763
|
+
componentProps: item.componentProps?.(position, getters) ?? {},
|
|
80688
80764
|
});
|
|
80689
80765
|
}
|
|
80690
80766
|
return cells;
|
|
@@ -83031,6 +83107,27 @@ class Spreadsheet extends owl.Component {
|
|
|
83031
83107
|
}
|
|
83032
83108
|
}
|
|
83033
83109
|
|
|
83110
|
+
class ReadonlyTransportFilter {
|
|
83111
|
+
transportService;
|
|
83112
|
+
constructor(transportService) {
|
|
83113
|
+
this.transportService = transportService;
|
|
83114
|
+
}
|
|
83115
|
+
async sendMessage(message) {
|
|
83116
|
+
if (message.type === "CLIENT_JOINED" ||
|
|
83117
|
+
message.type === "CLIENT_LEFT" ||
|
|
83118
|
+
message.type === "CLIENT_MOVED") {
|
|
83119
|
+
this.transportService.sendMessage(message);
|
|
83120
|
+
}
|
|
83121
|
+
// ignore all other messages
|
|
83122
|
+
}
|
|
83123
|
+
onNewMessage(id, callback) {
|
|
83124
|
+
this.transportService.onNewMessage(id, callback);
|
|
83125
|
+
}
|
|
83126
|
+
leave(id) {
|
|
83127
|
+
this.transportService.leave(id);
|
|
83128
|
+
}
|
|
83129
|
+
}
|
|
83130
|
+
|
|
83034
83131
|
function inverseCommand(cmd) {
|
|
83035
83132
|
return inverseCommandRegistry.get(cmd.type)(cmd);
|
|
83036
83133
|
}
|
|
@@ -87123,12 +87220,15 @@ class Model extends EventBus {
|
|
|
87123
87220
|
name: _t("Anonymous").toString(),
|
|
87124
87221
|
};
|
|
87125
87222
|
const transportService = config.transportService || new LocalTransportService();
|
|
87223
|
+
const isReadonly = config.mode === "readonly" || config.mode === "dashboard";
|
|
87126
87224
|
return {
|
|
87127
87225
|
...config,
|
|
87128
87226
|
mode: config.mode || "normal",
|
|
87129
87227
|
custom: config.custom || {},
|
|
87130
87228
|
external: this.setupExternalConfig(config.external || {}),
|
|
87131
|
-
transportService
|
|
87229
|
+
transportService: isReadonly
|
|
87230
|
+
? new ReadonlyTransportFilter(transportService)
|
|
87231
|
+
: transportService,
|
|
87132
87232
|
client,
|
|
87133
87233
|
moveClient: () => { },
|
|
87134
87234
|
snapshotRequested: false,
|
|
@@ -87541,6 +87641,7 @@ const components = {
|
|
|
87541
87641
|
ChartPanel,
|
|
87542
87642
|
ChartFigure,
|
|
87543
87643
|
ChartJsComponent,
|
|
87644
|
+
ClickableCellSortIcon,
|
|
87544
87645
|
ZoomableChartJsComponent,
|
|
87545
87646
|
Grid,
|
|
87546
87647
|
GridOverlay,
|
|
@@ -87626,6 +87727,8 @@ const constants = {
|
|
|
87626
87727
|
PIVOT_TABLE_CONFIG,
|
|
87627
87728
|
ChartTerms,
|
|
87628
87729
|
FIGURE_ID_SPLITTER,
|
|
87730
|
+
GRID_ICON_EDGE_LENGTH,
|
|
87731
|
+
GRID_ICON_MARGIN,
|
|
87629
87732
|
};
|
|
87630
87733
|
const chartHelpers = { ...CHART_HELPERS, ...CHART_RUNTIME_HELPERS };
|
|
87631
87734
|
|
|
@@ -87680,6 +87783,6 @@ exports.tokenColors = tokenColors;
|
|
|
87680
87783
|
exports.tokenize = tokenize;
|
|
87681
87784
|
|
|
87682
87785
|
|
|
87683
|
-
__info__.version = "18.5.0-alpha.
|
|
87684
|
-
__info__.date = "2025-08-
|
|
87685
|
-
__info__.hash = "
|
|
87786
|
+
__info__.version = "18.5.0-alpha.12";
|
|
87787
|
+
__info__.date = "2025-08-29T08:05:09.767Z";
|
|
87788
|
+
__info__.hash = "8ee7677";
|