@torpor/ui 0.3.5 → 0.3.6

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.
Files changed (225) hide show
  1. package/dist/metafile-esm.json +1 -1
  2. package/package.json +5 -2
  3. package/CHANGELOG.md +0 -344
  4. package/scripts/postbuild.ts +0 -127
  5. package/src/Accordion/Accordion.torp +0 -230
  6. package/src/Accordion/AccordionContent.torp +0 -46
  7. package/src/Accordion/AccordionHeader.torp +0 -45
  8. package/src/Accordion/AccordionItem.torp +0 -101
  9. package/src/Accordion/AccordionTrigger.torp +0 -70
  10. package/src/Accordion/AccordionTypes.ts +0 -36
  11. package/src/Accordion/index.ts +0 -7
  12. package/src/Breadcrumb/Breadcrumb.torp +0 -45
  13. package/src/Breadcrumb/BreadcrumbItem.torp +0 -30
  14. package/src/Breadcrumb/BreadcrumbSeparator.torp +0 -27
  15. package/src/Breadcrumb/index.ts +0 -5
  16. package/src/Calendar/Calendar.torp +0 -277
  17. package/src/Calendar/CalendarDay.torp +0 -78
  18. package/src/Calendar/CalendarTypes.ts +0 -22
  19. package/src/Calendar/index.ts +0 -4
  20. package/src/Contextual/Contextual.torp +0 -129
  21. package/src/Contextual/ContextualContent.torp +0 -112
  22. package/src/Contextual/ContextualTrigger.torp +0 -70
  23. package/src/Contextual/ContextualTypes.ts +0 -30
  24. package/src/Contextual/index.ts +0 -5
  25. package/src/Dialog/Dialog.torp +0 -136
  26. package/src/Dialog/DialogBody.torp +0 -44
  27. package/src/Dialog/DialogButton.torp +0 -66
  28. package/src/Dialog/DialogFooter.torp +0 -25
  29. package/src/Dialog/DialogHeader.torp +0 -45
  30. package/src/Dialog/DialogTypes.ts +0 -17
  31. package/src/Dialog/index.ts +0 -7
  32. package/src/Disclosure/Disclosure.torp +0 -82
  33. package/src/Disclosure/DisclosureContent.torp +0 -46
  34. package/src/Disclosure/DisclosureHeader.torp +0 -45
  35. package/src/Disclosure/DisclosureTrigger.torp +0 -47
  36. package/src/Disclosure/DisclosureTypes.ts +0 -13
  37. package/src/Disclosure/index.ts +0 -6
  38. package/src/Drawer/Drawer.torp +0 -127
  39. package/src/Drawer/DrawerContent.torp +0 -83
  40. package/src/Drawer/DrawerOverlay.torp +0 -42
  41. package/src/Drawer/DrawerTrigger.torp +0 -39
  42. package/src/Drawer/DrawerTypes.ts +0 -24
  43. package/src/Drawer/index.ts +0 -6
  44. package/src/Form/CheckBox.torp +0 -94
  45. package/src/Form/Field.torp +0 -95
  46. package/src/Form/File.torp +0 -102
  47. package/src/Form/Form.torp +0 -147
  48. package/src/Form/FormTypes.ts +0 -35
  49. package/src/Form/Hidden.torp +0 -25
  50. package/src/Form/Input.torp +0 -112
  51. package/src/Form/Label.torp +0 -35
  52. package/src/Form/Message.torp +0 -39
  53. package/src/Form/Option.torp +0 -28
  54. package/src/Form/Select.torp +0 -101
  55. package/src/Form/StandardSchemaV1.ts +0 -70
  56. package/src/Form/TextArea.torp +0 -105
  57. package/src/Form/index.ts +0 -13
  58. package/src/Menu/Menu.torp +0 -174
  59. package/src/Menu/MenuButton.torp +0 -74
  60. package/src/Menu/MenuCheck.torp +0 -89
  61. package/src/Menu/MenuGroup.torp +0 -31
  62. package/src/Menu/MenuIndicator.torp +0 -40
  63. package/src/Menu/MenuPopout.torp +0 -83
  64. package/src/Menu/MenuPopoutContent.torp +0 -84
  65. package/src/Menu/MenuPopoutTrigger.torp +0 -128
  66. package/src/Menu/MenuRadio.torp +0 -103
  67. package/src/Menu/MenuRadioGroup.torp +0 -109
  68. package/src/Menu/MenuSeparator.torp +0 -26
  69. package/src/Menu/MenuTypes.ts +0 -60
  70. package/src/Menu/index.ts +0 -25
  71. package/src/MenuBar/MenuBar.torp +0 -162
  72. package/src/MenuBar/MenuBarItem.torp +0 -116
  73. package/src/MenuBar/MenuBarItemContent.torp +0 -119
  74. package/src/MenuBar/MenuBarItemTrigger.torp +0 -99
  75. package/src/MenuBar/MenuBarTypes.ts +0 -36
  76. package/src/MenuBar/index.ts +0 -6
  77. package/src/Modal/Modal.torp +0 -122
  78. package/src/Modal/ModalContent.torp +0 -81
  79. package/src/Modal/ModalOverlay.torp +0 -42
  80. package/src/Modal/ModalTrigger.torp +0 -54
  81. package/src/Modal/ModalTypes.ts +0 -22
  82. package/src/Modal/index.ts +0 -10
  83. package/src/Modal/showModal.ts +0 -19
  84. package/src/Modal/showPrompt.ts +0 -23
  85. package/src/NavMenu/NavMenu.torp +0 -190
  86. package/src/NavMenu/NavMenuButton.torp +0 -55
  87. package/src/NavMenu/NavMenuElement.torp +0 -55
  88. package/src/NavMenu/NavMenuGroup.torp +0 -41
  89. package/src/NavMenu/NavMenuGroupHeader.torp +0 -41
  90. package/src/NavMenu/NavMenuLink.torp +0 -60
  91. package/src/NavMenu/NavMenuPopout.torp +0 -89
  92. package/src/NavMenu/NavMenuPopoutButton.torp +0 -129
  93. package/src/NavMenu/NavMenuPopoutContent.torp +0 -92
  94. package/src/NavMenu/NavMenuSeparator.torp +0 -24
  95. package/src/NavMenu/NavMenuTypes.ts +0 -32
  96. package/src/NavMenu/index.ts +0 -23
  97. package/src/Notification/Notification.torp +0 -71
  98. package/src/Notification/NotificationClose.torp +0 -39
  99. package/src/Notification/NotificationContainer.torp +0 -26
  100. package/src/Notification/NotificationContent.torp +0 -25
  101. package/src/Notification/NotificationTypes.ts +0 -5
  102. package/src/Notification/index.ts +0 -13
  103. package/src/Notification/showNotification.ts +0 -30
  104. package/src/Popover/Popover.torp +0 -129
  105. package/src/Popover/PopoverContent.torp +0 -117
  106. package/src/Popover/PopoverTrigger.torp +0 -62
  107. package/src/Popover/PopoverTypes.ts +0 -30
  108. package/src/Popover/index.ts +0 -6
  109. package/src/Popover/showPopover.ts +0 -24
  110. package/src/Slider/Slider.torp +0 -84
  111. package/src/Slider/index.ts +0 -3
  112. package/src/TabGroup/TabContent.torp +0 -49
  113. package/src/TabGroup/TabGroup.torp +0 -250
  114. package/src/TabGroup/TabGroupTypes.ts +0 -44
  115. package/src/TabGroup/TabHeader.torp +0 -81
  116. package/src/TabGroup/TabList.torp +0 -61
  117. package/src/TabGroup/TabTrigger.torp +0 -76
  118. package/src/TabGroup/index.ts +0 -7
  119. package/src/ambient.d.ts +0 -7
  120. package/src/icons/ArrowDown.torp +0 -18
  121. package/src/icons/ArrowLeft.torp +0 -18
  122. package/src/icons/ArrowRight.torp +0 -18
  123. package/src/icons/ArrowUp.torp +0 -18
  124. package/src/icons/Bars.torp +0 -20
  125. package/src/icons/Check.torp +0 -18
  126. package/src/icons/ChevronDown.torp +0 -18
  127. package/src/icons/ChevronLeft.torp +0 -18
  128. package/src/icons/ChevronRight.torp +0 -18
  129. package/src/icons/ChevronUp.torp +0 -18
  130. package/src/icons/Cross.torp +0 -19
  131. package/src/icons/IconTypes.ts +0 -10
  132. package/src/icons/Loading.torp +0 -19
  133. package/src/icons/Minus.torp +0 -18
  134. package/src/icons/Plus.torp +0 -19
  135. package/src/icons/index.ts +0 -31
  136. package/src/motion/fade.ts +0 -16
  137. package/src/motion/grow.ts +0 -23
  138. package/src/motion/index.ts +0 -6
  139. package/src/motion/measure.ts +0 -28
  140. package/src/motion/slide.ts +0 -45
  141. package/src/mount/clickPopover.ts +0 -51
  142. package/src/mount/contextPopover.ts +0 -51
  143. package/src/mount/disableScroll.ts +0 -28
  144. package/src/mount/hoverPopover.ts +0 -58
  145. package/src/mount/hoverTrigger.ts +0 -59
  146. package/src/mount/trapFocus.ts +0 -58
  147. package/src/utils/dateUtils.ts +0 -244
  148. package/src/utils/documentEvents.ts +0 -17
  149. package/src/utils/getId.ts +0 -6
  150. package/src/utils/getScrollParent.ts +0 -22
  151. package/src/utils/setContextPosition.ts +0 -31
  152. package/src/utils/setPopoverPosition.ts +0 -142
  153. package/test/Accordion/accessibility.test.ts +0 -59
  154. package/test/Accordion/components/AccordionAccessibility.torp +0 -44
  155. package/test/Accordion/components/AccordionKeyboard.torp +0 -32
  156. package/test/Accordion/components/AccordionList.torp +0 -23
  157. package/test/Accordion/components/AccordionMultiple.torp +0 -32
  158. package/test/Accordion/components/AccordionSingle.torp +0 -32
  159. package/test/Accordion/for-items.test.ts +0 -52
  160. package/test/Accordion/keyboard.test.ts +0 -64
  161. package/test/Accordion/multiple-item-toggle.test.ts +0 -32
  162. package/test/Accordion/multiple-item-value.test.ts +0 -17
  163. package/test/Accordion/single-item-toggle.test.ts +0 -31
  164. package/test/Accordion/single-item-value.test.ts +0 -17
  165. package/test/Breadcrumb/accessibility.test.ts +0 -29
  166. package/test/Breadcrumb/basic.test.ts +0 -17
  167. package/test/Breadcrumb/components/BreadcrumbTest.torp +0 -15
  168. package/test/Calendar/components/CalendarTest.torp +0 -9
  169. package/test/Calendar/default.test.ts +0 -18
  170. package/test/Dialog/accessibility-alert.test.ts +0 -40
  171. package/test/Dialog/accessibility-modal.test.ts +0 -52
  172. package/test/Dialog/components/DialogAccessibility.torp +0 -25
  173. package/test/Dialog/components/DialogFunction.torp +0 -36
  174. package/test/Dialog/components/DialogModal.torp +0 -30
  175. package/test/Dialog/components/DialogVariable.torp +0 -33
  176. package/test/Dialog/function.test.ts +0 -26
  177. package/test/Dialog/variable.test.ts +0 -27
  178. package/test/Disclosure/accessibility.test.ts +0 -31
  179. package/test/Disclosure/components/DisclosureTest.torp +0 -17
  180. package/test/Disclosure/default.test.ts +0 -15
  181. package/test/Disclosure/toggle.test.ts +0 -20
  182. package/test/Form/components/FieldTest.torp +0 -25
  183. package/test/Form/components/FormTest.torp +0 -31
  184. package/test/Form/components/InputTest.torp +0 -9
  185. package/test/Form/field.test.ts +0 -34
  186. package/test/Form/form.test.ts +0 -34
  187. package/test/Form/input.test.ts +0 -19
  188. package/test/Menu/accessibility.test.ts +0 -83
  189. package/test/Menu/basic.test.ts +0 -58
  190. package/test/Menu/components/MenuAccessibility.torp +0 -59
  191. package/test/Menu/components/MenuBasic.torp +0 -58
  192. package/test/MenuBar/accessibility.test.ts +0 -87
  193. package/test/MenuBar/basic.test.ts +0 -22
  194. package/test/MenuBar/components/MenuBarAccessibility.torp +0 -34
  195. package/test/MenuBar/components/MenuBarBasic.torp +0 -25
  196. package/test/NavMenu/accessibility.test.ts +0 -97
  197. package/test/NavMenu/basic.test.ts +0 -22
  198. package/test/NavMenu/components/NavMenuAccessibility.torp +0 -35
  199. package/test/NavMenu/components/NavMenuBasic.torp +0 -28
  200. package/test/Notification/accessibility.test.ts +0 -21
  201. package/test/Notification/components/CustomNotification.torp +0 -14
  202. package/test/Notification/components/NotificationAccessibility.torp +0 -14
  203. package/test/Notification/components/NotificationFunction.torp +0 -17
  204. package/test/Notification/components/NotificationVariable.torp +0 -22
  205. package/test/Notification/function.test.ts +0 -25
  206. package/test/Notification/variable.test.ts +0 -25
  207. package/test/Popover/components/CustomDialog.torp +0 -25
  208. package/test/Popover/components/PopoverFunction.torp +0 -37
  209. package/test/Popover/components/PopoverTrigger.torp +0 -36
  210. package/test/Popover/components/PopoverVariable.torp +0 -40
  211. package/test/Popover/function.test.ts +0 -21
  212. package/test/Popover/trigger.test.ts +0 -27
  213. package/test/Popover/variable.test.ts +0 -27
  214. package/test/TabGroup/accessibility.test.ts +0 -67
  215. package/test/TabGroup/components/TabGroupAccessibility.torp +0 -28
  216. package/test/TabGroup/components/TabGroupKeyboard.torp +0 -28
  217. package/test/TabGroup/components/TabGroupList.torp +0 -26
  218. package/test/TabGroup/components/TabGroupTrigger.torp +0 -28
  219. package/test/TabGroup/for-items.test.ts +0 -52
  220. package/test/TabGroup/item-trigger.test.ts +0 -33
  221. package/test/TabGroup/item-value.test.ts +0 -17
  222. package/test/TabGroup/keyboard.test.ts +0 -72
  223. package/tsconfig.json +0 -4
  224. package/tsup.config.ts +0 -37
  225. package/vitest.config.ts +0 -12
