ajo-ui 0.1.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/LICENSE +15 -0
- package/README.md +126 -0
- package/dist/accordion.js +130 -0
- package/dist/avatar.js +54 -0
- package/dist/calendar.js +2 -0
- package/dist/carousel.js +239 -0
- package/dist/chart.js +790 -0
- package/dist/checkbox-group.js +70 -0
- package/dist/checkbox.js +77 -0
- package/dist/chunks/bar-CVafh6C1.js +99 -0
- package/dist/chunks/calendar-q8jZ8Cxr.js +1923 -0
- package/dist/chunks/collection-DtRB63U4.js +111 -0
- package/dist/chunks/data-table-DpkWv4y4.js +1039 -0
- package/dist/chunks/menu-B45IyHHC.js +704 -0
- package/dist/chunks/native-BJdhd9XJ.js +20 -0
- package/dist/chunks/popup-C8Bb3l_g.js +459 -0
- package/dist/chunks/popup-surface-BDCgtVU0.js +18 -0
- package/dist/chunks/position-D6_i_SRn.js +434 -0
- package/dist/chunks/virtual-list-B7hjGkjk.js +413 -0
- package/dist/collapsible.js +106 -0
- package/dist/command.js +263 -0
- package/dist/context-menu.js +112 -0
- package/dist/data-table.js +5 -0
- package/dist/dialog.js +207 -0
- package/dist/direction.js +22 -0
- package/dist/drawer.js +139 -0
- package/dist/field.js +26 -0
- package/dist/index.js +38 -0
- package/dist/input-date.js +994 -0
- package/dist/input-group.js +52 -0
- package/dist/input-otp.js +179 -0
- package/dist/menu.js +2 -0
- package/dist/menubar.js +236 -0
- package/dist/message-scroller.js +446 -0
- package/dist/navigation-menu.js +330 -0
- package/dist/popover.js +307 -0
- package/dist/progress.js +39 -0
- package/dist/radio-group.js +107 -0
- package/dist/resizable.js +172 -0
- package/dist/select.js +961 -0
- package/dist/sidebar.js +343 -0
- package/dist/slider.js +259 -0
- package/dist/switch.js +53 -0
- package/dist/tabs.js +182 -0
- package/dist/toast.js +492 -0
- package/dist/toggle-group.js +111 -0
- package/dist/toggle.js +52 -0
- package/dist/toolbar.js +127 -0
- package/dist/tooltip.js +196 -0
- package/dist/utils.js +104 -0
- package/dist/virtual-list.js +2 -0
- package/package.json +250 -0
- package/src/accordion.tsx +261 -0
- package/src/availability.ts +261 -0
- package/src/avatar.tsx +99 -0
- package/src/bar.ts +156 -0
- package/src/calendar.tsx +1441 -0
- package/src/carousel.tsx +424 -0
- package/src/chart.tsx +1194 -0
- package/src/checkbox-group.tsx +132 -0
- package/src/checkbox.tsx +130 -0
- package/src/collapsible.tsx +188 -0
- package/src/collection.ts +154 -0
- package/src/command.tsx +511 -0
- package/src/context-menu.tsx +233 -0
- package/src/data-table-contract.ts +143 -0
- package/src/data-table-model.ts +760 -0
- package/src/data-table.tsx +475 -0
- package/src/dialog.tsx +393 -0
- package/src/direction.tsx +45 -0
- package/src/drawer.tsx +251 -0
- package/src/field.tsx +61 -0
- package/src/index.ts +37 -0
- package/src/input-date.tsx +1539 -0
- package/src/input-group.tsx +142 -0
- package/src/input-otp.tsx +324 -0
- package/src/menu-cluster.ts +124 -0
- package/src/menu.tsx +1095 -0
- package/src/menubar.tsx +459 -0
- package/src/message-scroller.tsx +732 -0
- package/src/native.ts +26 -0
- package/src/navigation-menu.tsx +578 -0
- package/src/popover.tsx +519 -0
- package/src/popup-surface.tsx +31 -0
- package/src/popup.ts +569 -0
- package/src/position.ts +523 -0
- package/src/progress.tsx +70 -0
- package/src/radio-group.tsx +186 -0
- package/src/resizable.tsx +310 -0
- package/src/segments.ts +922 -0
- package/src/select.tsx +1501 -0
- package/src/sidebar.tsx +683 -0
- package/src/slider.tsx +424 -0
- package/src/switch.tsx +104 -0
- package/src/tabs.tsx +314 -0
- package/src/toast.tsx +923 -0
- package/src/toggle-group.tsx +249 -0
- package/src/toggle.tsx +91 -0
- package/src/toolbar.tsx +212 -0
- package/src/tooltip.tsx +359 -0
- package/src/utils.ts +204 -0
- package/src/virtual-list.tsx +205 -0
- package/src/virtual.ts +385 -0
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { flag, strings } from "./utils.js";
|
|
2
|
+
import { Checkbox } from "./checkbox.js";
|
|
3
|
+
import { selection, statefulRootAttrs } from "ajo-cloves";
|
|
4
|
+
import { context } from "ajo/context";
|
|
5
|
+
import { Fragment, jsx } from "ajo/jsx-runtime";
|
|
6
|
+
//#region packages/ajo-ui/src/checkbox-group.tsx
|
|
7
|
+
var CheckboxGroupContext = context(null);
|
|
8
|
+
var CheckboxGroupRoot = function* ({ defaultValue }) {
|
|
9
|
+
let disabled = false;
|
|
10
|
+
let name;
|
|
11
|
+
let onValueChange;
|
|
12
|
+
const sel = selection(this, {
|
|
13
|
+
multiple: () => true,
|
|
14
|
+
fallback: strings(defaultValue),
|
|
15
|
+
onChange: (next, event) => onValueChange?.(next, event)
|
|
16
|
+
});
|
|
17
|
+
const checked = (value) => sel.has(value);
|
|
18
|
+
const change = (value, _checked, event) => {
|
|
19
|
+
if (disabled) return;
|
|
20
|
+
sel.toggle(value, event);
|
|
21
|
+
};
|
|
22
|
+
for (const args of this) {
|
|
23
|
+
disabled = Boolean(args.disabled);
|
|
24
|
+
name = args.name;
|
|
25
|
+
onValueChange = args.onValueChange;
|
|
26
|
+
sel.sync(args.value != null ? strings(args.value) : void 0);
|
|
27
|
+
CheckboxGroupContext({
|
|
28
|
+
checked,
|
|
29
|
+
disabled,
|
|
30
|
+
name,
|
|
31
|
+
toggle: change
|
|
32
|
+
});
|
|
33
|
+
yield /* @__PURE__ */ jsx(Fragment, { children: args.children });
|
|
34
|
+
}
|
|
35
|
+
};
|
|
36
|
+
/** Unstyled checkbox group cascading checked values, name, and disabled state to its items. */
|
|
37
|
+
var CheckboxGroup = ({ children, defaultValue, disabled, name, onValueChange, role = "group", value, ...attrs }) => {
|
|
38
|
+
const disabledFlag = Boolean(disabled);
|
|
39
|
+
return /* @__PURE__ */ jsx(CheckboxGroupRoot, {
|
|
40
|
+
...statefulRootAttrs(attrs),
|
|
41
|
+
defaultValue,
|
|
42
|
+
disabled: disabledFlag,
|
|
43
|
+
name,
|
|
44
|
+
onValueChange,
|
|
45
|
+
value,
|
|
46
|
+
"attr:aria-disabled": flag(disabledFlag),
|
|
47
|
+
"attr:data-disabled": flag(disabledFlag),
|
|
48
|
+
"attr:data-slot": "checkbox-group",
|
|
49
|
+
"attr:role": role,
|
|
50
|
+
children
|
|
51
|
+
});
|
|
52
|
+
};
|
|
53
|
+
/** Unstyled native checkbox item wired to the nearest group. */
|
|
54
|
+
var CheckboxGroupItem = ({ disabled, name, value, ...attrs }) => {
|
|
55
|
+
const group = CheckboxGroupContext();
|
|
56
|
+
const item = String(value);
|
|
57
|
+
const checked = group?.checked(item) ?? false;
|
|
58
|
+
return /* @__PURE__ */ jsx(Checkbox, {
|
|
59
|
+
...attrs,
|
|
60
|
+
checked,
|
|
61
|
+
"data-slot": "checkbox-group-item",
|
|
62
|
+
disabled: disabled ?? group?.disabled,
|
|
63
|
+
name: name ?? group?.name,
|
|
64
|
+
"set:checked": checked,
|
|
65
|
+
value: item,
|
|
66
|
+
onCheckedChange: (next, event) => group?.toggle(item, next, event)
|
|
67
|
+
});
|
|
68
|
+
};
|
|
69
|
+
//#endregion
|
|
70
|
+
export { CheckboxGroup, CheckboxGroupItem };
|
package/dist/checkbox.js
ADDED
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import { ariaChecked, bool, flag, syncCheckedState } from "./utils.js";
|
|
2
|
+
import { callHandler, callRef, dom } from "ajo-cloves";
|
|
3
|
+
import { Fragment, jsx, jsxs } from "ajo/jsx-runtime";
|
|
4
|
+
//#region packages/ajo-ui/src/checkbox.tsx
|
|
5
|
+
var stateFromAttrs = (attrs) => {
|
|
6
|
+
if (bool(attrs["set:indeterminate"])) return "indeterminate";
|
|
7
|
+
return bool(attrs["set:checked"] ?? attrs.checked ?? attrs.defaultChecked) ? "checked" : "unchecked";
|
|
8
|
+
};
|
|
9
|
+
var CheckboxRoot = function* () {
|
|
10
|
+
let input = null;
|
|
11
|
+
const sync = () => {
|
|
12
|
+
if (input) syncCheckedState(input, dom(this) ? this : null);
|
|
13
|
+
};
|
|
14
|
+
for (const { checkedIndicatorClass, inputAttrs, inputClass, indeterminateIndicatorClass, onCheckedChange } of this) {
|
|
15
|
+
const { class: _class, ref, "set:onchange": onChange, "set:oninput": onInput, type: _type, ...attrs } = inputAttrs;
|
|
16
|
+
const state = stateFromAttrs(inputAttrs);
|
|
17
|
+
if (dom(this)) this.dataset.state = state;
|
|
18
|
+
yield /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
19
|
+
/* @__PURE__ */ jsx("input", {
|
|
20
|
+
...attrs,
|
|
21
|
+
"aria-checked": ariaChecked(state),
|
|
22
|
+
class: inputClass,
|
|
23
|
+
"data-slot": "checkbox-input",
|
|
24
|
+
"data-state": state,
|
|
25
|
+
ref: (element) => {
|
|
26
|
+
input = element;
|
|
27
|
+
callRef(ref, element);
|
|
28
|
+
if (element) queueMicrotask(sync);
|
|
29
|
+
},
|
|
30
|
+
"set:onchange": (event) => {
|
|
31
|
+
callHandler(onChange, event);
|
|
32
|
+
sync();
|
|
33
|
+
onCheckedChange?.(event.currentTarget.checked, event);
|
|
34
|
+
},
|
|
35
|
+
"set:oninput": (event) => {
|
|
36
|
+
callHandler(onInput, event);
|
|
37
|
+
sync();
|
|
38
|
+
},
|
|
39
|
+
type: "checkbox"
|
|
40
|
+
}),
|
|
41
|
+
/* @__PURE__ */ jsx("span", {
|
|
42
|
+
"aria-hidden": "true",
|
|
43
|
+
class: checkedIndicatorClass,
|
|
44
|
+
"data-slot": "checkbox-indicator",
|
|
45
|
+
"data-state": "checked"
|
|
46
|
+
}),
|
|
47
|
+
/* @__PURE__ */ jsx("span", {
|
|
48
|
+
"aria-hidden": "true",
|
|
49
|
+
class: indeterminateIndicatorClass,
|
|
50
|
+
"data-slot": "checkbox-indicator",
|
|
51
|
+
"data-state": "indeterminate"
|
|
52
|
+
})
|
|
53
|
+
] });
|
|
54
|
+
}
|
|
55
|
+
};
|
|
56
|
+
CheckboxRoot.is = "span";
|
|
57
|
+
/** Unstyled native checkbox with state slots and form behavior. */
|
|
58
|
+
var Checkbox = ({ checkedIndicatorClass, class: classes, disabled, inputClass, indeterminateIndicatorClass, onCheckedChange, ...attrs }) => {
|
|
59
|
+
const inputAttrs = {
|
|
60
|
+
...attrs,
|
|
61
|
+
disabled
|
|
62
|
+
};
|
|
63
|
+
const state = stateFromAttrs(inputAttrs);
|
|
64
|
+
return /* @__PURE__ */ jsx(CheckboxRoot, {
|
|
65
|
+
checkedIndicatorClass,
|
|
66
|
+
inputAttrs,
|
|
67
|
+
inputClass,
|
|
68
|
+
indeterminateIndicatorClass,
|
|
69
|
+
onCheckedChange,
|
|
70
|
+
"attr:class": classes,
|
|
71
|
+
"attr:data-disabled": flag(disabled),
|
|
72
|
+
"attr:data-slot": attrs["data-slot"] ?? "checkbox",
|
|
73
|
+
"attr:data-state": state
|
|
74
|
+
});
|
|
75
|
+
};
|
|
76
|
+
//#endregion
|
|
77
|
+
export { Checkbox };
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
import { controlled, dom, roving, typeahead } from "ajo-cloves";
|
|
2
|
+
//#region packages/ajo-ui/src/bar.ts
|
|
3
|
+
/**
|
|
4
|
+
* The shared root machine for horizontal trigger bars (menubar,
|
|
5
|
+
* navigation-menu): one controlled open value ('' = closed), roving over a
|
|
6
|
+
* live trigger row with typeahead, and the open-follows-focus/hover policy.
|
|
7
|
+
*
|
|
8
|
+
* Movement (arrows, typeahead) only focuses the target trigger; the follow
|
|
9
|
+
* policy runs exactly once through the trigger's own focus handler, so
|
|
10
|
+
* controlled consumers see a single onValueChange per move.
|
|
11
|
+
*/
|
|
12
|
+
var bar = (host, opts) => {
|
|
13
|
+
const read = opts.value ?? ((trigger) => trigger.dataset.value ?? "");
|
|
14
|
+
const state = controlled(host, {
|
|
15
|
+
fallback: opts.initialValue ?? "",
|
|
16
|
+
onChange: opts.onValueChange
|
|
17
|
+
});
|
|
18
|
+
let focused = "";
|
|
19
|
+
const stop = () => {
|
|
20
|
+
if (!dom(host)) return "";
|
|
21
|
+
const row = opts.triggers();
|
|
22
|
+
if (!row.length) return "";
|
|
23
|
+
return focused && row.some((trigger) => read(trigger) === focused) ? focused : read(row[0]);
|
|
24
|
+
};
|
|
25
|
+
const setValue = (next, event) => {
|
|
26
|
+
if (next && opts.disabled?.()) return;
|
|
27
|
+
if (next === state.value) return;
|
|
28
|
+
if (next) focused = next;
|
|
29
|
+
state.set(next, event);
|
|
30
|
+
};
|
|
31
|
+
let following = false;
|
|
32
|
+
const follow = (next, event) => {
|
|
33
|
+
if (following) return;
|
|
34
|
+
if (!state.value || !next || next === state.value) return;
|
|
35
|
+
following = true;
|
|
36
|
+
try {
|
|
37
|
+
if (dom(host)) {
|
|
38
|
+
const row = opts.triggers();
|
|
39
|
+
const target = row.find((trigger) => read(trigger) === next);
|
|
40
|
+
const active = document.activeElement;
|
|
41
|
+
if (target && active && active !== target && host.contains(active) && !row.includes(active)) target.focus();
|
|
42
|
+
}
|
|
43
|
+
setValue(next, event);
|
|
44
|
+
} finally {
|
|
45
|
+
following = false;
|
|
46
|
+
}
|
|
47
|
+
};
|
|
48
|
+
const nav = roving(host, {
|
|
49
|
+
items: opts.triggers,
|
|
50
|
+
orientation: () => "horizontal",
|
|
51
|
+
loop: () => opts.loop?.() ?? true,
|
|
52
|
+
onMove: (target) => target.focus()
|
|
53
|
+
});
|
|
54
|
+
const ta = typeahead(host, {
|
|
55
|
+
items: opts.triggers,
|
|
56
|
+
onMatch: (target, event) => {
|
|
57
|
+
event.preventDefault();
|
|
58
|
+
target.focus();
|
|
59
|
+
}
|
|
60
|
+
});
|
|
61
|
+
return {
|
|
62
|
+
get value() {
|
|
63
|
+
return state.value;
|
|
64
|
+
},
|
|
65
|
+
get focused() {
|
|
66
|
+
return focused;
|
|
67
|
+
},
|
|
68
|
+
sync: (value) => state.sync(value),
|
|
69
|
+
setValue,
|
|
70
|
+
close: (event) => setValue("", event),
|
|
71
|
+
follow,
|
|
72
|
+
focus(next, event) {
|
|
73
|
+
if (state.value && next && next !== state.value) follow(next, event);
|
|
74
|
+
else if (focused !== next) {
|
|
75
|
+
focused = next;
|
|
76
|
+
host.next();
|
|
77
|
+
}
|
|
78
|
+
},
|
|
79
|
+
adopt(next) {
|
|
80
|
+
focused = next;
|
|
81
|
+
},
|
|
82
|
+
isTabbable(value) {
|
|
83
|
+
const current = stop();
|
|
84
|
+
return !current || current === value;
|
|
85
|
+
},
|
|
86
|
+
handle(event) {
|
|
87
|
+
if (nav.handle(event)) return true;
|
|
88
|
+
if (event.key === "Escape") {
|
|
89
|
+
if (!state.value) return false;
|
|
90
|
+
event.preventDefault();
|
|
91
|
+
setValue("", event);
|
|
92
|
+
return true;
|
|
93
|
+
}
|
|
94
|
+
return ta.handle(event);
|
|
95
|
+
}
|
|
96
|
+
};
|
|
97
|
+
};
|
|
98
|
+
//#endregion
|
|
99
|
+
export { bar as t };
|