@perses-dev/components 0.55.0-beta.12 → 0.55.0-beta.14
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/FormatControls/FormatControls.d.ts.map +1 -1
- package/dist/FormatControls/FormatControls.js +42 -4
- package/dist/FormatControls/FormatControls.js.map +1 -1
- package/dist/FormatControls/UnitSelector.js +4 -4
- package/dist/FormatControls/UnitSelector.js.map +1 -1
- package/dist/TimeSeriesTooltip/utils.d.ts.map +1 -1
- package/dist/TimeSeriesTooltip/utils.js +6 -2
- package/dist/TimeSeriesTooltip/utils.js.map +1 -1
- package/dist/model/custom.d.ts +22 -0
- package/dist/model/custom.d.ts.map +1 -0
- package/dist/model/custom.js +243 -0
- package/dist/model/custom.js.map +1 -0
- package/dist/model/index.d.ts +1 -0
- package/dist/model/index.d.ts.map +1 -1
- package/dist/model/index.js +1 -0
- package/dist/model/index.js.map +1 -1
- package/dist/model/units.d.ts +12 -10
- package/dist/model/units.d.ts.map +1 -1
- package/dist/model/units.js +33 -28
- package/dist/model/units.js.map +1 -1
- package/package.json +3 -3
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"FormatControls.d.ts","sourceRoot":"","sources":["../../src/FormatControls/FormatControls.tsx"],"names":[],"mappings":"AAcA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AAE1C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAM9C,MAAM,WAAW,mBAAmB;IAClC,KAAK,EAAE,aAAa,CAAC;IACrB,QAAQ,EAAE,CAAC,IAAI,EAAE,aAAa,KAAK,IAAI,CAAC;IACxC,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAiBD,wBAAgB,cAAc,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,QAAgB,EAAE,EAAE,mBAAmB,GAAG,YAAY,
|
|
1
|
+
{"version":3,"file":"FormatControls.d.ts","sourceRoot":"","sources":["../../src/FormatControls/FormatControls.tsx"],"names":[],"mappings":"AAcA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AAE1C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAM9C,MAAM,WAAW,mBAAmB;IAClC,KAAK,EAAE,aAAa,CAAC;IACrB,QAAQ,EAAE,CAAC,IAAI,EAAE,aAAa,KAAK,IAAI,CAAC;IACxC,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAiBD,wBAAgB,cAAc,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,QAAgB,EAAE,EAAE,mBAAmB,GAAG,YAAY,CAkGvG"}
|
|
@@ -11,8 +11,8 @@
|
|
|
11
11
|
// See the License for the specific language governing permissions and
|
|
12
12
|
// limitations under the License.
|
|
13
13
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
14
|
-
import { Switch } from "@mui/material";
|
|
15
|
-
import { isUnitWithDecimalPlaces, isUnitWithShortValues, shouldShortenValues } from "../model/index.js";
|
|
14
|
+
import { Switch, TextField } from "@mui/material";
|
|
15
|
+
import { isUnitWithDecimalPlaces, isUnitWithShortValues, shouldShortenValues, supportsCustomLabel } from "../model/index.js";
|
|
16
16
|
import { OptionsEditorControl } from "../OptionsEditorLayout/index.js";
|
|
17
17
|
import { SettingsAutocomplete } from "../SettingsAutocomplete/index.js";
|
|
18
18
|
import { UnitSelector } from "./UnitSelector.js";
|
|
@@ -55,10 +55,21 @@ export function FormatControls({ value, onChange, disabled = false }) {
|
|
|
55
55
|
const hasDecimalPlaces = isUnitWithDecimalPlaces(value);
|
|
56
56
|
const hasShortValues = isUnitWithShortValues(value);
|
|
57
57
|
const handleUnitChange = (newValue)=>{
|
|
58
|
-
|
|
58
|
+
const next = newValue || {
|
|
59
59
|
unit: 'decimal'
|
|
60
|
-
}
|
|
60
|
+
};
|
|
61
|
+
const customLabel = value.customLabel?.trim();
|
|
62
|
+
// Keep label only when the new unit supports customLabel (whitelist).
|
|
63
|
+
if (customLabel && supportsCustomLabel(next.unit)) {
|
|
64
|
+
onChange({
|
|
65
|
+
...next,
|
|
66
|
+
customLabel: value.customLabel
|
|
67
|
+
});
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
onChange(next);
|
|
61
71
|
};
|
|
72
|
+
const showCustomLabel = supportsCustomLabel(value.unit);
|
|
62
73
|
const handleDecimalPlacesChange = ({ decimalPlaces })=>{
|
|
63
74
|
if (hasDecimalPlaces) {
|
|
64
75
|
onChange({
|
|
@@ -75,6 +86,18 @@ export function FormatControls({ value, onChange, disabled = false }) {
|
|
|
75
86
|
});
|
|
76
87
|
}
|
|
77
88
|
};
|
|
89
|
+
const handleCustomLabelChange = (raw)=>{
|
|
90
|
+
// Keep raw input while typing (spaces allowed). Trim only when clearing / display.
|
|
91
|
+
if (raw === '') {
|
|
92
|
+
const { customLabel: _removed, ...rest } = value;
|
|
93
|
+
onChange(rest);
|
|
94
|
+
return;
|
|
95
|
+
}
|
|
96
|
+
onChange({
|
|
97
|
+
...value,
|
|
98
|
+
customLabel: raw
|
|
99
|
+
});
|
|
100
|
+
};
|
|
78
101
|
return /*#__PURE__*/ _jsxs(_Fragment, {
|
|
79
102
|
children: [
|
|
80
103
|
/*#__PURE__*/ _jsx(OptionsEditorControl, {
|
|
@@ -93,6 +116,21 @@ export function FormatControls({ value, onChange, disabled = false }) {
|
|
|
93
116
|
disabled: disabled
|
|
94
117
|
})
|
|
95
118
|
}),
|
|
119
|
+
showCustomLabel && /*#__PURE__*/ _jsx(OptionsEditorControl, {
|
|
120
|
+
label: "Custom label",
|
|
121
|
+
control: /*#__PURE__*/ _jsx(TextField, {
|
|
122
|
+
size: "small",
|
|
123
|
+
fullWidth: true,
|
|
124
|
+
value: value.customLabel ?? '',
|
|
125
|
+
onChange: (e)=>handleCustomLabelChange(e.target.value),
|
|
126
|
+
placeholder: "Optional display override (e.g. pnr/mn)",
|
|
127
|
+
disabled: disabled,
|
|
128
|
+
inputProps: {
|
|
129
|
+
'aria-label': 'custom unit label',
|
|
130
|
+
maxLength: 32
|
|
131
|
+
}
|
|
132
|
+
})
|
|
133
|
+
}),
|
|
96
134
|
/*#__PURE__*/ _jsx(OptionsEditorControl, {
|
|
97
135
|
label: "Decimals",
|
|
98
136
|
control: /*#__PURE__*/ _jsx(SettingsAutocomplete, {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/FormatControls/FormatControls.tsx"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\nimport type { SwitchProps } from '@mui/material';\nimport { Switch } from '@mui/material';\nimport type { ReactElement } from 'react';\n\nimport type { FormatOptions } from '../model';\nimport { isUnitWithDecimalPlaces, isUnitWithShortValues, shouldShortenValues } from '../model';\nimport { OptionsEditorControl } from '../OptionsEditorLayout';\nimport { SettingsAutocomplete } from '../SettingsAutocomplete';\nimport { UnitSelector } from './UnitSelector';\n\nexport interface FormatControlsProps {\n value: FormatOptions;\n onChange: (unit: FormatOptions) => void;\n disabled?: boolean;\n}\n\nconst DECIMAL_PLACES_OPTIONS: Array<{ id: string; label: string; decimalPlaces?: number }> = [\n { id: 'default', label: 'Default', decimalPlaces: undefined },\n { id: '0', label: '0', decimalPlaces: 0 },\n { id: '1', label: '1', decimalPlaces: 1 },\n { id: '2', label: '2', decimalPlaces: 2 },\n { id: '3', label: '3', decimalPlaces: 3 },\n { id: '4', label: '4', decimalPlaces: 4 },\n];\n\nfunction getOptionByDecimalPlaces(\n decimalPlaces?: number,\n): { id: string; label: string; decimalPlaces?: number } | undefined {\n return DECIMAL_PLACES_OPTIONS.find((o) => o.decimalPlaces === decimalPlaces);\n}\n\nexport function FormatControls({ value, onChange, disabled = false }: FormatControlsProps): ReactElement {\n const hasDecimalPlaces = isUnitWithDecimalPlaces(value);\n const hasShortValues = isUnitWithShortValues(value);\n\n const handleUnitChange = (newValue: FormatOptions | undefined): void => {\n
|
|
1
|
+
{"version":3,"sources":["../../src/FormatControls/FormatControls.tsx"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\nimport type { SwitchProps } from '@mui/material';\nimport { Switch, TextField } from '@mui/material';\nimport type { ReactElement } from 'react';\n\nimport type { FormatOptions } from '../model';\nimport { isUnitWithDecimalPlaces, isUnitWithShortValues, shouldShortenValues, supportsCustomLabel } from '../model';\nimport { OptionsEditorControl } from '../OptionsEditorLayout';\nimport { SettingsAutocomplete } from '../SettingsAutocomplete';\nimport { UnitSelector } from './UnitSelector';\n\nexport interface FormatControlsProps {\n value: FormatOptions;\n onChange: (unit: FormatOptions) => void;\n disabled?: boolean;\n}\n\nconst DECIMAL_PLACES_OPTIONS: Array<{ id: string; label: string; decimalPlaces?: number }> = [\n { id: 'default', label: 'Default', decimalPlaces: undefined },\n { id: '0', label: '0', decimalPlaces: 0 },\n { id: '1', label: '1', decimalPlaces: 1 },\n { id: '2', label: '2', decimalPlaces: 2 },\n { id: '3', label: '3', decimalPlaces: 3 },\n { id: '4', label: '4', decimalPlaces: 4 },\n];\n\nfunction getOptionByDecimalPlaces(\n decimalPlaces?: number,\n): { id: string; label: string; decimalPlaces?: number } | undefined {\n return DECIMAL_PLACES_OPTIONS.find((o) => o.decimalPlaces === decimalPlaces);\n}\n\nexport function FormatControls({ value, onChange, disabled = false }: FormatControlsProps): ReactElement {\n const hasDecimalPlaces = isUnitWithDecimalPlaces(value);\n const hasShortValues = isUnitWithShortValues(value);\n\n const handleUnitChange = (newValue: FormatOptions | undefined): void => {\n const next = newValue || { unit: 'decimal' };\n const customLabel = value.customLabel?.trim();\n // Keep label only when the new unit supports customLabel (whitelist).\n if (customLabel && supportsCustomLabel(next.unit)) {\n onChange({ ...next, customLabel: value.customLabel });\n return;\n }\n onChange(next);\n };\n\n const showCustomLabel = supportsCustomLabel(value.unit);\n\n const handleDecimalPlacesChange = ({\n decimalPlaces,\n }: {\n id: string;\n label: string;\n decimalPlaces?: number;\n }): void => {\n if (hasDecimalPlaces) {\n onChange({\n ...value,\n decimalPlaces: decimalPlaces,\n });\n }\n };\n\n const handleShortValuesChange: SwitchProps['onChange'] = (_: unknown, checked: boolean) => {\n if (hasShortValues) {\n onChange({\n ...value,\n shortValues: checked,\n });\n }\n };\n\n const handleCustomLabelChange = (raw: string): void => {\n // Keep raw input while typing (spaces allowed). Trim only when clearing / display.\n if (raw === '') {\n const { customLabel: _removed, ...rest } = value;\n onChange(rest as FormatOptions);\n return;\n }\n onChange({ ...value, customLabel: raw });\n };\n\n return (\n <>\n <OptionsEditorControl\n label=\"Short values\"\n control={\n <Switch\n checked={hasShortValues ? shouldShortenValues(value.shortValues) : false}\n onChange={handleShortValuesChange}\n disabled={!hasShortValues}\n />\n }\n />\n <OptionsEditorControl\n label=\"Unit\"\n control={<UnitSelector value={value} onChange={handleUnitChange} disabled={disabled} />}\n />\n {showCustomLabel && (\n <OptionsEditorControl\n label=\"Custom label\"\n control={\n <TextField\n size=\"small\"\n fullWidth\n value={value.customLabel ?? ''}\n onChange={(e) => handleCustomLabelChange(e.target.value)}\n placeholder=\"Optional display override (e.g. pnr/mn)\"\n disabled={disabled}\n inputProps={{ 'aria-label': 'custom unit label', maxLength: 32 }}\n />\n }\n />\n )}\n <OptionsEditorControl\n label=\"Decimals\"\n control={\n <SettingsAutocomplete\n value={getOptionByDecimalPlaces(value.decimalPlaces)}\n options={DECIMAL_PLACES_OPTIONS}\n getOptionLabel={(o) => o.label}\n onChange={(_, value) => handleDecimalPlacesChange(value)}\n disabled={!hasDecimalPlaces}\n disableClearable\n />\n }\n />\n </>\n );\n}\n"],"names":["Switch","TextField","isUnitWithDecimalPlaces","isUnitWithShortValues","shouldShortenValues","supportsCustomLabel","OptionsEditorControl","SettingsAutocomplete","UnitSelector","DECIMAL_PLACES_OPTIONS","id","label","decimalPlaces","undefined","getOptionByDecimalPlaces","find","o","FormatControls","value","onChange","disabled","hasDecimalPlaces","hasShortValues","handleUnitChange","newValue","next","unit","customLabel","trim","showCustomLabel","handleDecimalPlacesChange","handleShortValuesChange","_","checked","shortValues","handleCustomLabelChange","raw","_removed","rest","control","size","fullWidth","e","target","placeholder","inputProps","maxLength","options","getOptionLabel","disableClearable"],"mappings":"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"}
|
|
@@ -27,11 +27,11 @@ export function UnitSelector({ value, onChange, disabled = false, ...otherProps
|
|
|
27
27
|
const handleChange = (_, newValue)=>{
|
|
28
28
|
if (newValue === null) {
|
|
29
29
|
onChange(undefined);
|
|
30
|
-
|
|
31
|
-
onChange({
|
|
32
|
-
unit: newValue.id
|
|
33
|
-
});
|
|
30
|
+
return;
|
|
34
31
|
}
|
|
32
|
+
onChange({
|
|
33
|
+
unit: newValue.id
|
|
34
|
+
});
|
|
35
35
|
};
|
|
36
36
|
return /*#__PURE__*/ _jsx(SettingsAutocomplete, {
|
|
37
37
|
value: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/FormatControls/UnitSelector.tsx"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport { IconButton, InputAdornment, TextField } from '@mui/material';\nimport ClearIcon from 'mdi-material-ui/Close';\nimport type { ReactElement } from 'react';\n\nimport type { FormatOptions, UnitConfig } from '../model';\nimport { UNIT_CONFIG } from '../model';\nimport { SettingsAutocomplete } from '../SettingsAutocomplete';\n\nexport interface UnitSelectorProps {\n value?: FormatOptions;\n onChange: (format: FormatOptions | undefined) => void;\n disabled?: boolean;\n}\n\ntype AutocompleteUnitOption = UnitConfig & {\n id: NonNullable<FormatOptions['unit']>;\n};\n\nconst KIND_OPTIONS: readonly AutocompleteUnitOption[] = Object.entries(UNIT_CONFIG)\n .map<AutocompleteUnitOption>(([id, config]) => {\n return {\n ...config,\n id: id as AutocompleteUnitOption['id'],\n group: config.group || 'Decimal',\n };\n })\n .filter((config) => !config.disableSelectorOption);\n\nexport function UnitSelector({ value, onChange, disabled = false, ...otherProps }: UnitSelectorProps): ReactElement {\n const unitConfig = UNIT_CONFIG[value?.unit || 'decimal'];\n\n const handleChange = (_: unknown, newValue: AutocompleteUnitOption | null): void => {\n if (newValue === null) {\n onChange(undefined);\n }
|
|
1
|
+
{"version":3,"sources":["../../src/FormatControls/UnitSelector.tsx"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport { IconButton, InputAdornment, TextField } from '@mui/material';\nimport ClearIcon from 'mdi-material-ui/Close';\nimport type { ReactElement } from 'react';\n\nimport type { FormatOptions, UnitConfig } from '../model';\nimport { UNIT_CONFIG } from '../model';\nimport { SettingsAutocomplete } from '../SettingsAutocomplete';\n\nexport interface UnitSelectorProps {\n value?: FormatOptions;\n onChange: (format: FormatOptions | undefined) => void;\n disabled?: boolean;\n}\n\ntype AutocompleteUnitOption = UnitConfig & {\n id: NonNullable<FormatOptions['unit']>;\n};\n\nconst KIND_OPTIONS: readonly AutocompleteUnitOption[] = Object.entries(UNIT_CONFIG)\n .map<AutocompleteUnitOption>(([id, config]) => {\n return {\n ...config,\n id: id as AutocompleteUnitOption['id'],\n group: config.group || 'Decimal',\n };\n })\n .filter((config) => !config.disableSelectorOption);\n\nexport function UnitSelector({ value, onChange, disabled = false, ...otherProps }: UnitSelectorProps): ReactElement {\n const unitConfig = UNIT_CONFIG[value?.unit || 'decimal'];\n\n const handleChange = (_: unknown, newValue: AutocompleteUnitOption | null): void => {\n if (newValue === null) {\n onChange(undefined);\n return;\n }\n onChange({ unit: newValue.id } as FormatOptions);\n };\n\n return (\n <SettingsAutocomplete<AutocompleteUnitOption, false, true>\n value={{ id: value?.unit || 'decimal', ...unitConfig }}\n options={KIND_OPTIONS}\n groupBy={(option) => option.group ?? 'Decimal'}\n onChange={handleChange}\n disabled={disabled}\n disableClearable\n renderInput={({ InputProps, ...params }) => (\n <TextField\n {...params}\n slotProps={{\n input: {\n ...InputProps,\n endAdornment: (\n <>\n {InputProps.endAdornment}\n <InputAdornment position=\"end\">\n <IconButton\n size=\"small\"\n aria-label=\"clear unit\"\n onClick={() => onChange(undefined)}\n disabled={disabled}\n tabIndex={-1}\n >\n <ClearIcon fontSize=\"small\" />\n </IconButton>\n </InputAdornment>\n </>\n ),\n },\n }}\n />\n )}\n {...otherProps}\n />\n );\n}\n"],"names":["IconButton","InputAdornment","TextField","ClearIcon","UNIT_CONFIG","SettingsAutocomplete","KIND_OPTIONS","Object","entries","map","id","config","group","filter","disableSelectorOption","UnitSelector","value","onChange","disabled","otherProps","unitConfig","unit","handleChange","_","newValue","undefined","options","groupBy","option","disableClearable","renderInput","InputProps","params","slotProps","input","endAdornment","position","size","aria-label","onClick","tabIndex","fontSize"],"mappings":";AAAA,+BAA+B;AAC/B,kEAAkE;AAClE,mEAAmE;AACnE,0CAA0C;AAC1C,EAAE;AACF,6CAA6C;AAC7C,EAAE;AACF,sEAAsE;AACtE,oEAAoE;AACpE,2EAA2E;AAC3E,sEAAsE;AACtE,iCAAiC;AAEjC,SAASA,UAAU,EAAEC,cAAc,EAAEC,SAAS,QAAQ,gBAAgB;AACtE,OAAOC,eAAe,wBAAwB;AAI9C,SAASC,WAAW,QAAQ,oBAAW;AACvC,SAASC,oBAAoB,QAAQ,mCAA0B;AAY/D,MAAMC,eAAkDC,OAAOC,OAAO,CAACJ,aACpEK,GAAG,CAAyB,CAAC,CAACC,IAAIC,OAAO;IACxC,OAAO;QACL,GAAGA,MAAM;QACTD,IAAIA;QACJE,OAAOD,OAAOC,KAAK,IAAI;IACzB;AACF,GACCC,MAAM,CAAC,CAACF,SAAW,CAACA,OAAOG,qBAAqB;AAEnD,OAAO,SAASC,aAAa,EAAEC,KAAK,EAAEC,QAAQ,EAAEC,WAAW,KAAK,EAAE,GAAGC,YAA+B;IAClG,MAAMC,aAAahB,WAAW,CAACY,OAAOK,QAAQ,UAAU;IAExD,MAAMC,eAAe,CAACC,GAAYC;QAChC,IAAIA,aAAa,MAAM;YACrBP,SAASQ;YACT;QACF;QACAR,SAAS;YAAEI,MAAMG,SAASd,EAAE;QAAC;IAC/B;IAEA,qBACE,KAACL;QACCW,OAAO;YAAEN,IAAIM,OAAOK,QAAQ;YAAW,GAAGD,UAAU;QAAC;QACrDM,SAASpB;QACTqB,SAAS,CAACC,SAAWA,OAAOhB,KAAK,IAAI;QACrCK,UAAUK;QACVJ,UAAUA;QACVW,gBAAgB;QAChBC,aAAa,CAAC,EAAEC,UAAU,EAAE,GAAGC,QAAQ,iBACrC,KAAC9B;gBACE,GAAG8B,MAAM;gBACVC,WAAW;oBACTC,OAAO;wBACL,GAAGH,UAAU;wBACbI,4BACE;;gCACGJ,WAAWI,YAAY;8CACxB,KAAClC;oCAAemC,UAAS;8CACvB,cAAA,KAACpC;wCACCqC,MAAK;wCACLC,cAAW;wCACXC,SAAS,IAAMtB,SAASQ;wCACxBP,UAAUA;wCACVsB,UAAU,CAAC;kDAEX,cAAA,KAACrC;4CAAUsC,UAAS;;;;;;oBAK9B;gBACF;;QAGH,GAAGtB,UAAU;;AAGpB"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/TimeSeriesTooltip/utils.ts"],"names":[],"mappings":"AAaA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,eAAe,CAAC;AAE3C,OAAO,KAAK,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,cAAc,CAAC;AAE/D,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,UAAU,CAAC;AACvD,OAAO,KAAK,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AASrE;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,UAAU,CAAC,QAAQ,CAAC,EAC9B,SAAS,EAAE,iBAAiB,GAAG,IAAI,EACnC,aAAa,EAAE,MAAM,EACrB,YAAY,EAAE,MAAM,EACpB,gBAAgB,CAAC,EAAE,OAAO,GAAG,IAAI,GAChC,MAAM,GAAG,SAAS,CAuDpB;
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/TimeSeriesTooltip/utils.ts"],"names":[],"mappings":"AAaA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,eAAe,CAAC;AAE3C,OAAO,KAAK,EAAE,OAAO,IAAI,eAAe,EAAE,MAAM,cAAc,CAAC;AAE/D,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,UAAU,CAAC;AACvD,OAAO,KAAK,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AASrE;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,UAAU,CAAC,QAAQ,CAAC,EAC9B,SAAS,EAAE,iBAAiB,GAAG,IAAI,EACnC,aAAa,EAAE,MAAM,EACrB,YAAY,EAAE,MAAM,EACpB,gBAAgB,CAAC,EAAE,OAAO,GAAG,IAAI,GAChC,MAAM,GAAG,SAAS,CAuDpB;AASD;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,KAAK,EAAE,KAAK,EACZ,SAAS,EAAE,iBAAiB,GAAG,IAAI,EACnC,SAAS,CAAC,EAAE,MAAM,GACjB,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAwBzB;AAED,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,EAAE,KAAK,EAAE,eAAe,GAAG,MAAM,GAAG,IAAI,CAO1F;AAED;;;;GAIG;AACH,wBAAgB,yBAAyB,CACvC,SAAS,EAAE,MAAM,EACjB,MAAM,EAAE,MAAM,EACd,aAAa,EAAE,sBAAsB,EACrC,WAAW,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAC/B,MAAM,CAcR;AAED,wBAAgB,qBAAqB,CAAC,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,EAAE,KAAK,EAAE,eAAe,GAAG,MAAM,CAiCnH;AAED;;;;;;GAMG;AACH,wBAAgB,yBAAyB,CACvC,cAAc,EAAE,MAAM,EACtB,SAAS,EAAE,MAAM,EACjB,YAAY,EAAE,MAAM,EACpB,QAAQ,EAAE,MAAM,GACf;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CAQjC;AAED,wBAAgB,mBAAmB,CACjC,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,MAAM,EAClB,KAAK,EAAE,eAAe,GACrB;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAexC"}
|
|
@@ -58,6 +58,11 @@ import { TOOLTIP_MAX_WIDTH, TOOLTIP_MAX_HEIGHT, TOOLTIP_MIN_WIDTH, TOOLTIP_BG_CO
|
|
|
58
58
|
}
|
|
59
59
|
return `translate3d(${x}px, ${y}px, 0)`;
|
|
60
60
|
}
|
|
61
|
+
/**
|
|
62
|
+
* Stacking level of a pinned tooltip. It must cover the table legend's sticky header, which
|
|
63
|
+
* react-virtuoso renders at z-index 2, and stay below PanelHeader (5, in @perses-dev/dashboards),
|
|
64
|
+
* the drawer and the sticky dashboard header.
|
|
65
|
+
*/ const PINNED_TOOLTIP_Z_INDEX = 3;
|
|
61
66
|
/**
|
|
62
67
|
* Helper for tooltip positioning styles
|
|
63
68
|
*/ export function getTooltipStyles(theme, pinnedPos, maxHeight) {
|
|
@@ -78,8 +83,7 @@ import { TOOLTIP_MAX_WIDTH, TOOLTIP_MAX_HEIGHT, TOOLTIP_MIN_WIDTH, TOOLTIP_BG_CO
|
|
|
78
83
|
opacity: 1,
|
|
79
84
|
// Animating transform causes intermediate positions outside the viewport; animate opacity/visibility instead.
|
|
80
85
|
transition: 'opacity 0.1s ease-out, visibility 0.1s ease-out',
|
|
81
|
-
|
|
82
|
-
zIndex: pinnedPos !== null ? 'auto' : theme.zIndex.tooltip,
|
|
86
|
+
zIndex: pinnedPos !== null ? PINNED_TOOLTIP_Z_INDEX : theme.zIndex.tooltip,
|
|
83
87
|
overflow: 'hidden',
|
|
84
88
|
'&:hover': {
|
|
85
89
|
overflowY: 'auto'
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/TimeSeriesTooltip/utils.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport type { Theme } from '@mui/material';\nimport type { BarSeriesOption, LineSeriesOption } from 'echarts/charts';\nimport type { ECharts as EChartsInstance } from 'echarts/core';\n\nimport type { TimeChartSeriesMapping } from '../model';\nimport type { CursorCoordinates, CursorData } from './tooltip-model';\nimport {\n TOOLTIP_MAX_WIDTH,\n TOOLTIP_MAX_HEIGHT,\n TOOLTIP_MIN_WIDTH,\n TOOLTIP_BG_COLOR_FALLBACK,\n TOOLTIP_PADDING,\n} from './tooltip-model';\n\n/**\n * Determine position of tooltip depending on chart dimensions and the number of focused series.\n */\nexport function assembleTransform(\n mousePos: CursorData['coords'],\n pinnedPos: CursorCoordinates | null,\n tooltipHeight: number,\n tooltipWidth: number,\n containerElement?: Element | null,\n): string | undefined {\n if (mousePos === null) {\n return undefined;\n }\n\n const cursorPaddingX = 32;\n const cursorPaddingY = 16;\n\n if (pinnedPos !== null) {\n mousePos = pinnedPos;\n }\n\n if (mousePos.plotCanvas.x === undefined) return undefined;\n\n // Fall back to max size before the resize observer reports a real measurement.\n const effectiveHeight = tooltipHeight > 0 ? tooltipHeight : TOOLTIP_MAX_HEIGHT;\n const effectiveWidth = tooltipWidth > 0 ? tooltipWidth : TOOLTIP_MAX_WIDTH;\n\n let x = mousePos.page.x + cursorPaddingX; // Default to right side of the cursor\n let y = mousePos.page.y + cursorPaddingY;\n\n // If containerElement is defined, adjust coordinates relative to the container\n if (containerElement) {\n const containerRect = containerElement.getBoundingClientRect();\n x = x - containerRect.left + containerElement.scrollLeft;\n y = y - containerRect.top + containerElement.scrollTop;\n\n // Ensure tooltip does not go out of the container's bottom\n const containerBottom = containerRect.top + containerElement.scrollHeight;\n if (y + effectiveHeight > containerBottom) {\n y = Math.max(containerBottom - effectiveHeight - cursorPaddingY, TOOLTIP_PADDING / 2);\n }\n } else {\n // Ensure tooltip does not go out of the screen on the bottom\n if (y + effectiveHeight > window.innerHeight + window.scrollY) {\n y = Math.max(window.innerHeight + window.scrollY - effectiveHeight - cursorPaddingY, TOOLTIP_PADDING / 2);\n }\n }\n\n // Ensure tooltip does not go out of the screen on the right\n if (x + effectiveWidth > window.innerWidth) {\n x = mousePos.page.x - effectiveWidth - cursorPaddingX; // Move to the left of the cursor\n }\n\n // Ensure tooltip does not go out of the screen on the left\n if (x < cursorPaddingX) {\n x = cursorPaddingX;\n }\n\n // Ensure tooltip does not go out of the screen on the top\n if (y < TOOLTIP_PADDING / 2) {\n y = TOOLTIP_PADDING / 2;\n }\n\n return `translate3d(${x}px, ${y}px, 0)`;\n}\n\n/**\n * Helper for tooltip positioning styles\n */\nexport function getTooltipStyles(\n theme: Theme,\n pinnedPos: CursorCoordinates | null,\n maxHeight?: number,\n): Record<string, unknown> {\n const adjustedMaxHeight = maxHeight ? maxHeight - TOOLTIP_PADDING : undefined;\n return {\n minWidth: TOOLTIP_MIN_WIDTH,\n maxWidth: TOOLTIP_MAX_WIDTH,\n maxHeight: adjustedMaxHeight ?? TOOLTIP_MAX_HEIGHT,\n padding: 0,\n position: 'absolute',\n top: 0,\n left: 0,\n backgroundColor: theme.palette.designSystem?.grey[800] ?? TOOLTIP_BG_COLOR_FALLBACK,\n borderRadius: '6px',\n color: '#fff',\n fontSize: '11px',\n visibility: 'visible',\n opacity: 1,\n // Animating transform causes intermediate positions outside the viewport; animate opacity/visibility instead.\n transition: 'opacity 0.1s ease-out, visibility 0.1s ease-out',\n // Pinned tooltip should not float above the drawer/sticky header.\n zIndex: pinnedPos !== null ? 'auto' : theme.zIndex.tooltip,\n overflow: 'hidden',\n '&:hover': {\n overflowY: 'auto',\n },\n };\n}\n\nexport function getPixelXFromGrid(timestamp: number, chart: EChartsInstance): number | null {\n try {\n const pixelCoords = chart.convertToPixel('grid', [timestamp, 0]);\n return pixelCoords?.[0] ?? null;\n } catch {\n return null;\n }\n}\n\n/**\n * Returns the cumulative (visual) Y for a series, accumulating stack totals in-place.\n * For non-stacked series, returns the raw yValue unchanged.\n * Mutates `stackTotals` — pass a fresh Map for each cursor evaluation.\n */\nexport function calculateVisualYForSeries(\n seriesIdx: number,\n yValue: number,\n seriesMapping: TimeChartSeriesMapping,\n stackTotals: Map<string, number>,\n): number {\n const currentSeries = seriesMapping[seriesIdx];\n if (!currentSeries) return yValue;\n\n const stackId = (currentSeries as LineSeriesOption | BarSeriesOption).stack;\n if (!stackId) {\n return yValue;\n }\n\n const stackIdStr = stackId.toString();\n const currentTotal = stackTotals.get(stackIdStr) ?? 0;\n const newTotal = currentTotal + yValue;\n stackTotals.set(stackIdStr, newTotal);\n return newTotal;\n}\n\nexport function calculateBarBandwidth(timestamp: number, sortedTimestamps: number[], chart: EChartsInstance): number {\n const currentIdx = sortedTimestamps.indexOf(timestamp);\n if (currentIdx === -1) {\n return 20;\n }\n\n const prevTimestamp = currentIdx > 0 ? (sortedTimestamps[currentIdx - 1] ?? null) : null;\n const nextTimestamp = currentIdx < sortedTimestamps.length - 1 ? (sortedTimestamps[currentIdx + 1] ?? null) : null;\n\n const currentPixelX = getPixelXFromGrid(timestamp, chart);\n if (currentPixelX === null) return 20;\n\n let leftBound: number;\n let rightBound: number;\n\n if (prevTimestamp !== null && nextTimestamp !== null) {\n const prevPixelX = getPixelXFromGrid(prevTimestamp, chart) ?? currentPixelX;\n const nextPixelX = getPixelXFromGrid(nextTimestamp, chart) ?? currentPixelX;\n leftBound = (currentPixelX + prevPixelX) / 2;\n rightBound = (currentPixelX + nextPixelX) / 2;\n } else if (prevTimestamp !== null) {\n const prevPixelX = getPixelXFromGrid(prevTimestamp, chart) ?? currentPixelX;\n leftBound = (currentPixelX + prevPixelX) / 2;\n rightBound = currentPixelX + (currentPixelX - leftBound);\n } else if (nextTimestamp !== null) {\n const nextPixelX = getPixelXFromGrid(nextTimestamp, chart) ?? currentPixelX;\n rightBound = (currentPixelX + nextPixelX) / 2;\n leftBound = currentPixelX - (rightBound - currentPixelX);\n } else {\n return 20;\n }\n\n return Math.max(1, rightBound - leftBound);\n}\n\n/**\n * Computes the pixel left/right bounds of one bar segment within a group.\n * @param barRelativeIdx - zero-based index among bar-only series\n * @param bandwidth - total pixel width for the bar group\n * @param centerPixelX - pixel X of the bar group centre\n * @param barCount - total bar series count (lines excluded)\n */\nexport function calculateBarSegmentBounds(\n barRelativeIdx: number,\n bandwidth: number,\n centerPixelX: number,\n barCount: number,\n): { left: number; right: number } {\n const count = Math.max(1, barCount);\n const segmentWidth = bandwidth / count;\n const segmentLeft = centerPixelX - bandwidth / 2 + barRelativeIdx * segmentWidth;\n return {\n left: segmentLeft,\n right: segmentLeft + segmentWidth,\n };\n}\n\nexport function calculateBarYBounds(\n visualYBottom: number,\n visualYTop: number,\n chart: EChartsInstance,\n): { top: number; bottom: number } | null {\n try {\n const bottomPixel = chart.convertToPixel('grid', [0, visualYBottom]);\n const topPixel = chart.convertToPixel('grid', [0, visualYTop]);\n\n if (!bottomPixel || !topPixel || bottomPixel[1] === undefined || topPixel[1] === undefined) return null;\n\n // Y increases downward in pixels; min/max normalizes the mapping for negative bar values.\n return {\n top: Math.min(topPixel[1], bottomPixel[1]),\n bottom: Math.max(topPixel[1], bottomPixel[1]),\n };\n } catch {\n return null;\n }\n}\n"],"names":["TOOLTIP_MAX_WIDTH","TOOLTIP_MAX_HEIGHT","TOOLTIP_MIN_WIDTH","TOOLTIP_BG_COLOR_FALLBACK","TOOLTIP_PADDING","assembleTransform","mousePos","pinnedPos","tooltipHeight","tooltipWidth","containerElement","undefined","cursorPaddingX","cursorPaddingY","plotCanvas","x","effectiveHeight","effectiveWidth","page","y","containerRect","getBoundingClientRect","left","scrollLeft","top","scrollTop","containerBottom","scrollHeight","Math","max","window","innerHeight","scrollY","innerWidth","getTooltipStyles","theme","maxHeight","adjustedMaxHeight","minWidth","maxWidth","padding","position","backgroundColor","palette","designSystem","grey","borderRadius","color","fontSize","visibility","opacity","transition","zIndex","tooltip","overflow","overflowY","getPixelXFromGrid","timestamp","chart","pixelCoords","convertToPixel","calculateVisualYForSeries","seriesIdx","yValue","seriesMapping","stackTotals","currentSeries","stackId","stack","stackIdStr","toString","currentTotal","get","newTotal","set","calculateBarBandwidth","sortedTimestamps","currentIdx","indexOf","prevTimestamp","nextTimestamp","length","currentPixelX","leftBound","rightBound","prevPixelX","nextPixelX","calculateBarSegmentBounds","barRelativeIdx","bandwidth","centerPixelX","barCount","count","segmentWidth","segmentLeft","right","calculateBarYBounds","visualYBottom","visualYTop","bottomPixel","topPixel","min","bottom"],"mappings":"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"}
|
|
1
|
+
{"version":3,"sources":["../../src/TimeSeriesTooltip/utils.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport type { Theme } from '@mui/material';\nimport type { BarSeriesOption, LineSeriesOption } from 'echarts/charts';\nimport type { ECharts as EChartsInstance } from 'echarts/core';\n\nimport type { TimeChartSeriesMapping } from '../model';\nimport type { CursorCoordinates, CursorData } from './tooltip-model';\nimport {\n TOOLTIP_MAX_WIDTH,\n TOOLTIP_MAX_HEIGHT,\n TOOLTIP_MIN_WIDTH,\n TOOLTIP_BG_COLOR_FALLBACK,\n TOOLTIP_PADDING,\n} from './tooltip-model';\n\n/**\n * Determine position of tooltip depending on chart dimensions and the number of focused series.\n */\nexport function assembleTransform(\n mousePos: CursorData['coords'],\n pinnedPos: CursorCoordinates | null,\n tooltipHeight: number,\n tooltipWidth: number,\n containerElement?: Element | null,\n): string | undefined {\n if (mousePos === null) {\n return undefined;\n }\n\n const cursorPaddingX = 32;\n const cursorPaddingY = 16;\n\n if (pinnedPos !== null) {\n mousePos = pinnedPos;\n }\n\n if (mousePos.plotCanvas.x === undefined) return undefined;\n\n // Fall back to max size before the resize observer reports a real measurement.\n const effectiveHeight = tooltipHeight > 0 ? tooltipHeight : TOOLTIP_MAX_HEIGHT;\n const effectiveWidth = tooltipWidth > 0 ? tooltipWidth : TOOLTIP_MAX_WIDTH;\n\n let x = mousePos.page.x + cursorPaddingX; // Default to right side of the cursor\n let y = mousePos.page.y + cursorPaddingY;\n\n // If containerElement is defined, adjust coordinates relative to the container\n if (containerElement) {\n const containerRect = containerElement.getBoundingClientRect();\n x = x - containerRect.left + containerElement.scrollLeft;\n y = y - containerRect.top + containerElement.scrollTop;\n\n // Ensure tooltip does not go out of the container's bottom\n const containerBottom = containerRect.top + containerElement.scrollHeight;\n if (y + effectiveHeight > containerBottom) {\n y = Math.max(containerBottom - effectiveHeight - cursorPaddingY, TOOLTIP_PADDING / 2);\n }\n } else {\n // Ensure tooltip does not go out of the screen on the bottom\n if (y + effectiveHeight > window.innerHeight + window.scrollY) {\n y = Math.max(window.innerHeight + window.scrollY - effectiveHeight - cursorPaddingY, TOOLTIP_PADDING / 2);\n }\n }\n\n // Ensure tooltip does not go out of the screen on the right\n if (x + effectiveWidth > window.innerWidth) {\n x = mousePos.page.x - effectiveWidth - cursorPaddingX; // Move to the left of the cursor\n }\n\n // Ensure tooltip does not go out of the screen on the left\n if (x < cursorPaddingX) {\n x = cursorPaddingX;\n }\n\n // Ensure tooltip does not go out of the screen on the top\n if (y < TOOLTIP_PADDING / 2) {\n y = TOOLTIP_PADDING / 2;\n }\n\n return `translate3d(${x}px, ${y}px, 0)`;\n}\n\n/**\n * Stacking level of a pinned tooltip. It must cover the table legend's sticky header, which\n * react-virtuoso renders at z-index 2, and stay below PanelHeader (5, in @perses-dev/dashboards),\n * the drawer and the sticky dashboard header.\n */\nconst PINNED_TOOLTIP_Z_INDEX = 3;\n\n/**\n * Helper for tooltip positioning styles\n */\nexport function getTooltipStyles(\n theme: Theme,\n pinnedPos: CursorCoordinates | null,\n maxHeight?: number,\n): Record<string, unknown> {\n const adjustedMaxHeight = maxHeight ? maxHeight - TOOLTIP_PADDING : undefined;\n return {\n minWidth: TOOLTIP_MIN_WIDTH,\n maxWidth: TOOLTIP_MAX_WIDTH,\n maxHeight: adjustedMaxHeight ?? TOOLTIP_MAX_HEIGHT,\n padding: 0,\n position: 'absolute',\n top: 0,\n left: 0,\n backgroundColor: theme.palette.designSystem?.grey[800] ?? TOOLTIP_BG_COLOR_FALLBACK,\n borderRadius: '6px',\n color: '#fff',\n fontSize: '11px',\n visibility: 'visible',\n opacity: 1,\n // Animating transform causes intermediate positions outside the viewport; animate opacity/visibility instead.\n transition: 'opacity 0.1s ease-out, visibility 0.1s ease-out',\n zIndex: pinnedPos !== null ? PINNED_TOOLTIP_Z_INDEX : theme.zIndex.tooltip,\n overflow: 'hidden',\n '&:hover': {\n overflowY: 'auto',\n },\n };\n}\n\nexport function getPixelXFromGrid(timestamp: number, chart: EChartsInstance): number | null {\n try {\n const pixelCoords = chart.convertToPixel('grid', [timestamp, 0]);\n return pixelCoords?.[0] ?? null;\n } catch {\n return null;\n }\n}\n\n/**\n * Returns the cumulative (visual) Y for a series, accumulating stack totals in-place.\n * For non-stacked series, returns the raw yValue unchanged.\n * Mutates `stackTotals` — pass a fresh Map for each cursor evaluation.\n */\nexport function calculateVisualYForSeries(\n seriesIdx: number,\n yValue: number,\n seriesMapping: TimeChartSeriesMapping,\n stackTotals: Map<string, number>,\n): number {\n const currentSeries = seriesMapping[seriesIdx];\n if (!currentSeries) return yValue;\n\n const stackId = (currentSeries as LineSeriesOption | BarSeriesOption).stack;\n if (!stackId) {\n return yValue;\n }\n\n const stackIdStr = stackId.toString();\n const currentTotal = stackTotals.get(stackIdStr) ?? 0;\n const newTotal = currentTotal + yValue;\n stackTotals.set(stackIdStr, newTotal);\n return newTotal;\n}\n\nexport function calculateBarBandwidth(timestamp: number, sortedTimestamps: number[], chart: EChartsInstance): number {\n const currentIdx = sortedTimestamps.indexOf(timestamp);\n if (currentIdx === -1) {\n return 20;\n }\n\n const prevTimestamp = currentIdx > 0 ? (sortedTimestamps[currentIdx - 1] ?? null) : null;\n const nextTimestamp = currentIdx < sortedTimestamps.length - 1 ? (sortedTimestamps[currentIdx + 1] ?? null) : null;\n\n const currentPixelX = getPixelXFromGrid(timestamp, chart);\n if (currentPixelX === null) return 20;\n\n let leftBound: number;\n let rightBound: number;\n\n if (prevTimestamp !== null && nextTimestamp !== null) {\n const prevPixelX = getPixelXFromGrid(prevTimestamp, chart) ?? currentPixelX;\n const nextPixelX = getPixelXFromGrid(nextTimestamp, chart) ?? currentPixelX;\n leftBound = (currentPixelX + prevPixelX) / 2;\n rightBound = (currentPixelX + nextPixelX) / 2;\n } else if (prevTimestamp !== null) {\n const prevPixelX = getPixelXFromGrid(prevTimestamp, chart) ?? currentPixelX;\n leftBound = (currentPixelX + prevPixelX) / 2;\n rightBound = currentPixelX + (currentPixelX - leftBound);\n } else if (nextTimestamp !== null) {\n const nextPixelX = getPixelXFromGrid(nextTimestamp, chart) ?? currentPixelX;\n rightBound = (currentPixelX + nextPixelX) / 2;\n leftBound = currentPixelX - (rightBound - currentPixelX);\n } else {\n return 20;\n }\n\n return Math.max(1, rightBound - leftBound);\n}\n\n/**\n * Computes the pixel left/right bounds of one bar segment within a group.\n * @param barRelativeIdx - zero-based index among bar-only series\n * @param bandwidth - total pixel width for the bar group\n * @param centerPixelX - pixel X of the bar group centre\n * @param barCount - total bar series count (lines excluded)\n */\nexport function calculateBarSegmentBounds(\n barRelativeIdx: number,\n bandwidth: number,\n centerPixelX: number,\n barCount: number,\n): { left: number; right: number } {\n const count = Math.max(1, barCount);\n const segmentWidth = bandwidth / count;\n const segmentLeft = centerPixelX - bandwidth / 2 + barRelativeIdx * segmentWidth;\n return {\n left: segmentLeft,\n right: segmentLeft + segmentWidth,\n };\n}\n\nexport function calculateBarYBounds(\n visualYBottom: number,\n visualYTop: number,\n chart: EChartsInstance,\n): { top: number; bottom: number } | null {\n try {\n const bottomPixel = chart.convertToPixel('grid', [0, visualYBottom]);\n const topPixel = chart.convertToPixel('grid', [0, visualYTop]);\n\n if (!bottomPixel || !topPixel || bottomPixel[1] === undefined || topPixel[1] === undefined) return null;\n\n // Y increases downward in pixels; min/max normalizes the mapping for negative bar values.\n return {\n top: Math.min(topPixel[1], bottomPixel[1]),\n bottom: Math.max(topPixel[1], bottomPixel[1]),\n };\n } catch {\n return null;\n }\n}\n"],"names":["TOOLTIP_MAX_WIDTH","TOOLTIP_MAX_HEIGHT","TOOLTIP_MIN_WIDTH","TOOLTIP_BG_COLOR_FALLBACK","TOOLTIP_PADDING","assembleTransform","mousePos","pinnedPos","tooltipHeight","tooltipWidth","containerElement","undefined","cursorPaddingX","cursorPaddingY","plotCanvas","x","effectiveHeight","effectiveWidth","page","y","containerRect","getBoundingClientRect","left","scrollLeft","top","scrollTop","containerBottom","scrollHeight","Math","max","window","innerHeight","scrollY","innerWidth","PINNED_TOOLTIP_Z_INDEX","getTooltipStyles","theme","maxHeight","adjustedMaxHeight","minWidth","maxWidth","padding","position","backgroundColor","palette","designSystem","grey","borderRadius","color","fontSize","visibility","opacity","transition","zIndex","tooltip","overflow","overflowY","getPixelXFromGrid","timestamp","chart","pixelCoords","convertToPixel","calculateVisualYForSeries","seriesIdx","yValue","seriesMapping","stackTotals","currentSeries","stackId","stack","stackIdStr","toString","currentTotal","get","newTotal","set","calculateBarBandwidth","sortedTimestamps","currentIdx","indexOf","prevTimestamp","nextTimestamp","length","currentPixelX","leftBound","rightBound","prevPixelX","nextPixelX","calculateBarSegmentBounds","barRelativeIdx","bandwidth","centerPixelX","barCount","count","segmentWidth","segmentLeft","right","calculateBarYBounds","visualYBottom","visualYTop","bottomPixel","topPixel","min","bottom"],"mappings":"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"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Optional display override on standard formats.
|
|
3
|
+
* `unit` remains the stable key (multi-axis, maps, UI config);
|
|
4
|
+
* `customLabel` only changes the text shown after the scaled quantity.
|
|
5
|
+
*
|
|
6
|
+
* Data sizes (bytes/bits): keep SI/IEC scale (Ki, Mi, K, M, …) and replace the
|
|
7
|
+
* base unit — e.g. "1.46 KiB" + "prout" → "1.46 Ki prout" (not "gigaprout").
|
|
8
|
+
* Dates stay untouched (structured timestamps).
|
|
9
|
+
*/
|
|
10
|
+
export type WithCustomLabel = {
|
|
11
|
+
customLabel?: string;
|
|
12
|
+
};
|
|
13
|
+
/**
|
|
14
|
+
* Whether FormatControls / formatValue should honor customLabel for this unit key.
|
|
15
|
+
*/
|
|
16
|
+
export declare function supportsCustomLabel(unit?: string): boolean;
|
|
17
|
+
/**
|
|
18
|
+
* If customLabel is set and the unit is supported, replace the standard unit text
|
|
19
|
+
* with the display label. Dates leave `formatted` unchanged.
|
|
20
|
+
*/
|
|
21
|
+
export declare function applyCustomLabel(formatted: string, customLabel?: string, unit?: string): string;
|
|
22
|
+
//# sourceMappingURL=custom.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"custom.d.ts","sourceRoot":"","sources":["../../src/model/custom.ts"],"names":[],"mappings":"AAaA;;;;;;;;GAQG;AAEH,MAAM,MAAM,eAAe,GAAG;IAC5B,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,CAAC;AAgEF;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAK1D;AAKD;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,SAAS,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,GAAG,MAAM,CAwD/F"}
|
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
// Copyright The Perses Authors
|
|
2
|
+
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
3
|
+
// you may not use this file except in compliance with the License.
|
|
4
|
+
// You may obtain a copy of the License at
|
|
5
|
+
//
|
|
6
|
+
// http://www.apache.org/licenses/LICENSE-2.0
|
|
7
|
+
//
|
|
8
|
+
// Unless required by applicable law or agreed to in writing, software
|
|
9
|
+
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
10
|
+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
11
|
+
// See the License for the specific language governing permissions and
|
|
12
|
+
// limitations under the License.
|
|
13
|
+
/**
|
|
14
|
+
* Optional display override on standard formats.
|
|
15
|
+
* `unit` remains the stable key (multi-axis, maps, UI config);
|
|
16
|
+
* `customLabel` only changes the text shown after the scaled quantity.
|
|
17
|
+
*
|
|
18
|
+
* Data sizes (bytes/bits): keep SI/IEC scale (Ki, Mi, K, M, …) and replace the
|
|
19
|
+
* base unit — e.g. "1.46 KiB" + "prout" → "1.46 Ki prout" (not "gigaprout").
|
|
20
|
+
* Dates stay untouched (structured timestamps).
|
|
21
|
+
*/ /** Units where customLabel is not applied (unstructured / identity formats). */ const CUSTOM_LABEL_EXCLUDED_UNITS = new Set([
|
|
22
|
+
'datetime-iso',
|
|
23
|
+
'datetime-us',
|
|
24
|
+
'datetime-local',
|
|
25
|
+
'date-iso',
|
|
26
|
+
'date-us',
|
|
27
|
+
'date-local',
|
|
28
|
+
'time-local',
|
|
29
|
+
'time-iso',
|
|
30
|
+
'time-us',
|
|
31
|
+
'relative-time',
|
|
32
|
+
'unix-timestamp',
|
|
33
|
+
'unix-timestamp-ms'
|
|
34
|
+
]);
|
|
35
|
+
const DATA_SIZE_UNITS = new Set([
|
|
36
|
+
'bytes',
|
|
37
|
+
'decbytes',
|
|
38
|
+
'bits',
|
|
39
|
+
'decbits',
|
|
40
|
+
'bytes/sec',
|
|
41
|
+
'decbytes/sec',
|
|
42
|
+
'bits/sec',
|
|
43
|
+
'decbits/sec'
|
|
44
|
+
]);
|
|
45
|
+
const CURRENCY_UNITS = new Set([
|
|
46
|
+
'usd',
|
|
47
|
+
'eur',
|
|
48
|
+
'gbp',
|
|
49
|
+
'jpy',
|
|
50
|
+
'cny',
|
|
51
|
+
'cad',
|
|
52
|
+
'aud',
|
|
53
|
+
'chf',
|
|
54
|
+
'hkd',
|
|
55
|
+
'sgd',
|
|
56
|
+
'sek',
|
|
57
|
+
'krw',
|
|
58
|
+
'nok',
|
|
59
|
+
'nzd',
|
|
60
|
+
'inr',
|
|
61
|
+
'mxn',
|
|
62
|
+
'twd',
|
|
63
|
+
'zar',
|
|
64
|
+
'brl',
|
|
65
|
+
'dkk',
|
|
66
|
+
'pln',
|
|
67
|
+
'thb',
|
|
68
|
+
'ils',
|
|
69
|
+
'czk',
|
|
70
|
+
'clp',
|
|
71
|
+
'php',
|
|
72
|
+
'aed',
|
|
73
|
+
'cop',
|
|
74
|
+
'sar',
|
|
75
|
+
'myr',
|
|
76
|
+
'ron',
|
|
77
|
+
'afn'
|
|
78
|
+
]);
|
|
79
|
+
/**
|
|
80
|
+
* Whether FormatControls / formatValue should honor customLabel for this unit key.
|
|
81
|
+
*/ export function supportsCustomLabel(unit) {
|
|
82
|
+
if (!unit) {
|
|
83
|
+
return true;
|
|
84
|
+
}
|
|
85
|
+
return !CUSTOM_LABEL_EXCLUDED_UNITS.has(unit);
|
|
86
|
+
}
|
|
87
|
+
/** Sign + number (grouped / scientific). */ const LEADING_NUMBER = /^[+-]?(?:\d{1,3}(?:,\d{3})*|\d+)(?:\.\d+)?(?:[eE][+-]?\d+)?/;
|
|
88
|
+
/**
|
|
89
|
+
* If customLabel is set and the unit is supported, replace the standard unit text
|
|
90
|
+
* with the display label. Dates leave `formatted` unchanged.
|
|
91
|
+
*/ export function applyCustomLabel(formatted, customLabel, unit) {
|
|
92
|
+
const label = customLabel?.trim();
|
|
93
|
+
if (!label) {
|
|
94
|
+
return formatted;
|
|
95
|
+
}
|
|
96
|
+
if (!supportsCustomLabel(unit)) {
|
|
97
|
+
return formatted;
|
|
98
|
+
}
|
|
99
|
+
if (unit && DATA_SIZE_UNITS.has(unit)) {
|
|
100
|
+
return applyDataSizeCustomLabel(formatted, label);
|
|
101
|
+
}
|
|
102
|
+
if (unit && CURRENCY_UNITS.has(unit)) {
|
|
103
|
+
return applyCurrencyCustomLabel(formatted, label);
|
|
104
|
+
}
|
|
105
|
+
// formatTime zero sentinel
|
|
106
|
+
if (formatted === '0s') {
|
|
107
|
+
return `0 ${label}`;
|
|
108
|
+
}
|
|
109
|
+
// Percent: "12.3%" → "12.3 load"
|
|
110
|
+
if (unit === 'percent' || unit === 'percent-decimal') {
|
|
111
|
+
if (formatted.endsWith('%')) {
|
|
112
|
+
return `${formatted.slice(0, -1).trimEnd()} ${label}`;
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
// Temperature: "11°C" / "52°F"
|
|
116
|
+
if (unit === 'celsius' && formatted.endsWith('°C')) {
|
|
117
|
+
return `${formatted.slice(0, -2).trimEnd()} ${label}`;
|
|
118
|
+
}
|
|
119
|
+
if (unit === 'fahrenheit' && formatted.endsWith('°F')) {
|
|
120
|
+
return `${formatted.slice(0, -2).trimEnd()} ${label}`;
|
|
121
|
+
}
|
|
122
|
+
// Exact unit-key suffix: "10 ops/sec", "1.5K ops/sec"
|
|
123
|
+
if (unit && formatted.endsWith(` ${unit}`)) {
|
|
124
|
+
return `${formatted.slice(0, -(unit.length + 1))} ${label}`;
|
|
125
|
+
}
|
|
126
|
+
// Time units: Intl narrow often glues the suffix ("1ms", "1μs") with no space — the
|
|
127
|
+
// generic leadingQuantity path can leave "ms" if a consumer re-appends a label, and
|
|
128
|
+
// the bare append fallback would yield "1ms prout". Strip known time tokens first.
|
|
129
|
+
if (unit && TIME_FORMAT_UNITS.has(unit)) {
|
|
130
|
+
return applyTimeCustomLabel(formatted, label);
|
|
131
|
+
}
|
|
132
|
+
// Decimal / throughput fallback: keep leading quantity only
|
|
133
|
+
const qty = leadingQuantity(formatted);
|
|
134
|
+
if (qty !== null) {
|
|
135
|
+
return `${qty} ${label}`;
|
|
136
|
+
}
|
|
137
|
+
return `${formatted} ${label}`;
|
|
138
|
+
}
|
|
139
|
+
/** Time format unit keys (formatTime / Intl unit style). */ const TIME_FORMAT_UNITS = new Set([
|
|
140
|
+
'nanoseconds',
|
|
141
|
+
'microseconds',
|
|
142
|
+
'milliseconds',
|
|
143
|
+
'seconds',
|
|
144
|
+
'minutes',
|
|
145
|
+
'hours',
|
|
146
|
+
'days',
|
|
147
|
+
'weeks',
|
|
148
|
+
'months',
|
|
149
|
+
'years'
|
|
150
|
+
]);
|
|
151
|
+
/**
|
|
152
|
+
* Replace formatTime output with custom label.
|
|
153
|
+
* Handles glued narrow units (1ms, 500µs), spaced long forms (1 month), and
|
|
154
|
+
* multi-part strings (1d255ms) by keeping only the leading quantity (+ compact K/M/B/T).
|
|
155
|
+
*/ function applyTimeCustomLabel(formatted, label) {
|
|
156
|
+
const body = formatted.trim();
|
|
157
|
+
if (body === '0s' || body === '0') {
|
|
158
|
+
return `0 ${label}`;
|
|
159
|
+
}
|
|
160
|
+
// Strip trailing time tokens (repeat for compound "1d 2h", "1d255ms").
|
|
161
|
+
// Long names → multi-letter narrow (ms before m|s) → single-letter. One µ only (not µs|μs).
|
|
162
|
+
let stripped = body.replace(/\u03bc/g, '\u00b5'); // Greek μ → micro sign µ (Intl variants)
|
|
163
|
+
const timeToken = /(?:\s*)(?:milliseconds?|microseconds?|nanoseconds?|seconds?|minutes?|hours?|days?|weeks?|months?|years?|ms|us|ns|µs|[ywdhms])$/i;
|
|
164
|
+
let guard = 0;
|
|
165
|
+
while(timeToken.test(stripped) && guard++ < 8){
|
|
166
|
+
stripped = stripped.replace(timeToken, '').trimEnd();
|
|
167
|
+
}
|
|
168
|
+
if (stripped !== '' && stripped !== body) {
|
|
169
|
+
// Prefer full numeric head (incl. decimals / compact) from stripped body
|
|
170
|
+
const qty = leadingQuantity(stripped) ?? stripped;
|
|
171
|
+
return `${qty} ${label}`;
|
|
172
|
+
}
|
|
173
|
+
const qty = leadingQuantity(body);
|
|
174
|
+
if (qty !== null) {
|
|
175
|
+
return `${qty} ${label}`;
|
|
176
|
+
}
|
|
177
|
+
return `${body} ${label}`;
|
|
178
|
+
}
|
|
179
|
+
/**
|
|
180
|
+
* Bytes/bits (+ optional /s|/sec): keep scale (Ki, Mi, K, M, …), replace base unit.
|
|
181
|
+
* "1.46 KiB" + prout → "1.46 Ki prout"
|
|
182
|
+
* "1.5 KB/s" + wire → "1.5 K wire/s"
|
|
183
|
+
* "500 bytes" + prout → "500 prout"
|
|
184
|
+
*/ function applyDataSizeCustomLabel(formatted, label) {
|
|
185
|
+
let rate = '';
|
|
186
|
+
let body = formatted.trim();
|
|
187
|
+
const rateM = body.match(/(\/s(?:ec)?)$/i);
|
|
188
|
+
if (rateM?.[1]) {
|
|
189
|
+
rate = rateM[1];
|
|
190
|
+
body = body.slice(0, -rate.length).trimEnd();
|
|
191
|
+
}
|
|
192
|
+
// Long form: "500 bytes", "1,500 bits"
|
|
193
|
+
const long = body.match(/^(.+?)\s+(bytes?|bits?)$/i);
|
|
194
|
+
if (long?.[1]) {
|
|
195
|
+
return `${long[1].trim()} ${label}${rate}`;
|
|
196
|
+
}
|
|
197
|
+
// Short form: "1.46 KiB", "1.5 KB", "1.46 Kib", "1.5 Kb" (optional space before scale)
|
|
198
|
+
const short = body.match(/^(.+?)\s*([KMGTPE]i?)\s*([Bb])$/);
|
|
199
|
+
if (short?.[1] && short[2]) {
|
|
200
|
+
return `${short[1].trim()} ${short[2]} ${label}${rate}`;
|
|
201
|
+
}
|
|
202
|
+
const qty = leadingQuantity(body);
|
|
203
|
+
if (qty !== null) {
|
|
204
|
+
return `${qty} ${label}${rate}`;
|
|
205
|
+
}
|
|
206
|
+
return `${formatted} ${label}`;
|
|
207
|
+
}
|
|
208
|
+
/**
|
|
209
|
+
* Currency: drop symbol/code, keep amount + custom label.
|
|
210
|
+
* "$1,500" + credits → "1,500 credits"
|
|
211
|
+
*/ function applyCurrencyCustomLabel(formatted, label) {
|
|
212
|
+
// Strip common leading/trailing currency symbols and ISO codes.
|
|
213
|
+
// Keep optional leading sign so "-$1.23" → "-1.23 credits" (not "-$1.23 credits").
|
|
214
|
+
let body = formatted.trim();
|
|
215
|
+
body = body.replace(/^([+-]?)\s*[^\d\s+-]+/, '$1'); // -$1.23 / $1.23 / €12.3
|
|
216
|
+
body = body.replace(/\s*[A-Z]{3}$/, ''); // trailing USD
|
|
217
|
+
body = body.trim();
|
|
218
|
+
const qty = leadingQuantity(body);
|
|
219
|
+
if (qty !== null) {
|
|
220
|
+
return `${body} ${label}`;
|
|
221
|
+
}
|
|
222
|
+
return `${body} ${label}`;
|
|
223
|
+
}
|
|
224
|
+
/**
|
|
225
|
+
* Numeric prefix of a formatted value, keeping SI compact (1.5K)
|
|
226
|
+
* but not unit letters glued to the number (500ms → 500, not 500m).
|
|
227
|
+
*/ function leadingQuantity(formatted) {
|
|
228
|
+
const s = formatted.trimStart();
|
|
229
|
+
const num = s.match(LEADING_NUMBER);
|
|
230
|
+
if (!num?.[0]) {
|
|
231
|
+
return null;
|
|
232
|
+
}
|
|
233
|
+
const head = num[0];
|
|
234
|
+
const rest = s.slice(head.length);
|
|
235
|
+
// Compact decimal suffix K/M/B/T only when not starting a longer unit word (ms, min, …).
|
|
236
|
+
const compact = rest.match(/^([KMBT])(?=\s|$)/i);
|
|
237
|
+
if (compact) {
|
|
238
|
+
return head + compact[1];
|
|
239
|
+
}
|
|
240
|
+
return head;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
//# sourceMappingURL=custom.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/model/custom.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\n/**\n * Optional display override on standard formats.\n * `unit` remains the stable key (multi-axis, maps, UI config);\n * `customLabel` only changes the text shown after the scaled quantity.\n *\n * Data sizes (bytes/bits): keep SI/IEC scale (Ki, Mi, K, M, …) and replace the\n * base unit — e.g. \"1.46 KiB\" + \"prout\" → \"1.46 Ki prout\" (not \"gigaprout\").\n * Dates stay untouched (structured timestamps).\n */\n\nexport type WithCustomLabel = {\n customLabel?: string;\n};\n\n/** Units where customLabel is not applied (unstructured / identity formats). */\nconst CUSTOM_LABEL_EXCLUDED_UNITS = new Set([\n 'datetime-iso',\n 'datetime-us',\n 'datetime-local',\n 'date-iso',\n 'date-us',\n 'date-local',\n 'time-local',\n 'time-iso',\n 'time-us',\n 'relative-time',\n 'unix-timestamp',\n 'unix-timestamp-ms',\n]);\n\nconst DATA_SIZE_UNITS = new Set([\n 'bytes',\n 'decbytes',\n 'bits',\n 'decbits',\n 'bytes/sec',\n 'decbytes/sec',\n 'bits/sec',\n 'decbits/sec',\n]);\n\nconst CURRENCY_UNITS = new Set([\n 'usd',\n 'eur',\n 'gbp',\n 'jpy',\n 'cny',\n 'cad',\n 'aud',\n 'chf',\n 'hkd',\n 'sgd',\n 'sek',\n 'krw',\n 'nok',\n 'nzd',\n 'inr',\n 'mxn',\n 'twd',\n 'zar',\n 'brl',\n 'dkk',\n 'pln',\n 'thb',\n 'ils',\n 'czk',\n 'clp',\n 'php',\n 'aed',\n 'cop',\n 'sar',\n 'myr',\n 'ron',\n 'afn',\n]);\n\n/**\n * Whether FormatControls / formatValue should honor customLabel for this unit key.\n */\nexport function supportsCustomLabel(unit?: string): boolean {\n if (!unit) {\n return true;\n }\n return !CUSTOM_LABEL_EXCLUDED_UNITS.has(unit);\n}\n\n/** Sign + number (grouped / scientific). */\nconst LEADING_NUMBER = /^[+-]?(?:\\d{1,3}(?:,\\d{3})*|\\d+)(?:\\.\\d+)?(?:[eE][+-]?\\d+)?/;\n\n/**\n * If customLabel is set and the unit is supported, replace the standard unit text\n * with the display label. Dates leave `formatted` unchanged.\n */\nexport function applyCustomLabel(formatted: string, customLabel?: string, unit?: string): string {\n const label = customLabel?.trim();\n if (!label) {\n return formatted;\n }\n if (!supportsCustomLabel(unit)) {\n return formatted;\n }\n\n if (unit && DATA_SIZE_UNITS.has(unit)) {\n return applyDataSizeCustomLabel(formatted, label);\n }\n\n if (unit && CURRENCY_UNITS.has(unit)) {\n return applyCurrencyCustomLabel(formatted, label);\n }\n\n // formatTime zero sentinel\n if (formatted === '0s') {\n return `0 ${label}`;\n }\n\n // Percent: \"12.3%\" → \"12.3 load\"\n if (unit === 'percent' || unit === 'percent-decimal') {\n if (formatted.endsWith('%')) {\n return `${formatted.slice(0, -1).trimEnd()} ${label}`;\n }\n }\n\n // Temperature: \"11°C\" / \"52°F\"\n if (unit === 'celsius' && formatted.endsWith('°C')) {\n return `${formatted.slice(0, -2).trimEnd()} ${label}`;\n }\n if (unit === 'fahrenheit' && formatted.endsWith('°F')) {\n return `${formatted.slice(0, -2).trimEnd()} ${label}`;\n }\n\n // Exact unit-key suffix: \"10 ops/sec\", \"1.5K ops/sec\"\n if (unit && formatted.endsWith(` ${unit}`)) {\n return `${formatted.slice(0, -(unit.length + 1))} ${label}`;\n }\n\n // Time units: Intl narrow often glues the suffix (\"1ms\", \"1μs\") with no space — the\n // generic leadingQuantity path can leave \"ms\" if a consumer re-appends a label, and\n // the bare append fallback would yield \"1ms prout\". Strip known time tokens first.\n if (unit && TIME_FORMAT_UNITS.has(unit)) {\n return applyTimeCustomLabel(formatted, label);\n }\n\n // Decimal / throughput fallback: keep leading quantity only\n const qty = leadingQuantity(formatted);\n if (qty !== null) {\n return `${qty} ${label}`;\n }\n\n return `${formatted} ${label}`;\n}\n\n/** Time format unit keys (formatTime / Intl unit style). */\nconst TIME_FORMAT_UNITS = new Set([\n 'nanoseconds',\n 'microseconds',\n 'milliseconds',\n 'seconds',\n 'minutes',\n 'hours',\n 'days',\n 'weeks',\n 'months',\n 'years',\n]);\n\n/**\n * Replace formatTime output with custom label.\n * Handles glued narrow units (1ms, 500µs), spaced long forms (1 month), and\n * multi-part strings (1d255ms) by keeping only the leading quantity (+ compact K/M/B/T).\n */\nfunction applyTimeCustomLabel(formatted: string, label: string): string {\n const body = formatted.trim();\n if (body === '0s' || body === '0') {\n return `0 ${label}`;\n }\n\n // Strip trailing time tokens (repeat for compound \"1d 2h\", \"1d255ms\").\n // Long names → multi-letter narrow (ms before m|s) → single-letter. One µ only (not µs|μs).\n let stripped = body.replace(/\\u03bc/g, '\\u00b5'); // Greek μ → micro sign µ (Intl variants)\n const timeToken =\n /(?:\\s*)(?:milliseconds?|microseconds?|nanoseconds?|seconds?|minutes?|hours?|days?|weeks?|months?|years?|ms|us|ns|µs|[ywdhms])$/i;\n let guard = 0;\n while (timeToken.test(stripped) && guard++ < 8) {\n stripped = stripped.replace(timeToken, '').trimEnd();\n }\n if (stripped !== '' && stripped !== body) {\n // Prefer full numeric head (incl. decimals / compact) from stripped body\n const qty = leadingQuantity(stripped) ?? stripped;\n return `${qty} ${label}`;\n }\n\n const qty = leadingQuantity(body);\n if (qty !== null) {\n return `${qty} ${label}`;\n }\n return `${body} ${label}`;\n}\n\n/**\n * Bytes/bits (+ optional /s|/sec): keep scale (Ki, Mi, K, M, …), replace base unit.\n * \"1.46 KiB\" + prout → \"1.46 Ki prout\"\n * \"1.5 KB/s\" + wire → \"1.5 K wire/s\"\n * \"500 bytes\" + prout → \"500 prout\"\n */\nfunction applyDataSizeCustomLabel(formatted: string, label: string): string {\n let rate = '';\n let body = formatted.trim();\n const rateM = body.match(/(\\/s(?:ec)?)$/i);\n if (rateM?.[1]) {\n rate = rateM[1];\n body = body.slice(0, -rate.length).trimEnd();\n }\n\n // Long form: \"500 bytes\", \"1,500 bits\"\n const long = body.match(/^(.+?)\\s+(bytes?|bits?)$/i);\n if (long?.[1]) {\n return `${long[1].trim()} ${label}${rate}`;\n }\n\n // Short form: \"1.46 KiB\", \"1.5 KB\", \"1.46 Kib\", \"1.5 Kb\" (optional space before scale)\n const short = body.match(/^(.+?)\\s*([KMGTPE]i?)\\s*([Bb])$/);\n if (short?.[1] && short[2]) {\n return `${short[1].trim()} ${short[2]} ${label}${rate}`;\n }\n\n const qty = leadingQuantity(body);\n if (qty !== null) {\n return `${qty} ${label}${rate}`;\n }\n return `${formatted} ${label}`;\n}\n\n/**\n * Currency: drop symbol/code, keep amount + custom label.\n * \"$1,500\" + credits → \"1,500 credits\"\n */\nfunction applyCurrencyCustomLabel(formatted: string, label: string): string {\n // Strip common leading/trailing currency symbols and ISO codes.\n // Keep optional leading sign so \"-$1.23\" → \"-1.23 credits\" (not \"-$1.23 credits\").\n let body = formatted.trim();\n body = body.replace(/^([+-]?)\\s*[^\\d\\s+-]+/, '$1'); // -$1.23 / $1.23 / €12.3\n body = body.replace(/\\s*[A-Z]{3}$/, ''); // trailing USD\n body = body.trim();\n const qty = leadingQuantity(body);\n if (qty !== null) {\n return `${body} ${label}`;\n }\n return `${body} ${label}`;\n}\n\n/**\n * Numeric prefix of a formatted value, keeping SI compact (1.5K)\n * but not unit letters glued to the number (500ms → 500, not 500m).\n */\nfunction leadingQuantity(formatted: string): string | null {\n const s = formatted.trimStart();\n const num = s.match(LEADING_NUMBER);\n if (!num?.[0]) {\n return null;\n }\n const head = num[0];\n const rest = s.slice(head.length);\n\n // Compact decimal suffix K/M/B/T only when not starting a longer unit word (ms, min, …).\n const compact = rest.match(/^([KMBT])(?=\\s|$)/i);\n if (compact) {\n return head + compact[1];\n }\n\n return head;\n}\n"],"names":["CUSTOM_LABEL_EXCLUDED_UNITS","Set","DATA_SIZE_UNITS","CURRENCY_UNITS","supportsCustomLabel","unit","has","LEADING_NUMBER","applyCustomLabel","formatted","customLabel","label","trim","applyDataSizeCustomLabel","applyCurrencyCustomLabel","endsWith","slice","trimEnd","length","TIME_FORMAT_UNITS","applyTimeCustomLabel","qty","leadingQuantity","body","stripped","replace","timeToken","guard","test","rate","rateM","match","long","short","s","trimStart","num","head","rest","compact"],"mappings":"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"}
|
package/dist/model/index.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/model/index.ts"],"names":[],"mappings":"AAaA,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,kBAAkB,CAAC;AACjC,cAAc,UAAU,CAAC;AACzB,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,QAAQ,CAAC;AACvB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,WAAW,CAAC;AAC1B,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,cAAc,CAAC;AAC7B,cAAc,kBAAkB,CAAC;AACjC,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC;AAC7B,cAAc,iBAAiB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/model/index.ts"],"names":[],"mappings":"AAaA,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,kBAAkB,CAAC;AACjC,cAAc,UAAU,CAAC;AACzB,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,QAAQ,CAAC;AACvB,cAAc,SAAS,CAAC;AACxB,cAAc,YAAY,CAAC;AAC3B,cAAc,WAAW,CAAC;AAC1B,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,cAAc,CAAC;AAC7B,cAAc,UAAU,CAAC;AACzB,cAAc,kBAAkB,CAAC;AACjC,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC;AAC7B,cAAc,iBAAiB,CAAC"}
|
package/dist/model/index.js
CHANGED
|
@@ -24,6 +24,7 @@ export * from "./percent.js";
|
|
|
24
24
|
export * from "./temperature.js";
|
|
25
25
|
export * from "./decimal.js";
|
|
26
26
|
export * from "./throughput.js";
|
|
27
|
+
export * from "./custom.js";
|
|
27
28
|
export * from "./formatterCache.js";
|
|
28
29
|
export * from "./units.js";
|
|
29
30
|
export * from "./utils.js";
|
package/dist/model/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/model/index.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nexport * from './graph';\nexport * from './theme';\nexport * from './timeOption';\nexport * from './timeZoneOption';\nexport * from './action';\nexport * from './legend';\nexport * from './time';\nexport * from './bits';\nexport * from './bytes';\nexport * from './currency';\nexport * from './percent';\nexport * from './temperature';\nexport * from './decimal';\nexport * from './throughput';\nexport * from './formatterCache';\nexport * from './units';\nexport * from './utils';\nexport * from './types';\nexport * from './thresholds';\nexport * from './transforms';\nexport * from './value-mapping';\n"],"names":[],"mappings":"AAAA,+BAA+B;AAC/B,kEAAkE;AAClE,mEAAmE;AACnE,0CAA0C;AAC1C,EAAE;AACF,6CAA6C;AAC7C,EAAE;AACF,sEAAsE;AACtE,oEAAoE;AACpE,2EAA2E;AAC3E,sEAAsE;AACtE,iCAAiC;AAEjC,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,kBAAe;AAC7B,cAAc,sBAAmB;AACjC,cAAc,cAAW;AACzB,cAAc,cAAW;AACzB,cAAc,YAAS;AACvB,cAAc,YAAS;AACvB,cAAc,aAAU;AACxB,cAAc,gBAAa;AAC3B,cAAc,eAAY;AAC1B,cAAc,mBAAgB;AAC9B,cAAc,eAAY;AAC1B,cAAc,kBAAe;AAC7B,cAAc,sBAAmB;AACjC,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,kBAAe;AAC7B,cAAc,kBAAe;AAC7B,cAAc,qBAAkB"}
|
|
1
|
+
{"version":3,"sources":["../../src/model/index.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nexport * from './graph';\nexport * from './theme';\nexport * from './timeOption';\nexport * from './timeZoneOption';\nexport * from './action';\nexport * from './legend';\nexport * from './time';\nexport * from './bits';\nexport * from './bytes';\nexport * from './currency';\nexport * from './percent';\nexport * from './temperature';\nexport * from './decimal';\nexport * from './throughput';\nexport * from './custom';\nexport * from './formatterCache';\nexport * from './units';\nexport * from './utils';\nexport * from './types';\nexport * from './thresholds';\nexport * from './transforms';\nexport * from './value-mapping';\n"],"names":[],"mappings":"AAAA,+BAA+B;AAC/B,kEAAkE;AAClE,mEAAmE;AACnE,0CAA0C;AAC1C,EAAE;AACF,6CAA6C;AAC7C,EAAE;AACF,sEAAsE;AACtE,oEAAoE;AACpE,2EAA2E;AAC3E,sEAAsE;AACtE,iCAAiC;AAEjC,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,kBAAe;AAC7B,cAAc,sBAAmB;AACjC,cAAc,cAAW;AACzB,cAAc,cAAW;AACzB,cAAc,YAAS;AACvB,cAAc,YAAS;AACvB,cAAc,aAAU;AACxB,cAAc,gBAAa;AAC3B,cAAc,eAAY;AAC1B,cAAc,mBAAgB;AAC9B,cAAc,eAAY;AAC1B,cAAc,kBAAe;AAC7B,cAAc,cAAW;AACzB,cAAc,sBAAmB;AACjC,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,aAAU;AACxB,cAAc,kBAAe;AAC7B,cAAc,kBAAe;AAC7B,cAAc,qBAAkB"}
|
package/dist/model/units.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { BitsFormatOptions } from './bits';
|
|
2
2
|
import type { BytesFormatOptions } from './bytes';
|
|
3
3
|
import type { CurrencyFormatOptions } from './currency';
|
|
4
|
+
import type { WithCustomLabel } from './custom';
|
|
4
5
|
import type { DateFormatOptions } from './date';
|
|
5
6
|
import type { DecimalFormatOptions } from './decimal';
|
|
6
7
|
import type { PercentFormatOptions } from './percent';
|
|
@@ -79,7 +80,8 @@ export declare const UNIT_CONFIG: {
|
|
|
79
80
|
readonly "writes/sec": UnitConfig;
|
|
80
81
|
readonly years: UnitConfig;
|
|
81
82
|
};
|
|
82
|
-
|
|
83
|
+
/** Standard unit options plus optional display override (customLabel). */
|
|
84
|
+
export type FormatOptions = (TimeFormatOptions | PercentFormatOptions | DecimalFormatOptions | BytesFormatOptions | BitsFormatOptions | ThroughputFormatOptions | CurrencyFormatOptions | TemperatureFormatOptions | DateFormatOptions) & WithCustomLabel;
|
|
83
85
|
type HasDecimalPlaces<UnitOpt> = UnitOpt extends {
|
|
84
86
|
decimalPlaces?: number;
|
|
85
87
|
} ? UnitOpt : never;
|
|
@@ -90,16 +92,16 @@ export declare function formatValue(value: number, formatOptions?: FormatOptions
|
|
|
90
92
|
export declare function getUnitConfig(formatOptions: FormatOptions): UnitConfig;
|
|
91
93
|
export declare function getUnitGroup(formatOptions: FormatOptions): UnitGroup;
|
|
92
94
|
export declare function getUnitGroupConfig(formatOptions: FormatOptions): UnitGroupConfig;
|
|
93
|
-
export declare function isTimeUnit(formatOptions: FormatOptions): formatOptions is TimeFormatOptions;
|
|
94
|
-
export declare function isPercentUnit(formatOptions: FormatOptions): formatOptions is PercentFormatOptions;
|
|
95
|
-
export declare function isDecimalUnit(formatOptions: FormatOptions): formatOptions is DecimalFormatOptions;
|
|
96
|
-
export declare function isBytesUnit(formatOptions: FormatOptions): formatOptions is BytesFormatOptions;
|
|
97
|
-
export declare function isBitsUnit(formatOptions: FormatOptions): formatOptions is BitsFormatOptions;
|
|
95
|
+
export declare function isTimeUnit(formatOptions: FormatOptions): formatOptions is TimeFormatOptions & WithCustomLabel;
|
|
96
|
+
export declare function isPercentUnit(formatOptions: FormatOptions): formatOptions is PercentFormatOptions & WithCustomLabel;
|
|
97
|
+
export declare function isDecimalUnit(formatOptions: FormatOptions): formatOptions is DecimalFormatOptions & WithCustomLabel;
|
|
98
|
+
export declare function isBytesUnit(formatOptions: FormatOptions): formatOptions is BytesFormatOptions & WithCustomLabel;
|
|
99
|
+
export declare function isBitsUnit(formatOptions: FormatOptions): formatOptions is BitsFormatOptions & WithCustomLabel;
|
|
98
100
|
export declare function isUnitWithDecimalPlaces(formatOptions: FormatOptions): formatOptions is HasDecimalPlaces<FormatOptions>;
|
|
99
101
|
export declare function isUnitWithShortValues(formatOptions: FormatOptions): formatOptions is HasShortValues<FormatOptions>;
|
|
100
|
-
export declare function isThroughputUnit(formatOptions: FormatOptions): formatOptions is ThroughputFormatOptions;
|
|
101
|
-
export declare function isCurrencyUnit(formatOptions: FormatOptions): formatOptions is CurrencyFormatOptions;
|
|
102
|
-
export declare function isDateUnit(formatOptions: FormatOptions): formatOptions is DateFormatOptions;
|
|
103
|
-
export declare function isTemperatureUnit(formatOptions: FormatOptions): formatOptions is TemperatureFormatOptions;
|
|
102
|
+
export declare function isThroughputUnit(formatOptions: FormatOptions): formatOptions is ThroughputFormatOptions & WithCustomLabel;
|
|
103
|
+
export declare function isCurrencyUnit(formatOptions: FormatOptions): formatOptions is CurrencyFormatOptions & WithCustomLabel;
|
|
104
|
+
export declare function isDateUnit(formatOptions: FormatOptions): formatOptions is DateFormatOptions & WithCustomLabel;
|
|
105
|
+
export declare function isTemperatureUnit(formatOptions: FormatOptions): formatOptions is TemperatureFormatOptions & WithCustomLabel;
|
|
104
106
|
export {};
|
|
105
107
|
//# sourceMappingURL=units.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"units.d.ts","sourceRoot":"","sources":["../../src/model/units.ts"],"names":[],"mappings":"AAaA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,QAAQ,CAAC;AAEhD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,SAAS,CAAC;AAElD,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAC;AAExD,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,QAAQ,CAAC;AAEhD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC;AAEtD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC;AAEtD,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,eAAe,CAAC;AAE9D,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,cAAc,CAAC;AAE5D,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,QAAQ,CAAC;AAEhD,OAAO,KAAK,EAAE,SAAS,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAEtE;;;;;;GAMG;AAEH,eAAO,MAAM,iBAAiB,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,eAAe,CAAC,CAU1E,CAAC;AACF,eAAO,MAAM,WAAW;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAUd,CAAC;AAEX,MAAM,MAAM,aAAa,
|
|
1
|
+
{"version":3,"file":"units.d.ts","sourceRoot":"","sources":["../../src/model/units.ts"],"names":[],"mappings":"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"}
|
package/dist/model/units.js
CHANGED
|
@@ -13,6 +13,7 @@
|
|
|
13
13
|
import { formatBits, BITS_GROUP_CONFIG, BITS_UNIT_CONFIG } from "./bits.js";
|
|
14
14
|
import { formatBytes, BYTES_GROUP_CONFIG, BYTES_UNIT_CONFIG } from "./bytes.js";
|
|
15
15
|
import { formatCurrency, CURRENCY_GROUP_CONFIG, CURRENCY_UNIT_CONFIG } from "./currency.js";
|
|
16
|
+
import { applyCustomLabel, supportsCustomLabel } from "./custom.js";
|
|
16
17
|
import { formatDate, DATE_GROUP_CONFIG, DATE_UNIT_CONFIG } from "./date.js";
|
|
17
18
|
import { formatDecimal, DECIMAL_GROUP_CONFIG, DECIMAL_UNIT_CONFIG } from "./decimal.js";
|
|
18
19
|
import { formatPercent, PERCENT_GROUP_CONFIG, PERCENT_UNIT_CONFIG } from "./percent.js";
|
|
@@ -51,39 +52,43 @@ export function formatValue(value, formatOptions) {
|
|
|
51
52
|
if (!formatOptions) {
|
|
52
53
|
return value.toString();
|
|
53
54
|
}
|
|
55
|
+
let formatted;
|
|
54
56
|
if (isBytesUnit(formatOptions)) {
|
|
55
|
-
|
|
57
|
+
formatted = formatBytes(value, formatOptions);
|
|
58
|
+
} else if (isBitsUnit(formatOptions)) {
|
|
59
|
+
formatted = formatBits(value, formatOptions);
|
|
60
|
+
} else if (isDecimalUnit(formatOptions)) {
|
|
61
|
+
formatted = formatDecimal(value, formatOptions);
|
|
62
|
+
} else if (isPercentUnit(formatOptions)) {
|
|
63
|
+
formatted = formatPercent(value, formatOptions);
|
|
64
|
+
} else if (isTimeUnit(formatOptions)) {
|
|
65
|
+
formatted = formatTime(value, formatOptions);
|
|
66
|
+
} else if (isThroughputUnit(formatOptions)) {
|
|
67
|
+
formatted = formatThroughput(value, formatOptions);
|
|
68
|
+
} else if (isCurrencyUnit(formatOptions)) {
|
|
69
|
+
formatted = formatCurrency(value, formatOptions);
|
|
70
|
+
} else if (isDateUnit(formatOptions)) {
|
|
71
|
+
formatted = formatDate(value, formatOptions);
|
|
72
|
+
} else if (isTemperatureUnit(formatOptions)) {
|
|
73
|
+
formatted = formatTemperature(value, formatOptions);
|
|
74
|
+
} else {
|
|
75
|
+
const exhaustive = formatOptions;
|
|
76
|
+
throw new Error(`Unknown unit options ${exhaustive}`);
|
|
56
77
|
}
|
|
57
|
-
|
|
58
|
-
return formatBits(value, formatOptions);
|
|
59
|
-
}
|
|
60
|
-
if (isDecimalUnit(formatOptions)) {
|
|
61
|
-
return formatDecimal(value, formatOptions);
|
|
62
|
-
}
|
|
63
|
-
if (isPercentUnit(formatOptions)) {
|
|
64
|
-
return formatPercent(value, formatOptions);
|
|
65
|
-
}
|
|
66
|
-
if (isTimeUnit(formatOptions)) {
|
|
67
|
-
return formatTime(value, formatOptions);
|
|
68
|
-
}
|
|
69
|
-
if (isThroughputUnit(formatOptions)) {
|
|
70
|
-
return formatThroughput(value, formatOptions);
|
|
71
|
-
}
|
|
72
|
-
if (isCurrencyUnit(formatOptions)) {
|
|
73
|
-
return formatCurrency(value, formatOptions);
|
|
74
|
-
}
|
|
75
|
-
if (isDateUnit(formatOptions)) {
|
|
76
|
-
return formatDate(value, formatOptions);
|
|
77
|
-
}
|
|
78
|
-
if (isTemperatureUnit(formatOptions)) {
|
|
79
|
-
return formatTemperature(value, formatOptions);
|
|
80
|
-
}
|
|
81
|
-
const exhaustive = formatOptions;
|
|
82
|
-
throw new Error(`Unknown unit options ${exhaustive}`);
|
|
78
|
+
return applyCustomLabel(formatted, formatOptions.customLabel, formatOptions.unit);
|
|
83
79
|
}
|
|
84
80
|
export function getUnitConfig(formatOptions) {
|
|
85
81
|
const unit = formatOptions.unit ?? 'decimal';
|
|
86
|
-
|
|
82
|
+
const config = UNIT_CONFIG[unit];
|
|
83
|
+
const customLabel = formatOptions.customLabel?.trim();
|
|
84
|
+
// Only override display name when customLabel is supported for this unit key.
|
|
85
|
+
if (customLabel && supportsCustomLabel(unit)) {
|
|
86
|
+
return {
|
|
87
|
+
...config,
|
|
88
|
+
label: customLabel
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
return config;
|
|
87
92
|
}
|
|
88
93
|
export function getUnitGroup(formatOptions) {
|
|
89
94
|
return getUnitConfig(formatOptions).group ?? 'Decimal';
|
package/dist/model/units.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/model/units.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport type { BitsFormatOptions } from './bits';\nimport { formatBits, BITS_GROUP_CONFIG, BITS_UNIT_CONFIG } from './bits';\nimport type { BytesFormatOptions } from './bytes';\nimport { formatBytes, BYTES_GROUP_CONFIG, BYTES_UNIT_CONFIG } from './bytes';\nimport type { CurrencyFormatOptions } from './currency';\nimport { formatCurrency, CURRENCY_GROUP_CONFIG, CURRENCY_UNIT_CONFIG } from './currency';\nimport type { DateFormatOptions } from './date';\nimport { formatDate, DATE_GROUP_CONFIG, DATE_UNIT_CONFIG } from './date';\nimport type { DecimalFormatOptions } from './decimal';\nimport { formatDecimal, DECIMAL_GROUP_CONFIG, DECIMAL_UNIT_CONFIG } from './decimal';\nimport type { PercentFormatOptions } from './percent';\nimport { formatPercent, PERCENT_GROUP_CONFIG, PERCENT_UNIT_CONFIG } from './percent';\nimport type { TemperatureFormatOptions } from './temperature';\nimport { TEMPERATURE_GROUP_CONFIG, formatTemperature, TEMPERATURE_UNIT_CONFIG } from './temperature';\nimport type { ThroughputFormatOptions } from './throughput';\nimport { formatThroughput, THROUGHPUT_GROUP_CONFIG, THROUGHPUT_UNIT_CONFIG } from './throughput';\nimport type { TimeFormatOptions } from './time';\nimport { formatTime, TIME_GROUP_CONFIG, TIME_UNIT_CONFIG } from './time';\nimport type { UnitGroup, UnitGroupConfig, UnitConfig } from './types';\n\n/**\n * Most of the number formatting is based on Intl.NumberFormat, which is built into JavaScript.\n * Prefer Intl.NumbeFormat because it covers most use cases and will continue to be supported with time.\n *\n * To format bytes, we also make use of the `numbro` package,\n * because it can handle adding units like KB, MB, GB, etc. correctly.\n */\n\nexport const UNIT_GROUP_CONFIG: Readonly<Record<UnitGroup, UnitGroupConfig>> = {\n Time: TIME_GROUP_CONFIG,\n Percent: PERCENT_GROUP_CONFIG,\n Decimal: DECIMAL_GROUP_CONFIG,\n Bytes: BYTES_GROUP_CONFIG,\n Bits: BITS_GROUP_CONFIG,\n Throughput: THROUGHPUT_GROUP_CONFIG,\n Currency: CURRENCY_GROUP_CONFIG,\n Temperature: TEMPERATURE_GROUP_CONFIG,\n Date: DATE_GROUP_CONFIG,\n};\nexport const UNIT_CONFIG = {\n ...TIME_UNIT_CONFIG,\n ...PERCENT_UNIT_CONFIG,\n ...DECIMAL_UNIT_CONFIG,\n ...BYTES_UNIT_CONFIG,\n ...BITS_UNIT_CONFIG,\n ...THROUGHPUT_UNIT_CONFIG,\n ...CURRENCY_UNIT_CONFIG,\n ...TEMPERATURE_UNIT_CONFIG,\n ...DATE_UNIT_CONFIG,\n} as const;\n\nexport type FormatOptions =\n | TimeFormatOptions\n | PercentFormatOptions\n | DecimalFormatOptions\n | BytesFormatOptions\n | BitsFormatOptions\n | ThroughputFormatOptions\n | CurrencyFormatOptions\n | TemperatureFormatOptions\n | DateFormatOptions;\n\ntype HasDecimalPlaces<UnitOpt> = UnitOpt extends { decimalPlaces?: number } ? UnitOpt : never;\ntype HasShortValues<UnitOpt> = UnitOpt extends { shortValues?: boolean } ? UnitOpt : never;\n\nexport function formatValue(value: number, formatOptions?: FormatOptions): string {\n if (!formatOptions) {\n return value.toString();\n }\n\n if (isBytesUnit(formatOptions)) {\n return formatBytes(value, formatOptions);\n }\n\n if (isBitsUnit(formatOptions)) {\n return formatBits(value, formatOptions);\n }\n\n if (isDecimalUnit(formatOptions)) {\n return formatDecimal(value, formatOptions);\n }\n\n if (isPercentUnit(formatOptions)) {\n return formatPercent(value, formatOptions);\n }\n\n if (isTimeUnit(formatOptions)) {\n return formatTime(value, formatOptions);\n }\n\n if (isThroughputUnit(formatOptions)) {\n return formatThroughput(value, formatOptions);\n }\n\n if (isCurrencyUnit(formatOptions)) {\n return formatCurrency(value, formatOptions);\n }\n\n if (isDateUnit(formatOptions)) {\n return formatDate(value, formatOptions);\n }\n\n if (isTemperatureUnit(formatOptions)) {\n return formatTemperature(value, formatOptions);\n }\n\n const exhaustive: never = formatOptions;\n throw new Error(`Unknown unit options ${exhaustive}`);\n}\n\nexport function getUnitConfig(formatOptions: FormatOptions): UnitConfig {\n const unit = formatOptions.unit ?? 'decimal';\n return UNIT_CONFIG[unit];\n}\n\nexport function getUnitGroup(formatOptions: FormatOptions): UnitGroup {\n return getUnitConfig(formatOptions).group ?? 'Decimal';\n}\n\nexport function getUnitGroupConfig(formatOptions: FormatOptions): UnitGroupConfig {\n const unitConfig = getUnitConfig(formatOptions);\n return UNIT_GROUP_CONFIG[unitConfig.group ?? 'Decimal'];\n}\n\n// Type guards\nexport function isTimeUnit(formatOptions: FormatOptions): formatOptions is TimeFormatOptions {\n return getUnitGroup(formatOptions) === 'Time';\n}\n\nexport function isPercentUnit(formatOptions: FormatOptions): formatOptions is PercentFormatOptions {\n return getUnitGroup(formatOptions) === 'Percent';\n}\n\nexport function isDecimalUnit(formatOptions: FormatOptions): formatOptions is DecimalFormatOptions {\n return getUnitGroup(formatOptions) === 'Decimal';\n}\n\nexport function isBytesUnit(formatOptions: FormatOptions): formatOptions is BytesFormatOptions {\n return getUnitGroup(formatOptions) === 'Bytes';\n}\n\nexport function isBitsUnit(formatOptions: FormatOptions): formatOptions is BitsFormatOptions {\n return getUnitGroup(formatOptions) === 'Bits';\n}\n\nexport function isUnitWithDecimalPlaces(\n formatOptions: FormatOptions,\n): formatOptions is HasDecimalPlaces<FormatOptions> {\n const groupConfig = getUnitGroupConfig(formatOptions);\n\n return !!groupConfig.decimalPlaces;\n}\n\nexport function isUnitWithShortValues(formatOptions: FormatOptions): formatOptions is HasShortValues<FormatOptions> {\n const groupConfig = getUnitGroupConfig(formatOptions);\n\n return !!groupConfig.shortValues;\n}\n\nexport function isThroughputUnit(formatOptions: FormatOptions): formatOptions is ThroughputFormatOptions {\n return getUnitGroup(formatOptions) === 'Throughput';\n}\n\nexport function isCurrencyUnit(formatOptions: FormatOptions): formatOptions is CurrencyFormatOptions {\n return getUnitGroup(formatOptions) === 'Currency';\n}\n\nexport function isDateUnit(formatOptions: FormatOptions): formatOptions is DateFormatOptions {\n return getUnitGroup(formatOptions) === 'Date';\n}\n\nexport function isTemperatureUnit(formatOptions: FormatOptions): formatOptions is TemperatureFormatOptions {\n return getUnitGroup(formatOptions) === 'Temperature';\n}\n"],"names":["formatBits","BITS_GROUP_CONFIG","BITS_UNIT_CONFIG","formatBytes","BYTES_GROUP_CONFIG","BYTES_UNIT_CONFIG","formatCurrency","CURRENCY_GROUP_CONFIG","CURRENCY_UNIT_CONFIG","formatDate","DATE_GROUP_CONFIG","DATE_UNIT_CONFIG","formatDecimal","DECIMAL_GROUP_CONFIG","DECIMAL_UNIT_CONFIG","formatPercent","PERCENT_GROUP_CONFIG","PERCENT_UNIT_CONFIG","TEMPERATURE_GROUP_CONFIG","formatTemperature","TEMPERATURE_UNIT_CONFIG","formatThroughput","THROUGHPUT_GROUP_CONFIG","THROUGHPUT_UNIT_CONFIG","formatTime","TIME_GROUP_CONFIG","TIME_UNIT_CONFIG","UNIT_GROUP_CONFIG","Time","Percent","Decimal","Bytes","Bits","Throughput","Currency","Temperature","Date","UNIT_CONFIG","formatValue","value","formatOptions","toString","isBytesUnit","isBitsUnit","isDecimalUnit","isPercentUnit","isTimeUnit","isThroughputUnit","isCurrencyUnit","isDateUnit","isTemperatureUnit","exhaustive","Error","getUnitConfig","unit","getUnitGroup","group","getUnitGroupConfig","unitConfig","isUnitWithDecimalPlaces","groupConfig","decimalPlaces","isUnitWithShortValues","shortValues"],"mappings":"AAAA,+BAA+B;AAC/B,kEAAkE;AAClE,mEAAmE;AACnE,0CAA0C;AAC1C,EAAE;AACF,6CAA6C;AAC7C,EAAE;AACF,sEAAsE;AACtE,oEAAoE;AACpE,2EAA2E;AAC3E,sEAAsE;AACtE,iCAAiC;AAGjC,SAASA,UAAU,EAAEC,iBAAiB,EAAEC,gBAAgB,QAAQ,YAAS;AAEzE,SAASC,WAAW,EAAEC,kBAAkB,EAAEC,iBAAiB,QAAQ,aAAU;AAE7E,SAASC,cAAc,EAAEC,qBAAqB,EAAEC,oBAAoB,QAAQ,gBAAa;AAEzF,SAASC,UAAU,EAAEC,iBAAiB,EAAEC,gBAAgB,QAAQ,YAAS;AAEzE,SAASC,aAAa,EAAEC,oBAAoB,EAAEC,mBAAmB,QAAQ,eAAY;AAErF,SAASC,aAAa,EAAEC,oBAAoB,EAAEC,mBAAmB,QAAQ,eAAY;AAErF,SAASC,wBAAwB,EAAEC,iBAAiB,EAAEC,uBAAuB,QAAQ,mBAAgB;AAErG,SAASC,gBAAgB,EAAEC,uBAAuB,EAAEC,sBAAsB,QAAQ,kBAAe;AAEjG,SAASC,UAAU,EAAEC,iBAAiB,EAAEC,gBAAgB,QAAQ,YAAS;AAGzE;;;;;;CAMC,GAED,OAAO,MAAMC,oBAAkE;IAC7EC,MAAMH;IACNI,SAASb;IACTc,SAASjB;IACTkB,OAAO3B;IACP4B,MAAM/B;IACNgC,YAAYX;IACZY,UAAU3B;IACV4B,aAAajB;IACbkB,MAAM1B;AACR,EAAE;AACF,OAAO,MAAM2B,cAAc;IACzB,GAAGX,gBAAgB;IACnB,GAAGT,mBAAmB;IACtB,GAAGH,mBAAmB;IACtB,GAAGT,iBAAiB;IACpB,GAAGH,gBAAgB;IACnB,GAAGqB,sBAAsB;IACzB,GAAGf,oBAAoB;IACvB,GAAGY,uBAAuB;IAC1B,GAAGT,gBAAgB;AACrB,EAAW;AAgBX,OAAO,SAAS2B,YAAYC,KAAa,EAAEC,aAA6B;IACtE,IAAI,CAACA,eAAe;QAClB,OAAOD,MAAME,QAAQ;IACvB;IAEA,IAAIC,YAAYF,gBAAgB;QAC9B,OAAOrC,YAAYoC,OAAOC;IAC5B;IAEA,IAAIG,WAAWH,gBAAgB;QAC7B,OAAOxC,WAAWuC,OAAOC;IAC3B;IAEA,IAAII,cAAcJ,gBAAgB;QAChC,OAAO5B,cAAc2B,OAAOC;IAC9B;IAEA,IAAIK,cAAcL,gBAAgB;QAChC,OAAOzB,cAAcwB,OAAOC;IAC9B;IAEA,IAAIM,WAAWN,gBAAgB;QAC7B,OAAOhB,WAAWe,OAAOC;IAC3B;IAEA,IAAIO,iBAAiBP,gBAAgB;QACnC,OAAOnB,iBAAiBkB,OAAOC;IACjC;IAEA,IAAIQ,eAAeR,gBAAgB;QACjC,OAAOlC,eAAeiC,OAAOC;IAC/B;IAEA,IAAIS,WAAWT,gBAAgB;QAC7B,OAAO/B,WAAW8B,OAAOC;IAC3B;IAEA,IAAIU,kBAAkBV,gBAAgB;QACpC,OAAOrB,kBAAkBoB,OAAOC;IAClC;IAEA,MAAMW,aAAoBX;IAC1B,MAAM,IAAIY,MAAM,CAAC,qBAAqB,EAAED,YAAY;AACtD;AAEA,OAAO,SAASE,cAAcb,aAA4B;IACxD,MAAMc,OAAOd,cAAcc,IAAI,IAAI;IACnC,OAAOjB,WAAW,CAACiB,KAAK;AAC1B;AAEA,OAAO,SAASC,aAAaf,aAA4B;IACvD,OAAOa,cAAcb,eAAegB,KAAK,IAAI;AAC/C;AAEA,OAAO,SAASC,mBAAmBjB,aAA4B;IAC7D,MAAMkB,aAAaL,cAAcb;IACjC,OAAOb,iBAAiB,CAAC+B,WAAWF,KAAK,IAAI,UAAU;AACzD;AAEA,cAAc;AACd,OAAO,SAASV,WAAWN,aAA4B;IACrD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASK,cAAcL,aAA4B;IACxD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASI,cAAcJ,aAA4B;IACxD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASE,YAAYF,aAA4B;IACtD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASG,WAAWH,aAA4B;IACrD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASmB,wBACdnB,aAA4B;IAE5B,MAAMoB,cAAcH,mBAAmBjB;IAEvC,OAAO,CAAC,CAACoB,YAAYC,aAAa;AACpC;AAEA,OAAO,SAASC,sBAAsBtB,aAA4B;IAChE,MAAMoB,cAAcH,mBAAmBjB;IAEvC,OAAO,CAAC,CAACoB,YAAYG,WAAW;AAClC;AAEA,OAAO,SAAShB,iBAAiBP,aAA4B;IAC3D,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASQ,eAAeR,aAA4B;IACzD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASS,WAAWT,aAA4B;IACrD,OAAOe,aAAaf,mBAAmB;AACzC;AAEA,OAAO,SAASU,kBAAkBV,aAA4B;IAC5D,OAAOe,aAAaf,mBAAmB;AACzC"}
|
|
1
|
+
{"version":3,"sources":["../../src/model/units.ts"],"sourcesContent":["// Copyright The Perses Authors\n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//\n// http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n\nimport type { BitsFormatOptions } from './bits';\nimport { formatBits, BITS_GROUP_CONFIG, BITS_UNIT_CONFIG } from './bits';\nimport type { BytesFormatOptions } from './bytes';\nimport { formatBytes, BYTES_GROUP_CONFIG, BYTES_UNIT_CONFIG } from './bytes';\nimport type { CurrencyFormatOptions } from './currency';\nimport { formatCurrency, CURRENCY_GROUP_CONFIG, CURRENCY_UNIT_CONFIG } from './currency';\nimport type { WithCustomLabel } from './custom';\nimport { applyCustomLabel, supportsCustomLabel } from './custom';\nimport type { DateFormatOptions } from './date';\nimport { formatDate, DATE_GROUP_CONFIG, DATE_UNIT_CONFIG } from './date';\nimport type { DecimalFormatOptions } from './decimal';\nimport { formatDecimal, DECIMAL_GROUP_CONFIG, DECIMAL_UNIT_CONFIG } from './decimal';\nimport type { PercentFormatOptions } from './percent';\nimport { formatPercent, PERCENT_GROUP_CONFIG, PERCENT_UNIT_CONFIG } from './percent';\nimport type { TemperatureFormatOptions } from './temperature';\nimport { TEMPERATURE_GROUP_CONFIG, formatTemperature, TEMPERATURE_UNIT_CONFIG } from './temperature';\nimport type { ThroughputFormatOptions } from './throughput';\nimport { formatThroughput, THROUGHPUT_GROUP_CONFIG, THROUGHPUT_UNIT_CONFIG } from './throughput';\nimport type { TimeFormatOptions } from './time';\nimport { formatTime, TIME_GROUP_CONFIG, TIME_UNIT_CONFIG } from './time';\nimport type { UnitGroup, UnitGroupConfig, UnitConfig } from './types';\n\n/**\n * Most of the number formatting is based on Intl.NumberFormat, which is built into JavaScript.\n * Prefer Intl.NumbeFormat because it covers most use cases and will continue to be supported with time.\n *\n * To format bytes, we also make use of the `numbro` package,\n * because it can handle adding units like KB, MB, GB, etc. correctly.\n */\n\nexport const UNIT_GROUP_CONFIG: Readonly<Record<UnitGroup, UnitGroupConfig>> = {\n Time: TIME_GROUP_CONFIG,\n Percent: PERCENT_GROUP_CONFIG,\n Decimal: DECIMAL_GROUP_CONFIG,\n Bytes: BYTES_GROUP_CONFIG,\n Bits: BITS_GROUP_CONFIG,\n Throughput: THROUGHPUT_GROUP_CONFIG,\n Currency: CURRENCY_GROUP_CONFIG,\n Temperature: TEMPERATURE_GROUP_CONFIG,\n Date: DATE_GROUP_CONFIG,\n};\nexport const UNIT_CONFIG = {\n ...TIME_UNIT_CONFIG,\n ...PERCENT_UNIT_CONFIG,\n ...DECIMAL_UNIT_CONFIG,\n ...BYTES_UNIT_CONFIG,\n ...BITS_UNIT_CONFIG,\n ...THROUGHPUT_UNIT_CONFIG,\n ...CURRENCY_UNIT_CONFIG,\n ...TEMPERATURE_UNIT_CONFIG,\n ...DATE_UNIT_CONFIG,\n} as const;\n\n/** Standard unit options plus optional display override (customLabel). */\nexport type FormatOptions = (\n | TimeFormatOptions\n | PercentFormatOptions\n | DecimalFormatOptions\n | BytesFormatOptions\n | BitsFormatOptions\n | ThroughputFormatOptions\n | CurrencyFormatOptions\n | TemperatureFormatOptions\n | DateFormatOptions\n) &\n WithCustomLabel;\n\ntype HasDecimalPlaces<UnitOpt> = UnitOpt extends { decimalPlaces?: number } ? UnitOpt : never;\ntype HasShortValues<UnitOpt> = UnitOpt extends { shortValues?: boolean } ? UnitOpt : never;\n\nexport function formatValue(value: number, formatOptions?: FormatOptions): string {\n if (!formatOptions) {\n return value.toString();\n }\n\n let formatted: string;\n if (isBytesUnit(formatOptions)) {\n formatted = formatBytes(value, formatOptions);\n } else if (isBitsUnit(formatOptions)) {\n formatted = formatBits(value, formatOptions);\n } else if (isDecimalUnit(formatOptions)) {\n formatted = formatDecimal(value, formatOptions);\n } else if (isPercentUnit(formatOptions)) {\n formatted = formatPercent(value, formatOptions);\n } else if (isTimeUnit(formatOptions)) {\n formatted = formatTime(value, formatOptions);\n } else if (isThroughputUnit(formatOptions)) {\n formatted = formatThroughput(value, formatOptions);\n } else if (isCurrencyUnit(formatOptions)) {\n formatted = formatCurrency(value, formatOptions);\n } else if (isDateUnit(formatOptions)) {\n formatted = formatDate(value, formatOptions);\n } else if (isTemperatureUnit(formatOptions)) {\n formatted = formatTemperature(value, formatOptions);\n } else {\n const exhaustive: never = formatOptions;\n throw new Error(`Unknown unit options ${exhaustive}`);\n }\n\n return applyCustomLabel(formatted, formatOptions.customLabel, formatOptions.unit);\n}\n\nexport function getUnitConfig(formatOptions: FormatOptions): UnitConfig {\n const unit = formatOptions.unit ?? 'decimal';\n const config = UNIT_CONFIG[unit];\n const customLabel = formatOptions.customLabel?.trim();\n // Only override display name when customLabel is supported for this unit key.\n if (customLabel && supportsCustomLabel(unit)) {\n return { ...config, label: customLabel };\n }\n return config;\n}\n\nexport function getUnitGroup(formatOptions: FormatOptions): UnitGroup {\n return getUnitConfig(formatOptions).group ?? 'Decimal';\n}\n\nexport function getUnitGroupConfig(formatOptions: FormatOptions): UnitGroupConfig {\n const unitConfig = getUnitConfig(formatOptions);\n return UNIT_GROUP_CONFIG[unitConfig.group ?? 'Decimal'];\n}\n\n// Type guards\nexport function isTimeUnit(formatOptions: FormatOptions): formatOptions is TimeFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Time';\n}\n\nexport function isPercentUnit(formatOptions: FormatOptions): formatOptions is PercentFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Percent';\n}\n\nexport function isDecimalUnit(formatOptions: FormatOptions): formatOptions is DecimalFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Decimal';\n}\n\nexport function isBytesUnit(formatOptions: FormatOptions): formatOptions is BytesFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Bytes';\n}\n\nexport function isBitsUnit(formatOptions: FormatOptions): formatOptions is BitsFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Bits';\n}\n\nexport function isUnitWithDecimalPlaces(\n formatOptions: FormatOptions,\n): formatOptions is HasDecimalPlaces<FormatOptions> {\n const groupConfig = getUnitGroupConfig(formatOptions);\n\n return !!groupConfig.decimalPlaces;\n}\n\nexport function isUnitWithShortValues(formatOptions: FormatOptions): formatOptions is HasShortValues<FormatOptions> {\n const groupConfig = getUnitGroupConfig(formatOptions);\n\n return !!groupConfig.shortValues;\n}\n\nexport function isThroughputUnit(\n formatOptions: FormatOptions,\n): formatOptions is ThroughputFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Throughput';\n}\n\nexport function isCurrencyUnit(formatOptions: FormatOptions): formatOptions is CurrencyFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Currency';\n}\n\nexport function isDateUnit(formatOptions: FormatOptions): formatOptions is DateFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Date';\n}\n\nexport function isTemperatureUnit(\n formatOptions: FormatOptions,\n): formatOptions is TemperatureFormatOptions & WithCustomLabel {\n return getUnitGroup(formatOptions) === 'Temperature';\n}\n"],"names":["formatBits","BITS_GROUP_CONFIG","BITS_UNIT_CONFIG","formatBytes","BYTES_GROUP_CONFIG","BYTES_UNIT_CONFIG","formatCurrency","CURRENCY_GROUP_CONFIG","CURRENCY_UNIT_CONFIG","applyCustomLabel","supportsCustomLabel","formatDate","DATE_GROUP_CONFIG","DATE_UNIT_CONFIG","formatDecimal","DECIMAL_GROUP_CONFIG","DECIMAL_UNIT_CONFIG","formatPercent","PERCENT_GROUP_CONFIG","PERCENT_UNIT_CONFIG","TEMPERATURE_GROUP_CONFIG","formatTemperature","TEMPERATURE_UNIT_CONFIG","formatThroughput","THROUGHPUT_GROUP_CONFIG","THROUGHPUT_UNIT_CONFIG","formatTime","TIME_GROUP_CONFIG","TIME_UNIT_CONFIG","UNIT_GROUP_CONFIG","Time","Percent","Decimal","Bytes","Bits","Throughput","Currency","Temperature","Date","UNIT_CONFIG","formatValue","value","formatOptions","toString","formatted","isBytesUnit","isBitsUnit","isDecimalUnit","isPercentUnit","isTimeUnit","isThroughputUnit","isCurrencyUnit","isDateUnit","isTemperatureUnit","exhaustive","Error","customLabel","unit","getUnitConfig","config","trim","label","getUnitGroup","group","getUnitGroupConfig","unitConfig","isUnitWithDecimalPlaces","groupConfig","decimalPlaces","isUnitWithShortValues","shortValues"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@perses-dev/components",
|
|
3
|
-
"version": "0.55.0-beta.
|
|
3
|
+
"version": "0.55.0-beta.14",
|
|
4
4
|
"description": "Common UI components used across Perses features",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"homepage": "https://github.com/perses/perses/blob/main/README.md",
|
|
@@ -34,8 +34,8 @@
|
|
|
34
34
|
"@date-fns/tz": "^1.4.1",
|
|
35
35
|
"@fontsource/inter": "^5.0.0",
|
|
36
36
|
"@mui/x-date-pickers": "^7.23.1",
|
|
37
|
-
"@perses-dev/spec": "0.3.0-beta.
|
|
38
|
-
"@perses-dev/client": "0.55.0-beta.
|
|
37
|
+
"@perses-dev/spec": "0.3.0-beta.10",
|
|
38
|
+
"@perses-dev/client": "0.55.0-beta.14",
|
|
39
39
|
"numbro": "^2.3.6",
|
|
40
40
|
"@tanstack/match-sorter-utils": "^8.19.4",
|
|
41
41
|
"@tanstack/react-table": "^8.20.5",
|