@mindees/atlas 0.1.0 → 0.2.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/a11y.d.ts +1 -1
- package/dist/a11y.d.ts.map +1 -1
- package/dist/a11y.js.map +1 -1
- package/dist/components.d.ts +83 -0
- package/dist/components.d.ts.map +1 -0
- package/dist/components.js +283 -0
- package/dist/components.js.map +1 -0
- package/dist/environment.d.ts +66 -0
- package/dist/environment.d.ts.map +1 -0
- package/dist/environment.js +72 -0
- package/dist/environment.js.map +1 -0
- package/dist/index.d.ts +5 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +5 -2
- package/dist/index.js.map +1 -1
- package/dist/list.d.ts +46 -1
- package/dist/list.d.ts.map +1 -1
- package/dist/list.js +47 -1
- package/dist/list.js.map +1 -1
- package/dist/tokens.d.ts +210 -0
- package/dist/tokens.d.ts.map +1 -0
- package/dist/tokens.js +185 -0
- package/dist/tokens.js.map +1 -0
- package/package.json +3 -3
package/dist/a11y.d.ts
CHANGED
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
* @module
|
|
9
9
|
*/
|
|
10
10
|
/** A WAI-ARIA-ish role, mapped straight to the host `role` attribute on web. */
|
|
11
|
-
type Role = 'button' | 'link' | 'image' | 'heading' | 'list' | 'listitem' | 'text' | 'textbox' | 'checkbox' | 'switch' | 'radio' | 'tab' | 'tabpanel' | 'dialog' | 'alert' | 'status' | 'none' | 'presentation';
|
|
11
|
+
type Role = 'button' | 'link' | 'image' | 'heading' | 'list' | 'listitem' | 'text' | 'textbox' | 'checkbox' | 'switch' | 'radio' | 'tab' | 'tabpanel' | 'dialog' | 'alert' | 'status' | 'separator' | 'progressbar' | 'none' | 'presentation';
|
|
12
12
|
/** Accessibility state, lowered to the matching `aria-*` attributes. */
|
|
13
13
|
interface A11yState {
|
|
14
14
|
disabled?: boolean;
|
package/dist/a11y.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"a11y.d.ts","names":[],"sources":["../src/a11y.ts"],"mappings":";;AAUA;;;;AAAgB;
|
|
1
|
+
{"version":3,"file":"a11y.d.ts","names":[],"sources":["../src/a11y.ts"],"mappings":";;AAUA;;;;AAAgB;AAuBhB;;;KAvBY,IAAA;;UAuBK,SAAA;EACf,QAAA;EACA,QAAA;EACA,OAAA;EACA,QAAA;EACA,IAAA;EACA,MAAA;AAAA;;UAIe,SAAA;EAYE;EAVjB,IAAA,GAAO,IAAA;EAAA;EAEP,KAAA;EAEA;EAAA,UAAA;EAIA;EAFA,WAAA;EAIQ;EAFR,IAAA;EAEiB;EAAjB,KAAA,GAAQ,SAAS;AAAA;;;;;iBAOH,WAAA,CAAY,IAAA,EAAM,SAAA,GAAY,MAAM"}
|
package/dist/a11y.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"a11y.js","names":[],"sources":["../src/a11y.ts"],"sourcesContent":["/**\n * Atlas accessibility — a single typed `A11yProps` surface lowered to `role` + `aria-*`\n * attribute props. The DOM backend passes these through verbatim (`setAttribute`), so web a11y\n * is real; native hosts receive them as serialized props (interpretation is a 🔬 research-track\n * host concern — carried, never silently dropped). See `docs/adr/0022-atlas-primitives.md`.\n *\n * @module\n */\n\n/** A WAI-ARIA-ish role, mapped straight to the host `role` attribute on web. */\nexport type Role =\n | 'button'\n | 'link'\n | 'image'\n | 'heading'\n | 'list'\n | 'listitem'\n | 'text'\n | 'textbox'\n | 'checkbox'\n | 'switch'\n | 'radio'\n | 'tab'\n | 'tabpanel'\n | 'dialog'\n | 'alert'\n | 'status'\n | 'none'\n | 'presentation'\n\n/** Accessibility state, lowered to the matching `aria-*` attributes. */\nexport interface A11yState {\n disabled?: boolean\n selected?: boolean\n checked?: boolean\n expanded?: boolean\n busy?: boolean\n hidden?: boolean\n}\n\n/** The accessibility surface every Atlas primitive accepts. */\nexport interface A11yProps {\n /** ARIA role (web `role`). */\n role?: Role\n /** Accessible name (`aria-label`). */\n label?: string\n /** Id(s) of the element(s) labelling this one (`aria-labelledby`). */\n labelledBy?: string\n /** Id(s) of the element(s) describing this one (`aria-describedby`). */\n describedBy?: string\n /** Live-region politeness (`aria-live`). */\n live?: 'off' | 'polite' | 'assertive'\n /** Accessibility state (`aria-disabled`/`-selected`/`-checked`/`-expanded`/`-busy`/`aria-hidden`). */\n state?: A11yState\n}\n\n/**\n * Lower {@link A11yProps} to a host prop bag of `role` + `aria-*` (only keys that are defined,\n * so omitted props stay omitted — exactOptionalPropertyTypes-safe).\n */\nexport function toA11yProps(a11y: A11yProps): Record<string, string> {\n const out: Record<string, string> = {}\n if (a11y.role !== undefined) out.role = a11y.role\n if (a11y.label !== undefined) out['aria-label'] = a11y.label\n if (a11y.labelledBy !== undefined) out['aria-labelledby'] = a11y.labelledBy\n if (a11y.describedBy !== undefined) out['aria-describedby'] = a11y.describedBy\n if (a11y.live !== undefined) out['aria-live'] = a11y.live\n const s = a11y.state\n if (s) {\n if (s.disabled !== undefined) out['aria-disabled'] = String(s.disabled)\n if (s.selected !== undefined) out['aria-selected'] = String(s.selected)\n if (s.checked !== undefined) out['aria-checked'] = String(s.checked)\n if (s.expanded !== undefined) out['aria-expanded'] = String(s.expanded)\n if (s.busy !== undefined) out['aria-busy'] = String(s.busy)\n if (s.hidden !== undefined) out['aria-hidden'] = String(s.hidden)\n }\n return out\n}\n"],"mappings":";;;;;
|
|
1
|
+
{"version":3,"file":"a11y.js","names":[],"sources":["../src/a11y.ts"],"sourcesContent":["/**\n * Atlas accessibility — a single typed `A11yProps` surface lowered to `role` + `aria-*`\n * attribute props. The DOM backend passes these through verbatim (`setAttribute`), so web a11y\n * is real; native hosts receive them as serialized props (interpretation is a 🔬 research-track\n * host concern — carried, never silently dropped). See `docs/adr/0022-atlas-primitives.md`.\n *\n * @module\n */\n\n/** A WAI-ARIA-ish role, mapped straight to the host `role` attribute on web. */\nexport type Role =\n | 'button'\n | 'link'\n | 'image'\n | 'heading'\n | 'list'\n | 'listitem'\n | 'text'\n | 'textbox'\n | 'checkbox'\n | 'switch'\n | 'radio'\n | 'tab'\n | 'tabpanel'\n | 'dialog'\n | 'alert'\n | 'status'\n | 'separator'\n | 'progressbar'\n | 'none'\n | 'presentation'\n\n/** Accessibility state, lowered to the matching `aria-*` attributes. */\nexport interface A11yState {\n disabled?: boolean\n selected?: boolean\n checked?: boolean\n expanded?: boolean\n busy?: boolean\n hidden?: boolean\n}\n\n/** The accessibility surface every Atlas primitive accepts. */\nexport interface A11yProps {\n /** ARIA role (web `role`). */\n role?: Role\n /** Accessible name (`aria-label`). */\n label?: string\n /** Id(s) of the element(s) labelling this one (`aria-labelledby`). */\n labelledBy?: string\n /** Id(s) of the element(s) describing this one (`aria-describedby`). */\n describedBy?: string\n /** Live-region politeness (`aria-live`). */\n live?: 'off' | 'polite' | 'assertive'\n /** Accessibility state (`aria-disabled`/`-selected`/`-checked`/`-expanded`/`-busy`/`aria-hidden`). */\n state?: A11yState\n}\n\n/**\n * Lower {@link A11yProps} to a host prop bag of `role` + `aria-*` (only keys that are defined,\n * so omitted props stay omitted — exactOptionalPropertyTypes-safe).\n */\nexport function toA11yProps(a11y: A11yProps): Record<string, string> {\n const out: Record<string, string> = {}\n if (a11y.role !== undefined) out.role = a11y.role\n if (a11y.label !== undefined) out['aria-label'] = a11y.label\n if (a11y.labelledBy !== undefined) out['aria-labelledby'] = a11y.labelledBy\n if (a11y.describedBy !== undefined) out['aria-describedby'] = a11y.describedBy\n if (a11y.live !== undefined) out['aria-live'] = a11y.live\n const s = a11y.state\n if (s) {\n if (s.disabled !== undefined) out['aria-disabled'] = String(s.disabled)\n if (s.selected !== undefined) out['aria-selected'] = String(s.selected)\n if (s.checked !== undefined) out['aria-checked'] = String(s.checked)\n if (s.expanded !== undefined) out['aria-expanded'] = String(s.expanded)\n if (s.busy !== undefined) out['aria-busy'] = String(s.busy)\n if (s.hidden !== undefined) out['aria-hidden'] = String(s.hidden)\n }\n return out\n}\n"],"mappings":";;;;;AA8DA,SAAgB,YAAY,MAAyC;CACnE,MAAM,MAA8B,CAAC;CACrC,IAAI,KAAK,SAAS,KAAA,GAAW,IAAI,OAAO,KAAK;CAC7C,IAAI,KAAK,UAAU,KAAA,GAAW,IAAI,gBAAgB,KAAK;CACvD,IAAI,KAAK,eAAe,KAAA,GAAW,IAAI,qBAAqB,KAAK;CACjE,IAAI,KAAK,gBAAgB,KAAA,GAAW,IAAI,sBAAsB,KAAK;CACnE,IAAI,KAAK,SAAS,KAAA,GAAW,IAAI,eAAe,KAAK;CACrD,MAAM,IAAI,KAAK;CACf,IAAI,GAAG;EACL,IAAI,EAAE,aAAa,KAAA,GAAW,IAAI,mBAAmB,OAAO,EAAE,QAAQ;EACtE,IAAI,EAAE,aAAa,KAAA,GAAW,IAAI,mBAAmB,OAAO,EAAE,QAAQ;EACtE,IAAI,EAAE,YAAY,KAAA,GAAW,IAAI,kBAAkB,OAAO,EAAE,OAAO;EACnE,IAAI,EAAE,aAAa,KAAA,GAAW,IAAI,mBAAmB,OAAO,EAAE,QAAQ;EACtE,IAAI,EAAE,SAAS,KAAA,GAAW,IAAI,eAAe,OAAO,EAAE,IAAI;EAC1D,IAAI,EAAE,WAAW,KAAA,GAAW,IAAI,iBAAiB,OAAO,EAAE,MAAM;CAClE;CACA,OAAO;AACT"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { StyleInput } from "./style.js";
|
|
2
|
+
import { BaseProps, Reactive } from "./host.js";
|
|
3
|
+
import { Component, MindeesNode } from "@mindees/core";
|
|
4
|
+
|
|
5
|
+
//#region src/components.d.ts
|
|
6
|
+
/** A surface that groups one coherent unit of content. */
|
|
7
|
+
interface CardProps extends BaseProps {
|
|
8
|
+
readonly children?: MindeesNode;
|
|
9
|
+
/** Visual emphasis. `elevated` (default) lifts off the bg; `filled` is a soft tint; `outlined` is a hairline. */
|
|
10
|
+
readonly variant?: 'elevated' | 'filled' | 'outlined';
|
|
11
|
+
/** Internal padding (handbook default 16). */
|
|
12
|
+
readonly padding?: number | string;
|
|
13
|
+
/** Corner radius (handbook 12–16 for app cards). */
|
|
14
|
+
readonly radius?: number;
|
|
15
|
+
}
|
|
16
|
+
declare const Card: Component<CardProps>;
|
|
17
|
+
/** A thin rule separating content. */
|
|
18
|
+
interface DividerProps extends BaseProps {
|
|
19
|
+
readonly orientation?: 'horizontal' | 'vertical';
|
|
20
|
+
readonly thickness?: number;
|
|
21
|
+
/** Override color (defaults to the theme border). */
|
|
22
|
+
readonly color?: string;
|
|
23
|
+
}
|
|
24
|
+
declare const Divider: Component<DividerProps>;
|
|
25
|
+
type BadgeTone = 'neutral' | 'info' | 'success' | 'warning' | 'danger';
|
|
26
|
+
/** A compact status/count pill. */
|
|
27
|
+
interface BadgeProps extends BaseProps {
|
|
28
|
+
readonly children?: MindeesNode;
|
|
29
|
+
readonly tone?: BadgeTone;
|
|
30
|
+
}
|
|
31
|
+
declare const Badge: Component<BadgeProps>;
|
|
32
|
+
/** A circular user image, falling back to initials. */
|
|
33
|
+
interface AvatarProps extends BaseProps {
|
|
34
|
+
readonly src?: string;
|
|
35
|
+
readonly name?: string;
|
|
36
|
+
/** Diameter in px (default 40). */
|
|
37
|
+
readonly size?: number;
|
|
38
|
+
}
|
|
39
|
+
declare const Avatar: Component<AvatarProps>;
|
|
40
|
+
/** A compact, optionally-selectable token (filter/choice/input). */
|
|
41
|
+
interface ChipProps extends Omit<BaseProps, 'style'> {
|
|
42
|
+
readonly label: string;
|
|
43
|
+
readonly selected?: Reactive<boolean>;
|
|
44
|
+
readonly disabled?: boolean;
|
|
45
|
+
readonly onPress?: () => void;
|
|
46
|
+
readonly leading?: MindeesNode;
|
|
47
|
+
readonly trailing?: MindeesNode;
|
|
48
|
+
readonly style?: Reactive<StyleInput>;
|
|
49
|
+
}
|
|
50
|
+
declare const Chip: Component<ChipProps>;
|
|
51
|
+
/** A binary on/off toggle (composed track + knob; flips instantly on press). */
|
|
52
|
+
interface SwitchProps extends Omit<BaseProps, 'style'> {
|
|
53
|
+
/** Controlled state (static or reactive). */
|
|
54
|
+
readonly value: Reactive<boolean>;
|
|
55
|
+
readonly onValueChange?: (value: boolean) => void;
|
|
56
|
+
readonly disabled?: boolean;
|
|
57
|
+
readonly style?: Reactive<StyleInput>;
|
|
58
|
+
}
|
|
59
|
+
declare const Switch: Component<SwitchProps>;
|
|
60
|
+
/** A container that pads itself by the live safe-area insets (notch, home indicator, …). */
|
|
61
|
+
interface SafeAreaViewProps extends BaseProps {
|
|
62
|
+
readonly children?: MindeesNode;
|
|
63
|
+
/** Which edges to inset (default: all four). */
|
|
64
|
+
readonly edges?: ReadonlyArray<'top' | 'right' | 'bottom' | 'left'>;
|
|
65
|
+
}
|
|
66
|
+
declare const SafeAreaView: Component<SafeAreaViewProps>;
|
|
67
|
+
/** A container that pads its bottom by the live keyboard height so content stays visible. */
|
|
68
|
+
interface KeyboardAvoidingViewProps extends BaseProps {
|
|
69
|
+
readonly children?: MindeesNode;
|
|
70
|
+
}
|
|
71
|
+
declare const KeyboardAvoidingView: Component<KeyboardAvoidingViewProps>;
|
|
72
|
+
/** A determinate progress bar (track + reactive fill). */
|
|
73
|
+
interface ProgressBarProps extends BaseProps {
|
|
74
|
+
/** Progress 0..1 (static or reactive). Values outside the range are clamped. */
|
|
75
|
+
readonly value?: Reactive<number>;
|
|
76
|
+
readonly trackColor?: string;
|
|
77
|
+
readonly color?: string;
|
|
78
|
+
readonly height?: number;
|
|
79
|
+
}
|
|
80
|
+
declare const ProgressBar: Component<ProgressBarProps>;
|
|
81
|
+
//#endregion
|
|
82
|
+
export { Avatar, AvatarProps, Badge, BadgeProps, Card, CardProps, Chip, ChipProps, Divider, DividerProps, KeyboardAvoidingView, KeyboardAvoidingViewProps, ProgressBar, ProgressBarProps, SafeAreaView, SafeAreaViewProps, Switch, SwitchProps };
|
|
83
|
+
//# sourceMappingURL=components.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"components.d.ts","names":[],"sources":["../src/components.ts"],"mappings":";;;;;;UA8CiB,SAAA,SAAkB,SAAS;EAAA,SACjC,QAAA,GAAW,WAAA;EAQT;EAAA,SANF,OAAA;;WAEA,OAAA;EAI2B;EAAA,SAF3B,MAAA;AAAA;AAAA,cAEE,IAAA,EAAM,SAAS,CAAC,SAAA;;UA4BZ,YAAA,SAAqB,SAAS;EAAA,SACpC,WAAA;EAAA,SACA,SAAA;EAEA;EAAA,SAAA,KAAA;AAAA;AAAA,cAEE,OAAA,EAAS,SAAS,CAAC,YAAA;AAAA,KAoBpB,SAAA;;UAUK,UAAA,SAAmB,SAAA;EAAA,SACzB,QAAA,GAAW,WAAA;EAAA,SACX,IAAA,GAAO,SAAA;AAAA;AAAA,cAEL,KAAA,EAAO,SAAS,CAAC,UAAA;;UAwCb,WAAA,SAAoB,SAAS;EAAA,SACnC,GAAA;EAAA,SACA,IAAA;;WAEA,IAAA;AAAA;AAAA,cAEE,MAAA,EAAQ,SAAS,CAAC,WAAA;;UA2Cd,SAAA,SAAkB,IAAA,CAAK,SAAA;EAAA,SAC7B,KAAA;EAAA,SACA,QAAA,GAAW,QAAA;EAAA,SACX,QAAA;EAAA,SACA,OAAA;EAAA,SACA,OAAA,GAAU,WAAA;EAAA,SACV,QAAA,GAAW,WAAA;EAAA,SACX,KAAA,GAAQ,QAAA,CAAS,UAAA;AAAA;AAAA,cAEf,IAAA,EAAM,SAAS,CAAC,SAAA;;UAuDZ,WAAA,SAAoB,IAAA,CAAK,SAAA;EAzJF;EAAA,SA2J7B,KAAA,EAAO,QAAA;EAAA,SACP,aAAA,IAAiB,KAAA;EAAA,SACjB,QAAA;EAAA,SACA,KAAA,GAAQ,QAAA,CAAS,UAAA;AAAA;AAAA,cAEf,MAAA,EAAQ,SAAS,CAAC,WAAA;;UA4Cd,iBAAA,SAA0B,SAAA;EAAA,SAChC,QAAA,GAAW,WAAA;EAjKP;EAAA,SAmKJ,KAAA,GAAQ,aAAA;AAAA;AAAA,cAEN,YAAA,EAAc,SAAS,CAAC,iBAAA;;UAsBpB,yBAAA,SAAkC,SAAS;EAAA,SACjD,QAAA,GAAW,WAAA;AAAA;AAAA,cAET,oBAAA,EAAsB,SAAS,CAAC,yBAAA;;UAY5B,gBAAA,SAAyB,SAAS;EAxJ9B;EAAA,SA0JV,KAAA,GAAQ,QAAA;EAAA,SACR,UAAA;EAAA,SACA,KAAA;EAAA,SACA,MAAA;AAAA;AAAA,cAEE,WAAA,EAAa,SAAS,CAAC,gBAAA"}
|
|
@@ -0,0 +1,283 @@
|
|
|
1
|
+
import { useKeyboard, useSafeAreaInsets } from "./environment.js";
|
|
2
|
+
import { flattenStyle } from "./style.js";
|
|
3
|
+
import { Image, Pressable, Text, View } from "./primitives.js";
|
|
4
|
+
import { fontWeight, radius, space, useTheme } from "./tokens.js";
|
|
5
|
+
import { createElement } from "@mindees/core";
|
|
6
|
+
//#region src/components.ts
|
|
7
|
+
/**
|
|
8
|
+
* Atlas components — higher-level building blocks composed purely from the primitives
|
|
9
|
+
* (View/Text/Pressable/Image) + the device hooks. No new host concepts, so every one
|
|
10
|
+
* renders on web *and* native today, and stays fine-grained: reactive bits are accessor
|
|
11
|
+
* styles, so only the changed node re-runs (no component re-render).
|
|
12
|
+
*
|
|
13
|
+
* Colors come from the design tokens via {@link useTheme}, so components re-theme
|
|
14
|
+
* automatically light↔dark (handbook §23/§31). Spacing/radius/type use the token scales.
|
|
15
|
+
*
|
|
16
|
+
* @module
|
|
17
|
+
*/
|
|
18
|
+
/** Merge a base style with a caller's (possibly reactive) style, staying reactive if either is. */
|
|
19
|
+
function mergeStyle(base, style) {
|
|
20
|
+
const baseFn = typeof base === "function" ? base : null;
|
|
21
|
+
const styleFn = typeof style === "function" ? style : null;
|
|
22
|
+
if (baseFn || styleFn) {
|
|
23
|
+
const baseVal = base;
|
|
24
|
+
const styleVal = style;
|
|
25
|
+
return () => flattenStyle([baseFn ? baseFn() : baseVal, styleFn ? styleFn() : styleVal]);
|
|
26
|
+
}
|
|
27
|
+
return flattenStyle([base, style]);
|
|
28
|
+
}
|
|
29
|
+
/** Normalize a `Reactive<T>` to an accessor. */
|
|
30
|
+
function toAccessor(value, fallback) {
|
|
31
|
+
if (typeof value === "function") return value;
|
|
32
|
+
return () => value === void 0 ? fallback : value;
|
|
33
|
+
}
|
|
34
|
+
const Card = (props) => {
|
|
35
|
+
const theme = useTheme();
|
|
36
|
+
const { variant = "elevated", padding = space.md, radius: radius$1 = radius.lg, style, children, ...rest } = props;
|
|
37
|
+
const base = () => {
|
|
38
|
+
const c = theme().color;
|
|
39
|
+
return {
|
|
40
|
+
padding,
|
|
41
|
+
borderRadius: radius$1,
|
|
42
|
+
...variant === "outlined" ? {
|
|
43
|
+
borderWidth: 1,
|
|
44
|
+
borderColor: c.border
|
|
45
|
+
} : variant === "filled" ? { backgroundColor: c.surfaceVariant } : {
|
|
46
|
+
backgroundColor: c.surface,
|
|
47
|
+
borderWidth: 1,
|
|
48
|
+
borderColor: c.border
|
|
49
|
+
}
|
|
50
|
+
};
|
|
51
|
+
};
|
|
52
|
+
return createElement(View, {
|
|
53
|
+
...rest,
|
|
54
|
+
style: mergeStyle(base, style)
|
|
55
|
+
}, children);
|
|
56
|
+
};
|
|
57
|
+
const Divider = (props) => {
|
|
58
|
+
const theme = useTheme();
|
|
59
|
+
const { orientation = "horizontal", thickness = 1, color, style, ...rest } = props;
|
|
60
|
+
const base = () => {
|
|
61
|
+
const bg = color ?? theme().color.border;
|
|
62
|
+
return orientation === "horizontal" ? {
|
|
63
|
+
height: thickness,
|
|
64
|
+
alignSelf: "stretch",
|
|
65
|
+
backgroundColor: bg
|
|
66
|
+
} : {
|
|
67
|
+
width: thickness,
|
|
68
|
+
alignSelf: "stretch",
|
|
69
|
+
backgroundColor: bg
|
|
70
|
+
};
|
|
71
|
+
};
|
|
72
|
+
return createElement(View, {
|
|
73
|
+
...rest,
|
|
74
|
+
role: rest.role ?? "separator",
|
|
75
|
+
style: mergeStyle(base, style)
|
|
76
|
+
});
|
|
77
|
+
};
|
|
78
|
+
/** Resolve a tone to its {bg, fg} in the active theme. */
|
|
79
|
+
function toneColors(tone, theme) {
|
|
80
|
+
const c = theme.color;
|
|
81
|
+
if (tone === "neutral") return {
|
|
82
|
+
bg: c.surfaceVariant,
|
|
83
|
+
fg: c.text
|
|
84
|
+
};
|
|
85
|
+
return {
|
|
86
|
+
bg: c[tone],
|
|
87
|
+
fg: c.onTone
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
const Badge = (props) => {
|
|
91
|
+
const theme = useTheme();
|
|
92
|
+
const { tone = "neutral", style, children, ...rest } = props;
|
|
93
|
+
const base = () => ({
|
|
94
|
+
display: "flex",
|
|
95
|
+
alignItems: "center",
|
|
96
|
+
justifyContent: "center",
|
|
97
|
+
paddingTop: space["3xs"],
|
|
98
|
+
paddingBottom: space["3xs"],
|
|
99
|
+
paddingLeft: space.xs,
|
|
100
|
+
paddingRight: space.xs,
|
|
101
|
+
borderRadius: radius.full,
|
|
102
|
+
backgroundColor: toneColors(tone, theme()).bg
|
|
103
|
+
});
|
|
104
|
+
const textStyle = () => ({
|
|
105
|
+
fontSize: 12,
|
|
106
|
+
fontWeight: fontWeight.semibold,
|
|
107
|
+
color: toneColors(tone, theme()).fg
|
|
108
|
+
});
|
|
109
|
+
return createElement(View, {
|
|
110
|
+
...rest,
|
|
111
|
+
role: rest.role ?? "status",
|
|
112
|
+
style: mergeStyle(base, style)
|
|
113
|
+
}, createElement(Text, { style: textStyle }, children));
|
|
114
|
+
};
|
|
115
|
+
/** Up-to-two-letter initials from a name. */
|
|
116
|
+
function initialsOf(name) {
|
|
117
|
+
const parts = name.trim().split(/\s+/).filter(Boolean);
|
|
118
|
+
if (parts.length === 0) return "?";
|
|
119
|
+
return ((parts[0]?.[0] ?? "") + (parts.length > 1 ? parts[parts.length - 1]?.[0] ?? "" : "")).toUpperCase();
|
|
120
|
+
}
|
|
121
|
+
const Avatar = (props) => {
|
|
122
|
+
const theme = useTheme();
|
|
123
|
+
const { src, name, size = 40, style, ...rest } = props;
|
|
124
|
+
const base = () => ({
|
|
125
|
+
width: size,
|
|
126
|
+
height: size,
|
|
127
|
+
borderRadius: size / 2,
|
|
128
|
+
overflow: "hidden",
|
|
129
|
+
display: "flex",
|
|
130
|
+
alignItems: "center",
|
|
131
|
+
justifyContent: "center",
|
|
132
|
+
backgroundColor: theme().color.surfaceVariant
|
|
133
|
+
});
|
|
134
|
+
const content = src ? createElement(Image, {
|
|
135
|
+
src,
|
|
136
|
+
label: name ?? "",
|
|
137
|
+
...name ? {} : { decorative: true },
|
|
138
|
+
style: {
|
|
139
|
+
width: size,
|
|
140
|
+
height: size
|
|
141
|
+
}
|
|
142
|
+
}) : createElement(Text, { style: () => ({
|
|
143
|
+
fontSize: Math.round(size * .4),
|
|
144
|
+
fontWeight: fontWeight.semibold,
|
|
145
|
+
color: theme().color.text
|
|
146
|
+
}) }, name ? initialsOf(name) : "?");
|
|
147
|
+
return createElement(View, {
|
|
148
|
+
...rest,
|
|
149
|
+
label: rest.label ?? name,
|
|
150
|
+
style: mergeStyle(base, style)
|
|
151
|
+
}, content);
|
|
152
|
+
};
|
|
153
|
+
const Chip = (props) => {
|
|
154
|
+
const theme = useTheme();
|
|
155
|
+
const { label, selected = false, disabled, onPress, leading, trailing, style, ...rest } = props;
|
|
156
|
+
const isSelected = toAccessor(selected, false);
|
|
157
|
+
const base = () => {
|
|
158
|
+
const c = theme().color;
|
|
159
|
+
const on = isSelected();
|
|
160
|
+
return {
|
|
161
|
+
display: "flex",
|
|
162
|
+
flexDirection: "row",
|
|
163
|
+
alignItems: "center",
|
|
164
|
+
justifyContent: "center",
|
|
165
|
+
gap: space["2xs"],
|
|
166
|
+
minHeight: 32,
|
|
167
|
+
paddingTop: space["2xs"],
|
|
168
|
+
paddingBottom: space["2xs"],
|
|
169
|
+
paddingLeft: space.sm,
|
|
170
|
+
paddingRight: space.sm,
|
|
171
|
+
borderRadius: radius.full,
|
|
172
|
+
borderWidth: 1,
|
|
173
|
+
borderColor: on ? c.primary : c.border,
|
|
174
|
+
backgroundColor: on ? c.primary : "transparent",
|
|
175
|
+
opacity: disabled ? .5 : 1
|
|
176
|
+
};
|
|
177
|
+
};
|
|
178
|
+
const inner = [
|
|
179
|
+
leading,
|
|
180
|
+
createElement(Text, { style: () => ({
|
|
181
|
+
fontSize: 14,
|
|
182
|
+
fontWeight: fontWeight.medium,
|
|
183
|
+
color: isSelected() ? theme().color.onPrimary : theme().color.text
|
|
184
|
+
}) }, label),
|
|
185
|
+
trailing
|
|
186
|
+
].filter((n) => n != null);
|
|
187
|
+
return createElement(Pressable, {
|
|
188
|
+
...rest,
|
|
189
|
+
role: rest.role ?? "button",
|
|
190
|
+
...onPress ? { onPress } : {},
|
|
191
|
+
...disabled ? { disabled: true } : {},
|
|
192
|
+
style: mergeStyle(base, style)
|
|
193
|
+
}, inner);
|
|
194
|
+
};
|
|
195
|
+
const Switch = (props) => {
|
|
196
|
+
const theme = useTheme();
|
|
197
|
+
const { value, onValueChange, disabled, style, ...rest } = props;
|
|
198
|
+
const isOn = toAccessor(value, false);
|
|
199
|
+
const track = () => ({
|
|
200
|
+
display: "flex",
|
|
201
|
+
flexDirection: "row",
|
|
202
|
+
alignItems: "center",
|
|
203
|
+
justifyContent: isOn() ? "flex-end" : "flex-start",
|
|
204
|
+
width: 52,
|
|
205
|
+
height: 32,
|
|
206
|
+
borderRadius: radius.full,
|
|
207
|
+
padding: 3,
|
|
208
|
+
backgroundColor: isOn() ? theme().color.primary : theme().color.textMuted,
|
|
209
|
+
opacity: disabled ? .5 : 1
|
|
210
|
+
});
|
|
211
|
+
const knob = createElement(View, { style: () => ({
|
|
212
|
+
width: 26,
|
|
213
|
+
height: 26,
|
|
214
|
+
borderRadius: 13,
|
|
215
|
+
backgroundColor: theme().color.onPrimary
|
|
216
|
+
}) });
|
|
217
|
+
const handlePress = onValueChange && !disabled ? () => onValueChange(!isOn()) : void 0;
|
|
218
|
+
return createElement(Pressable, {
|
|
219
|
+
...rest,
|
|
220
|
+
role: rest.role ?? "switch",
|
|
221
|
+
state: {
|
|
222
|
+
...rest.state ?? {},
|
|
223
|
+
checked: isOn()
|
|
224
|
+
},
|
|
225
|
+
...disabled ? { disabled: true } : {},
|
|
226
|
+
...handlePress ? { onPress: handlePress } : {},
|
|
227
|
+
style: mergeStyle(track, style)
|
|
228
|
+
}, knob);
|
|
229
|
+
};
|
|
230
|
+
const SafeAreaView = (props) => {
|
|
231
|
+
const insets = useSafeAreaInsets();
|
|
232
|
+
const { edges, style, children, ...rest } = props;
|
|
233
|
+
const wants = (edge) => !edges || edges.includes(edge);
|
|
234
|
+
const base = () => {
|
|
235
|
+
const i = insets();
|
|
236
|
+
return {
|
|
237
|
+
paddingTop: wants("top") ? i.top : 0,
|
|
238
|
+
paddingRight: wants("right") ? i.right : 0,
|
|
239
|
+
paddingBottom: wants("bottom") ? i.bottom : 0,
|
|
240
|
+
paddingLeft: wants("left") ? i.left : 0
|
|
241
|
+
};
|
|
242
|
+
};
|
|
243
|
+
return createElement(View, {
|
|
244
|
+
...rest,
|
|
245
|
+
style: mergeStyle(base, style)
|
|
246
|
+
}, children);
|
|
247
|
+
};
|
|
248
|
+
const KeyboardAvoidingView = (props) => {
|
|
249
|
+
const keyboard = useKeyboard();
|
|
250
|
+
const { style, children, ...rest } = props;
|
|
251
|
+
const base = () => ({ paddingBottom: keyboard().height });
|
|
252
|
+
return createElement(View, {
|
|
253
|
+
...rest,
|
|
254
|
+
style: mergeStyle(base, style)
|
|
255
|
+
}, children);
|
|
256
|
+
};
|
|
257
|
+
const ProgressBar = (props) => {
|
|
258
|
+
const theme = useTheme();
|
|
259
|
+
const { value = 0, trackColor, color, height = 6, style, ...rest } = props;
|
|
260
|
+
const progress = toAccessor(value, 0);
|
|
261
|
+
const track = () => ({
|
|
262
|
+
width: "100%",
|
|
263
|
+
height,
|
|
264
|
+
borderRadius: height / 2,
|
|
265
|
+
overflow: "hidden",
|
|
266
|
+
backgroundColor: trackColor ?? theme().color.surfaceVariant
|
|
267
|
+
});
|
|
268
|
+
const fill = () => ({
|
|
269
|
+
height,
|
|
270
|
+
borderRadius: height / 2,
|
|
271
|
+
backgroundColor: color ?? theme().color.primary,
|
|
272
|
+
width: `${Math.max(0, Math.min(1, progress())) * 100}%`
|
|
273
|
+
});
|
|
274
|
+
return createElement(View, {
|
|
275
|
+
...rest,
|
|
276
|
+
role: rest.role ?? "progressbar",
|
|
277
|
+
style: mergeStyle(track, style)
|
|
278
|
+
}, createElement(View, { style: fill }));
|
|
279
|
+
};
|
|
280
|
+
//#endregion
|
|
281
|
+
export { Avatar, Badge, Card, Chip, Divider, KeyboardAvoidingView, ProgressBar, SafeAreaView, Switch };
|
|
282
|
+
|
|
283
|
+
//# sourceMappingURL=components.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"components.js","names":["radiusScale","radius"],"sources":["../src/components.ts"],"sourcesContent":["/**\n * Atlas components — higher-level building blocks composed purely from the primitives\n * (View/Text/Pressable/Image) + the device hooks. No new host concepts, so every one\n * renders on web *and* native today, and stays fine-grained: reactive bits are accessor\n * styles, so only the changed node re-runs (no component re-render).\n *\n * Colors come from the design tokens via {@link useTheme}, so components re-theme\n * automatically light↔dark (handbook §23/§31). Spacing/radius/type use the token scales.\n *\n * @module\n */\n\nimport { type Accessor, type Component, createElement, type MindeesNode } from '@mindees/core'\nimport { useKeyboard, useSafeAreaInsets } from './environment'\nimport type { BaseProps, Reactive } from './host'\nimport { Image, Pressable, Text, View } from './primitives'\nimport { flattenStyle, type StyleInput } from './style'\nimport { fontWeight, radius as radiusScale, space, type Theme, useTheme } from './tokens'\n\n/** Merge a base style with a caller's (possibly reactive) style, staying reactive if either is. */\nfunction mergeStyle(\n base: StyleInput | Accessor<StyleInput>,\n style: Reactive<StyleInput> | undefined,\n): Reactive<StyleInput> {\n const baseFn = typeof base === 'function' ? (base as Accessor<StyleInput>) : null\n const styleFn = typeof style === 'function' ? (style as Accessor<StyleInput>) : null\n if (baseFn || styleFn) {\n // In each branch the non-fn side isn't a function, so the StyleInput cast is sound.\n const baseVal = base as StyleInput\n const styleVal = style as StyleInput\n return () => flattenStyle([baseFn ? baseFn() : baseVal, styleFn ? styleFn() : styleVal])\n }\n return flattenStyle([base as StyleInput, style as StyleInput])\n}\n\n/** Normalize a `Reactive<T>` to an accessor. */\nfunction toAccessor<T>(value: Reactive<T>, fallback: T): Accessor<T> {\n if (typeof value === 'function') return value as Accessor<T>\n return () => (value === undefined ? fallback : value)\n}\n\n// ---------------------------------------------------------------------------\n// Card\n// ---------------------------------------------------------------------------\n\n/** A surface that groups one coherent unit of content. */\nexport interface CardProps extends BaseProps {\n readonly children?: MindeesNode\n /** Visual emphasis. `elevated` (default) lifts off the bg; `filled` is a soft tint; `outlined` is a hairline. */\n readonly variant?: 'elevated' | 'filled' | 'outlined'\n /** Internal padding (handbook default 16). */\n readonly padding?: number | string\n /** Corner radius (handbook 12–16 for app cards). */\n readonly radius?: number\n}\nexport const Card: Component<CardProps> = (props) => {\n const theme = useTheme()\n const {\n variant = 'elevated',\n padding = space.md,\n radius = radiusScale.lg,\n style,\n children,\n ...rest\n } = props\n const base: Accessor<StyleInput> = () => {\n const c = theme().color\n const surface: StyleInput =\n variant === 'outlined'\n ? { borderWidth: 1, borderColor: c.border }\n : variant === 'filled'\n ? { backgroundColor: c.surfaceVariant }\n : { backgroundColor: c.surface, borderWidth: 1, borderColor: c.border }\n return { padding, borderRadius: radius, ...surface }\n }\n return createElement(View, { ...rest, style: mergeStyle(base, style) }, children)\n}\n\n// ---------------------------------------------------------------------------\n// Divider\n// ---------------------------------------------------------------------------\n\n/** A thin rule separating content. */\nexport interface DividerProps extends BaseProps {\n readonly orientation?: 'horizontal' | 'vertical'\n readonly thickness?: number\n /** Override color (defaults to the theme border). */\n readonly color?: string\n}\nexport const Divider: Component<DividerProps> = (props) => {\n const theme = useTheme()\n const { orientation = 'horizontal', thickness = 1, color, style, ...rest } = props\n const base: Accessor<StyleInput> = () => {\n const bg = color ?? theme().color.border\n return orientation === 'horizontal'\n ? { height: thickness, alignSelf: 'stretch', backgroundColor: bg }\n : { width: thickness, alignSelf: 'stretch', backgroundColor: bg }\n }\n return createElement(View, {\n ...rest,\n role: rest.role ?? 'separator',\n style: mergeStyle(base, style),\n })\n}\n\n// ---------------------------------------------------------------------------\n// Badge\n// ---------------------------------------------------------------------------\n\nexport type BadgeTone = 'neutral' | 'info' | 'success' | 'warning' | 'danger'\n\n/** Resolve a tone to its {bg, fg} in the active theme. */\nfunction toneColors(tone: BadgeTone, theme: Theme): { bg: string; fg: string } {\n const c = theme.color\n if (tone === 'neutral') return { bg: c.surfaceVariant, fg: c.text }\n return { bg: c[tone], fg: c.onTone }\n}\n\n/** A compact status/count pill. */\nexport interface BadgeProps extends BaseProps {\n readonly children?: MindeesNode\n readonly tone?: BadgeTone\n}\nexport const Badge: Component<BadgeProps> = (props) => {\n const theme = useTheme()\n const { tone = 'neutral', style, children, ...rest } = props\n const base: Accessor<StyleInput> = () => ({\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n paddingTop: space['3xs'],\n paddingBottom: space['3xs'],\n paddingLeft: space.xs,\n paddingRight: space.xs,\n borderRadius: radiusScale.full,\n backgroundColor: toneColors(tone, theme()).bg,\n })\n const textStyle: Accessor<StyleInput> = () => ({\n fontSize: 12,\n fontWeight: fontWeight.semibold,\n color: toneColors(tone, theme()).fg,\n })\n return createElement(\n View,\n { ...rest, role: rest.role ?? 'status', style: mergeStyle(base, style) },\n createElement(Text, { style: textStyle }, children),\n )\n}\n\n// ---------------------------------------------------------------------------\n// Avatar\n// ---------------------------------------------------------------------------\n\n/** Up-to-two-letter initials from a name. */\nfunction initialsOf(name: string): string {\n const parts = name.trim().split(/\\s+/).filter(Boolean)\n if (parts.length === 0) return '?'\n const first = parts[0]?.[0] ?? ''\n const last = parts.length > 1 ? (parts[parts.length - 1]?.[0] ?? '') : ''\n return (first + last).toUpperCase()\n}\n\n/** A circular user image, falling back to initials. */\nexport interface AvatarProps extends BaseProps {\n readonly src?: string\n readonly name?: string\n /** Diameter in px (default 40). */\n readonly size?: number\n}\nexport const Avatar: Component<AvatarProps> = (props) => {\n const theme = useTheme()\n const { src, name, size = 40, style, ...rest } = props\n const base: Accessor<StyleInput> = () => ({\n width: size,\n height: size,\n borderRadius: size / 2,\n overflow: 'hidden',\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n backgroundColor: theme().color.surfaceVariant,\n })\n const content = src\n ? createElement(Image, {\n src,\n label: name ?? '',\n ...(name ? {} : { decorative: true }),\n style: { width: size, height: size },\n })\n : createElement(\n Text,\n {\n style: () => ({\n fontSize: Math.round(size * 0.4),\n fontWeight: fontWeight.semibold,\n color: theme().color.text,\n }),\n },\n name ? initialsOf(name) : '?',\n )\n return createElement(\n View,\n { ...rest, label: rest.label ?? name, style: mergeStyle(base, style) },\n content,\n )\n}\n\n// ---------------------------------------------------------------------------\n// Chip\n// ---------------------------------------------------------------------------\n\n/** A compact, optionally-selectable token (filter/choice/input). */\nexport interface ChipProps extends Omit<BaseProps, 'style'> {\n readonly label: string\n readonly selected?: Reactive<boolean>\n readonly disabled?: boolean\n readonly onPress?: () => void\n readonly leading?: MindeesNode\n readonly trailing?: MindeesNode\n readonly style?: Reactive<StyleInput>\n}\nexport const Chip: Component<ChipProps> = (props) => {\n const theme = useTheme()\n const { label, selected = false, disabled, onPress, leading, trailing, style, ...rest } = props\n const isSelected = toAccessor(selected, false)\n const base: Accessor<StyleInput> = () => {\n const c = theme().color\n const on = isSelected()\n return {\n display: 'flex',\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: 'center',\n gap: space['2xs'],\n minHeight: 32,\n paddingTop: space['2xs'],\n paddingBottom: space['2xs'],\n paddingLeft: space.sm,\n paddingRight: space.sm,\n borderRadius: radiusScale.full,\n borderWidth: 1,\n borderColor: on ? c.primary : c.border,\n backgroundColor: on ? c.primary : 'transparent',\n opacity: disabled ? 0.5 : 1,\n }\n }\n const text = createElement(\n Text,\n {\n style: () => ({\n fontSize: 14,\n fontWeight: fontWeight.medium,\n color: isSelected() ? theme().color.onPrimary : theme().color.text,\n }),\n },\n label,\n )\n const inner: MindeesNode = [leading, text, trailing].filter((n) => n != null) as MindeesNode\n return createElement(\n Pressable,\n {\n ...rest,\n role: rest.role ?? 'button',\n ...(onPress ? { onPress } : {}),\n ...(disabled ? { disabled: true } : {}),\n style: mergeStyle(base, style),\n },\n inner,\n )\n}\n\n// ---------------------------------------------------------------------------\n// Switch\n// ---------------------------------------------------------------------------\n\n/** A binary on/off toggle (composed track + knob; flips instantly on press). */\nexport interface SwitchProps extends Omit<BaseProps, 'style'> {\n /** Controlled state (static or reactive). */\n readonly value: Reactive<boolean>\n readonly onValueChange?: (value: boolean) => void\n readonly disabled?: boolean\n readonly style?: Reactive<StyleInput>\n}\nexport const Switch: Component<SwitchProps> = (props) => {\n const theme = useTheme()\n const { value, onValueChange, disabled, style, ...rest } = props\n const isOn = toAccessor(value, false)\n const track: Accessor<StyleInput> = () => ({\n display: 'flex',\n flexDirection: 'row',\n alignItems: 'center',\n justifyContent: isOn() ? 'flex-end' : 'flex-start',\n width: 52,\n height: 32,\n borderRadius: radiusScale.full,\n padding: 3,\n backgroundColor: isOn() ? theme().color.primary : theme().color.textMuted,\n opacity: disabled ? 0.5 : 1,\n })\n const knob = createElement(View, {\n style: () => ({\n width: 26,\n height: 26,\n borderRadius: 13,\n backgroundColor: theme().color.onPrimary,\n }),\n })\n const handlePress = onValueChange && !disabled ? () => onValueChange(!isOn()) : undefined\n return createElement(\n Pressable,\n {\n ...rest,\n role: rest.role ?? 'switch',\n state: { ...(rest.state ?? {}), checked: isOn() },\n ...(disabled ? { disabled: true } : {}),\n ...(handlePress ? { onPress: handlePress } : {}),\n style: mergeStyle(track, style),\n },\n knob,\n )\n}\n\n// ---------------------------------------------------------------------------\n// SafeAreaView\n// ---------------------------------------------------------------------------\n\n/** A container that pads itself by the live safe-area insets (notch, home indicator, …). */\nexport interface SafeAreaViewProps extends BaseProps {\n readonly children?: MindeesNode\n /** Which edges to inset (default: all four). */\n readonly edges?: ReadonlyArray<'top' | 'right' | 'bottom' | 'left'>\n}\nexport const SafeAreaView: Component<SafeAreaViewProps> = (props) => {\n const insets = useSafeAreaInsets()\n const { edges, style, children, ...rest } = props\n const wants = (edge: 'top' | 'right' | 'bottom' | 'left'): boolean =>\n !edges || edges.includes(edge)\n const base: Accessor<StyleInput> = () => {\n const i = insets()\n return {\n paddingTop: wants('top') ? i.top : 0,\n paddingRight: wants('right') ? i.right : 0,\n paddingBottom: wants('bottom') ? i.bottom : 0,\n paddingLeft: wants('left') ? i.left : 0,\n }\n }\n return createElement(View, { ...rest, style: mergeStyle(base, style) }, children)\n}\n\n// ---------------------------------------------------------------------------\n// KeyboardAvoidingView\n// ---------------------------------------------------------------------------\n\n/** A container that pads its bottom by the live keyboard height so content stays visible. */\nexport interface KeyboardAvoidingViewProps extends BaseProps {\n readonly children?: MindeesNode\n}\nexport const KeyboardAvoidingView: Component<KeyboardAvoidingViewProps> = (props) => {\n const keyboard = useKeyboard()\n const { style, children, ...rest } = props\n const base: Accessor<StyleInput> = () => ({ paddingBottom: keyboard().height })\n return createElement(View, { ...rest, style: mergeStyle(base, style) }, children)\n}\n\n// ---------------------------------------------------------------------------\n// ProgressBar (determinate)\n// ---------------------------------------------------------------------------\n\n/** A determinate progress bar (track + reactive fill). */\nexport interface ProgressBarProps extends BaseProps {\n /** Progress 0..1 (static or reactive). Values outside the range are clamped. */\n readonly value?: Reactive<number>\n readonly trackColor?: string\n readonly color?: string\n readonly height?: number\n}\nexport const ProgressBar: Component<ProgressBarProps> = (props) => {\n const theme = useTheme()\n const { value = 0, trackColor, color, height = 6, style, ...rest } = props\n const progress = toAccessor(value, 0)\n const track: Accessor<StyleInput> = () => ({\n width: '100%',\n height,\n borderRadius: height / 2,\n overflow: 'hidden',\n backgroundColor: trackColor ?? theme().color.surfaceVariant,\n })\n const fill: Accessor<StyleInput> = () => ({\n height,\n borderRadius: height / 2,\n backgroundColor: color ?? theme().color.primary,\n width: `${Math.max(0, Math.min(1, progress())) * 100}%`,\n })\n return createElement(\n View,\n { ...rest, role: rest.role ?? 'progressbar', style: mergeStyle(track, style) },\n createElement(View, { style: fill }),\n )\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
//#region src/environment.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Platform environment + device hooks — the signal-backed equivalents of React
|
|
4
|
+
* Native's `useWindowDimensions`, `useColorScheme`, `useSafeAreaInsets`, `Keyboard`.
|
|
5
|
+
*
|
|
6
|
+
* The environment is a small set of signals the host/runtime feeds via
|
|
7
|
+
* {@link setEnvironment} (e.g. the native host on launch/rotation/theme change, or a
|
|
8
|
+
* web adapter wired to `window`/`matchMedia`). The hooks return Quantum-style reactive
|
|
9
|
+
* **accessors**, so reads are fine-grained — only the nodes that use a value re-run
|
|
10
|
+
* when it changes (e.g. rotating the device updates exactly the layout that reads
|
|
11
|
+
* window size), with no whole-tree re-render.
|
|
12
|
+
*
|
|
13
|
+
* @module
|
|
14
|
+
*/
|
|
15
|
+
/** Logical window size + density (RN's `useWindowDimensions`). */
|
|
16
|
+
interface WindowDimensions {
|
|
17
|
+
/** Logical width (dp/pt). */
|
|
18
|
+
readonly width: number;
|
|
19
|
+
/** Logical height (dp/pt). */
|
|
20
|
+
readonly height: number;
|
|
21
|
+
/** Device pixel ratio. */
|
|
22
|
+
readonly scale: number;
|
|
23
|
+
/** User font-scaling factor (Dynamic Type / font size setting). */
|
|
24
|
+
readonly fontScale: number;
|
|
25
|
+
}
|
|
26
|
+
/** Safe-area insets in dp/pt (notch, status bar, home indicator, gesture areas). */
|
|
27
|
+
interface SafeAreaInsets {
|
|
28
|
+
readonly top: number;
|
|
29
|
+
readonly right: number;
|
|
30
|
+
readonly bottom: number;
|
|
31
|
+
readonly left: number;
|
|
32
|
+
}
|
|
33
|
+
/** Soft-keyboard state. */
|
|
34
|
+
interface KeyboardState {
|
|
35
|
+
readonly visible: boolean;
|
|
36
|
+
/** Keyboard height in dp/pt when visible, else 0. */
|
|
37
|
+
readonly height: number;
|
|
38
|
+
}
|
|
39
|
+
/** The active color scheme (RN's `useColorScheme`). */
|
|
40
|
+
type ColorScheme = 'light' | 'dark';
|
|
41
|
+
/** The full platform environment. */
|
|
42
|
+
interface PlatformEnvironment {
|
|
43
|
+
readonly window: WindowDimensions;
|
|
44
|
+
readonly colorScheme: ColorScheme;
|
|
45
|
+
readonly safeAreaInsets: SafeAreaInsets;
|
|
46
|
+
readonly keyboard: KeyboardState;
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Update the platform environment. The host/runtime calls this — once on launch and
|
|
50
|
+
* again on changes (rotation, theme switch, keyboard show/hide). Only provided fields
|
|
51
|
+
* change; each is a fine-grained signal write, so only the readers of that field re-run.
|
|
52
|
+
*/
|
|
53
|
+
declare function setEnvironment(env: Partial<PlatformEnvironment>): void;
|
|
54
|
+
/** A snapshot of the current environment (non-reactive; for one-off reads). */
|
|
55
|
+
declare function getEnvironment(): PlatformEnvironment;
|
|
56
|
+
/** Reactive accessor for the window dimensions (updates on resize/rotation). */
|
|
57
|
+
declare function useWindowDimensions(): () => WindowDimensions;
|
|
58
|
+
/** Reactive accessor for the active color scheme (updates on theme change). */
|
|
59
|
+
declare function useColorScheme(): () => ColorScheme;
|
|
60
|
+
/** Reactive accessor for the safe-area insets. */
|
|
61
|
+
declare function useSafeAreaInsets(): () => SafeAreaInsets;
|
|
62
|
+
/** Reactive accessor for the soft-keyboard state. */
|
|
63
|
+
declare function useKeyboard(): () => KeyboardState;
|
|
64
|
+
//#endregion
|
|
65
|
+
export { ColorScheme, KeyboardState, PlatformEnvironment, SafeAreaInsets, WindowDimensions, getEnvironment, setEnvironment, useColorScheme, useKeyboard, useSafeAreaInsets, useWindowDimensions };
|
|
66
|
+
//# sourceMappingURL=environment.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"environment.d.ts","names":[],"sources":["../src/environment.ts"],"mappings":";;AAiBA;;;;;;;;;AAQoB;AAIpB;;;UAZiB,gBAAA;EAaN;EAAA,SAXA,KAAA;EAaA;EAAA,SAXA,MAAA;EAYI;EAAA,SAVJ,KAAA;EAcM;EAAA,SAZN,SAAA;AAAA;;UAIM,cAAA;EAAA,SACN,GAAA;EAAA,SACA,KAAA;EAAA,SACA,MAAA;EAAA,SACA,IAAA;AAAA;AAcX;AAAA,UAViB,aAAA;EAAA,SACN,OAAA;EAUQ;EAAA,SARR,MAAM;AAAA;;KAIL,WAAA;;UAGK,mBAAA;EAAA,SACN,MAAA,EAAQ,gBAAA;EAAA,SACR,WAAA,EAAa,WAAA;EAAA,SACb,cAAA,EAAgB,cAAA;EAAA,SAChB,QAAA,EAAU,aAAA;AAAA;;;;AAAa;AAalC;iBAAgB,cAAA,CAAe,GAAA,EAAK,OAAO,CAAC,mBAAA;;iBAQ5B,cAAA,IAAkB,mBAAmB;;iBAUrC,mBAAA,UAA6B,gBAAgB;;iBAK7C,cAAA,UAAwB,WAAW;AAvBa;AAAA,iBA4BhD,iBAAA,UAA2B,cAAc;;iBAKzC,WAAA,UAAqB,aAAa"}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { signal } from "@mindees/core";
|
|
2
|
+
//#region src/environment.ts
|
|
3
|
+
/**
|
|
4
|
+
* Platform environment + device hooks — the signal-backed equivalents of React
|
|
5
|
+
* Native's `useWindowDimensions`, `useColorScheme`, `useSafeAreaInsets`, `Keyboard`.
|
|
6
|
+
*
|
|
7
|
+
* The environment is a small set of signals the host/runtime feeds via
|
|
8
|
+
* {@link setEnvironment} (e.g. the native host on launch/rotation/theme change, or a
|
|
9
|
+
* web adapter wired to `window`/`matchMedia`). The hooks return Quantum-style reactive
|
|
10
|
+
* **accessors**, so reads are fine-grained — only the nodes that use a value re-run
|
|
11
|
+
* when it changes (e.g. rotating the device updates exactly the layout that reads
|
|
12
|
+
* window size), with no whole-tree re-render.
|
|
13
|
+
*
|
|
14
|
+
* @module
|
|
15
|
+
*/
|
|
16
|
+
const windowSignal = signal({
|
|
17
|
+
width: 0,
|
|
18
|
+
height: 0,
|
|
19
|
+
scale: 1,
|
|
20
|
+
fontScale: 1
|
|
21
|
+
});
|
|
22
|
+
const colorSchemeSignal = signal("light");
|
|
23
|
+
const safeAreaSignal = signal({
|
|
24
|
+
top: 0,
|
|
25
|
+
right: 0,
|
|
26
|
+
bottom: 0,
|
|
27
|
+
left: 0
|
|
28
|
+
});
|
|
29
|
+
const keyboardSignal = signal({
|
|
30
|
+
visible: false,
|
|
31
|
+
height: 0
|
|
32
|
+
});
|
|
33
|
+
/**
|
|
34
|
+
* Update the platform environment. The host/runtime calls this — once on launch and
|
|
35
|
+
* again on changes (rotation, theme switch, keyboard show/hide). Only provided fields
|
|
36
|
+
* change; each is a fine-grained signal write, so only the readers of that field re-run.
|
|
37
|
+
*/
|
|
38
|
+
function setEnvironment(env) {
|
|
39
|
+
if (env.window) windowSignal.set(env.window);
|
|
40
|
+
if (env.colorScheme) colorSchemeSignal.set(env.colorScheme);
|
|
41
|
+
if (env.safeAreaInsets) safeAreaSignal.set(env.safeAreaInsets);
|
|
42
|
+
if (env.keyboard) keyboardSignal.set(env.keyboard);
|
|
43
|
+
}
|
|
44
|
+
/** A snapshot of the current environment (non-reactive; for one-off reads). */
|
|
45
|
+
function getEnvironment() {
|
|
46
|
+
return {
|
|
47
|
+
window: windowSignal(),
|
|
48
|
+
colorScheme: colorSchemeSignal(),
|
|
49
|
+
safeAreaInsets: safeAreaSignal(),
|
|
50
|
+
keyboard: keyboardSignal()
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
/** Reactive accessor for the window dimensions (updates on resize/rotation). */
|
|
54
|
+
function useWindowDimensions() {
|
|
55
|
+
return windowSignal;
|
|
56
|
+
}
|
|
57
|
+
/** Reactive accessor for the active color scheme (updates on theme change). */
|
|
58
|
+
function useColorScheme() {
|
|
59
|
+
return colorSchemeSignal;
|
|
60
|
+
}
|
|
61
|
+
/** Reactive accessor for the safe-area insets. */
|
|
62
|
+
function useSafeAreaInsets() {
|
|
63
|
+
return safeAreaSignal;
|
|
64
|
+
}
|
|
65
|
+
/** Reactive accessor for the soft-keyboard state. */
|
|
66
|
+
function useKeyboard() {
|
|
67
|
+
return keyboardSignal;
|
|
68
|
+
}
|
|
69
|
+
//#endregion
|
|
70
|
+
export { getEnvironment, setEnvironment, useColorScheme, useKeyboard, useSafeAreaInsets, useWindowDimensions };
|
|
71
|
+
|
|
72
|
+
//# sourceMappingURL=environment.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"environment.js","names":[],"sources":["../src/environment.ts"],"sourcesContent":["/**\n * Platform environment + device hooks — the signal-backed equivalents of React\n * Native's `useWindowDimensions`, `useColorScheme`, `useSafeAreaInsets`, `Keyboard`.\n *\n * The environment is a small set of signals the host/runtime feeds via\n * {@link setEnvironment} (e.g. the native host on launch/rotation/theme change, or a\n * web adapter wired to `window`/`matchMedia`). The hooks return Quantum-style reactive\n * **accessors**, so reads are fine-grained — only the nodes that use a value re-run\n * when it changes (e.g. rotating the device updates exactly the layout that reads\n * window size), with no whole-tree re-render.\n *\n * @module\n */\n\nimport { signal } from '@mindees/core'\n\n/** Logical window size + density (RN's `useWindowDimensions`). */\nexport interface WindowDimensions {\n /** Logical width (dp/pt). */\n readonly width: number\n /** Logical height (dp/pt). */\n readonly height: number\n /** Device pixel ratio. */\n readonly scale: number\n /** User font-scaling factor (Dynamic Type / font size setting). */\n readonly fontScale: number\n}\n\n/** Safe-area insets in dp/pt (notch, status bar, home indicator, gesture areas). */\nexport interface SafeAreaInsets {\n readonly top: number\n readonly right: number\n readonly bottom: number\n readonly left: number\n}\n\n/** Soft-keyboard state. */\nexport interface KeyboardState {\n readonly visible: boolean\n /** Keyboard height in dp/pt when visible, else 0. */\n readonly height: number\n}\n\n/** The active color scheme (RN's `useColorScheme`). */\nexport type ColorScheme = 'light' | 'dark'\n\n/** The full platform environment. */\nexport interface PlatformEnvironment {\n readonly window: WindowDimensions\n readonly colorScheme: ColorScheme\n readonly safeAreaInsets: SafeAreaInsets\n readonly keyboard: KeyboardState\n}\n\nconst windowSignal = signal<WindowDimensions>({ width: 0, height: 0, scale: 1, fontScale: 1 })\nconst colorSchemeSignal = signal<ColorScheme>('light')\nconst safeAreaSignal = signal<SafeAreaInsets>({ top: 0, right: 0, bottom: 0, left: 0 })\nconst keyboardSignal = signal<KeyboardState>({ visible: false, height: 0 })\n\n/**\n * Update the platform environment. The host/runtime calls this — once on launch and\n * again on changes (rotation, theme switch, keyboard show/hide). Only provided fields\n * change; each is a fine-grained signal write, so only the readers of that field re-run.\n */\nexport function setEnvironment(env: Partial<PlatformEnvironment>): void {\n if (env.window) windowSignal.set(env.window)\n if (env.colorScheme) colorSchemeSignal.set(env.colorScheme)\n if (env.safeAreaInsets) safeAreaSignal.set(env.safeAreaInsets)\n if (env.keyboard) keyboardSignal.set(env.keyboard)\n}\n\n/** A snapshot of the current environment (non-reactive; for one-off reads). */\nexport function getEnvironment(): PlatformEnvironment {\n return {\n window: windowSignal(),\n colorScheme: colorSchemeSignal(),\n safeAreaInsets: safeAreaSignal(),\n keyboard: keyboardSignal(),\n }\n}\n\n/** Reactive accessor for the window dimensions (updates on resize/rotation). */\nexport function useWindowDimensions(): () => WindowDimensions {\n return windowSignal\n}\n\n/** Reactive accessor for the active color scheme (updates on theme change). */\nexport function useColorScheme(): () => ColorScheme {\n return colorSchemeSignal\n}\n\n/** Reactive accessor for the safe-area insets. */\nexport function useSafeAreaInsets(): () => SafeAreaInsets {\n return safeAreaSignal\n}\n\n/** Reactive accessor for the soft-keyboard state. */\nexport function useKeyboard(): () => KeyboardState {\n return keyboardSignal\n}\n"],"mappings":";;;;;;;;;;;;;;;AAsDA,MAAM,eAAe,OAAyB;CAAE,OAAO;CAAG,QAAQ;CAAG,OAAO;CAAG,WAAW;AAAE,CAAC;AAC7F,MAAM,oBAAoB,OAAoB,OAAO;AACrD,MAAM,iBAAiB,OAAuB;CAAE,KAAK;CAAG,OAAO;CAAG,QAAQ;CAAG,MAAM;AAAE,CAAC;AACtF,MAAM,iBAAiB,OAAsB;CAAE,SAAS;CAAO,QAAQ;AAAE,CAAC;;;;;;AAO1E,SAAgB,eAAe,KAAyC;CACtE,IAAI,IAAI,QAAQ,aAAa,IAAI,IAAI,MAAM;CAC3C,IAAI,IAAI,aAAa,kBAAkB,IAAI,IAAI,WAAW;CAC1D,IAAI,IAAI,gBAAgB,eAAe,IAAI,IAAI,cAAc;CAC7D,IAAI,IAAI,UAAU,eAAe,IAAI,IAAI,QAAQ;AACnD;;AAGA,SAAgB,iBAAsC;CACpD,OAAO;EACL,QAAQ,aAAa;EACrB,aAAa,kBAAkB;EAC/B,gBAAgB,eAAe;EAC/B,UAAU,eAAe;CAC3B;AACF;;AAGA,SAAgB,sBAA8C;CAC5D,OAAO;AACT;;AAGA,SAAgB,iBAAoC;CAClD,OAAO;AACT;;AAGA,SAAgB,oBAA0C;CACxD,OAAO;AACT;;AAGA,SAAgB,cAAmC;CACjD,OAAO;AACT"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1,14 +1,17 @@
|
|
|
1
1
|
import { A11yProps, A11yState, Role, toA11yProps } from "./a11y.js";
|
|
2
2
|
import { StyleInput, StyleObject, StyleValue, flattenStyle } from "./style.js";
|
|
3
3
|
import { BaseProps, Reactive, resolveStyle, toHostProps } from "./host.js";
|
|
4
|
+
import { Avatar, AvatarProps, Badge, BadgeProps, Card, CardProps, Chip, ChipProps, Divider, DividerProps, KeyboardAvoidingView, KeyboardAvoidingViewProps, ProgressBar, ProgressBarProps, SafeAreaView, SafeAreaViewProps, Switch, SwitchProps } from "./components.js";
|
|
5
|
+
import { ColorScheme, KeyboardState, PlatformEnvironment, SafeAreaInsets, WindowDimensions, getEnvironment, setEnvironment, useColorScheme, useKeyboard, useSafeAreaInsets, useWindowDimensions } from "./environment.js";
|
|
4
6
|
import { Button, ButtonProps, Column, Image, ImageProps, InteractionState, Pressable, PressableProps, Row, ScrollView, ScrollViewProps, Spacer, SpacerProps, Stack, StackProps, Text, TextInput, TextInputProps, TextProps, View, ViewProps, usePressable } from "./primitives.js";
|
|
7
|
+
import { Theme, ThemeColors, duration, easing, fontSize, fontWeight, getTheme, lineHeight, palette, radius, space, tokens, useTheme } from "./tokens.js";
|
|
5
8
|
import { Maturity, NotImplementedError, PackageInfo, notImplemented } from "@mindees/core";
|
|
6
9
|
|
|
7
10
|
//#region src/index.d.ts
|
|
8
11
|
/** The npm package name. */
|
|
9
12
|
declare const name = "@mindees/atlas";
|
|
10
13
|
/** The package version. All `@mindees/*` packages share one locked version line. */
|
|
11
|
-
declare const VERSION = "0.
|
|
14
|
+
declare const VERSION = "0.2.0";
|
|
12
15
|
/** Current maturity of this package. See the repository `STATUS.md`. */
|
|
13
16
|
declare const maturity: Maturity;
|
|
14
17
|
/**
|
|
@@ -18,5 +21,5 @@ declare const maturity: Maturity;
|
|
|
18
21
|
*/
|
|
19
22
|
declare const info: PackageInfo;
|
|
20
23
|
//#endregion
|
|
21
|
-
export { type A11yProps, type A11yState, type BaseProps, Button, type ButtonProps, Column, Image, type ImageProps, type InteractionState, type Maturity, NotImplementedError, type PackageInfo, Pressable, type PressableProps, type Reactive, type Role, Row, ScrollView, type ScrollViewProps, Spacer, type SpacerProps, Stack, type StackProps, type StyleInput, type StyleObject, type StyleValue, Text, TextInput, type TextInputProps, type TextProps, VERSION, View, type ViewProps, flattenStyle, info, maturity, name, notImplemented, resolveStyle, toA11yProps, toHostProps, usePressable };
|
|
24
|
+
export { type A11yProps, type A11yState, Avatar, type AvatarProps, Badge, type BadgeProps, type BaseProps, Button, type ButtonProps, Card, type CardProps, Chip, type ChipProps, type ColorScheme, Column, Divider, type DividerProps, Image, type ImageProps, type InteractionState, KeyboardAvoidingView, type KeyboardAvoidingViewProps, type KeyboardState, type Maturity, NotImplementedError, type PackageInfo, type PlatformEnvironment, Pressable, type PressableProps, ProgressBar, type ProgressBarProps, type Reactive, type Role, Row, type SafeAreaInsets, SafeAreaView, type SafeAreaViewProps, ScrollView, type ScrollViewProps, Spacer, type SpacerProps, Stack, type StackProps, type StyleInput, type StyleObject, type StyleValue, Switch, type SwitchProps, Text, TextInput, type TextInputProps, type TextProps, type Theme, type ThemeColors, VERSION, View, type ViewProps, type WindowDimensions, duration, easing, flattenStyle, fontSize, fontWeight, getEnvironment, getTheme, info, lineHeight, maturity, name, notImplemented, palette, radius, resolveStyle, setEnvironment, space, toA11yProps, toHostProps, tokens, useColorScheme, useKeyboard, usePressable, useSafeAreaInsets, useTheme, useWindowDimensions };
|
|
22
25
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":[],"sources":["../src/index.ts"],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.ts","names":[],"sources":["../src/index.ts"],"mappings":";;;;;;;;;;;cAea,IAAA;AAAI;AAAA,cAGJ,OAAA;;cAGA,QAAA,EAAU,QAAyB;;AAH5B;AAGpB;;;cAOa,IAAA,EAAM,WAAiE"}
|