@@ -1,122 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { ModalContextName, type ModalContext, type ModalState } from "./ModalTypes";
3
-
4
- interface ModalProps {
5
- /** An ID for the root element */
6
- id?: string;
7
- /** Classes for the root element */
8
- class?: ClassValue,
9
- /** Styles for the root element */
10
- style?: StyleValue,
11
- /** Whether the modal is visible */
12
- visible?: boolean,
13
- /** A function to be called when the user selects a response */
14
- callback?: ((value: any) => void),
15
- /** Raised when the modal is opened or closed */
16
- ontoggle?: (open: boolean) => void,
17
- /** Raised when the modal has opened */
18
- onopen?: () => void,
19
- /** Raised when the modal has closed */
20
- onclose?: (result: any) => void,
21
- }
22
-
23
- /**
24
- * A modal window that can be used to show rich content or obtain information from a user.
25
- *
26
- * See [the WAI ARIA guidelines for Modals](https://www.w3.org/WAI/ARIA/apg/patterns/dialogmodal/).
27
- *
28
- * The structure of a Modal is:
29
- *
30
- * ```
31
- * <Modal>
32
- * <ModalOverlay />
33
- * <ModalTrigger /> (optional)
34
- * <ModalContent />
35
- * </Modal>
36
- * ```
37
- */
38
- export default function Modal($props: ModalProps | undefined) {
39
- let $state: ModalState = $watch({
40
- visible: false,
41
- })
42
-
43
- // Sync props and state
44
- $run(() => {
45
- $state.visible = $props?.visible ?? false;
46
- });
47
- $run(() => {
48
- if ($props !== undefined) {
49
- $props.visible = $state.visible;
50
- }
51
- });
52
-
53
- let result: any;
54
-
55
- // Set the context to pass down to items
56
- let context: ModalContext = {
57
- handleButton,
58
- handleClickOutside,
59
- state: $state,
60
- };
61
- $context[ModalContextName] = context;
62
-
63
- // Dispatch the toggle event when the modal is opened or closed
64
- let firstToggle = true;
65
- $run(() => {
66
- const ontoggle = $props?.ontoggle;
67
- const onopen = $props?.onopen;
68
- const onclose = $props?.onclose;
69
- const visible = $state.visible;
70
- if (firstToggle) {
71
- firstToggle = false;
72
- } else {
73
- if (ontoggle) ontoggle(visible);
74
- if (visible) {
75
- if (onopen) onopen()
76
- } else {
77
- if (onclose) onclose(result);
78
- }
79
- }
80
- });
81
-
82
- function handleButton(type: "confirm" | "cancel" | undefined, value?: any) {
83
- // Get the button's result
84
- switch (type) {
85
- case "confirm": {
86
- result = value || true;
87
- break;
88
- }
89
- case "cancel": {
90
- result = value || false;
91
- break;
92
- }
93
- default: {
94
- result = value;
95
- break;
96
- }
97
- }
98
-
99
- // Hide the modal
100
- $state.visible = false;
101
-
102
- // Call the callback
103
- if ($props?.callback) {
104
- $props?.callback(result);
105
- }
106
- }
107
-
108
- function handleClickOutside(e: MouseEvent) {
109
- e.preventDefault();
110
- $state.visible = false;
111
- }
112
-
113
- @render {
114
- <div
115
- {$props?.id}
116
- class={["torp-modal", $props?.class]}
117
- {$props?.style}
118
- >
119
- <slot />
120
- </div>
121
- }
122
- }
@@ -1,81 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { addDocumentEvent, removeDocumentEvent } from "../utils/documentEvents";
3
- import { ModalContextName, type ModalContext } from "./ModalTypes";
4
-
5
- interface ModalContentProps {
6
- /** An ID for the root element */
7
- id?: string;
8
- /** Classes for the root element */
9
- class?: ClassValue,
10
- /** Styles for the root element */
11
- style?: StyleValue,
12
- }
13
-
14
- /**
15
- * The content that is displayed for a Modal when it is open, displayed
16
- * alongside an element.
17
- */
18
- export default function ModalContent($props: ModalContentProps | undefined) {
19
- let div: HTMLDivElement;
20
- let shown = false;
21
- let closeOnClick = false;
22
-
23
- // Get stuff out of the ModalContext
24
- const context = $context[ModalContextName] as ModalContext;
25
- if (!context) {
26
- throw new Error("ModalContent must be contained within a Modal");
27
- }
28
- let $state = context.state;
29
-
30
- $run(() => {
31
- if (!$state.visible) {
32
- hide();
33
- }
34
- });
35
-
36
- function show() {
37
- shown = true;
38
-
39
- // HACK: Because this Modal could be shown with a click, we need to wait for another mousedown
40
- // before we close on click. Otherwise the click immediately bubbles to the document
41
- closeOnClick = false;
42
- addDocumentEvent("mousedown", handleDocumentMouseDown);
43
- addDocumentEvent("click", handleDocumentClick);
44
- }
45
-
46
- function hide() {
47
- if (!shown) return;
48
-
49
- removeDocumentEvent("mousedown", handleDocumentMouseDown);
50
- removeDocumentEvent("click", handleDocumentClick);
51
- }
52
-
53
- function handleDocumentMouseDown() {
54
- closeOnClick = true;
55
- }
56
-
57
- function handleDocumentClick(e: MouseEvent) {
58
- if (
59
- closeOnClick &&
60
- div &&
61
- !div.contains(e.target as HTMLElement)
62
- ) {
63
- e.preventDefault();
64
- context.handleClickOutside!(e);
65
- }
66
- }
67
-
68
- @render {
69
- @if ($state.visible) {
70
- <div
71
- {$props?.id}
72
- class={["torp-modal-content", $props?.class]}
73
- {$props?.style}
74
- &ref={div}
75
- onmount={show}
76
- >
77
- <slot />
78
- </div>
79
- }
80
- }
81
- }
@@ -1,42 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { disableScroll } from "../mount/disableScroll";
3
- import { ModalContextName, type ModalContext } from "./ModalTypes";
4
-
5
- interface ModalOverlayProps {
6
- /** An ID for the root element */
7
- id?: string;
8
- /** Classes for the root element */
9
- class?: ClassValue,
10
- /** Styles for the root element */
11
- style?: StyleValue,
12
- }
13
-
14
- /**
15
- * The background overlay for a modal popup component (e.g. Context, Dialog or Popover).
16
- * Adding an overlay automatically sets the component's `modal` value to true.
17
- */
18
- export default function ModalOverlay($props: ModalOverlayProps | undefined) {
19
- // Get stuff out of the ModalContext
20
- const context = $context[ModalContextName] as ModalContext;
21
- if (!context) {
22
- throw new Error("ModalOverlay must be contained within a Modal");
23
- }
24
- let $state = context.state;
25
-
26
- // Any popup with an overlay is modal
27
- $state.modal = true;
28
-
29
- @render {
30
- @if ($state.visible) {
31
- <div
32
- {$props?.id}
33
- class={["torp-modal-overlay", $props?.class]}
34
- {$props?.style}
35
- tabindex="-1"
36
- onmount={(el) => disableScroll(el)}
37
- >
38
- <slot />
39
- </div>
40
- }
41
- }
42
- }
@@ -1,54 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { ModalContextName, type ModalContext } from "./ModalTypes";
3
- import hoverTrigger from "../mount/hoverTrigger";
4
-
5
- interface ModalTriggerProps {
6
- /** An ID for the root element */
7
- id?: string;
8
- /** Classes for the root element */
9
- class?: ClassValue,
10
- /** Styles for the root element */
11
- style?: StyleValue,
12
- /** Whether the modal is activated by click/press or by hover **/
13
- activation?: "press" | "hover"
14
- }
15
-
16
- /**
17
- * The button that causes a Modal to appear or disappear.
18
- */
19
- export default function ModalTrigger($props: ModalTriggerProps | undefined) {
20
- let activation = $props?.activation ?? "press";
21
-
22
- // Get stuff out of the ModalContext
23
- const context = $context[ModalContextName] as ModalContext;
24
- if (!context) {
25
- throw new Error("ModalTrigger must be contained within a Modal");
26
- }
27
- let $state = context.state;
28
-
29
- function handleClick() {
30
- if (activation !== "press") return;
31
-
32
- $state.visible = !$state.visible;
33
- }
34
-
35
- function handleHover() {
36
- if (activation !== "hover") return;
37
-
38
- $state.visible = !$state.visible
39
- }
40
-
41
- @render {
42
- <button
43
- type="button"
44
- {$props?.id}
45
- class={["torp-modal-trigger", $props?.class]}
46
- {$props?.style}
47
- onclick={handleClick}
48
- onmount={(el) => hoverTrigger(el, { onHover: handleHover, onExit: handleHover })}
49
- &ref={context.anchorElement}
50
- >
51
- <slot />
52
- </button>
53
- }
54
- }
@@ -1,22 +0,0 @@
1
- export const ModalContextName = "Modal";
2
-
3
- /** The shared context for modal components (Contextual, Prompt and Modal) */
4
- export interface ModalContext {
5
- handleButton: (type: "confirm" | "cancel" | undefined, value?: any) => void;
6
- // HACK: We need to be able to let children (i.e. Dialogs) override the click outside functionality
7
- // There may be a more elegant way to accomplish this too
8
- handleClickOutside?: (e: MouseEvent) => void;
9
- state: ModalState;
10
- // HACK: focusFirstElement is necessary because if we focus the first element e.g. in a Dialog's
11
- // onMount, it will scroll the page to the focused element and mess up our careful positioning
12
- // We need to be able to manually set the order to
13
- // 1. set visible (so we have an element with content)
14
- // 2. set position (so the element is in the right place)
15
- // 3. set focus (for accessibility)
16
- // There may be a more elegant way to accomplish this!
17
- focusFirstElement?: () => void;
18
- }
19
-
20
- export interface ModalState {
21
- visible: boolean;
22
- }
@@ -1,10 +0,0 @@
1
- import Modal from "./Modal.torp";
2
- import ModalContent from "./ModalContent.torp";
3
- import ModalOverlay from "./ModalOverlay.torp";
4
- import ModalTrigger from "./ModalTrigger.torp";
5
- import showModal from "./showModal";
6
- import showPrompt from "./showPrompt";
7
-
8
- export { Modal, ModalContent, ModalOverlay, ModalTrigger };
9
-
10
- export { showModal, showPrompt };
@@ -1,19 +0,0 @@
1
- // TODO: Allow passing in a variable -- so that you can show an inline modal
2
- import type { Component } from "@torpor/view";
3
-
4
- /**
5
- * Shows a modal component in code.
6
- * @param modal The modal component
7
- * @param props The properties for the modal component
8
- * @param target The target element to show the modal in
9
- * @returns The value selected by the user
10
- */
11
- export default function showModal(
12
- modal: Component,
13
- props?: Record<PropertyKey, any>,
14
- target?: Element,
15
- ): void {
16
- // Create the modal
17
- // TODO: This needs to clean up after itself, like the mount methods do
18
- modal(target || document.body, null, props);
19
- }
@@ -1,23 +0,0 @@
1
- import type { Component } from "@torpor/view";
2
-
3
- /**
4
- * Shows a modal component in code, and asynchronously returns the value selected by the user.
5
- * @param modal The modal component
6
- * @param props The properties for the modal component
7
- * @param target The target element to show the modal in
8
- * @returns The value selected by the user
9
- */
10
- export default function showPrompt(
11
- modal: Component,
12
- props?: Record<PropertyKey, any>,
13
- target?: Element,
14
- ): Promise<any> {
15
- return new Promise((resolve) => {
16
- // Add the promise as the callback
17
- const allProps = Object.assign({}, props, { callback: resolve });
18
-
19
- // Create the modal
20
- // TODO: This needs to clean up after itself, like the use methods do
21
- modal(target || document.body, null, allProps);
22
- });
23
- }
@@ -1,190 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import {
3
- NavMenuContextName,
4
- type NavMenuContext,
5
- type ItemState,
6
- NavMenuPopoutContextName,
7
- type NavMenuPopoutContext
8
- } from "./NavMenuTypes";
9
-
10
- interface NavMenuProps {
11
- /** An ID for the root element */
12
- id?: string;
13
- /** Classes for the root element */
14
- class?: ClassValue,
15
- /** Styles for the root element */
16
- style?: StyleValue,
17
- /** An ARIA label for describing the menu to screen readers */
18
- ariaLabel?: string | undefined,
19
- /** The orientation of the menu, which affects keyboard navigation */
20
- orientation?: "horizontal" | "vertical",
21
- }
22
-
23
- /**
24
- * A list of links for navigating a website.
25
- *
26
- * See [the WAI ARIA guidelines for Menus](https://www.w3.org/WAI/ARIA/apg/patterns/menu/).
27
- *
28
- * The structure of a NavMenu is:
29
- *
30
- * ```
31
- * <NavMenu>
32
- * <NavMenuLink />
33
- * <NavMenuSeparator /> (optional)
34
- * <NavMenuPopout /> (optional)
35
- * ...
36
- * </NavMenu>
37
- * ```
38
- */
39
- export default function NavMenu($props: NavMenuProps | undefined) {
40
- let orientation = $props?.orientation ?? "horizontal";
41
-
42
- // A collection containing the state and some functions for each item
43
- let itemStates: ItemState[] = [];
44
- let focusIndex = -1;
45
-
46
- // Check whether this is a menu in a popout
47
- const popoutContext = $context[NavMenuPopoutContextName] as NavMenuPopoutContext;
48
- const inPopout = !!popoutContext;
49
- let popoutState = popoutContext?.state;
50
-
51
- // Set the focusFirstElement method in the PopoverContext(s) so that it can be called after everything has been shown
52
- if (popoutContext) {
53
- popoutContext.focusFirstElement = focusFirstElement;
54
- }
55
-
56
- // Set the context to pass down to items
57
- let context: NavMenuContext = {
58
- handleItemFocus,
59
- handleItemKey,
60
- registerItem
61
- };
62
- $context[NavMenuContextName] = context;
63
-
64
- // If the NavMenu is not in a popout, focus its first item. Otherwise the popout will call focusFirstElement, below
65
- function handleFocus() {
66
- if (!popoutContext && itemStates.length) {
67
- itemStates[0].setFocused();
68
- }
69
- }
70
-
71
- function focusFirstElement() {
72
- if (itemStates.length) {
73
- itemStates[0].setFocused();
74
- }
75
- }
76
-
77
- function registerItem(setFocused: () => void) {
78
- // Add the item's state to the array and return its index
79
- const newItemState: ItemState = {
80
- setFocused
81
- };
82
- itemStates.push(newItemState);
83
- itemStates = itemStates;
84
- return { index: itemStates.length - 1 };
85
- }
86
-
87
- function handleItemFocus(index: number) {
88
- focusIndex = index;
89
- }
90
-
91
- function handleItemKey(e: KeyboardEvent) {
92
- switch (e.key) {
93
- case "Esc":
94
- case "Escape": {
95
- if (inPopout) {
96
- e.preventDefault();
97
- //setPopoutVisible(false);
98
- popoutState.visible = false;
99
- }
100
- break;
101
- }
102
- case "Right":
103
- case "ArrowRight": {
104
- if (orientation === "horizontal") {
105
- e.preventDefault();
106
- focusItem("next");
107
- }
108
- break;
109
- }
110
- case "Left":
111
- case "ArrowLeft": {
112
- if (orientation === "horizontal") {
113
- e.preventDefault();
114
- focusItem("previous");
115
- }
116
- break;
117
- }
118
- case "Down":
119
- case "ArrowDown": {
120
- if (orientation === "vertical") {
121
- e.preventDefault();
122
- focusItem("next");
123
- }
124
- break;
125
- }
126
- case "Up":
127
- case "ArrowUp": {
128
- if (orientation === "vertical") {
129
- e.preventDefault();
130
- focusItem("previous");
131
- } else {
132
- // TODO: This should be based on what side the menu shows on
133
- // And on the orientation
134
- if (inPopout) {
135
- e.preventDefault();
136
- popoutState.visible = false;
137
- }
138
- }
139
- break;
140
- }
141
- case "Home": {
142
- e.preventDefault();
143
- focusItem("start");
144
- break;
145
- }
146
- case "End": {
147
- e.preventDefault();
148
- focusItem("end");
149
- break;
150
- }
151
- }
152
- }
153
-
154
- function focusItem(target: "start" | "previous" | "next" | "end") {
155
- switch (target) {
156
- case "start": {
157
- focusIndex = 0;
158
- break;
159
- }
160
- case "previous": {
161
- focusIndex = Math.max(0, focusIndex - 1);
162
- break;
163
- }
164
- case "next": {
165
- focusIndex = Math.min(itemStates.length - 1, focusIndex + 1);
166
- break;
167
- }
168
- case "end": {
169
- focusIndex = itemStates.length - 1;
170
- break;
171
- }
172
- }
173
- itemStates[focusIndex]?.setFocused();
174
- }
175
-
176
- @render {
177
- <nav
178
- {$props?.id}
179
- class={["torp-nav-menu", $props?.class]}
180
- {$props?.style}
181
- tabindex="0"
182
- role="menubar"
183
- aria-label={$props?.ariaLabel}
184
- aria-orientation={orientation}
185
- onfocus={handleFocus}
186
- >
187
- <slot />
188
- </nav>
189
- }
190
- }
@@ -1,55 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { NavMenuContextName, type NavMenuContext } from "./NavMenuTypes";
3
-
4
- interface NavMenuButtonProps {
5
- /** An ID for the root element */
6
- id?: string;
7
- /** Classes for the root element */
8
- class?: ClassValue,
9
- /** Styles for the root element */
10
- style?: StyleValue,
11
- /** Whether this button is disabled */
12
- disabled?: boolean,
13
- }
14
-
15
- /**
16
- * A button that is placed in a NavMenu to carry out a non-navigation action such as logging out.
17
- *
18
- */
19
- export default function NavMenuButton($props: NavMenuButtonProps | undefined) {
20
- let button: HTMLButtonElement;
21
-
22
- // Get stuff out of the NavMenuContext
23
- const menuContext = $context[NavMenuContextName] as NavMenuContext;
24
- if (!menuContext) {
25
- throw new Error("NavMenuButton must be contained within a NavMenu");
26
- }
27
- const { registerItem, handleItemKey, handleItemFocus } = menuContext;
28
-
29
- // Register this item with the parent NavMenu and store the index
30
- const { index } = registerItem(setFocused);
31
-
32
- function setFocused() {
33
- button.focus();
34
- }
35
-
36
- @render {
37
- <button
38
- {$props?.id}
39
- class={["torp-nav-menu-button", $props?.class]}
40
- {$props?.style}
41
- type="button"
42
- {$props?.disabled}
43
- role="menuitem"
44
- aria-disabled={$props?.disabled ? "true" : undefined}
45
- data-disabled={$props?.disabled ? "true" : undefined}
46
- onkeydown
47
- onkeydown={handleItemKey}
48
- onclick
49
- onfocus={() => handleItemFocus(index)}
50
- &ref={button}
51
- >
52
- <slot />
53
- </button>
54
- }
55
- }
@@ -1,55 +0,0 @@
1
- import type { ClassValue, StyleValue } from "@torpor/view";
2
- import { NavMenuContextName, type NavMenuContext } from "./NavMenuTypes";
3
-
4
- interface NavMenuElementProps {
5
- /** An ID for the root element */
6
- id?: string;
7
- /** Classes for the root element */
8
- class?: ClassValue,
9
- /** Styles for the root element */
10
- style?: StyleValue,
11
- /** Whether this button is disabled */
12
- disabled?: boolean,
13
- /** An element that can be focused via keyboard navigation */
14
- element?: HTMLElement,
15
- }
16
-
17
- /**
18
- * An element of any type that can be placed in a NavMenu.
19
- *
20
- */
21
- export default function NavMenuElement($props: NavMenuElementProps | undefined) {
22
- // Get stuff out of the NavMenuContext
23
- const menuContext = $context[NavMenuContextName] as NavMenuContext;
24
- if (!menuContext) {
25
- throw new Error("NavMenuElement must be contained within a NavMenu");
26
- }
27
- const { registerItem, handleItemKey, handleItemFocus } = menuContext;
28
-
29
- // Register this item with the parent NavMenu and store the index
30
- const { index } = registerItem(setFocused);
31
-
32
- function setFocused() {
33
- if ($props?.element) {
34
- $props.element.focus();
35
- }
36
- }
37
-
38
- @render {
39
- <div
40
- {$props?.id}
41
- class={["torp-nav-menu-div", $props?.class]}
42
- {$props?.style}
43
- type="div"
44
- role="menuitem"
45
- aria-disabled={$props?.disabled ? "true" : undefined}
46
- data-disabled={$props?.disabled ? "true" : undefined}
47
- onkeydown
48
- onkeydown={handleItemKey}
49
- onclick
50
- onfocus={() => handleItemFocus(index)}
51
- >
52
- <slot />
53
- </div>
54
- }
55
- }