foldkit 0.33.5 → 0.34.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/README.md +19 -19
- package/dist/devtools/overlay-styles.d.ts +1 -1
- package/dist/devtools/overlay-styles.d.ts.map +1 -1
- package/dist/devtools/overlay-styles.js +3 -0
- package/dist/devtools/overlay.d.ts.map +1 -1
- package/dist/devtools/overlay.js +79 -34
- package/dist/html/index.d.ts +431 -5
- package/dist/html/index.d.ts.map +1 -1
- package/dist/html/index.js +1 -0
- package/dist/html/public.d.ts +1 -2
- package/dist/html/public.d.ts.map +1 -1
- package/dist/html/public.js +1 -2
- package/dist/task/dom.d.ts +6 -6
- package/dist/task/dom.js +6 -6
- package/dist/task/inert.d.ts +2 -2
- package/dist/task/inert.js +2 -2
- package/dist/task/scrollLock.d.ts +2 -2
- package/dist/task/scrollLock.js +2 -2
- package/dist/ui/checkbox/index.d.ts +5 -9
- package/dist/ui/checkbox/index.d.ts.map +1 -1
- package/dist/ui/checkbox/index.js +7 -10
- package/dist/ui/checkbox/public.d.ts +1 -1
- package/dist/ui/checkbox/public.d.ts.map +1 -1
- package/dist/ui/combobox/multi.d.ts +31 -10
- package/dist/ui/combobox/multi.d.ts.map +1 -1
- package/dist/ui/combobox/multi.js +1 -1
- package/dist/ui/combobox/public.d.ts +1 -1
- package/dist/ui/combobox/public.d.ts.map +1 -1
- package/dist/ui/combobox/shared.d.ts +53 -14
- package/dist/ui/combobox/shared.d.ts.map +1 -1
- package/dist/ui/combobox/shared.js +72 -28
- package/dist/ui/combobox/single.d.ts +31 -10
- package/dist/ui/combobox/single.d.ts.map +1 -1
- package/dist/ui/combobox/single.js +1 -1
- package/dist/ui/dialog/index.d.ts +14 -8
- package/dist/ui/dialog/index.d.ts.map +1 -1
- package/dist/ui/dialog/index.js +21 -12
- package/dist/ui/dialog/public.d.ts +1 -1
- package/dist/ui/dialog/public.d.ts.map +1 -1
- package/dist/ui/dialog/public.js +1 -1
- package/dist/ui/disclosure/index.d.ts +11 -8
- package/dist/ui/disclosure/index.d.ts.map +1 -1
- package/dist/ui/disclosure/index.js +20 -18
- package/dist/ui/disclosure/public.d.ts +1 -1
- package/dist/ui/disclosure/public.d.ts.map +1 -1
- package/dist/ui/listbox/multi.d.ts +34 -9
- package/dist/ui/listbox/multi.d.ts.map +1 -1
- package/dist/ui/listbox/multi.js +1 -1
- package/dist/ui/listbox/public.d.ts +1 -1
- package/dist/ui/listbox/public.d.ts.map +1 -1
- package/dist/ui/listbox/shared.d.ts +57 -13
- package/dist/ui/listbox/shared.d.ts.map +1 -1
- package/dist/ui/listbox/shared.js +77 -27
- package/dist/ui/listbox/single.d.ts +34 -9
- package/dist/ui/listbox/single.d.ts.map +1 -1
- package/dist/ui/listbox/single.js +1 -1
- package/dist/ui/menu/index.d.ts +39 -11
- package/dist/ui/menu/index.d.ts.map +1 -1
- package/dist/ui/menu/index.js +81 -32
- package/dist/ui/menu/public.d.ts +1 -1
- package/dist/ui/menu/public.d.ts.map +1 -1
- package/dist/ui/popover/index.d.ts +28 -12
- package/dist/ui/popover/index.d.ts.map +1 -1
- package/dist/ui/popover/index.js +50 -24
- package/dist/ui/popover/public.d.ts +1 -1
- package/dist/ui/popover/public.d.ts.map +1 -1
- package/dist/ui/radioGroup/index.d.ts +8 -7
- package/dist/ui/radioGroup/index.d.ts.map +1 -1
- package/dist/ui/radioGroup/index.js +12 -9
- package/dist/ui/radioGroup/public.d.ts +1 -1
- package/dist/ui/radioGroup/public.d.ts.map +1 -1
- package/dist/ui/switch/index.d.ts +5 -9
- package/dist/ui/switch/index.d.ts.map +1 -1
- package/dist/ui/switch/index.js +7 -10
- package/dist/ui/switch/public.d.ts +1 -1
- package/dist/ui/switch/public.d.ts.map +1 -1
- package/dist/ui/tabs/index.d.ts +9 -7
- package/dist/ui/tabs/index.d.ts.map +1 -1
- package/dist/ui/tabs/index.js +27 -17
- package/dist/ui/tabs/public.d.ts +1 -1
- package/dist/ui/tabs/public.d.ts.map +1 -1
- package/package.json +3 -3
|
@@ -74,8 +74,20 @@ export const MovedPointerOverItem = m('MovedPointerOverItem', {
|
|
|
74
74
|
export const RequestedItemClick = m('RequestedItemClick', {
|
|
75
75
|
index: S.Number,
|
|
76
76
|
});
|
|
77
|
-
/**
|
|
78
|
-
export const
|
|
77
|
+
/** Sent when the scroll lock command completes. */
|
|
78
|
+
export const CompletedScrollLock = m('CompletedScrollLock');
|
|
79
|
+
/** Sent when the scroll unlock command completes. */
|
|
80
|
+
export const CompletedScrollUnlock = m('CompletedScrollUnlock');
|
|
81
|
+
/** Sent when the inert-others command completes. */
|
|
82
|
+
export const CompletedInertSetup = m('CompletedInertSetup');
|
|
83
|
+
/** Sent when the restore-inert command completes. */
|
|
84
|
+
export const CompletedInertTeardown = m('CompletedInertTeardown');
|
|
85
|
+
/** Sent when the focus-input command completes. */
|
|
86
|
+
export const CompletedInputFocus = m('CompletedInputFocus');
|
|
87
|
+
/** Sent when the scroll-into-view command completes after keyboard activation. */
|
|
88
|
+
export const CompletedScrollIntoView = m('CompletedScrollIntoView');
|
|
89
|
+
/** Sent when the programmatic item click command completes. */
|
|
90
|
+
export const CompletedItemClick = m('CompletedItemClick');
|
|
79
91
|
/** Sent internally when a double-rAF completes, advancing the transition to its animating phase. */
|
|
80
92
|
export const AdvancedTransitionFrame = m('AdvancedTransitionFrame');
|
|
81
93
|
/** Sent internally when all CSS transitions on the items container have completed. */
|
|
@@ -89,7 +101,7 @@ export const UpdatedInputValue = m('UpdatedInputValue', {
|
|
|
89
101
|
/** Sent when the optional toggle button is clicked. */
|
|
90
102
|
export const PressedToggleButton = m('PressedToggleButton');
|
|
91
103
|
/** Union of all messages the combobox component can produce. */
|
|
92
|
-
export const Message = S.Union(Opened, Closed, ClosedByTab, ActivatedItem, DeactivatedItem, SelectedItem, MovedPointerOverItem, RequestedItemClick,
|
|
104
|
+
export const Message = S.Union(Opened, Closed, ClosedByTab, ActivatedItem, DeactivatedItem, SelectedItem, MovedPointerOverItem, RequestedItemClick, CompletedScrollLock, CompletedScrollUnlock, CompletedInertSetup, CompletedInertTeardown, CompletedInputFocus, CompletedScrollIntoView, CompletedItemClick, AdvancedTransitionFrame, EndedTransition, DetectedInputMovement, UpdatedInputValue, PressedToggleButton);
|
|
93
105
|
// SELECTORS
|
|
94
106
|
export const inputSelector = (id) => `#${id}-input`;
|
|
95
107
|
export const inputWrapperSelector = (id) => `#${id}-input-wrapper`;
|
|
@@ -111,14 +123,14 @@ export const makeUpdate = (handlers) => {
|
|
|
111
123
|
const withUpdateReturn = M.withReturnType();
|
|
112
124
|
return (model, message) => {
|
|
113
125
|
const maybeNextFrame = OptionExt.when(model.isAnimated, Task.nextFrame.pipe(Effect.as(AdvancedTransitionFrame())));
|
|
114
|
-
const maybeLockScroll = OptionExt.when(model.isModal, Task.lockScroll.pipe(Effect.as(
|
|
115
|
-
const maybeUnlockScroll = OptionExt.when(model.isModal, Task.unlockScroll.pipe(Effect.as(
|
|
126
|
+
const maybeLockScroll = OptionExt.when(model.isModal, Task.lockScroll.pipe(Effect.as(CompletedScrollLock())));
|
|
127
|
+
const maybeUnlockScroll = OptionExt.when(model.isModal, Task.unlockScroll.pipe(Effect.as(CompletedScrollUnlock())));
|
|
116
128
|
const maybeInertOthers = OptionExt.when(model.isModal, Task.inertOthers(model.id, [
|
|
117
129
|
inputWrapperSelector(model.id),
|
|
118
130
|
itemsSelector(model.id),
|
|
119
|
-
]).pipe(Effect.as(
|
|
120
|
-
const maybeRestoreInert = OptionExt.when(model.isModal, Task.restoreInert(model.id).pipe(Effect.as(
|
|
121
|
-
const focusInput = Task.focus(inputSelector(model.id)).pipe(Effect.ignore, Effect.as(
|
|
131
|
+
]).pipe(Effect.as(CompletedInertSetup())));
|
|
132
|
+
const maybeRestoreInert = OptionExt.when(model.isModal, Task.restoreInert(model.id).pipe(Effect.as(CompletedInertTeardown())));
|
|
133
|
+
const focusInput = Task.focus(inputSelector(model.id)).pipe(Effect.ignore, Effect.as(CompletedInputFocus()));
|
|
122
134
|
return M.value(message).pipe(withUpdateReturn, M.tagsExhaustive({
|
|
123
135
|
Opened: ({ maybeActiveItemIndex }) => {
|
|
124
136
|
const nextModel = constrainedEvo(model, {
|
|
@@ -165,7 +177,7 @@ export const makeUpdate = (handlers) => {
|
|
|
165
177
|
nextModel,
|
|
166
178
|
activationTrigger === 'Keyboard'
|
|
167
179
|
? [
|
|
168
|
-
Task.scrollIntoView(itemSelector(model.id, index)).pipe(Effect.ignore, Effect.as(
|
|
180
|
+
Task.scrollIntoView(itemSelector(model.id, index)).pipe(Effect.ignore, Effect.as(CompletedScrollIntoView())),
|
|
169
181
|
]
|
|
170
182
|
: [],
|
|
171
183
|
];
|
|
@@ -201,7 +213,7 @@ export const makeUpdate = (handlers) => {
|
|
|
201
213
|
RequestedItemClick: ({ index }) => [
|
|
202
214
|
model,
|
|
203
215
|
[
|
|
204
|
-
Task.clickElement(itemSelector(model.id, index)).pipe(Effect.ignore, Effect.as(
|
|
216
|
+
Task.clickElement(itemSelector(model.id, index)).pipe(Effect.ignore, Effect.as(CompletedItemClick())),
|
|
205
217
|
],
|
|
206
218
|
],
|
|
207
219
|
UpdatedInputValue: ({ value }) => {
|
|
@@ -282,14 +294,20 @@ export const makeUpdate = (handlers) => {
|
|
|
282
294
|
}),
|
|
283
295
|
[],
|
|
284
296
|
]), M.orElse(() => [model, []])),
|
|
285
|
-
|
|
297
|
+
CompletedScrollLock: () => [model, []],
|
|
298
|
+
CompletedScrollUnlock: () => [model, []],
|
|
299
|
+
CompletedInertSetup: () => [model, []],
|
|
300
|
+
CompletedInertTeardown: () => [model, []],
|
|
301
|
+
CompletedInputFocus: () => [model, []],
|
|
302
|
+
CompletedScrollIntoView: () => [model, []],
|
|
303
|
+
CompletedItemClick: () => [model, []],
|
|
286
304
|
}));
|
|
287
305
|
};
|
|
288
306
|
};
|
|
289
307
|
/** Creates a combobox view function from variant-specific behavior. Shared rendering logic (input, items, transitions, keyboard navigation) is handled internally; only selection display varies by variant. */
|
|
290
308
|
export const makeView = (behavior) => (config) => {
|
|
291
|
-
const { div, input, AriaActiveDescendant, AriaControls, AriaDisabled, AriaExpanded, AriaInvalid, AriaLabelledBy, AriaMultiSelectable, AriaSelected, Attribute, Autocomplete, Class, DataAttribute, Id, Name, OnBlur, OnClick, OnDestroy, OnFocus, OnInput, OnInsert, OnKeyDownPreventDefault, OnPointerLeave, OnPointerMove, Role, Style, Tabindex, Type, Value, keyed, } = html();
|
|
292
|
-
const { model: { id, isOpen, immediate, transitionState, maybeActiveItemIndex }, toMessage, items, itemToConfig, itemToValue, itemToDisplayText, isItemDisabled, inputClassName, inputPlaceholder, itemsClassName, itemsScrollClassName, backdropClassName, className,
|
|
309
|
+
const { div, input, AriaActiveDescendant, AriaControls, AriaDisabled, AriaExpanded, AriaInvalid, AriaLabelledBy, AriaMultiSelectable, AriaSelected, Attribute, Autocomplete, Class, DataAttribute, Id, Name, OnBlur, OnClick, OnDestroy, OnFocus, OnInput, OnInsert, OnKeyDownPreventDefault, OnPointerLeave, OnPointerMove, Placeholder, Role, Style, Tabindex, Type, Value, keyed, } = html();
|
|
310
|
+
const { model: { id, isOpen, immediate, transitionState, maybeActiveItemIndex }, toMessage, items, itemToConfig, itemToValue, itemToDisplayText, isItemDisabled, inputClassName, inputAttributes = [], inputPlaceholder, inputWrapperClassName, inputWrapperAttributes = [], itemsClassName, itemsAttributes = [], itemsScrollClassName, itemsScrollAttributes = [], backdropClassName, backdropAttributes = [], className, attributes = [], buttonContent, buttonClassName, buttonAttributes = [], formName, isDisabled, isInvalid, openOnFocus, itemGroupKey, groupToHeading, groupClassName, groupAttributes = [], separatorClassName, separatorAttributes = [], anchor, } = config;
|
|
293
311
|
const isLeaving = transitionState === 'LeaveStart' || transitionState === 'LeaveAnimating';
|
|
294
312
|
const isVisible = isOpen || isLeaving;
|
|
295
313
|
const transitionAttributes = M.value(transitionState).pipe(M.when('EnterStart', () => [
|
|
@@ -373,10 +391,9 @@ export const makeView = (behavior) => (config) => {
|
|
|
373
391
|
onNone: () => [],
|
|
374
392
|
onSome: index => [AriaActiveDescendant(itemId(id, index))],
|
|
375
393
|
});
|
|
376
|
-
const
|
|
394
|
+
const resolvedInputAttributes = [
|
|
377
395
|
Id(`${id}-input`),
|
|
378
396
|
Role('combobox'),
|
|
379
|
-
Class(inputClassName),
|
|
380
397
|
AriaExpanded(isVisible),
|
|
381
398
|
AriaControls(`${id}-items`),
|
|
382
399
|
Attribute('aria-autocomplete', 'list'),
|
|
@@ -384,7 +401,7 @@ export const makeView = (behavior) => (config) => {
|
|
|
384
401
|
Autocomplete('off'),
|
|
385
402
|
Value(config.model.inputValue),
|
|
386
403
|
...maybeActiveDescendant,
|
|
387
|
-
...(inputPlaceholder ? [
|
|
404
|
+
...(inputPlaceholder ? [Placeholder(inputPlaceholder)] : []),
|
|
388
405
|
...(isDisabled
|
|
389
406
|
? [AriaDisabled(true), DataAttribute('disabled', '')]
|
|
390
407
|
: [
|
|
@@ -410,6 +427,8 @@ export const makeView = (behavior) => (config) => {
|
|
|
410
427
|
}),
|
|
411
428
|
]
|
|
412
429
|
: []),
|
|
430
|
+
...(inputClassName ? [Class(inputClassName)] : []),
|
|
431
|
+
...inputAttributes,
|
|
413
432
|
];
|
|
414
433
|
const hooks = anchor
|
|
415
434
|
? anchorHooks({
|
|
@@ -434,9 +453,10 @@ export const makeView = (behavior) => (config) => {
|
|
|
434
453
|
...(behavior.ariaMultiSelectable ? [AriaMultiSelectable(true)] : []),
|
|
435
454
|
AriaLabelledBy(`${id}-input`),
|
|
436
455
|
Tabindex(-1),
|
|
437
|
-
Class(itemsClassName),
|
|
438
456
|
...anchorAttributes,
|
|
439
457
|
...transitionAttributes,
|
|
458
|
+
...(itemsClassName ? [Class(itemsClassName)] : []),
|
|
459
|
+
...itemsAttributes,
|
|
440
460
|
];
|
|
441
461
|
const comboboxItems = Array.map(items, (item, index) => {
|
|
442
462
|
const isActiveItem = Option.exists(maybeActiveItemIndex, activeIndex => activeIndex === index);
|
|
@@ -452,7 +472,6 @@ export const makeView = (behavior) => (config) => {
|
|
|
452
472
|
Id(itemId(id, index)),
|
|
453
473
|
Role('option'),
|
|
454
474
|
AriaSelected(isSelectedItem),
|
|
455
|
-
Class(itemConfig.className),
|
|
456
475
|
...(isActiveItem ? [DataAttribute('active', '')] : []),
|
|
457
476
|
...(isSelectedItem ? [DataAttribute('selected', '')] : []),
|
|
458
477
|
...(isDisabledItem
|
|
@@ -472,6 +491,7 @@ export const makeView = (behavior) => (config) => {
|
|
|
472
491
|
OnPointerLeave(pointerType => OptionExt.when(pointerType !== 'touch', toMessage(DeactivatedItem()))),
|
|
473
492
|
]
|
|
474
493
|
: []),
|
|
494
|
+
...(itemConfig.className ? [Class(itemConfig.className)] : []),
|
|
475
495
|
], [itemConfig.content]);
|
|
476
496
|
});
|
|
477
497
|
const renderGroupedItems = () => {
|
|
@@ -488,7 +508,11 @@ export const makeView = (behavior) => (config) => {
|
|
|
488
508
|
const headingElement = Option.match(maybeHeading, {
|
|
489
509
|
onNone: () => [],
|
|
490
510
|
onSome: heading => [
|
|
491
|
-
keyed('div')(headingId, [
|
|
511
|
+
keyed('div')(headingId, [
|
|
512
|
+
Id(headingId),
|
|
513
|
+
Role('presentation'),
|
|
514
|
+
...(heading.className ? [Class(heading.className)] : []),
|
|
515
|
+
], [heading.content]),
|
|
492
516
|
],
|
|
493
517
|
});
|
|
494
518
|
const groupContent = [...headingElement, ...segment.items];
|
|
@@ -496,37 +520,51 @@ export const makeView = (behavior) => (config) => {
|
|
|
496
520
|
Role('group'),
|
|
497
521
|
...(Option.isSome(maybeHeading) ? [AriaLabelledBy(headingId)] : []),
|
|
498
522
|
...(groupClassName ? [Class(groupClassName)] : []),
|
|
523
|
+
...groupAttributes,
|
|
499
524
|
], groupContent);
|
|
500
|
-
const separator = segmentIndex > 0 &&
|
|
525
|
+
const separator = segmentIndex > 0 &&
|
|
526
|
+
(separatorClassName ||
|
|
527
|
+
Array.isNonEmptyReadonlyArray(separatorAttributes))
|
|
501
528
|
? [
|
|
502
|
-
keyed('div')(`${id}-separator-${segmentIndex}`, [
|
|
529
|
+
keyed('div')(`${id}-separator-${segmentIndex}`, [
|
|
530
|
+
Role('separator'),
|
|
531
|
+
...(separatorClassName ? [Class(separatorClassName)] : []),
|
|
532
|
+
...separatorAttributes,
|
|
533
|
+
], []),
|
|
503
534
|
]
|
|
504
535
|
: [];
|
|
505
536
|
return [...separator, groupElement];
|
|
506
537
|
});
|
|
507
538
|
};
|
|
508
539
|
const backdrop = keyed('div')(`${id}-backdrop`, [
|
|
509
|
-
Class(backdropClassName),
|
|
510
540
|
...(isLeaving ? [] : [OnClick(toMessage(Closed()))]),
|
|
541
|
+
...(backdropClassName ? [Class(backdropClassName)] : []),
|
|
542
|
+
...backdropAttributes,
|
|
511
543
|
], []);
|
|
512
544
|
const renderedItems = renderGroupedItems();
|
|
513
|
-
const scrollableItems = itemsScrollClassName
|
|
514
|
-
|
|
545
|
+
const scrollableItems = itemsScrollClassName ||
|
|
546
|
+
Array.isNonEmptyReadonlyArray(itemsScrollAttributes)
|
|
547
|
+
? [
|
|
548
|
+
div([
|
|
549
|
+
...(itemsScrollClassName ? [Class(itemsScrollClassName)] : []),
|
|
550
|
+
...itemsScrollAttributes,
|
|
551
|
+
], renderedItems),
|
|
552
|
+
]
|
|
515
553
|
: renderedItems;
|
|
516
554
|
const visibleContent = [
|
|
517
555
|
backdrop,
|
|
518
556
|
keyed('div')(`${id}-items-container`, itemsContainerAttributes, scrollableItems),
|
|
519
557
|
];
|
|
520
|
-
const
|
|
558
|
+
const resolvedInputWrapperAttributes = [
|
|
521
559
|
Id(`${id}-input-wrapper`),
|
|
522
560
|
...(inputWrapperClassName ? [Class(inputWrapperClassName)] : []),
|
|
561
|
+
...inputWrapperAttributes,
|
|
523
562
|
];
|
|
524
|
-
const toggleButton = buttonContent
|
|
563
|
+
const toggleButton = buttonContent
|
|
525
564
|
? [
|
|
526
565
|
keyed('button')(`${id}-button`, [
|
|
527
566
|
Id(`${id}-button`),
|
|
528
567
|
Type('button'),
|
|
529
|
-
Class(buttonClassName),
|
|
530
568
|
Tabindex(-1),
|
|
531
569
|
AriaControls(`${id}-items`),
|
|
532
570
|
AriaExpanded(isVisible),
|
|
@@ -535,6 +573,8 @@ export const makeView = (behavior) => (config) => {
|
|
|
535
573
|
? [AriaDisabled(true), DataAttribute('disabled', '')]
|
|
536
574
|
: [OnClick(toMessage(PressedToggleButton()))]),
|
|
537
575
|
OnInsert(preventBlurOnPointerDown),
|
|
576
|
+
...(buttonClassName ? [Class(buttonClassName)] : []),
|
|
577
|
+
...buttonAttributes,
|
|
538
578
|
], [buttonContent]),
|
|
539
579
|
]
|
|
540
580
|
: [];
|
|
@@ -550,12 +590,16 @@ export const makeView = (behavior) => (config) => {
|
|
|
550
590
|
: [];
|
|
551
591
|
const wrapperAttributes = [
|
|
552
592
|
...(className ? [Class(className)] : []),
|
|
593
|
+
...attributes,
|
|
553
594
|
...(isVisible ? [DataAttribute('open', '')] : []),
|
|
554
595
|
...(isDisabled ? [DataAttribute('disabled', '')] : []),
|
|
555
596
|
...(isInvalid ? [DataAttribute('invalid', '')] : []),
|
|
556
597
|
];
|
|
557
598
|
return div(wrapperAttributes, [
|
|
558
|
-
div(
|
|
599
|
+
div(resolvedInputWrapperAttributes, [
|
|
600
|
+
input(resolvedInputAttributes),
|
|
601
|
+
...toggleButton,
|
|
602
|
+
]),
|
|
559
603
|
...(isVisible && Array.isNonEmptyReadonlyArray(items)
|
|
560
604
|
? visibleContent
|
|
561
605
|
: []),
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Option, Schema as S } from 'effect';
|
|
2
|
-
import type
|
|
2
|
+
import { type Html } from '../../html';
|
|
3
3
|
import { type BaseInitConfig, type BaseViewConfig } from './shared';
|
|
4
4
|
/** Schema for the single-select combobox component's state, tracking open/closed status, active item, input value, selected item, and display text. */
|
|
5
5
|
export declare const Model: S.extend<S.Struct<{
|
|
@@ -70,8 +70,6 @@ export declare const update: (model: {
|
|
|
70
70
|
readonly maybeSelectedItem: Option.Option<string>;
|
|
71
71
|
readonly maybeSelectedDisplayText: Option.Option<string>;
|
|
72
72
|
}, readonly import("../../command").Command<{
|
|
73
|
-
readonly _tag: "NoOp";
|
|
74
|
-
} | {
|
|
75
73
|
readonly _tag: "Opened";
|
|
76
74
|
readonly maybeActiveItemIndex: Option.Option<number>;
|
|
77
75
|
} | {
|
|
@@ -100,6 +98,20 @@ export declare const update: (model: {
|
|
|
100
98
|
} | {
|
|
101
99
|
readonly _tag: "RequestedItemClick";
|
|
102
100
|
readonly index: number;
|
|
101
|
+
} | {
|
|
102
|
+
readonly _tag: "CompletedScrollLock";
|
|
103
|
+
} | {
|
|
104
|
+
readonly _tag: "CompletedScrollUnlock";
|
|
105
|
+
} | {
|
|
106
|
+
readonly _tag: "CompletedInertSetup";
|
|
107
|
+
} | {
|
|
108
|
+
readonly _tag: "CompletedInertTeardown";
|
|
109
|
+
} | {
|
|
110
|
+
readonly _tag: "CompletedInputFocus";
|
|
111
|
+
} | {
|
|
112
|
+
readonly _tag: "CompletedScrollIntoView";
|
|
113
|
+
} | {
|
|
114
|
+
readonly _tag: "CompletedItemClick";
|
|
103
115
|
} | {
|
|
104
116
|
readonly _tag: "AdvancedTransitionFrame";
|
|
105
117
|
} | {
|
|
@@ -136,28 +148,35 @@ export declare const view: <Message, Item extends string>(config: Readonly<{
|
|
|
136
148
|
readonly maybeSelectedItem: Option.Option<string>;
|
|
137
149
|
readonly maybeSelectedDisplayText: Option.Option<string>;
|
|
138
150
|
};
|
|
139
|
-
toMessage: (message: import("./shared").Opened | import("./shared").Closed | import("./shared").ClosedByTab | import("./shared").ActivatedItem | import("./shared").DeactivatedItem | import("./shared").SelectedItem | import("./shared").MovedPointerOverItem | import("./shared").RequestedItemClick | import("./shared").UpdatedInputValue | import("./shared").PressedToggleButton | import("./shared").
|
|
151
|
+
toMessage: (message: import("./shared").Opened | import("./shared").Closed | import("./shared").ClosedByTab | import("./shared").ActivatedItem | import("./shared").DeactivatedItem | import("./shared").SelectedItem | import("./shared").MovedPointerOverItem | import("./shared").RequestedItemClick | import("./shared").UpdatedInputValue | import("./shared").PressedToggleButton | import("./shared").CompletedScrollLock | import("./shared").CompletedScrollUnlock | import("./shared").CompletedInertSetup | import("./shared").CompletedInertTeardown | import("./shared").CompletedInputFocus | import("./shared").CompletedScrollIntoView | import("./shared").CompletedItemClick) => Message;
|
|
140
152
|
items: readonly Item[];
|
|
141
153
|
itemToConfig: (item: Item, context: Readonly<{
|
|
142
154
|
isActive: boolean;
|
|
143
155
|
isDisabled: boolean;
|
|
144
156
|
isSelected: boolean;
|
|
145
157
|
}>) => Readonly<{
|
|
146
|
-
className
|
|
158
|
+
className?: string;
|
|
147
159
|
content: Html;
|
|
148
160
|
}>;
|
|
149
161
|
itemToValue: (item: Item, index: number) => string;
|
|
150
162
|
itemToDisplayText: (item: Item, index: number) => string;
|
|
151
163
|
isItemDisabled?: (item: Item, index: number) => boolean;
|
|
152
|
-
inputClassName
|
|
164
|
+
inputClassName?: string;
|
|
165
|
+
inputAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
153
166
|
inputPlaceholder?: string;
|
|
154
|
-
|
|
167
|
+
inputWrapperClassName?: string;
|
|
168
|
+
inputWrapperAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
169
|
+
itemsClassName?: string;
|
|
170
|
+
itemsAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
155
171
|
itemsScrollClassName?: string;
|
|
156
|
-
|
|
172
|
+
itemsScrollAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
173
|
+
backdropClassName?: string;
|
|
174
|
+
backdropAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
157
175
|
className?: string;
|
|
158
|
-
|
|
176
|
+
attributes?: readonly import("../../html").Attribute<Message>[];
|
|
159
177
|
buttonContent?: Html;
|
|
160
178
|
buttonClassName?: string;
|
|
179
|
+
buttonAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
161
180
|
formName?: string;
|
|
162
181
|
isDisabled?: boolean;
|
|
163
182
|
isInvalid?: boolean;
|
|
@@ -165,10 +184,12 @@ export declare const view: <Message, Item extends string>(config: Readonly<{
|
|
|
165
184
|
itemGroupKey?: (item: Item, index: number) => string;
|
|
166
185
|
groupToHeading?: (groupKey: string) => Readonly<{
|
|
167
186
|
content: Html;
|
|
168
|
-
className
|
|
187
|
+
className?: string;
|
|
169
188
|
}> | undefined;
|
|
170
189
|
groupClassName?: string;
|
|
190
|
+
groupAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
171
191
|
separatorClassName?: string;
|
|
192
|
+
separatorAttributes?: readonly import("../../html").Attribute<Message>[];
|
|
172
193
|
anchor?: Readonly<{
|
|
173
194
|
placement?: import("@floating-ui/dom").Placement;
|
|
174
195
|
gap?: number;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"single.d.ts","sourceRoot":"","sources":["../../../src/ui/combobox/single.ts"],"names":[],"mappings":"AAAA,OAAO,EAAS,MAAM,EAAE,MAAM,IAAI,CAAC,EAAQ,MAAM,QAAQ,CAAA;AAEzD,OAAO,KAAK,
|
|
1
|
+
{"version":3,"file":"single.d.ts","sourceRoot":"","sources":["../../../src/ui/combobox/single.ts"],"names":[],"mappings":"AAAA,OAAO,EAAS,MAAM,EAAE,MAAM,IAAI,CAAC,EAAQ,MAAM,QAAQ,CAAA;AAEzD,OAAO,EAAE,KAAK,IAAI,EAAc,MAAM,YAAY,CAAA;AAElD,OAAO,EACL,KAAK,cAAc,EAEnB,KAAK,cAAc,EAKpB,MAAM,UAAU,CAAA;AAIjB,uJAAuJ;AACvJ,eAAO,MAAM,KAAK;;;;;;;;;;;;;;;;;;;GAOjB,CAAA;AAED,MAAM,MAAM,KAAK,GAAG,OAAO,KAAK,CAAC,IAAI,CAAA;AAIrC,8RAA8R;AAC9R,MAAM,MAAM,UAAU,GAAG,cAAc,GACrC,QAAQ,CAAC;IACP,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,mBAAmB,CAAC,EAAE,MAAM,CAAA;CAC7B,CAAC,CAAA;AAEJ,4IAA4I;AAC5I,eAAO,MAAM,IAAI,GAAI,QAAQ,UAAU,KAAG,KAMxC,CAAA;AAIF,uIAAuI;AACvI,eAAO,MAAM,MAAM;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAqDjB,CAAA;AAIF,wEAAwE;AACxE,MAAM,MAAM,UAAU,CAAC,OAAO,EAAE,IAAI,SAAS,MAAM,IAAI,cAAc,CACnE,OAAO,EACP,IAAI,EACJ,KAAK,CACN,CAAA;AAED,0IAA0I;AAC1I,eAAO,MAAM,IAAI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;WAOf,CAAA;AAEF;6EAC6E;AAC7E,eAAO,MAAM,IAAI,GAAI,OAAO,EAAE,IAAI,SAAS,MAAM,EAC/C,cAAc,IAAI,CAAC,UAAU,CAAC,OAAO,EAAE,IAAI,CAAC,EAAE,OAAO,GAAG,WAAW,CAAC,KACnE,CAAC,CACF,KAAK,EAAE,KAAK,EACZ,SAAS,EAAE,cAAc,CAAC,OAAO,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC,WAAW,CAAC,KACzD,IAAI,CAgBR,CAAA"}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Array, Option, Schema as S, pipe } from 'effect';
|
|
2
|
-
import { createLazy } from '../../html
|
|
2
|
+
import { createLazy } from '../../html';
|
|
3
3
|
import { evo } from '../../struct';
|
|
4
4
|
import { BaseModel, baseInit, closedBaseModel, makeUpdate, makeView, } from './shared';
|
|
5
5
|
// MODEL
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Schema as S } from 'effect';
|
|
2
2
|
import type { Command } from '../../command';
|
|
3
|
-
import type
|
|
3
|
+
import { type Attribute, type Html } from '../../html';
|
|
4
4
|
/** Schema for the dialog component's state, tracking its unique ID, open/closed status, animation support, and transition phase. */
|
|
5
5
|
export declare const Model: S.Struct<{
|
|
6
6
|
id: typeof S.String;
|
|
@@ -13,17 +13,20 @@ export type Model = typeof Model.Type;
|
|
|
13
13
|
export declare const Opened: import("../../schema").CallableTaggedStruct<"Opened", {}>;
|
|
14
14
|
/** Sent when the dialog should close (Escape key, backdrop click, or programmatic). Triggers the closeModal command. */
|
|
15
15
|
export declare const Closed: import("../../schema").CallableTaggedStruct<"Closed", {}>;
|
|
16
|
-
/**
|
|
17
|
-
export declare const
|
|
16
|
+
/** Sent when the show-dialog command completes (scroll lock + showModal). */
|
|
17
|
+
export declare const CompletedDialogShow: import("../../schema").CallableTaggedStruct<"CompletedDialogShow", {}>;
|
|
18
|
+
/** Sent when the close-dialog command completes (closeModal + scroll unlock). */
|
|
19
|
+
export declare const CompletedDialogClose: import("../../schema").CallableTaggedStruct<"CompletedDialogClose", {}>;
|
|
18
20
|
/** Sent internally when a double-rAF completes, advancing the transition to its animating phase. */
|
|
19
21
|
export declare const AdvancedTransitionFrame: import("../../schema").CallableTaggedStruct<"AdvancedTransitionFrame", {}>;
|
|
20
22
|
/** Sent internally when all CSS transitions on the dialog panel have completed. */
|
|
21
23
|
export declare const EndedTransition: import("../../schema").CallableTaggedStruct<"EndedTransition", {}>;
|
|
22
24
|
/** Union of all messages the dialog component can produce. */
|
|
23
|
-
export declare const Message: S.Union<[import("../../schema").CallableTaggedStruct<"Opened", {}>, import("../../schema").CallableTaggedStruct<"Closed", {}>, import("../../schema").CallableTaggedStruct<"
|
|
25
|
+
export declare const Message: S.Union<[import("../../schema").CallableTaggedStruct<"Opened", {}>, import("../../schema").CallableTaggedStruct<"Closed", {}>, import("../../schema").CallableTaggedStruct<"CompletedDialogShow", {}>, import("../../schema").CallableTaggedStruct<"CompletedDialogClose", {}>, import("../../schema").CallableTaggedStruct<"AdvancedTransitionFrame", {}>, import("../../schema").CallableTaggedStruct<"EndedTransition", {}>]>;
|
|
24
26
|
export type Opened = typeof Opened.Type;
|
|
25
27
|
export type Closed = typeof Closed.Type;
|
|
26
|
-
export type
|
|
28
|
+
export type CompletedDialogShow = typeof CompletedDialogShow.Type;
|
|
29
|
+
export type CompletedDialogClose = typeof CompletedDialogClose.Type;
|
|
27
30
|
export type Message = typeof Message.Type;
|
|
28
31
|
/** Configuration for creating a dialog model with `init`. `isAnimated` enables CSS transition coordination (default `false`). */
|
|
29
32
|
export type InitConfig = Readonly<{
|
|
@@ -43,11 +46,14 @@ export declare const descriptionId: (model: Model) => string;
|
|
|
43
46
|
/** Configuration for rendering a dialog with `view`. */
|
|
44
47
|
export type ViewConfig<Message> = Readonly<{
|
|
45
48
|
model: Model;
|
|
46
|
-
toMessage: (message: Closed |
|
|
49
|
+
toMessage: (message: Closed | CompletedDialogShow | CompletedDialogClose) => Message;
|
|
47
50
|
panelContent: Html;
|
|
48
|
-
panelClassName
|
|
49
|
-
|
|
51
|
+
panelClassName?: string;
|
|
52
|
+
panelAttributes?: ReadonlyArray<Attribute<Message>>;
|
|
53
|
+
backdropClassName?: string;
|
|
54
|
+
backdropAttributes?: ReadonlyArray<Attribute<Message>>;
|
|
50
55
|
className?: string;
|
|
56
|
+
attributes?: ReadonlyArray<Attribute<Message>>;
|
|
51
57
|
}>;
|
|
52
58
|
/** Renders a headless dialog component backed by the native `<dialog>` element with `showModal()`. */
|
|
53
59
|
export declare const view: <Message>(config: ViewConfig<Message>) => Html;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/ui/dialog/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAqC,MAAM,IAAI,CAAC,EAAE,MAAM,QAAQ,CAAA;AAEvE,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/ui/dialog/index.ts"],"names":[],"mappings":"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"}
|
package/dist/ui/dialog/index.js
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { Array, Effect, Match as M, Option, Schema as S } from 'effect';
|
|
2
2
|
import { OptionExt } from '../../effectExtensions';
|
|
3
|
-
import { html } from '../../html';
|
|
4
|
-
import { createLazy } from '../../html/lazy';
|
|
3
|
+
import { createLazy, html } from '../../html';
|
|
5
4
|
import { m } from '../../message';
|
|
6
5
|
import { evo } from '../../struct';
|
|
7
6
|
import * as Task from '../../task';
|
|
@@ -19,14 +18,16 @@ export const Model = S.Struct({
|
|
|
19
18
|
export const Opened = m('Opened');
|
|
20
19
|
/** Sent when the dialog should close (Escape key, backdrop click, or programmatic). Triggers the closeModal command. */
|
|
21
20
|
export const Closed = m('Closed');
|
|
22
|
-
/**
|
|
23
|
-
export const
|
|
21
|
+
/** Sent when the show-dialog command completes (scroll lock + showModal). */
|
|
22
|
+
export const CompletedDialogShow = m('CompletedDialogShow');
|
|
23
|
+
/** Sent when the close-dialog command completes (closeModal + scroll unlock). */
|
|
24
|
+
export const CompletedDialogClose = m('CompletedDialogClose');
|
|
24
25
|
/** Sent internally when a double-rAF completes, advancing the transition to its animating phase. */
|
|
25
26
|
export const AdvancedTransitionFrame = m('AdvancedTransitionFrame');
|
|
26
27
|
/** Sent internally when all CSS transitions on the dialog panel have completed. */
|
|
27
28
|
export const EndedTransition = m('EndedTransition');
|
|
28
29
|
/** Union of all messages the dialog component can produce. */
|
|
29
|
-
export const Message = S.Union(Opened, Closed,
|
|
30
|
+
export const Message = S.Union(Opened, Closed, CompletedDialogShow, CompletedDialogClose, AdvancedTransitionFrame, EndedTransition);
|
|
30
31
|
/** Creates an initial dialog model from a config. Defaults to closed and non-animated. */
|
|
31
32
|
export const init = (config) => ({
|
|
32
33
|
id: config.id,
|
|
@@ -43,7 +44,7 @@ export const update = (model, message) => {
|
|
|
43
44
|
const maybeNextFrame = OptionExt.when(model.isAnimated, Task.nextFrame.pipe(Effect.as(AdvancedTransitionFrame())));
|
|
44
45
|
return M.value(message).pipe(withUpdateReturn, M.tagsExhaustive({
|
|
45
46
|
Opened: () => {
|
|
46
|
-
const maybeShow = Option.liftPredicate(Task.lockScroll.pipe(Effect.andThen(() => Task.showModal(dialogSelector(model.id))), Effect.ignore, Effect.as(
|
|
47
|
+
const maybeShow = Option.liftPredicate(Task.lockScroll.pipe(Effect.andThen(() => Task.showModal(dialogSelector(model.id))), Effect.ignore, Effect.as(CompletedDialogShow())), () => !model.isOpen);
|
|
47
48
|
return [
|
|
48
49
|
evo(model, {
|
|
49
50
|
isOpen: () => true,
|
|
@@ -67,7 +68,7 @@ export const update = (model, message) => {
|
|
|
67
68
|
Option.toArray(maybeNextFrame),
|
|
68
69
|
];
|
|
69
70
|
}
|
|
70
|
-
const maybeClose = Option.liftPredicate(Task.closeModal(dialogSelector(model.id)).pipe(Effect.andThen(() => Task.unlockScroll), Effect.ignore, Effect.as(
|
|
71
|
+
const maybeClose = Option.liftPredicate(Task.closeModal(dialogSelector(model.id)).pipe(Effect.andThen(() => Task.unlockScroll), Effect.ignore, Effect.as(CompletedDialogClose())), () => model.isOpen);
|
|
71
72
|
return [evo(model, { isOpen: () => false }), Option.toArray(maybeClose)];
|
|
72
73
|
},
|
|
73
74
|
AdvancedTransitionFrame: () => M.value(model.transitionState).pipe(withUpdateReturn, M.when('EnterStart', () => [
|
|
@@ -87,10 +88,11 @@ export const update = (model, message) => {
|
|
|
87
88
|
]), M.when('LeaveAnimating', () => [
|
|
88
89
|
evo(model, { transitionState: () => 'Idle' }),
|
|
89
90
|
[
|
|
90
|
-
Task.closeModal(dialogSelector(model.id)).pipe(Effect.andThen(() => Task.unlockScroll), Effect.ignore, Effect.as(
|
|
91
|
+
Task.closeModal(dialogSelector(model.id)).pipe(Effect.andThen(() => Task.unlockScroll), Effect.ignore, Effect.as(CompletedDialogClose())),
|
|
91
92
|
],
|
|
92
93
|
]), M.orElse(() => [model, []])),
|
|
93
|
-
|
|
94
|
+
CompletedDialogShow: () => [model, []],
|
|
95
|
+
CompletedDialogClose: () => [model, []],
|
|
94
96
|
}));
|
|
95
97
|
};
|
|
96
98
|
// VIEW
|
|
@@ -101,7 +103,7 @@ export const descriptionId = (model) => `${model.id}-description`;
|
|
|
101
103
|
/** Renders a headless dialog component backed by the native `<dialog>` element with `showModal()`. */
|
|
102
104
|
export const view = (config) => {
|
|
103
105
|
const { AriaDescribedBy, AriaLabelledBy, Class, DataAttribute, Id, OnCancel, OnClick, Style, keyed, } = html();
|
|
104
|
-
const { model: { id, isOpen, transitionState }, toMessage, panelContent, panelClassName, backdropClassName, className, } = config;
|
|
106
|
+
const { model: { id, isOpen, transitionState }, toMessage, panelContent, panelClassName, panelAttributes = [], backdropClassName, backdropAttributes = [], className, attributes = [], } = config;
|
|
105
107
|
const isLeaving = transitionState === 'LeaveStart' || transitionState === 'LeaveAnimating';
|
|
106
108
|
const isVisible = isOpen || isLeaving;
|
|
107
109
|
const transitionAttributes = M.value(transitionState).pipe(M.when('EnterStart', () => [
|
|
@@ -134,13 +136,20 @@ export const view = (config) => {
|
|
|
134
136
|
}),
|
|
135
137
|
...(isVisible ? [DataAttribute('open', '')] : []),
|
|
136
138
|
...(className ? [Class(className)] : []),
|
|
139
|
+
...attributes,
|
|
137
140
|
];
|
|
138
141
|
const backdrop = keyed('div')(`${id}-backdrop`, [
|
|
139
|
-
Class(backdropClassName),
|
|
140
142
|
...transitionAttributes,
|
|
141
143
|
...(isLeaving ? [] : [OnClick(toMessage(Closed()))]),
|
|
144
|
+
...(backdropClassName ? [Class(backdropClassName)] : []),
|
|
145
|
+
...backdropAttributes,
|
|
142
146
|
], []);
|
|
143
|
-
const panel = keyed('div')(`${id}-panel`, [
|
|
147
|
+
const panel = keyed('div')(`${id}-panel`, [
|
|
148
|
+
Id(`${id}-panel`),
|
|
149
|
+
...transitionAttributes,
|
|
150
|
+
...(panelClassName ? [Class(panelClassName)] : []),
|
|
151
|
+
...panelAttributes,
|
|
152
|
+
], [panelContent]);
|
|
144
153
|
const content = isVisible ? [backdrop, panel] : [];
|
|
145
154
|
return keyed('dialog')(id, dialogAttributes, content);
|
|
146
155
|
};
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
export { init, update, view, lazy, titleId, descriptionId, Model, Message, Opened, Closed,
|
|
1
|
+
export { init, update, view, lazy, titleId, descriptionId, Model, Message, Opened, Closed, CompletedDialogShow, CompletedDialogClose, AdvancedTransitionFrame, EndedTransition, } from './index';
|
|
2
2
|
export type { InitConfig, ViewConfig } from './index';
|
|
3
3
|
//# sourceMappingURL=public.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"public.d.ts","sourceRoot":"","sources":["../../../src/ui/dialog/public.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,IAAI,EACJ,MAAM,EACN,IAAI,EACJ,IAAI,EACJ,OAAO,EACP,aAAa,EACb,KAAK,EACL,OAAO,EACP,MAAM,EACN,MAAM,EACN,
|
|
1
|
+
{"version":3,"file":"public.d.ts","sourceRoot":"","sources":["../../../src/ui/dialog/public.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,IAAI,EACJ,MAAM,EACN,IAAI,EACJ,IAAI,EACJ,OAAO,EACP,aAAa,EACb,KAAK,EACL,OAAO,EACP,MAAM,EACN,MAAM,EACN,mBAAmB,EACnB,oBAAoB,EACpB,uBAAuB,EACvB,eAAe,GAChB,MAAM,SAAS,CAAA;AAEhB,YAAY,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,SAAS,CAAA"}
|
package/dist/ui/dialog/public.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export { init, update, view, lazy, titleId, descriptionId, Model, Message, Opened, Closed,
|
|
1
|
+
export { init, update, view, lazy, titleId, descriptionId, Model, Message, Opened, Closed, CompletedDialogShow, CompletedDialogClose, AdvancedTransitionFrame, EndedTransition, } from './index';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Schema as S } from 'effect';
|
|
2
2
|
import type { Command } from '../../command';
|
|
3
|
-
import type
|
|
3
|
+
import { type Attribute, type Html, type TagName } from '../../html';
|
|
4
4
|
/** Schema for the disclosure component's state, tracking its unique ID and open/closed status. */
|
|
5
5
|
export declare const Model: S.Struct<{
|
|
6
6
|
id: typeof S.String;
|
|
@@ -11,13 +11,13 @@ export type Model = typeof Model.Type;
|
|
|
11
11
|
export declare const Toggled: import("../../schema").CallableTaggedStruct<"Toggled", {}>;
|
|
12
12
|
/** Sent to explicitly close the disclosure, regardless of its current state. */
|
|
13
13
|
export declare const Closed: import("../../schema").CallableTaggedStruct<"Closed", {}>;
|
|
14
|
-
/**
|
|
15
|
-
export declare const
|
|
14
|
+
/** Sent when the focus-button command completes after closing. */
|
|
15
|
+
export declare const CompletedButtonFocus: import("../../schema").CallableTaggedStruct<"CompletedButtonFocus", {}>;
|
|
16
16
|
/** Union of all messages the disclosure component can produce. */
|
|
17
|
-
export declare const Message: S.Union<[import("../../schema").CallableTaggedStruct<"Toggled", {}>, import("../../schema").CallableTaggedStruct<"Closed", {}>, import("../../schema").CallableTaggedStruct<"
|
|
17
|
+
export declare const Message: S.Union<[import("../../schema").CallableTaggedStruct<"Toggled", {}>, import("../../schema").CallableTaggedStruct<"Closed", {}>, import("../../schema").CallableTaggedStruct<"CompletedButtonFocus", {}>]>;
|
|
18
18
|
export type Toggled = typeof Toggled.Type;
|
|
19
19
|
export type Closed = typeof Closed.Type;
|
|
20
|
-
export type
|
|
20
|
+
export type CompletedButtonFocus = typeof CompletedButtonFocus.Type;
|
|
21
21
|
export type Message = typeof Message.Type;
|
|
22
22
|
/** Configuration for creating a disclosure model with `init`. */
|
|
23
23
|
export type InitConfig = Readonly<{
|
|
@@ -31,16 +31,19 @@ export declare const update: (model: Model, message: Message) => [Model, Readonl
|
|
|
31
31
|
/** Configuration for rendering a disclosure with `view`. */
|
|
32
32
|
export type ViewConfig<Message> = Readonly<{
|
|
33
33
|
model: Model;
|
|
34
|
-
toMessage: (message: Toggled | Closed |
|
|
35
|
-
buttonClassName
|
|
34
|
+
toMessage: (message: Toggled | Closed | CompletedButtonFocus) => Message;
|
|
35
|
+
buttonClassName?: string;
|
|
36
|
+
buttonAttributes?: ReadonlyArray<Attribute<Message>>;
|
|
36
37
|
buttonContent: Html;
|
|
37
|
-
panelClassName
|
|
38
|
+
panelClassName?: string;
|
|
39
|
+
panelAttributes?: ReadonlyArray<Attribute<Message>>;
|
|
38
40
|
panelContent: Html;
|
|
39
41
|
isDisabled?: boolean;
|
|
40
42
|
persistPanel?: boolean;
|
|
41
43
|
buttonElement?: TagName;
|
|
42
44
|
panelElement?: TagName;
|
|
43
45
|
className?: string;
|
|
46
|
+
attributes?: ReadonlyArray<Attribute<Message>>;
|
|
44
47
|
}>;
|
|
45
48
|
/** Renders a headless disclosure component with accessible ARIA attributes and keyboard support. */
|
|
46
49
|
export declare const view: <Message>(config: ViewConfig<Message>) => Html;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/ui/disclosure/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAA8B,MAAM,IAAI,CAAC,EAAE,MAAM,QAAQ,CAAA;AAEhE,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/ui/disclosure/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAA8B,MAAM,IAAI,CAAC,EAAE,MAAM,QAAQ,CAAA;AAEhE,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;AAC5C,OAAO,EACL,KAAK,SAAS,EACd,KAAK,IAAI,EACT,KAAK,OAAO,EAGb,MAAM,YAAY,CAAA;AAOnB,kGAAkG;AAClG,eAAO,MAAM,KAAK;;;EAGhB,CAAA;AAEF,MAAM,MAAM,KAAK,GAAG,OAAO,KAAK,CAAC,IAAI,CAAA;AAIrC,iFAAiF;AACjF,eAAO,MAAM,OAAO,4DAAe,CAAA;AACnC,gFAAgF;AAChF,eAAO,MAAM,MAAM,2DAAc,CAAA;AACjC,kEAAkE;AAClE,eAAO,MAAM,oBAAoB,yEAA4B,CAAA;AAE7D,kEAAkE;AAClE,eAAO,MAAM,OAAO,2MAAiD,CAAA;AAErE,MAAM,MAAM,OAAO,GAAG,OAAO,OAAO,CAAC,IAAI,CAAA;AACzC,MAAM,MAAM,MAAM,GAAG,OAAO,MAAM,CAAC,IAAI,CAAA;AACvC,MAAM,MAAM,oBAAoB,GAAG,OAAO,oBAAoB,CAAC,IAAI,CAAA;AAEnE,MAAM,MAAM,OAAO,GAAG,OAAO,OAAO,CAAC,IAAI,CAAA;AAIzC,iEAAiE;AACjE,MAAM,MAAM,UAAU,GAAG,QAAQ,CAAC;IAChC,EAAE,EAAE,MAAM,CAAA;IACV,MAAM,CAAC,EAAE,OAAO,CAAA;CACjB,CAAC,CAAA;AAEF,6EAA6E;AAC7E,eAAO,MAAM,IAAI,GAAI,QAAQ,UAAU,KAAG,KAGxC,CAAA;AAUF,8EAA8E;AAC9E,eAAO,MAAM,MAAM,GACjB,OAAO,KAAK,EACZ,SAAS,OAAO,KACf,CAAC,KAAK,EAAE,aAAa,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC,CA+BvC,CAAA;AAIH,4DAA4D;AAC5D,MAAM,MAAM,UAAU,CAAC,OAAO,IAAI,QAAQ,CAAC;IACzC,KAAK,EAAE,KAAK,CAAA;IACZ,SAAS,EAAE,CAAC,OAAO,EAAE,OAAO,GAAG,MAAM,GAAG,oBAAoB,KAAK,OAAO,CAAA;IACxE,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,gBAAgB,CAAC,EAAE,aAAa,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAA;IACpD,aAAa,EAAE,IAAI,CAAA;IACnB,cAAc,CAAC,EAAE,MAAM,CAAA;IACvB,eAAe,CAAC,EAAE,aAAa,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAA;IACnD,YAAY,EAAE,IAAI,CAAA;IAClB,UAAU,CAAC,EAAE,OAAO,CAAA;IACpB,YAAY,CAAC,EAAE,OAAO,CAAA;IACtB,aAAa,CAAC,EAAE,OAAO,CAAA;IACvB,YAAY,CAAC,EAAE,OAAO,CAAA;IACtB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,UAAU,CAAC,EAAE,aAAa,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAA;CAC/C,CAAC,CAAA;AAEF,oGAAoG;AACpG,eAAO,MAAM,IAAI,GAAI,OAAO,EAAE,QAAQ,UAAU,CAAC,OAAO,CAAC,KAAG,IAgG3D,CAAA;AAED;6EAC6E;AAC7E,eAAO,MAAM,IAAI,GAAI,OAAO,EAC1B,cAAc,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,OAAO,GAAG,WAAW,CAAC,KAC7D,CAAC,CAAC,KAAK,EAAE,KAAK,EAAE,SAAS,EAAE,UAAU,CAAC,OAAO,CAAC,CAAC,WAAW,CAAC,KAAK,IAAI,CAgBtE,CAAA"}
|