@glasshome/widget-sdk 1.17.1 → 1.18.0
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/deprecations.js +7 -0
- package/dist/framework/components/anatomy.d.ts +1 -1
- package/dist/framework/design-system/z-index.d.ts +0 -1
- package/dist/framework/gestures/use-widget-gestures.d.ts +1 -1
- package/dist/framework/hooks/use-confirm.d.ts +1 -1
- package/dist/framework/types.d.ts +47 -89
- package/dist/framework/utils/empty-state.d.ts +0 -43
- package/dist/framework/utils/index.d.ts +0 -1
- package/dist/framework/variants/built-in-variants.d.ts +2 -39
- package/dist/index.js +113 -167
- package/package.json +7 -6
- package/preview/host.tsx +4 -2
- package/dist/framework/variants/index.d.ts +0 -7
- package/dist/framework/variants/variant-utils.d.ts +0 -105
package/dist/deprecations.js
CHANGED
|
@@ -87,6 +87,13 @@ var e = "https://glasshome.app/docs/widget-sdk/config", t = [
|
|
|
87
87
|
replacement: "the Widget's tone or color; the fill follows the card",
|
|
88
88
|
docsUrl: "https://glasshome.app/docs/widget-sdk/widget",
|
|
89
89
|
sourcePattern: "<WidgetSliderFill[^>]*\\scolor="
|
|
90
|
+
},
|
|
91
|
+
{
|
|
92
|
+
id: "WidgetVariantConfig.layout",
|
|
93
|
+
since: "1.18.0",
|
|
94
|
+
removeIn: "2.0.0",
|
|
95
|
+
replacement: "WidgetVariantConfig.styles (container, class, cssVars)",
|
|
96
|
+
docsUrl: "https://glasshome.app/docs/widgets/widget-sdk#variants"
|
|
90
97
|
}
|
|
91
98
|
];
|
|
92
99
|
function n(e) {
|
|
@@ -52,7 +52,7 @@ export declare function WidgetAction(props: {
|
|
|
52
52
|
/** Visible label; without one the action is a square icon control named by `aria-label`. */
|
|
53
53
|
children?: JSX.Element;
|
|
54
54
|
"aria-label"?: string;
|
|
55
|
-
run: () =>
|
|
55
|
+
run: () => unknown;
|
|
56
56
|
confirm?: Confirm;
|
|
57
57
|
/** Key within a shared `confirm`; defaults to the label or icon. */
|
|
58
58
|
id?: string;
|
|
@@ -29,7 +29,7 @@ export interface GestureHandlers {
|
|
|
29
29
|
/** Keyboard door: Enter or Space taps, the context-menu key or Shift+F10 holds. */
|
|
30
30
|
onKeyDown?: (e: KeyboardEvent) => void;
|
|
31
31
|
}
|
|
32
|
-
|
|
32
|
+
interface HoldFlood {
|
|
33
33
|
x: number;
|
|
34
34
|
y: number;
|
|
35
35
|
/** Radius that reaches the farthest corner, so the fill ends as the hold fires. */
|
|
@@ -4,7 +4,7 @@ export interface Confirm {
|
|
|
4
4
|
/** Whether anything ran a moment ago. */
|
|
5
5
|
any: () => boolean;
|
|
6
6
|
/** Runs the action; resolves whether it succeeded. */
|
|
7
|
-
run: (keys: string[], action: () =>
|
|
7
|
+
run: (keys: string[], action: () => unknown) => Promise<boolean>;
|
|
8
8
|
}
|
|
9
9
|
/**
|
|
10
10
|
* For actions that leave no state to show (a scene, a button press, a stop): the keys that just ran,
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/** Core type definitions for the Widget Framework. */
|
|
2
2
|
import type { JSX } from "solid-js";
|
|
3
3
|
/** Slide gesture configuration */
|
|
4
|
-
|
|
4
|
+
interface SlideGestureConfig {
|
|
5
5
|
/** Current value */
|
|
6
6
|
value: number;
|
|
7
7
|
/** Value change handler */
|
|
@@ -18,7 +18,7 @@ export interface SlideGestureConfig {
|
|
|
18
18
|
/**
|
|
19
19
|
* Hold gesture configuration
|
|
20
20
|
*/
|
|
21
|
-
|
|
21
|
+
interface HoldGestureConfig {
|
|
22
22
|
/** Action to perform on hold */
|
|
23
23
|
action: () => void;
|
|
24
24
|
/** Hold delay in ms (default: 300) */
|
|
@@ -35,21 +35,15 @@ export interface GestureConfig {
|
|
|
35
35
|
/** Slide gesture configuration */
|
|
36
36
|
slide?: SlideGestureConfig;
|
|
37
37
|
}
|
|
38
|
-
/**
|
|
39
|
-
* CSS variable-based styling configuration
|
|
40
|
-
*/
|
|
38
|
+
/** Look applied to the widget shell: inline style, utility classes and CSS custom properties. */
|
|
41
39
|
export interface WidgetStyles {
|
|
42
|
-
/** Inline CSS properties applied to widget container */
|
|
43
40
|
container?: JSX.CSSProperties;
|
|
44
|
-
/** Tailwind utility classes (for simple styling) */
|
|
45
41
|
class?: string;
|
|
46
|
-
/** CSS custom properties for themeable values */
|
|
47
42
|
cssVars?: Record<`--widget-${string}` | `--glass-${string}`, string | number>;
|
|
48
43
|
}
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
export interface FlexLayoutStrategy {
|
|
44
|
+
type WidgetElement = "icon" | "title" | "subtitle" | "status" | "value" | "metrics" | "content" | "background" | "overlay" | "decorations";
|
|
45
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
46
|
+
type LayoutStrategy = {
|
|
53
47
|
type: "flex";
|
|
54
48
|
direction: "row" | "column" | "row-reverse" | "column-reverse";
|
|
55
49
|
align: "start" | "center" | "end" | "stretch";
|
|
@@ -57,106 +51,69 @@ export interface FlexLayoutStrategy {
|
|
|
57
51
|
wrap?: boolean;
|
|
58
52
|
gap?: string;
|
|
59
53
|
order?: Partial<Record<WidgetElement, number>>;
|
|
60
|
-
}
|
|
61
|
-
/**
|
|
62
|
-
* Grid layout strategy with type-safe configuration
|
|
63
|
-
*/
|
|
64
|
-
export interface GridLayoutStrategy {
|
|
54
|
+
} | {
|
|
65
55
|
type: "grid";
|
|
66
56
|
areas: string;
|
|
67
57
|
columns?: string;
|
|
68
58
|
rows?: string;
|
|
69
59
|
gap?: string;
|
|
70
60
|
elementAreas: Partial<Record<WidgetElement, string>>;
|
|
71
|
-
}
|
|
72
|
-
/**
|
|
73
|
-
* Absolute positioning strategy with type-safe configuration
|
|
74
|
-
*/
|
|
75
|
-
export interface AbsoluteLayoutStrategy {
|
|
61
|
+
} | {
|
|
76
62
|
type: "absolute";
|
|
77
|
-
positions: Partial<Record<WidgetElement,
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
63
|
+
positions: Partial<Record<WidgetElement, {
|
|
64
|
+
top?: string;
|
|
65
|
+
right?: string;
|
|
66
|
+
bottom?: string;
|
|
67
|
+
left?: string;
|
|
68
|
+
transform?: string;
|
|
69
|
+
}>>;
|
|
70
|
+
} | {
|
|
83
71
|
type: "custom";
|
|
84
72
|
renderer: string;
|
|
85
|
-
}
|
|
86
|
-
/**
|
|
87
|
-
* Discriminated union of all layout strategies
|
|
88
|
-
*/
|
|
89
|
-
export type LayoutStrategy = FlexLayoutStrategy | GridLayoutStrategy | AbsoluteLayoutStrategy | CustomLayoutStrategy;
|
|
90
|
-
/**
|
|
91
|
-
* Position configuration for absolute layout
|
|
92
|
-
*/
|
|
93
|
-
export interface PositionConfig {
|
|
94
|
-
top?: string;
|
|
95
|
-
right?: string;
|
|
96
|
-
bottom?: string;
|
|
97
|
-
left?: string;
|
|
98
|
-
transform?: string;
|
|
99
|
-
}
|
|
100
|
-
/**
|
|
101
|
-
* Widget element identifiers for layout configuration
|
|
102
|
-
*/
|
|
103
|
-
export type WidgetElement = "icon" | "title" | "subtitle" | "status" | "value" | "metrics" | "content" | "background" | "overlay" | "decorations";
|
|
104
|
-
/**
|
|
105
|
-
* Element-specific configuration
|
|
106
|
-
*/
|
|
107
|
-
export interface ElementConfig {
|
|
108
|
-
visible?: Partial<Record<WidgetElement, boolean>>;
|
|
109
|
-
styles?: Partial<Record<WidgetElement, JSX.CSSProperties>>;
|
|
110
|
-
classNames?: Partial<Record<WidgetElement, string>>;
|
|
111
|
-
}
|
|
112
|
-
/**
|
|
113
|
-
* Plugin system configuration (serializable)
|
|
114
|
-
*/
|
|
115
|
-
export interface VariantPlugins {
|
|
116
|
-
background?: string;
|
|
117
|
-
overlay?: string;
|
|
118
|
-
decorations?: string[];
|
|
119
|
-
}
|
|
120
|
-
/**
|
|
121
|
-
* Interaction configuration
|
|
122
|
-
*/
|
|
123
|
-
export interface InteractionConfig {
|
|
124
|
-
hover?: boolean;
|
|
125
|
-
active?: boolean;
|
|
126
|
-
focus?: boolean;
|
|
127
|
-
hoverScale?: number;
|
|
128
|
-
activeScale?: number;
|
|
129
|
-
}
|
|
130
|
-
/**
|
|
131
|
-
* Complete variant configuration
|
|
132
|
-
*/
|
|
73
|
+
};
|
|
74
|
+
/** A custom shell look; only `styles` is applied. */
|
|
133
75
|
export interface WidgetVariantConfig {
|
|
134
76
|
id: string;
|
|
135
77
|
name: string;
|
|
136
78
|
description?: string;
|
|
137
79
|
styles?: WidgetStyles;
|
|
80
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
138
81
|
layout?: LayoutStrategy;
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
82
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
83
|
+
elements?: {
|
|
84
|
+
visible?: Partial<Record<WidgetElement, boolean>>;
|
|
85
|
+
styles?: Partial<Record<WidgetElement, JSX.CSSProperties>>;
|
|
86
|
+
classNames?: Partial<Record<WidgetElement, string>>;
|
|
87
|
+
};
|
|
88
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
89
|
+
plugins?: {
|
|
90
|
+
background?: string;
|
|
91
|
+
overlay?: string;
|
|
92
|
+
decorations?: string[];
|
|
93
|
+
};
|
|
94
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
95
|
+
interactions?: {
|
|
96
|
+
hover?: boolean;
|
|
97
|
+
active?: boolean;
|
|
98
|
+
focus?: boolean;
|
|
99
|
+
hoverScale?: number;
|
|
100
|
+
activeScale?: number;
|
|
101
|
+
};
|
|
102
|
+
/** @deprecated Never read by the shell. Removed in 2.0.0. */
|
|
142
103
|
extends?: string;
|
|
143
104
|
}
|
|
144
|
-
/**
|
|
145
|
-
* Variant registry type
|
|
146
|
-
*/
|
|
147
|
-
export type VariantRegistry = Record<string, WidgetVariantConfig>;
|
|
148
105
|
/** Unique entity identifier (e.g., "light.living_room") */
|
|
149
|
-
|
|
106
|
+
type EntityId = string;
|
|
150
107
|
/** Entity domain (e.g., "light", "sensor", "switch") */
|
|
151
|
-
|
|
108
|
+
type EntityDomain = string;
|
|
152
109
|
/** Area identifier */
|
|
153
|
-
|
|
110
|
+
type AreaId = string;
|
|
154
111
|
/** Device identifier */
|
|
155
|
-
|
|
112
|
+
type DeviceId = string;
|
|
156
113
|
/** Label identifier */
|
|
157
|
-
|
|
114
|
+
type LabelId = string;
|
|
158
115
|
/** Entity category for filtering */
|
|
159
|
-
|
|
116
|
+
type EntityCategory = "config" | "diagnostic" | null;
|
|
160
117
|
/**
|
|
161
118
|
* Full entity view interface representing a Home Assistant entity.
|
|
162
119
|
* This is the canonical type used by SDK framework utils and widgets.
|
|
@@ -219,3 +176,4 @@ export interface EntityView {
|
|
|
219
176
|
/** Bitmask of supported features */
|
|
220
177
|
supportedFeatures?: number;
|
|
221
178
|
}
|
|
179
|
+
export {};
|
|
@@ -1,49 +1,6 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Empty State Utilities
|
|
3
|
-
*
|
|
4
|
-
* Helper functions for creating consistent empty state configurations across widgets.
|
|
5
|
-
*/
|
|
6
1
|
import type { JSX } from "solid-js";
|
|
7
|
-
/**
|
|
8
|
-
* Empty state configuration for a widget
|
|
9
|
-
*/
|
|
10
2
|
export interface WidgetEmptyStateConfig {
|
|
11
|
-
/** Icon to display */
|
|
12
3
|
icon: JSX.Element;
|
|
13
|
-
/** Main title/heading */
|
|
14
4
|
title: string;
|
|
15
|
-
/** Descriptive message */
|
|
16
5
|
message: string;
|
|
17
6
|
}
|
|
18
|
-
export interface EmptyStateConfigOptions {
|
|
19
|
-
/** Icon to display */
|
|
20
|
-
icon: JSX.Element;
|
|
21
|
-
/** Main title/heading */
|
|
22
|
-
title: string;
|
|
23
|
-
/** Descriptive message (optional - uses default template if not provided) */
|
|
24
|
-
message?: string;
|
|
25
|
-
/** Entity type for default message template (e.g., "a light", "a lock") */
|
|
26
|
-
entityType?: string;
|
|
27
|
-
}
|
|
28
|
-
/**
|
|
29
|
-
* Creates a consistent empty state configuration for widgets
|
|
30
|
-
*
|
|
31
|
-
* @example
|
|
32
|
-
* ```typescript
|
|
33
|
-
* // Custom message
|
|
34
|
-
* const config = createEmptyStateConfig({
|
|
35
|
-
* icon: <Thermometer />,
|
|
36
|
-
* title: "No climate entity",
|
|
37
|
-
* message: "Configure this widget to add a climate device",
|
|
38
|
-
* });
|
|
39
|
-
*
|
|
40
|
-
* // Default message template
|
|
41
|
-
* const config = createEmptyStateConfig({
|
|
42
|
-
* icon: <Lock />,
|
|
43
|
-
* title: "No lock entity",
|
|
44
|
-
* entityType: "a lock",
|
|
45
|
-
* });
|
|
46
|
-
* // Result: message = "Configure this widget to add a lock"
|
|
47
|
-
* ```
|
|
48
|
-
*/
|
|
49
|
-
export declare function createEmptyStateConfig(options: EmptyStateConfigOptions): WidgetEmptyStateConfig;
|
|
@@ -5,7 +5,6 @@
|
|
|
5
5
|
* in this directory are still consumed internally even when not part of the
|
|
6
6
|
* public re-export surface.
|
|
7
7
|
*/
|
|
8
|
-
export { cn } from "./cn";
|
|
9
8
|
export { copyText, type CopyState, useCopyText } from "./clipboard";
|
|
10
9
|
export { calculateLightGroup, calculateSensorGroup, type LightGroupResult, type SensorGroupResult, type SensorGroupType, } from "./entity-aggregation";
|
|
11
10
|
export { countActiveEntities, getEntityAttribute, isEntityActive, } from "./entity-state";
|
|
@@ -1,39 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
*
|
|
4
|
-
* Simplified set of pre-built variant definitions that ship with the framework.
|
|
5
|
-
* These variants can be used as-is or extended/composed.
|
|
6
|
-
*
|
|
7
|
-
* Includes 3 core variants (classic-glass, minimal, compact-horizontal).
|
|
8
|
-
* Additional variants can be added later or created by widget authors
|
|
9
|
-
* using the variant composition utilities.
|
|
10
|
-
*/
|
|
11
|
-
import type { VariantRegistry, WidgetVariantConfig } from "../types";
|
|
12
|
-
export declare const classicGlass: WidgetVariantConfig;
|
|
13
|
-
export declare const minimal: WidgetVariantConfig;
|
|
14
|
-
export declare const compactHorizontal: WidgetVariantConfig;
|
|
15
|
-
/**
|
|
16
|
-
* Built-in variant registry
|
|
17
|
-
* Maps variant IDs to their configurations
|
|
18
|
-
*/
|
|
19
|
-
export declare const builtInVariants: VariantRegistry;
|
|
20
|
-
/**
|
|
21
|
-
* Get a variant by ID from the built-in registry
|
|
22
|
-
*
|
|
23
|
-
* @param id Variant ID
|
|
24
|
-
* @returns Variant configuration or undefined if not found
|
|
25
|
-
*/
|
|
26
|
-
export declare function getBuiltInVariant(id: string): WidgetVariantConfig | undefined;
|
|
27
|
-
/**
|
|
28
|
-
* Check if a variant ID is a built-in variant
|
|
29
|
-
*
|
|
30
|
-
* @param id Variant ID to check
|
|
31
|
-
* @returns True if the variant is built-in
|
|
32
|
-
*/
|
|
33
|
-
export declare function isBuiltInVariant(id: string): boolean;
|
|
34
|
-
/**
|
|
35
|
-
* Get all built-in variant IDs
|
|
36
|
-
*
|
|
37
|
-
* @returns Array of built-in variant IDs
|
|
38
|
-
*/
|
|
39
|
-
export declare function getBuiltInVariantIds(): string[];
|
|
1
|
+
import type { WidgetStyles } from "../types";
|
|
2
|
+
export declare function getBuiltInVariantStyles(id: string): WidgetStyles | undefined;
|
package/dist/index.js
CHANGED
|
@@ -727,87 +727,30 @@ function ir(e) {
|
|
|
727
727
|
let n = t.createElement("style");
|
|
728
728
|
n.setAttribute("data-glasshome-tokens", ""), n.textContent = $n, t.head.appendChild(n), er = !0;
|
|
729
729
|
}
|
|
730
|
+
//#endregion
|
|
731
|
+
//#region src/framework/variants/built-in-variants.ts
|
|
730
732
|
var ar = {
|
|
731
|
-
"classic-glass": {
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
|
|
746
|
-
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
focus: !0,
|
|
750
|
-
hoverScale: 1.02,
|
|
751
|
-
activeScale: .98
|
|
752
|
-
}
|
|
753
|
-
},
|
|
754
|
-
minimal: {
|
|
755
|
-
id: "minimal",
|
|
756
|
-
name: "Minimal",
|
|
757
|
-
description: "Clean, minimal design with no background effects",
|
|
758
|
-
styles: { cssVars: {
|
|
759
|
-
"--widget-padding": "1rem",
|
|
760
|
-
"--glass-base": "transparent",
|
|
761
|
-
"--glass-wash": "0%",
|
|
762
|
-
"--glass-light": "0",
|
|
763
|
-
"--glass-rim": "0",
|
|
764
|
-
"--glass-lift": "0",
|
|
765
|
-
"--glass-edge": "transparent"
|
|
766
|
-
} },
|
|
767
|
-
layout: {
|
|
768
|
-
type: "flex",
|
|
769
|
-
direction: "column",
|
|
770
|
-
align: "start",
|
|
771
|
-
justify: "start",
|
|
772
|
-
gap: "0.5rem"
|
|
773
|
-
},
|
|
774
|
-
elements: { visible: {
|
|
775
|
-
background: !1,
|
|
776
|
-
decorations: !1
|
|
777
|
-
} },
|
|
778
|
-
interactions: {
|
|
779
|
-
hover: !1,
|
|
780
|
-
active: !1,
|
|
781
|
-
focus: !0
|
|
782
|
-
}
|
|
783
|
-
},
|
|
784
|
-
"compact-horizontal": {
|
|
785
|
-
id: "compact-horizontal",
|
|
786
|
-
name: "Compact Horizontal",
|
|
787
|
-
description: "Horizontal layout for compact widgets",
|
|
788
|
-
styles: { cssVars: {
|
|
789
|
-
"--widget-padding": "1rem",
|
|
790
|
-
"--widget-icon-size": "2.5rem",
|
|
791
|
-
"--widget-backdrop": "blur(16px) saturate(1.8)"
|
|
792
|
-
} },
|
|
793
|
-
layout: {
|
|
794
|
-
type: "flex",
|
|
795
|
-
direction: "row",
|
|
796
|
-
align: "center",
|
|
797
|
-
justify: "start",
|
|
798
|
-
gap: "1rem"
|
|
799
|
-
},
|
|
800
|
-
interactions: {
|
|
801
|
-
hover: !0,
|
|
802
|
-
active: !0,
|
|
803
|
-
focus: !0,
|
|
804
|
-
hoverScale: 1.02,
|
|
805
|
-
activeScale: .98
|
|
806
|
-
}
|
|
807
|
-
}
|
|
733
|
+
"classic-glass": { cssVars: {
|
|
734
|
+
"--widget-padding": "1.5rem",
|
|
735
|
+
"--widget-backdrop": "blur(var(--glass-blur, var(--material-blur, 24px))) saturate(1.8)"
|
|
736
|
+
} },
|
|
737
|
+
minimal: { cssVars: {
|
|
738
|
+
"--widget-padding": "1rem",
|
|
739
|
+
"--glass-base": "transparent",
|
|
740
|
+
"--glass-wash": "0%",
|
|
741
|
+
"--glass-light": "0",
|
|
742
|
+
"--glass-rim": "0",
|
|
743
|
+
"--glass-lift": "0",
|
|
744
|
+
"--glass-edge": "transparent"
|
|
745
|
+
} },
|
|
746
|
+
"compact-horizontal": { cssVars: {
|
|
747
|
+
"--widget-padding": "1rem",
|
|
748
|
+
"--widget-icon-size": "2.5rem",
|
|
749
|
+
"--widget-backdrop": "blur(16px) saturate(1.8)"
|
|
750
|
+
} }
|
|
808
751
|
};
|
|
809
752
|
function or(e) {
|
|
810
|
-
return ar[e];
|
|
753
|
+
return Object.hasOwn(ar, e) ? ar[e] : void 0;
|
|
811
754
|
}
|
|
812
755
|
//#endregion
|
|
813
756
|
//#region src/framework/backgrounds/WidgetSliderFill.tsx
|
|
@@ -922,7 +865,8 @@ function xr(e = 2e3) {
|
|
|
922
865
|
//#endregion
|
|
923
866
|
//#region src/framework/utils/entity-aggregation.ts
|
|
924
867
|
function Sr(e, t = !1) {
|
|
925
|
-
|
|
868
|
+
let n = e[0];
|
|
869
|
+
if (!n) return {
|
|
926
870
|
isGroup: !1,
|
|
927
871
|
state: "unknown",
|
|
928
872
|
isOn: !1,
|
|
@@ -934,84 +878,85 @@ function Sr(e, t = !1) {
|
|
|
934
878
|
totalCount: 0,
|
|
935
879
|
description: "No entities"
|
|
936
880
|
};
|
|
937
|
-
let
|
|
938
|
-
if (!
|
|
939
|
-
let
|
|
881
|
+
let r = e.length > 1;
|
|
882
|
+
if (!r) {
|
|
883
|
+
let e = n, t = e.state === "on", r = e.attributes?.brightness || 0, i = Math.round(r / 255 * 100);
|
|
940
884
|
return {
|
|
941
885
|
isGroup: !1,
|
|
942
|
-
state:
|
|
943
|
-
isOn:
|
|
944
|
-
isUnavailable:
|
|
886
|
+
state: e.state,
|
|
887
|
+
isOn: t,
|
|
888
|
+
isUnavailable: e.state === "unavailable",
|
|
945
889
|
brightness: r,
|
|
946
890
|
brightnessPercent: i,
|
|
947
|
-
color: Tr(
|
|
948
|
-
onCount: +!!
|
|
891
|
+
color: Tr(e),
|
|
892
|
+
onCount: +!!t,
|
|
949
893
|
totalCount: 1,
|
|
950
|
-
description:
|
|
894
|
+
description: t ? "On" : "Off"
|
|
951
895
|
};
|
|
952
896
|
}
|
|
953
|
-
let
|
|
897
|
+
let i = 0, a = 0, o = 0, s = 0, c = 0, l = 0, u = [];
|
|
954
898
|
for (let t of e) switch (t.state) {
|
|
955
899
|
case "on":
|
|
956
|
-
if (
|
|
900
|
+
if (i++, t.attributes?.brightness !== void 0 && (c += t.attributes.brightness, l++), t.attributes?.rgb_color) u.push(t.attributes.rgb_color);
|
|
957
901
|
else if (t.attributes?.hs_color) {
|
|
958
902
|
let [e, n] = t.attributes.hs_color;
|
|
959
|
-
|
|
903
|
+
u.push(wr(e, n));
|
|
960
904
|
}
|
|
961
905
|
break;
|
|
962
906
|
case "off":
|
|
963
|
-
|
|
907
|
+
a++;
|
|
964
908
|
break;
|
|
965
909
|
case "unknown":
|
|
966
|
-
|
|
910
|
+
o++;
|
|
967
911
|
break;
|
|
968
|
-
case "unavailable":
|
|
912
|
+
case "unavailable": s++;
|
|
969
913
|
}
|
|
970
|
-
let
|
|
971
|
-
t ?
|
|
972
|
-
let
|
|
973
|
-
if (
|
|
974
|
-
let e = Math.round(
|
|
975
|
-
|
|
976
|
-
} else
|
|
977
|
-
let
|
|
978
|
-
return
|
|
979
|
-
isGroup:
|
|
980
|
-
state:
|
|
981
|
-
isOn:
|
|
982
|
-
isUnavailable:
|
|
983
|
-
brightness:
|
|
984
|
-
brightnessPercent:
|
|
985
|
-
color:
|
|
986
|
-
onCount:
|
|
987
|
-
totalCount:
|
|
988
|
-
description:
|
|
914
|
+
let d = e.length, f = s === d, p = o + s === d, m = i > 0, h = i === d, g = a === d, _, v;
|
|
915
|
+
t ? f ? (_ = "unavailable", v = !1) : o > 0 || s > 0 ? (_ = "unknown", v = !1) : a > 0 ? (_ = "off", v = !1) : (_ = "on", v = !0) : f ? (_ = "unavailable", v = !1) : p ? (_ = "unknown", v = !1) : m ? (_ = "on", v = !0) : (_ = "off", v = !1);
|
|
916
|
+
let y = l > 0 ? Math.round(c / l) : 0, b = Math.round(y / 255 * 100), x;
|
|
917
|
+
if (u.length > 0) {
|
|
918
|
+
let e = Math.round(u.reduce((e, t) => e + t[0], 0) / u.length), t = Math.round(u.reduce((e, t) => e + t[1], 0) / u.length), n = Math.round(u.reduce((e, t) => e + t[2], 0) / u.length), r = y / 255;
|
|
919
|
+
x = `rgb(${Math.round(e * r)}, ${Math.round(t * r)}, ${Math.round(n * r)})`;
|
|
920
|
+
} else x = Tr(n);
|
|
921
|
+
let S;
|
|
922
|
+
return S = h ? "All on" : g ? "All off" : i > 0 ? `${i} of ${d} on` : "Off", {
|
|
923
|
+
isGroup: r,
|
|
924
|
+
state: _,
|
|
925
|
+
isOn: v,
|
|
926
|
+
isUnavailable: _ === "unavailable",
|
|
927
|
+
brightness: y,
|
|
928
|
+
brightnessPercent: b,
|
|
929
|
+
color: x,
|
|
930
|
+
onCount: i,
|
|
931
|
+
totalCount: d,
|
|
932
|
+
description: S
|
|
989
933
|
};
|
|
990
934
|
}
|
|
991
935
|
function Cr(e, t = "mean", n = !0) {
|
|
992
|
-
|
|
936
|
+
let r = e[0];
|
|
937
|
+
if (!r) return {
|
|
993
938
|
isGroup: !1,
|
|
994
939
|
state: "unknown",
|
|
995
940
|
numericValue: null,
|
|
996
941
|
isUnavailable: !0,
|
|
997
942
|
description: "No entities"
|
|
998
943
|
};
|
|
999
|
-
let
|
|
1000
|
-
if (!
|
|
1001
|
-
let
|
|
1002
|
-
return Number.isNaN(
|
|
944
|
+
let i = e.length > 1;
|
|
945
|
+
if (!i) {
|
|
946
|
+
let e = r, t = Number.parseFloat(e.state), n = e.state;
|
|
947
|
+
return Number.isNaN(t) || (n = Number.isInteger(t) ? t.toString() : t.toFixed(1)), {
|
|
1003
948
|
isGroup: !1,
|
|
1004
|
-
state:
|
|
1005
|
-
numericValue: Number.isNaN(
|
|
1006
|
-
isUnavailable:
|
|
1007
|
-
unit:
|
|
1008
|
-
description:
|
|
949
|
+
state: n,
|
|
950
|
+
numericValue: Number.isNaN(t) ? null : t,
|
|
951
|
+
isUnavailable: e.state === "unavailable",
|
|
952
|
+
unit: e.unitOfMeasurement ?? void 0,
|
|
953
|
+
description: n
|
|
1009
954
|
};
|
|
1010
955
|
}
|
|
1011
|
-
let
|
|
956
|
+
let a = [], o = [], s = 0, c;
|
|
1012
957
|
for (let t of e) {
|
|
1013
|
-
if (!
|
|
1014
|
-
|
|
958
|
+
if (!c && t.unitOfMeasurement && (c = t.unitOfMeasurement), t.state === "unavailable") {
|
|
959
|
+
s++, o.push({
|
|
1015
960
|
entityId: t.id,
|
|
1016
961
|
value: "unavailable",
|
|
1017
962
|
friendly_name: t.friendlyName
|
|
@@ -1019,69 +964,69 @@ function Cr(e, t = "mean", n = !0) {
|
|
|
1019
964
|
continue;
|
|
1020
965
|
}
|
|
1021
966
|
let e = Number.parseFloat(t.state);
|
|
1022
|
-
isNaN(e) ? n ||
|
|
967
|
+
isNaN(e) ? n || o.push({
|
|
1023
968
|
entityId: t.id,
|
|
1024
969
|
value: t.state,
|
|
1025
970
|
friendly_name: t.friendlyName
|
|
1026
|
-
}) : (
|
|
971
|
+
}) : (a.push(e), o.push({
|
|
1027
972
|
entityId: t.id,
|
|
1028
973
|
value: e,
|
|
1029
974
|
friendly_name: t.friendlyName
|
|
1030
975
|
}));
|
|
1031
976
|
}
|
|
1032
|
-
let
|
|
1033
|
-
if (
|
|
1034
|
-
isGroup:
|
|
1035
|
-
state:
|
|
977
|
+
let l = s === e.length, u = a.at(-1);
|
|
978
|
+
if (l || u === void 0) return {
|
|
979
|
+
isGroup: i,
|
|
980
|
+
state: l ? "unavailable" : "unknown",
|
|
1036
981
|
numericValue: null,
|
|
1037
|
-
isUnavailable:
|
|
1038
|
-
unit:
|
|
1039
|
-
description:
|
|
1040
|
-
memberValues:
|
|
982
|
+
isUnavailable: l,
|
|
983
|
+
unit: c,
|
|
984
|
+
description: l ? "Unavailable" : "No numeric values",
|
|
985
|
+
memberValues: o
|
|
1041
986
|
};
|
|
1042
|
-
let
|
|
987
|
+
let d, f;
|
|
1043
988
|
switch (t) {
|
|
1044
989
|
case "min":
|
|
1045
|
-
|
|
990
|
+
d = Math.min(...a), f = "Minimum";
|
|
1046
991
|
break;
|
|
1047
992
|
case "max":
|
|
1048
|
-
|
|
993
|
+
d = Math.max(...a), f = "Maximum";
|
|
1049
994
|
break;
|
|
1050
995
|
case "mean":
|
|
1051
|
-
|
|
996
|
+
d = a.reduce((e, t) => e + t, 0) / a.length, f = "Average";
|
|
1052
997
|
break;
|
|
1053
998
|
case "median": {
|
|
1054
|
-
let e = [...
|
|
1055
|
-
|
|
999
|
+
let e = [...a].sort((e, t) => e - t), t = Math.floor(e.length / 2), n = e[t] ?? u;
|
|
1000
|
+
d = e.length % 2 == 0 ? ((e[t - 1] ?? n) + n) / 2 : n, f = "Median";
|
|
1056
1001
|
break;
|
|
1057
1002
|
}
|
|
1058
1003
|
case "sum":
|
|
1059
|
-
|
|
1004
|
+
d = a.reduce((e, t) => e + t, 0), f = "Sum";
|
|
1060
1005
|
break;
|
|
1061
1006
|
case "last":
|
|
1062
|
-
|
|
1007
|
+
d = u, f = "Latest";
|
|
1063
1008
|
break;
|
|
1064
1009
|
case "range":
|
|
1065
|
-
|
|
1010
|
+
d = Math.max(...a) - Math.min(...a), f = "Range";
|
|
1066
1011
|
break;
|
|
1067
1012
|
case "product":
|
|
1068
|
-
|
|
1013
|
+
d = a.reduce((e, t) => e * t, 1), f = "Product";
|
|
1069
1014
|
break;
|
|
1070
1015
|
case "std_dev": {
|
|
1071
|
-
let e =
|
|
1072
|
-
|
|
1016
|
+
let e = a.reduce((e, t) => e + t, 0) / a.length, t = a.reduce((t, n) => t + (n - e) ** 2, 0) / a.length;
|
|
1017
|
+
d = Math.sqrt(t), f = "Std Dev";
|
|
1073
1018
|
break;
|
|
1074
1019
|
}
|
|
1075
|
-
default:
|
|
1020
|
+
default: d = a.reduce((e, t) => e + t, 0) / a.length, f = "Average";
|
|
1076
1021
|
}
|
|
1077
1022
|
return {
|
|
1078
|
-
isGroup:
|
|
1079
|
-
state: Number.isInteger(
|
|
1080
|
-
numericValue:
|
|
1023
|
+
isGroup: i,
|
|
1024
|
+
state: Number.isInteger(d) ? d.toString() : d.toFixed(1),
|
|
1025
|
+
numericValue: d,
|
|
1081
1026
|
isUnavailable: !1,
|
|
1082
|
-
unit:
|
|
1083
|
-
description: `${
|
|
1084
|
-
memberValues:
|
|
1027
|
+
unit: c,
|
|
1028
|
+
description: `${f} of ${a.length}`,
|
|
1029
|
+
memberValues: o
|
|
1085
1030
|
};
|
|
1086
1031
|
}
|
|
1087
1032
|
function wr(e, t) {
|
|
@@ -1206,13 +1151,13 @@ function Vr(t) {
|
|
|
1206
1151
|
};
|
|
1207
1152
|
n && Object.defineProperty(d, tn, { value: n });
|
|
1208
1153
|
let f = D(() => {
|
|
1209
|
-
if (t.variant) return typeof t.variant == "string" ? or(t.variant) : t.variant;
|
|
1154
|
+
if (t.variant) return typeof t.variant == "string" ? or(t.variant) : t.variant.styles;
|
|
1210
1155
|
}), p = e(() => t.gradient, "widget.gradient"), m = D(() => ({
|
|
1211
1156
|
"container-type": "size",
|
|
1212
1157
|
"container-name": "widget",
|
|
1213
1158
|
"touch-action": o() && !t.isEditMode ? o()?.touchAction() : void 0,
|
|
1214
|
-
...f()?.
|
|
1215
|
-
...f()?.
|
|
1159
|
+
...f()?.container,
|
|
1160
|
+
...f()?.cssVars || {},
|
|
1216
1161
|
...t.tone ? { "--widget-color": `var(--tone-${t.tone})` } : {},
|
|
1217
1162
|
...t.color ? { "--widget-color": t.color } : {},
|
|
1218
1163
|
...t.tone && t.tone !== "neutral" || t.color ? { "--glass-tone": "var(--widget-color)" } : {},
|
|
@@ -1295,7 +1240,7 @@ function Vr(t) {
|
|
|
1295
1240
|
return P((t) => R(e, "z-index", K.OVERLAY)), e;
|
|
1296
1241
|
})();
|
|
1297
1242
|
})(), null), P((r) => {
|
|
1298
|
-
var i = X("glasshome-widget glass", "relative h-full w-full select-none overflow-hidden rounded-xl", f()?.
|
|
1243
|
+
var i = X("glasshome-widget glass", "relative h-full w-full select-none overflow-hidden rounded-xl", f()?.class, t.class), a = m(), o = t.confirmed || void 0, s = h() ? 0 : void 0, c = K.CONTENT;
|
|
1299
1244
|
return i !== r.e && M(e, r.e = i), r.t = z(e, a, r.t), o !== r.a && L(e, "data-confirmed", r.a = o), s !== r.o && L(e, "tabindex", r.o = s), c !== r.i && R(n, "z-index", r.i = c), r;
|
|
1300
1245
|
}, {
|
|
1301
1246
|
e: void 0,
|
|
@@ -1797,7 +1742,7 @@ function ki(e) {
|
|
|
1797
1742
|
let t = e.replace(/([a-z\d])([A-Z])/g, "$1 $2").replace(/[_-]+/g, " ");
|
|
1798
1743
|
return t.charAt(0).toUpperCase() + t.slice(1).toLowerCase();
|
|
1799
1744
|
}
|
|
1800
|
-
var Ai = (e) => typeof e != "object"
|
|
1745
|
+
var Ai = (e) => e === null || typeof e != "object" && typeof e != "function";
|
|
1801
1746
|
function ji(e) {
|
|
1802
1747
|
return e == null ? "None" : String(e);
|
|
1803
1748
|
}
|
|
@@ -1884,7 +1829,7 @@ function Ii(e) {
|
|
|
1884
1829
|
})();
|
|
1885
1830
|
}
|
|
1886
1831
|
function Li(e) {
|
|
1887
|
-
let t = D(() => Object.entries(e.record)), n = D(() => t().
|
|
1832
|
+
let t = D(() => Object.entries(e.record)), n = D(() => t().flatMap(([e, t]) => Ai(t) ? [[e, t]] : [])), r = D(() => t().filter(([, e]) => !Ai(e)));
|
|
1888
1833
|
return N(w, {
|
|
1889
1834
|
get when() {
|
|
1890
1835
|
return t().length > 0;
|
|
@@ -2829,7 +2774,7 @@ function Qa() {
|
|
|
2829
2774
|
//#region src/version.ts
|
|
2830
2775
|
var $a = {
|
|
2831
2776
|
name: "@glasshome/widget-sdk",
|
|
2832
|
-
version: "1.
|
|
2777
|
+
version: "1.18.0",
|
|
2833
2778
|
description: "SDK for building GlassHome dashboard widgets with SolidJS",
|
|
2834
2779
|
keywords: [
|
|
2835
2780
|
"glasshome",
|
|
@@ -2885,16 +2830,16 @@ var $a = {
|
|
|
2885
2830
|
test: "bun test src && vitest run",
|
|
2886
2831
|
"test:dom": "vitest run",
|
|
2887
2832
|
"test:dom:watch": "vitest",
|
|
2888
|
-
"typecheck:test": "tsc --noEmit -p tsconfig.test.json"
|
|
2833
|
+
"typecheck:test": "tsc --noEmit -p tsconfig.test.json",
|
|
2834
|
+
"check:dead": "fallow dead-code --fail-on-issues"
|
|
2889
2835
|
},
|
|
2890
2836
|
peerDependencies: {
|
|
2891
|
-
"@glasshome/sync-layer": "0.9.
|
|
2892
|
-
"@glasshome/ui": "1.
|
|
2837
|
+
"@glasshome/sync-layer": "0.9.1",
|
|
2838
|
+
"@glasshome/ui": "1.21.1",
|
|
2893
2839
|
"solid-js": "^1.9.11"
|
|
2894
2840
|
},
|
|
2895
2841
|
dependencies: {
|
|
2896
2842
|
"@glasshome/widget-contract": "0.3.0",
|
|
2897
|
-
"@modular-forms/solid": "^0.25.1",
|
|
2898
2843
|
"@tailwindcss/vite": "^4.1.13",
|
|
2899
2844
|
clsx: "^2.1.1",
|
|
2900
2845
|
"happy-dom": "^20.0.0",
|
|
@@ -2904,10 +2849,11 @@ var $a = {
|
|
|
2904
2849
|
zod: "^4.1.13"
|
|
2905
2850
|
},
|
|
2906
2851
|
devDependencies: {
|
|
2907
|
-
"@glasshome/ui": "1.
|
|
2852
|
+
"@glasshome/ui": "1.21.1",
|
|
2908
2853
|
"@solidjs/testing-library": "^0.8.10",
|
|
2909
2854
|
"@types/bun": "^1.4.0",
|
|
2910
2855
|
"@types/node": "^25.2.2",
|
|
2856
|
+
fallow: "3.17.0",
|
|
2911
2857
|
typescript: "^7.0.2",
|
|
2912
2858
|
vite: "^8.1.0",
|
|
2913
2859
|
"vite-plugin-solid": "^2.11.12",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@glasshome/widget-sdk",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.18.0",
|
|
4
4
|
"description": "SDK for building GlassHome dashboard widgets with SolidJS",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"glasshome",
|
|
@@ -56,16 +56,16 @@
|
|
|
56
56
|
"test": "bun test src && vitest run",
|
|
57
57
|
"test:dom": "vitest run",
|
|
58
58
|
"test:dom:watch": "vitest",
|
|
59
|
-
"typecheck:test": "tsc --noEmit -p tsconfig.test.json"
|
|
59
|
+
"typecheck:test": "tsc --noEmit -p tsconfig.test.json",
|
|
60
|
+
"check:dead": "fallow dead-code --fail-on-issues"
|
|
60
61
|
},
|
|
61
62
|
"peerDependencies": {
|
|
62
|
-
"@glasshome/sync-layer": "0.9.
|
|
63
|
-
"@glasshome/ui": "1.
|
|
63
|
+
"@glasshome/sync-layer": "0.9.1",
|
|
64
|
+
"@glasshome/ui": "1.21.1",
|
|
64
65
|
"solid-js": "^1.9.11"
|
|
65
66
|
},
|
|
66
67
|
"dependencies": {
|
|
67
68
|
"@glasshome/widget-contract": "0.3.0",
|
|
68
|
-
"@modular-forms/solid": "^0.25.1",
|
|
69
69
|
"@tailwindcss/vite": "^4.1.13",
|
|
70
70
|
"clsx": "^2.1.1",
|
|
71
71
|
"happy-dom": "^20.0.0",
|
|
@@ -75,10 +75,11 @@
|
|
|
75
75
|
"zod": "^4.1.13"
|
|
76
76
|
},
|
|
77
77
|
"devDependencies": {
|
|
78
|
-
"@glasshome/ui": "1.
|
|
78
|
+
"@glasshome/ui": "1.21.1",
|
|
79
79
|
"@solidjs/testing-library": "^0.8.10",
|
|
80
80
|
"@types/bun": "^1.4.0",
|
|
81
81
|
"@types/node": "^25.2.2",
|
|
82
|
+
"fallow": "3.17.0",
|
|
82
83
|
"typescript": "^7.0.2",
|
|
83
84
|
"vite": "^8.1.0",
|
|
84
85
|
"vite-plugin-solid": "^2.11.12",
|
package/preview/host.tsx
CHANGED
|
@@ -4,7 +4,7 @@ import { render } from "solid-js/web";
|
|
|
4
4
|
|
|
5
5
|
function PreviewHost() {
|
|
6
6
|
const [isDark, setIsDark] = createSignal(false);
|
|
7
|
-
const [config
|
|
7
|
+
const [config] = createSignal(widget.manifest.defaultConfig || {});
|
|
8
8
|
|
|
9
9
|
const toggleDark = () => {
|
|
10
10
|
const next = !isDark();
|
|
@@ -86,4 +86,6 @@ function PreviewHost() {
|
|
|
86
86
|
);
|
|
87
87
|
}
|
|
88
88
|
|
|
89
|
-
|
|
89
|
+
const root = document.getElementById("root");
|
|
90
|
+
if (!root) throw new Error("preview: #root is missing");
|
|
91
|
+
render(() => <PreviewHost />, root);
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Variant System - Barrel Export
|
|
3
|
-
*
|
|
4
|
-
* Built-in variant presets and composition utilities.
|
|
5
|
-
*/
|
|
6
|
-
export { builtInVariants, classicGlass, compactHorizontal, getBuiltInVariant, getBuiltInVariantIds, isBuiltInVariant, minimal, } from "./built-in-variants";
|
|
7
|
-
export { applyCssVars, applyLayout, composeVariants, createFlexLayout, extendVariant, mergeVariants, } from "./variant-utils";
|
|
@@ -1,105 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Variant Composition Utilities
|
|
3
|
-
*
|
|
4
|
-
* Utilities for creating, merging, extending, and composing widget variants.
|
|
5
|
-
* Enables flexible variant system with type safety and composability.
|
|
6
|
-
*/
|
|
7
|
-
import type { FlexLayoutStrategy, LayoutStrategy, WidgetVariantConfig } from "../types";
|
|
8
|
-
/**
|
|
9
|
-
* Merge two complete variant configurations
|
|
10
|
-
*
|
|
11
|
-
* Deep merges all properties, with `override` taking precedence.
|
|
12
|
-
* Layout strategies are replaced, not merged (since they have different shapes).
|
|
13
|
-
*
|
|
14
|
-
* @example
|
|
15
|
-
* ```tsx
|
|
16
|
-
* const customVariant = mergeVariants(classicGlass, {
|
|
17
|
-
* styles: {
|
|
18
|
-
* cssVars: {
|
|
19
|
-
* "--glass-base": "oklch(0.2 0 0 / 0.5)"
|
|
20
|
-
* }
|
|
21
|
-
* }
|
|
22
|
-
* });
|
|
23
|
-
* ```
|
|
24
|
-
*/
|
|
25
|
-
export declare function mergeVariants(base: WidgetVariantConfig, override: Partial<WidgetVariantConfig>): WidgetVariantConfig;
|
|
26
|
-
/**
|
|
27
|
-
* Extend a base variant with partial overrides
|
|
28
|
-
*
|
|
29
|
-
* Similar to mergeVariants but returns a new variant that references the base
|
|
30
|
-
* via the `extends` property. Useful for variant inheritance chains.
|
|
31
|
-
*
|
|
32
|
-
* @example
|
|
33
|
-
* ```tsx
|
|
34
|
-
* const darkGlass = extendVariant("classic-glass", {
|
|
35
|
-
* id: "dark-glass",
|
|
36
|
-
* name: "Dark Glass",
|
|
37
|
-
* styles: {
|
|
38
|
-
* cssVars: {
|
|
39
|
-
* "--glass-base": "oklch(0.2 0 0 / 0.5)"
|
|
40
|
-
* }
|
|
41
|
-
* }
|
|
42
|
-
* });
|
|
43
|
-
* ```
|
|
44
|
-
*/
|
|
45
|
-
export declare function extendVariant(baseId: string, override: Partial<WidgetVariantConfig> & {
|
|
46
|
-
id: string;
|
|
47
|
-
name: string;
|
|
48
|
-
}): WidgetVariantConfig;
|
|
49
|
-
/**
|
|
50
|
-
* Compose multiple variants together (left to right precedence)
|
|
51
|
-
*
|
|
52
|
-
* Merges multiple variants in sequence, with later variants taking precedence.
|
|
53
|
-
* Useful for combining layout + styling + interaction variants.
|
|
54
|
-
*
|
|
55
|
-
* @example
|
|
56
|
-
* ```tsx
|
|
57
|
-
* const custom = composeVariants(
|
|
58
|
-
* minimal, // Base: minimal styling
|
|
59
|
-
* centeredLayout, // Add: centered layout
|
|
60
|
-
* largeIcons // Add: large icon sizing
|
|
61
|
-
* );
|
|
62
|
-
* ```
|
|
63
|
-
*/
|
|
64
|
-
export declare function composeVariants(...variants: WidgetVariantConfig[]): WidgetVariantConfig;
|
|
65
|
-
/**
|
|
66
|
-
* Apply a layout strategy override to a variant
|
|
67
|
-
*
|
|
68
|
-
* Convenience function for changing just the layout of a variant.
|
|
69
|
-
*
|
|
70
|
-
* @example
|
|
71
|
-
* ```tsx
|
|
72
|
-
* const centered = applyLayout(minimal, {
|
|
73
|
-
* type: "flex",
|
|
74
|
-
* direction: "column",
|
|
75
|
-
* align: "center",
|
|
76
|
-
* justify: "center"
|
|
77
|
-
* });
|
|
78
|
-
* ```
|
|
79
|
-
*/
|
|
80
|
-
export declare function applyLayout(variant: WidgetVariantConfig, layout: LayoutStrategy): WidgetVariantConfig;
|
|
81
|
-
/**
|
|
82
|
-
* Apply CSS variable overrides to a variant
|
|
83
|
-
*
|
|
84
|
-
* Convenience function for changing just the CSS variables of a variant.
|
|
85
|
-
*
|
|
86
|
-
* @example
|
|
87
|
-
* ```tsx
|
|
88
|
-
* const blueTinted = applyCssVars(classicGlass, {
|
|
89
|
-
* "--glass-tone": "oklch(0.62 0.2 260)",
|
|
90
|
-
* "--glass-wash": "30%"
|
|
91
|
-
* });
|
|
92
|
-
* ```
|
|
93
|
-
*/
|
|
94
|
-
export declare function applyCssVars(variant: WidgetVariantConfig, cssVars: Record<`--widget-${string}` | `--glass-${string}`, string | number>): WidgetVariantConfig;
|
|
95
|
-
/**
|
|
96
|
-
* Create a flex layout strategy
|
|
97
|
-
*
|
|
98
|
-
* Convenience function for creating common flex layouts.
|
|
99
|
-
*
|
|
100
|
-
* @example
|
|
101
|
-
* ```tsx
|
|
102
|
-
* const layout = createFlexLayout("column", "center", "center");
|
|
103
|
-
* ```
|
|
104
|
-
*/
|
|
105
|
-
export declare function createFlexLayout(direction?: FlexLayoutStrategy["direction"], align?: FlexLayoutStrategy["align"], justify?: FlexLayoutStrategy["justify"], options?: Partial<FlexLayoutStrategy>): FlexLayoutStrategy;
|