@record-evolution/widget-navbutton 1.0.8 → 1.0.10
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/widget-navbutton.js +58 -42
- package/dist/widget-navbutton.js.map +1 -1
- package/package.json +5 -4
- package/src/widget-navbutton.ts +43 -12
- package/thumbnail.webp +0 -0
package/dist/widget-navbutton.js
CHANGED
|
@@ -1,16 +1,22 @@
|
|
|
1
|
-
import { css as
|
|
2
|
-
import { property as
|
|
1
|
+
import { css as d, LitElement as h, html as m } from "lit";
|
|
2
|
+
import { property as c, state as u, customElement as p } from "lit/decorators.js";
|
|
3
3
|
import "@material/web/icon/icon.js";
|
|
4
4
|
import "@material/web/button/filled-button.js";
|
|
5
|
-
|
|
6
|
-
var
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
return r && i && f(e, o, i), i;
|
|
5
|
+
var f = Object.defineProperty, b = Object.getOwnPropertyDescriptor, n = (t, e, o, r) => {
|
|
6
|
+
for (var l = r > 1 ? void 0 : r ? b(e, o) : e, s = t.length - 1, a; s >= 0; s--)
|
|
7
|
+
(a = t[s]) && (l = (r ? a(e, o, l) : a(l)) || l);
|
|
8
|
+
return r && l && f(e, o, l), l;
|
|
10
9
|
};
|
|
11
|
-
|
|
10
|
+
const g = (t) => {
|
|
11
|
+
if (!t) return !0;
|
|
12
|
+
const e = t.trim().toLowerCase();
|
|
13
|
+
if (e === "transparent") return !0;
|
|
14
|
+
const o = e.match(/^(?:rgba|hsla)\([^)]*[,/]\s*([\d.]+%?)\s*\)$/);
|
|
15
|
+
return o ? parseFloat(o[1]) === 0 : /^#[0-9a-f]{8}$/.test(e) ? e.slice(7) === "00" : /^#[0-9a-f]{4}$/.test(e) ? e[4] === "0" : !1;
|
|
16
|
+
};
|
|
17
|
+
let i = class extends h {
|
|
12
18
|
constructor() {
|
|
13
|
-
super(...arguments), this.version = "1.0.
|
|
19
|
+
super(...arguments), this.version = "1.0.10";
|
|
14
20
|
}
|
|
15
21
|
update(t) {
|
|
16
22
|
t.has("theme") && this.registerTheme(this.theme), super.update(t);
|
|
@@ -19,8 +25,8 @@ let l = class extends h {
|
|
|
19
25
|
this.registerTheme(this.theme);
|
|
20
26
|
}
|
|
21
27
|
registerTheme(t) {
|
|
22
|
-
const e = getComputedStyle(this).getPropertyValue("--re-text-color").trim(), o = getComputedStyle(this).getPropertyValue("--re-tile-background-color").trim();
|
|
23
|
-
this.themeBgColor = o ||
|
|
28
|
+
const e = getComputedStyle(this).getPropertyValue("--re-text-color").trim(), o = getComputedStyle(this).getPropertyValue("--re-tile-background-color").trim(), r = t?.theme_object?.backgroundColor;
|
|
29
|
+
this.themeBgColor = o || (g(r) ? void 0 : r), this.themeTitleColor = e || t?.theme_object?.title?.textStyle?.color;
|
|
24
30
|
}
|
|
25
31
|
handleNavItemClick() {
|
|
26
32
|
let t;
|
|
@@ -42,35 +48,42 @@ let l = class extends h {
|
|
|
42
48
|
o.label && (e = e.split(`{{${o.label}}}`).join(encodeURIComponent(String(o.value ?? ""))));
|
|
43
49
|
if (e.includes("*")) {
|
|
44
50
|
const o = (this.route || "").split("/").filter(Boolean), r = e.split("/").filter(Boolean);
|
|
45
|
-
for (let
|
|
46
|
-
r[
|
|
51
|
+
for (let l = 0; l < r.length; l++)
|
|
52
|
+
r[l] === "*" && (r[l] = o[l] ?? "");
|
|
47
53
|
e = (e.startsWith("/") ? "/" : "") + r.filter(Boolean).join("/");
|
|
48
54
|
}
|
|
49
55
|
return e;
|
|
50
56
|
}
|
|
51
57
|
render() {
|
|
52
|
-
const t = this.inputData?.style?.fontSize ?? 16, e =
|
|
53
|
-
return
|
|
58
|
+
const t = this.inputData?.style?.fontSize ?? 16, e = t * 1.5, o = this.inputData?.style?.color || this.themeTitleColor || "black", r = this.inputData?.style?.backgroundColor || this.themeBgColor || "white", l = Math.max(40, Math.round(t * 2.5));
|
|
59
|
+
return m`
|
|
54
60
|
<md-filled-button
|
|
55
|
-
style="
|
|
56
|
-
|
|
61
|
+
style="--btn-fg: ${o};
|
|
62
|
+
font-size: ${t}px;
|
|
63
|
+
--md-filled-button-label-text-size: ${t}px;
|
|
64
|
+
--md-filled-button-container-height: ${l}px;
|
|
65
|
+
--md-filled-button-icon-size: ${e}px;
|
|
66
|
+
--md-filled-button-label-text-color: ${o};
|
|
57
67
|
--md-filled-button-hover-label-text-color: ${o};
|
|
58
68
|
--md-filled-button-pressed-label-text-color: ${o};
|
|
59
69
|
--md-filled-button-focus-label-text-color: ${o};
|
|
70
|
+
--md-filled-button-icon-color: ${o};
|
|
71
|
+
--md-filled-button-hover-icon-color: ${o};
|
|
72
|
+
--md-filled-button-pressed-icon-color: ${o};
|
|
73
|
+
--md-filled-button-focus-icon-color: ${o};
|
|
60
74
|
--md-filled-button-container-color: ${r};
|
|
61
75
|
"
|
|
62
76
|
@click=${() => this.handleNavItemClick()}
|
|
63
77
|
>
|
|
64
78
|
${this.inputData?.title}
|
|
65
|
-
<md-
|
|
66
|
-
<md-icon slot="icon" style="font-size: ${e}px; color: ${o}"
|
|
79
|
+
<md-icon slot="icon" style="--md-icon-size: ${e}px;"
|
|
67
80
|
>${this.inputData?.iconName}</md-icon
|
|
68
81
|
>
|
|
69
82
|
</md-filled-button>
|
|
70
83
|
`;
|
|
71
84
|
}
|
|
72
85
|
};
|
|
73
|
-
|
|
86
|
+
i.styles = d`
|
|
74
87
|
:host {
|
|
75
88
|
display: flex;
|
|
76
89
|
align-items: center;
|
|
@@ -90,30 +103,33 @@ l.styles = c`
|
|
|
90
103
|
flex: 1;
|
|
91
104
|
--md-filled-button-container-shape: 4px;
|
|
92
105
|
--md-filled-button-container-shadow-color: none;
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
--md-ripple-
|
|
106
|
+
/* State layers follow the configured label color; a hard-coded
|
|
107
|
+
accent stays teal no matter how the button is styled. */
|
|
108
|
+
--md-ripple-hover-color: var(--btn-fg);
|
|
109
|
+
--md-ripple-pressed-color: var(--btn-fg);
|
|
110
|
+
--md-filled-button-hover-state-layer-color: var(--btn-fg);
|
|
111
|
+
--md-filled-button-pressed-state-layer-color: var(--btn-fg);
|
|
96
112
|
}
|
|
97
113
|
`;
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
],
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
],
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
],
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
],
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
],
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
],
|
|
114
|
+
n([
|
|
115
|
+
c({ type: Object })
|
|
116
|
+
], i.prototype, "inputData", 2);
|
|
117
|
+
n([
|
|
118
|
+
c({ type: Object })
|
|
119
|
+
], i.prototype, "theme", 2);
|
|
120
|
+
n([
|
|
121
|
+
c({ type: String })
|
|
122
|
+
], i.prototype, "route", 2);
|
|
123
|
+
n([
|
|
124
|
+
u()
|
|
125
|
+
], i.prototype, "themeBgColor", 2);
|
|
126
|
+
n([
|
|
127
|
+
u()
|
|
128
|
+
], i.prototype, "themeTitleColor", 2);
|
|
129
|
+
i = n([
|
|
130
|
+
p("widget-navbutton-1.0.10")
|
|
131
|
+
], i);
|
|
116
132
|
export {
|
|
117
|
-
|
|
133
|
+
i as WidgetNavbutton
|
|
118
134
|
};
|
|
119
135
|
//# sourceMappingURL=widget-navbutton.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"widget-navbutton.js","sources":["../src/widget-navbutton.ts"],"sourcesContent":["import { html, css, LitElement, PropertyValues } from 'lit'\nimport { customElement, property, state } from 'lit/decorators.js'\nimport { InputData } from './definition-schema'\n\nimport '@material/web/icon/icon.js'\nimport '@material/web/button/filled-button.js'\nimport '@material/web/ripple/ripple.js'\n\ntype Theme = {\n theme_name: string\n theme_object: any\n}\n\n@customElement('widget-navbutton-versionplaceholder')\nexport class WidgetNavbutton extends LitElement {\n @property({ type: Object }) inputData?: InputData\n @property({ type: Object }) theme?: Theme\n @property({ type: String }) route?: string\n\n @state() private themeBgColor?: string\n @state() private themeTitleColor?: string\n\n version: string = 'versionplaceholder'\n\n update(changedProperties: Map<string, any>) {\n if (changedProperties.has('theme')) {\n this.registerTheme(this.theme)\n }\n\n super.update(changedProperties)\n }\n\n protected firstUpdated(_changedProperties: PropertyValues): void {\n this.registerTheme(this.theme)\n }\n\n registerTheme(theme?: Theme) {\n const cssTextColor = getComputedStyle(this).getPropertyValue('--re-text-color').trim()\n const cssBgColor = getComputedStyle(this).getPropertyValue('--re-tile-background-color').trim()\n this.themeBgColor = cssBgColor || this.theme?.theme_object?.backgroundColor\n this.themeTitleColor = cssTextColor || this.theme?.theme_object?.title?.textStyle?.color\n }\n\n handleNavItemClick() {\n let goto: string\n if (this.inputData?.route === '') {\n goto = '/' + this.route?.split('/').filter(Boolean).slice(0, -1).join('/') + '/' || '/'\n goto = goto === '//' ? '/' : goto\n } else {\n goto =\n this.resolveRoute({\n route: this.inputData?.route,\n variables: this.inputData?.variables\n }) || '/'\n }\n const event = new CustomEvent('nav-submit', {\n detail: { path: goto },\n bubbles: true,\n composed: true\n })\n this.dispatchEvent(event)\n }\n\n resolveRoute(item?: any): string | undefined {\n let route = String(item?.route ?? '')\n if (item?.variables) {\n for (const variable of item.variables) {\n if (variable.label) {\n route = route\n .split(`{{${variable.label}}}`)\n .join(encodeURIComponent(String(variable.value ?? '')))\n }\n }\n }\n if (route.includes('*')) {\n const currentSegments = (this.route || '').split('/').filter(Boolean)\n const routeSegments = route.split('/').filter(Boolean)\n for (let i = 0; i < routeSegments.length; i++) {\n if (routeSegments[i] === '*') {\n routeSegments[i] = currentSegments[i] ?? ''\n }\n }\n route = (route.startsWith('/') ? '/' : '') + routeSegments.filter(Boolean).join('/')\n }\n return route\n }\n\n static styles = css`\n :host {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 100%;\n height: 100%;\n font-family: sans-serif;\n box-sizing: border-box;\n margin: auto;\n padding: 2cqh 2cqw;\n }\n\n md-icon {\n font-family: 'Material Symbols Outlined';\n }\n md-filled-button {\n flex: 1;\n --md-filled-button-container-shape: 4px;\n --md-filled-button-container-shadow-color: none;\n --md-sys-color-primary: #006a6a;\n --md-ripple-hover-color: var(--md-sys-color-primary);\n --md-ripple-pressed-color: var(--md-sys-color-primary);\n }\n `\n\n render() {\n const fontSize = this.inputData?.style?.fontSize ?? 16\n const iconFontSize = (this.inputData?.style?.fontSize ?? 16) * 1.5\n const fontColor = this.inputData?.style?.color || this.themeTitleColor || 'black'\n const bgColor = this.inputData?.style?.backgroundColor || this.themeBgColor || 'white'\n const gap = fontSize * 0.4\n return html`\n <md-filled-button\n style=\"font-size: ${fontSize}px; \n --md-filled-button-label-text-color: ${fontColor}; \n --md-filled-button-hover-label-text-color: ${fontColor};\n --md-filled-button-pressed-label-text-color: ${fontColor};\n --md-filled-button-focus-label-text-color: ${fontColor};\n --md-filled-button-container-color: ${bgColor};\n \"\n @click=${() => this.handleNavItemClick()}\n >\n ${this.inputData?.title}\n <md-ripple></md-ripple>\n <md-icon slot=\"icon\" style=\"font-size: ${iconFontSize}px; color: ${fontColor}\"\n >${this.inputData?.iconName}</md-icon\n >\n </md-filled-button>\n `\n }\n}\n"],"names":["WidgetNavbutton","LitElement","changedProperties","_changedProperties","theme","cssTextColor","cssBgColor","goto","event","item","route","variable","currentSegments","routeSegments","fontSize","iconFontSize","fontColor","bgColor","html","css","__decorateClass","property","state","customElement"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"widget-navbutton.js","sources":["../src/widget-navbutton.ts"],"sourcesContent":["import { html, css, LitElement, PropertyValues } from 'lit'\nimport { customElement, property, state } from 'lit/decorators.js'\nimport { InputData } from './definition-schema'\n\nimport '@material/web/icon/icon.js'\nimport '@material/web/button/filled-button.js'\n\ntype Theme = {\n theme_name: string\n theme_object: any\n}\n\n/**\n * ECharts themes describe a *chart canvas*, and most of them set\n * `backgroundColor` to a fully transparent colour (the light theme uses\n * `rgba(0, 0, 0, 0)`). That is a valid, truthy colour string, so using it\n * verbatim as the button background paints nothing at all. Treat any\n * fully transparent theme colour as \"no colour\" so the fallback kicks in.\n */\nconst isTransparent = (color?: string) => {\n if (!color) return true\n const value = color.trim().toLowerCase()\n if (value === 'transparent') return true\n const functional = value.match(/^(?:rgba|hsla)\\([^)]*[,/]\\s*([\\d.]+%?)\\s*\\)$/)\n if (functional) return parseFloat(functional[1]) === 0\n // #rrggbbaa / #rgba\n if (/^#[0-9a-f]{8}$/.test(value)) return value.slice(7) === '00'\n if (/^#[0-9a-f]{4}$/.test(value)) return value[4] === '0'\n return false\n}\n\n@customElement('widget-navbutton-versionplaceholder')\nexport class WidgetNavbutton extends LitElement {\n @property({ type: Object }) inputData?: InputData\n @property({ type: Object }) theme?: Theme\n @property({ type: String }) route?: string\n\n @state() private themeBgColor?: string\n @state() private themeTitleColor?: string\n\n version: string = 'versionplaceholder'\n\n update(changedProperties: Map<string, any>) {\n if (changedProperties.has('theme')) {\n this.registerTheme(this.theme)\n }\n\n super.update(changedProperties)\n }\n\n protected firstUpdated(_changedProperties: PropertyValues): void {\n this.registerTheme(this.theme)\n }\n\n registerTheme(theme?: Theme) {\n const cssTextColor = getComputedStyle(this).getPropertyValue('--re-text-color').trim()\n const cssBgColor = getComputedStyle(this).getPropertyValue('--re-tile-background-color').trim()\n const themeBgColor = theme?.theme_object?.backgroundColor\n this.themeBgColor = cssBgColor || (isTransparent(themeBgColor) ? undefined : themeBgColor)\n this.themeTitleColor = cssTextColor || theme?.theme_object?.title?.textStyle?.color\n }\n\n handleNavItemClick() {\n let goto: string\n if (this.inputData?.route === '') {\n goto = '/' + this.route?.split('/').filter(Boolean).slice(0, -1).join('/') + '/' || '/'\n goto = goto === '//' ? '/' : goto\n } else {\n goto =\n this.resolveRoute({\n route: this.inputData?.route,\n variables: this.inputData?.variables\n }) || '/'\n }\n const event = new CustomEvent('nav-submit', {\n detail: { path: goto },\n bubbles: true,\n composed: true\n })\n this.dispatchEvent(event)\n }\n\n resolveRoute(item?: any): string | undefined {\n let route = String(item?.route ?? '')\n if (item?.variables) {\n for (const variable of item.variables) {\n if (variable.label) {\n route = route\n .split(`{{${variable.label}}}`)\n .join(encodeURIComponent(String(variable.value ?? '')))\n }\n }\n }\n if (route.includes('*')) {\n const currentSegments = (this.route || '').split('/').filter(Boolean)\n const routeSegments = route.split('/').filter(Boolean)\n for (let i = 0; i < routeSegments.length; i++) {\n if (routeSegments[i] === '*') {\n routeSegments[i] = currentSegments[i] ?? ''\n }\n }\n route = (route.startsWith('/') ? '/' : '') + routeSegments.filter(Boolean).join('/')\n }\n return route\n }\n\n static styles = css`\n :host {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 100%;\n height: 100%;\n font-family: sans-serif;\n box-sizing: border-box;\n margin: auto;\n padding: 2cqh 2cqw;\n }\n\n md-icon {\n font-family: 'Material Symbols Outlined';\n }\n md-filled-button {\n flex: 1;\n --md-filled-button-container-shape: 4px;\n --md-filled-button-container-shadow-color: none;\n /* State layers follow the configured label color; a hard-coded\n accent stays teal no matter how the button is styled. */\n --md-ripple-hover-color: var(--btn-fg);\n --md-ripple-pressed-color: var(--btn-fg);\n --md-filled-button-hover-state-layer-color: var(--btn-fg);\n --md-filled-button-pressed-state-layer-color: var(--btn-fg);\n }\n `\n\n render() {\n const fontSize = this.inputData?.style?.fontSize ?? 16\n const iconFontSize = fontSize * 1.5\n const fontColor = this.inputData?.style?.color || this.themeTitleColor || 'black'\n const bgColor = this.inputData?.style?.backgroundColor || this.themeBgColor || 'white'\n // The container height is a fixed 40px token, so it has to grow with the\n // label or larger font sizes overflow the button.\n const buttonHeight = Math.max(40, Math.round(fontSize * 2.5))\n return html`\n <md-filled-button\n style=\"--btn-fg: ${fontColor};\n font-size: ${fontSize}px;\n --md-filled-button-label-text-size: ${fontSize}px;\n --md-filled-button-container-height: ${buttonHeight}px;\n --md-filled-button-icon-size: ${iconFontSize}px;\n --md-filled-button-label-text-color: ${fontColor};\n --md-filled-button-hover-label-text-color: ${fontColor};\n --md-filled-button-pressed-label-text-color: ${fontColor};\n --md-filled-button-focus-label-text-color: ${fontColor};\n --md-filled-button-icon-color: ${fontColor};\n --md-filled-button-hover-icon-color: ${fontColor};\n --md-filled-button-pressed-icon-color: ${fontColor};\n --md-filled-button-focus-icon-color: ${fontColor};\n --md-filled-button-container-color: ${bgColor};\n \"\n @click=${() => this.handleNavItemClick()}\n >\n ${this.inputData?.title}\n <md-icon slot=\"icon\" style=\"--md-icon-size: ${iconFontSize}px;\"\n >${this.inputData?.iconName}</md-icon\n >\n </md-filled-button>\n `\n }\n}\n"],"names":["isTransparent","color","value","functional","WidgetNavbutton","LitElement","changedProperties","_changedProperties","theme","cssTextColor","cssBgColor","themeBgColor","goto","event","item","route","variable","currentSegments","routeSegments","i","fontSize","iconFontSize","fontColor","bgColor","buttonHeight","html","css","__decorateClass","property","state","customElement"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
"description": "Webcomponent widget-navbutton following open-wc recommendations",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"author": "widget-navbutton",
|
|
6
|
-
"version": "1.0.
|
|
6
|
+
"version": "1.0.10",
|
|
7
7
|
"engines": {
|
|
8
8
|
"node": ">=24.9.0",
|
|
9
9
|
"npm": ">=10.0.2"
|
|
@@ -14,11 +14,12 @@
|
|
|
14
14
|
"files": [
|
|
15
15
|
"dist",
|
|
16
16
|
"src",
|
|
17
|
-
"thumbnail.png"
|
|
17
|
+
"thumbnail.png",
|
|
18
|
+
"thumbnail.webp"
|
|
18
19
|
],
|
|
19
20
|
"scripts": {
|
|
20
21
|
"analyze": "cem analyze --litelement",
|
|
21
|
-
"start": "vite",
|
|
22
|
+
"start": "vite build --watch & vite",
|
|
22
23
|
"build": "vite build",
|
|
23
24
|
"watch": "vite build --watch",
|
|
24
25
|
"link": "npm run build && npm link && cd ../RESWARM/frontend && npm link @record-evolution/widget-navbutton",
|
|
@@ -27,7 +28,7 @@
|
|
|
27
28
|
"release": "npm run build && npm run types && npm version patch --tag-version-prefix='' && git push && git push --tag && npm run build"
|
|
28
29
|
},
|
|
29
30
|
"dependencies": {
|
|
30
|
-
"lit": "^3.3.
|
|
31
|
+
"lit": "^3.3.3",
|
|
31
32
|
"tslib": "^2.8.1"
|
|
32
33
|
},
|
|
33
34
|
"peerDependencies": {
|
package/src/widget-navbutton.ts
CHANGED
|
@@ -4,13 +4,31 @@ import { InputData } from './definition-schema'
|
|
|
4
4
|
|
|
5
5
|
import '@material/web/icon/icon.js'
|
|
6
6
|
import '@material/web/button/filled-button.js'
|
|
7
|
-
import '@material/web/ripple/ripple.js'
|
|
8
7
|
|
|
9
8
|
type Theme = {
|
|
10
9
|
theme_name: string
|
|
11
10
|
theme_object: any
|
|
12
11
|
}
|
|
13
12
|
|
|
13
|
+
/**
|
|
14
|
+
* ECharts themes describe a *chart canvas*, and most of them set
|
|
15
|
+
* `backgroundColor` to a fully transparent colour (the light theme uses
|
|
16
|
+
* `rgba(0, 0, 0, 0)`). That is a valid, truthy colour string, so using it
|
|
17
|
+
* verbatim as the button background paints nothing at all. Treat any
|
|
18
|
+
* fully transparent theme colour as "no colour" so the fallback kicks in.
|
|
19
|
+
*/
|
|
20
|
+
const isTransparent = (color?: string) => {
|
|
21
|
+
if (!color) return true
|
|
22
|
+
const value = color.trim().toLowerCase()
|
|
23
|
+
if (value === 'transparent') return true
|
|
24
|
+
const functional = value.match(/^(?:rgba|hsla)\([^)]*[,/]\s*([\d.]+%?)\s*\)$/)
|
|
25
|
+
if (functional) return parseFloat(functional[1]) === 0
|
|
26
|
+
// #rrggbbaa / #rgba
|
|
27
|
+
if (/^#[0-9a-f]{8}$/.test(value)) return value.slice(7) === '00'
|
|
28
|
+
if (/^#[0-9a-f]{4}$/.test(value)) return value[4] === '0'
|
|
29
|
+
return false
|
|
30
|
+
}
|
|
31
|
+
|
|
14
32
|
@customElement('widget-navbutton-versionplaceholder')
|
|
15
33
|
export class WidgetNavbutton extends LitElement {
|
|
16
34
|
@property({ type: Object }) inputData?: InputData
|
|
@@ -37,8 +55,9 @@ export class WidgetNavbutton extends LitElement {
|
|
|
37
55
|
registerTheme(theme?: Theme) {
|
|
38
56
|
const cssTextColor = getComputedStyle(this).getPropertyValue('--re-text-color').trim()
|
|
39
57
|
const cssBgColor = getComputedStyle(this).getPropertyValue('--re-tile-background-color').trim()
|
|
40
|
-
|
|
41
|
-
this.
|
|
58
|
+
const themeBgColor = theme?.theme_object?.backgroundColor
|
|
59
|
+
this.themeBgColor = cssBgColor || (isTransparent(themeBgColor) ? undefined : themeBgColor)
|
|
60
|
+
this.themeTitleColor = cssTextColor || theme?.theme_object?.title?.textStyle?.color
|
|
42
61
|
}
|
|
43
62
|
|
|
44
63
|
handleNavItemClick() {
|
|
@@ -105,32 +124,44 @@ export class WidgetNavbutton extends LitElement {
|
|
|
105
124
|
flex: 1;
|
|
106
125
|
--md-filled-button-container-shape: 4px;
|
|
107
126
|
--md-filled-button-container-shadow-color: none;
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
--md-ripple-
|
|
127
|
+
/* State layers follow the configured label color; a hard-coded
|
|
128
|
+
accent stays teal no matter how the button is styled. */
|
|
129
|
+
--md-ripple-hover-color: var(--btn-fg);
|
|
130
|
+
--md-ripple-pressed-color: var(--btn-fg);
|
|
131
|
+
--md-filled-button-hover-state-layer-color: var(--btn-fg);
|
|
132
|
+
--md-filled-button-pressed-state-layer-color: var(--btn-fg);
|
|
111
133
|
}
|
|
112
134
|
`
|
|
113
135
|
|
|
114
136
|
render() {
|
|
115
137
|
const fontSize = this.inputData?.style?.fontSize ?? 16
|
|
116
|
-
const iconFontSize =
|
|
138
|
+
const iconFontSize = fontSize * 1.5
|
|
117
139
|
const fontColor = this.inputData?.style?.color || this.themeTitleColor || 'black'
|
|
118
140
|
const bgColor = this.inputData?.style?.backgroundColor || this.themeBgColor || 'white'
|
|
119
|
-
|
|
141
|
+
// The container height is a fixed 40px token, so it has to grow with the
|
|
142
|
+
// label or larger font sizes overflow the button.
|
|
143
|
+
const buttonHeight = Math.max(40, Math.round(fontSize * 2.5))
|
|
120
144
|
return html`
|
|
121
145
|
<md-filled-button
|
|
122
|
-
style="
|
|
123
|
-
|
|
146
|
+
style="--btn-fg: ${fontColor};
|
|
147
|
+
font-size: ${fontSize}px;
|
|
148
|
+
--md-filled-button-label-text-size: ${fontSize}px;
|
|
149
|
+
--md-filled-button-container-height: ${buttonHeight}px;
|
|
150
|
+
--md-filled-button-icon-size: ${iconFontSize}px;
|
|
151
|
+
--md-filled-button-label-text-color: ${fontColor};
|
|
124
152
|
--md-filled-button-hover-label-text-color: ${fontColor};
|
|
125
153
|
--md-filled-button-pressed-label-text-color: ${fontColor};
|
|
126
154
|
--md-filled-button-focus-label-text-color: ${fontColor};
|
|
155
|
+
--md-filled-button-icon-color: ${fontColor};
|
|
156
|
+
--md-filled-button-hover-icon-color: ${fontColor};
|
|
157
|
+
--md-filled-button-pressed-icon-color: ${fontColor};
|
|
158
|
+
--md-filled-button-focus-icon-color: ${fontColor};
|
|
127
159
|
--md-filled-button-container-color: ${bgColor};
|
|
128
160
|
"
|
|
129
161
|
@click=${() => this.handleNavItemClick()}
|
|
130
162
|
>
|
|
131
163
|
${this.inputData?.title}
|
|
132
|
-
<md-
|
|
133
|
-
<md-icon slot="icon" style="font-size: ${iconFontSize}px; color: ${fontColor}"
|
|
164
|
+
<md-icon slot="icon" style="--md-icon-size: ${iconFontSize}px;"
|
|
134
165
|
>${this.inputData?.iconName}</md-icon
|
|
135
166
|
>
|
|
136
167
|
</md-filled-button>
|
package/thumbnail.webp
ADDED
|
Binary file
|