@hanzogui/toast 3.0.2 → 7.3.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.
Files changed (270) hide show
  1. package/dist/cjs/Toast.cjs +149 -141
  2. package/dist/cjs/Toast.native.js +149 -142
  3. package/dist/cjs/Toast.native.js.map +1 -1
  4. package/dist/cjs/ToastAnnounce.cjs +81 -75
  5. package/dist/cjs/ToastAnnounce.native.js +86 -80
  6. package/dist/cjs/ToastAnnounce.native.js.map +1 -1
  7. package/dist/cjs/ToastComposable.cjs +933 -0
  8. package/dist/cjs/ToastComposable.native.js +1025 -0
  9. package/dist/cjs/ToastComposable.native.js.map +1 -0
  10. package/dist/cjs/ToastImperative.cjs +99 -80
  11. package/dist/cjs/ToastImperative.native.js +104 -96
  12. package/dist/cjs/ToastImperative.native.js.map +1 -1
  13. package/dist/cjs/ToastImpl.cjs +303 -241
  14. package/dist/cjs/ToastImpl.native.js +311 -273
  15. package/dist/cjs/ToastImpl.native.js.map +1 -1
  16. package/dist/cjs/ToastItemFrame.cjs +143 -0
  17. package/dist/cjs/ToastItemFrame.native.js +148 -0
  18. package/dist/cjs/ToastItemFrame.native.js.map +1 -0
  19. package/dist/cjs/ToastPortal.cjs +23 -18
  20. package/dist/cjs/ToastPortal.native.js +27 -22
  21. package/dist/cjs/ToastPortal.native.js.map +1 -1
  22. package/dist/cjs/ToastProvider.cjs +103 -99
  23. package/dist/cjs/ToastProvider.native.js +108 -106
  24. package/dist/cjs/ToastProvider.native.js.map +1 -1
  25. package/dist/cjs/ToastState.cjs +311 -0
  26. package/dist/cjs/ToastState.native.js +324 -0
  27. package/dist/cjs/ToastState.native.js.map +1 -0
  28. package/dist/cjs/ToastViewport.cjs +276 -235
  29. package/dist/cjs/ToastViewport.native.js +302 -274
  30. package/dist/cjs/ToastViewport.native.js.map +1 -1
  31. package/dist/cjs/Toaster.cjs +87 -0
  32. package/dist/cjs/Toaster.native.js +91 -0
  33. package/dist/cjs/Toaster.native.js.map +1 -0
  34. package/dist/cjs/constants.cjs +14 -12
  35. package/dist/cjs/constants.native.js +14 -12
  36. package/dist/cjs/constants.native.js.map +1 -1
  37. package/dist/cjs/createNativeToast.cjs +43 -35
  38. package/dist/cjs/createNativeToast.native.js +42 -30
  39. package/dist/cjs/createNativeToast.native.js.map +1 -1
  40. package/dist/cjs/dispatchNativeToast.cjs +47 -0
  41. package/dist/cjs/dispatchNativeToast.native.js +52 -0
  42. package/dist/cjs/dispatchNativeToast.native.js.map +1 -0
  43. package/dist/cjs/index.cjs +7 -5
  44. package/dist/cjs/index.native.js +7 -5
  45. package/dist/cjs/index.native.js.map +1 -1
  46. package/dist/cjs/types.cjs +7 -5
  47. package/dist/cjs/types.native.js +7 -5
  48. package/dist/cjs/types.native.js.map +1 -1
  49. package/dist/cjs/useAnimatedDragGesture.cjs +214 -0
  50. package/dist/cjs/useAnimatedDragGesture.native.js +224 -0
  51. package/dist/cjs/useAnimatedDragGesture.native.js.map +1 -0
  52. package/dist/cjs/useReducedMotion.cjs +74 -0
  53. package/dist/cjs/useReducedMotion.native.js +83 -0
  54. package/dist/cjs/useReducedMotion.native.js.map +1 -0
  55. package/dist/cjs/useToastAnimations.cjs +294 -0
  56. package/dist/cjs/useToastAnimations.native.js +304 -0
  57. package/dist/cjs/useToastAnimations.native.js.map +1 -0
  58. package/dist/cjs/v2.cjs +36 -0
  59. package/dist/cjs/v2.native.js +39 -0
  60. package/dist/cjs/v2.native.js.map +1 -0
  61. package/dist/esm/Toast.mjs +112 -106
  62. package/dist/esm/Toast.mjs.map +1 -1
  63. package/dist/esm/Toast.native.js +112 -107
  64. package/dist/esm/Toast.native.js.map +1 -1
  65. package/dist/esm/ToastAnnounce.mjs +46 -42
  66. package/dist/esm/ToastAnnounce.mjs.map +1 -1
  67. package/dist/esm/ToastAnnounce.native.js +52 -48
  68. package/dist/esm/ToastAnnounce.native.js.map +1 -1
  69. package/dist/esm/ToastComposable.mjs +895 -0
  70. package/dist/esm/ToastComposable.mjs.map +1 -0
  71. package/dist/esm/ToastComposable.native.js +984 -0
  72. package/dist/esm/ToastComposable.native.js.map +1 -0
  73. package/dist/esm/ToastImperative.mjs +71 -54
  74. package/dist/esm/ToastImperative.mjs.map +1 -1
  75. package/dist/esm/ToastImperative.native.js +76 -70
  76. package/dist/esm/ToastImperative.native.js.map +1 -1
  77. package/dist/esm/ToastImpl.mjs +261 -201
  78. package/dist/esm/ToastImpl.mjs.map +1 -1
  79. package/dist/esm/ToastImpl.native.js +270 -234
  80. package/dist/esm/ToastImpl.native.js.map +1 -1
  81. package/dist/esm/ToastItemFrame.mjs +114 -0
  82. package/dist/esm/ToastItemFrame.mjs.map +1 -0
  83. package/dist/esm/ToastItemFrame.native.js +116 -0
  84. package/dist/esm/ToastItemFrame.native.js.map +1 -0
  85. package/dist/esm/ToastPortal.mjs +8 -5
  86. package/dist/esm/ToastPortal.mjs.map +1 -1
  87. package/dist/esm/ToastPortal.native.js +12 -9
  88. package/dist/esm/ToastPortal.native.js.map +1 -1
  89. package/dist/esm/ToastProvider.mjs +71 -69
  90. package/dist/esm/ToastProvider.mjs.map +1 -1
  91. package/dist/esm/ToastProvider.native.js +77 -77
  92. package/dist/esm/ToastProvider.native.js.map +1 -1
  93. package/dist/esm/ToastState.mjs +285 -0
  94. package/dist/esm/ToastState.mjs.map +1 -0
  95. package/dist/esm/ToastState.native.js +295 -0
  96. package/dist/esm/ToastState.native.js.map +1 -0
  97. package/dist/esm/ToastViewport.mjs +238 -199
  98. package/dist/esm/ToastViewport.mjs.map +1 -1
  99. package/dist/esm/ToastViewport.native.js +265 -239
  100. package/dist/esm/ToastViewport.native.js.map +1 -1
  101. package/dist/esm/Toaster.mjs +51 -0
  102. package/dist/esm/Toaster.mjs.map +1 -0
  103. package/dist/esm/Toaster.native.js +52 -0
  104. package/dist/esm/Toaster.native.js.map +1 -0
  105. package/dist/esm/constants.mjs +2 -2
  106. package/dist/esm/constants.mjs.map +1 -1
  107. package/dist/esm/constants.native.js +2 -2
  108. package/dist/esm/constants.native.js.map +1 -1
  109. package/dist/esm/createNativeToast.mjs +29 -24
  110. package/dist/esm/createNativeToast.mjs.map +1 -1
  111. package/dist/esm/createNativeToast.native.js +27 -18
  112. package/dist/esm/createNativeToast.native.js.map +1 -1
  113. package/dist/esm/dispatchNativeToast.mjs +22 -0
  114. package/dist/esm/dispatchNativeToast.mjs.map +1 -0
  115. package/dist/esm/dispatchNativeToast.native.js +24 -0
  116. package/dist/esm/dispatchNativeToast.native.js.map +1 -0
  117. package/dist/esm/useAnimatedDragGesture.mjs +178 -0
  118. package/dist/esm/useAnimatedDragGesture.mjs.map +1 -0
  119. package/dist/esm/useAnimatedDragGesture.native.js +185 -0
  120. package/dist/esm/useAnimatedDragGesture.native.js.map +1 -0
  121. package/dist/esm/useReducedMotion.mjs +38 -0
  122. package/dist/esm/useReducedMotion.mjs.map +1 -0
  123. package/dist/esm/useReducedMotion.native.js +44 -0
  124. package/dist/esm/useReducedMotion.native.js.map +1 -0
  125. package/dist/esm/useToastAnimations.mjs +258 -0
  126. package/dist/esm/useToastAnimations.mjs.map +1 -0
  127. package/dist/esm/useToastAnimations.native.js +265 -0
  128. package/dist/esm/useToastAnimations.native.js.map +1 -0
  129. package/dist/esm/v2.mjs +6 -0
  130. package/dist/esm/v2.mjs.map +1 -0
  131. package/dist/esm/v2.native.js +6 -0
  132. package/dist/esm/v2.native.js.map +1 -0
  133. package/dist/jsx/Toast.mjs +112 -106
  134. package/dist/jsx/Toast.mjs.map +1 -1
  135. package/dist/jsx/Toast.native.js +149 -142
  136. package/dist/jsx/Toast.native.js.map +1 -1
  137. package/dist/jsx/ToastAnnounce.mjs +46 -42
  138. package/dist/jsx/ToastAnnounce.mjs.map +1 -1
  139. package/dist/jsx/ToastAnnounce.native.js +86 -80
  140. package/dist/jsx/ToastAnnounce.native.js.map +1 -1
  141. package/dist/jsx/ToastComposable.mjs +895 -0
  142. package/dist/jsx/ToastComposable.mjs.map +1 -0
  143. package/dist/jsx/ToastComposable.native.js +1025 -0
  144. package/dist/jsx/ToastComposable.native.js.map +1 -0
  145. package/dist/jsx/ToastImperative.mjs +71 -54
  146. package/dist/jsx/ToastImperative.mjs.map +1 -1
  147. package/dist/jsx/ToastImperative.native.js +104 -96
  148. package/dist/jsx/ToastImperative.native.js.map +1 -1
  149. package/dist/jsx/ToastImpl.mjs +261 -201
  150. package/dist/jsx/ToastImpl.mjs.map +1 -1
  151. package/dist/jsx/ToastImpl.native.js +311 -273
  152. package/dist/jsx/ToastImpl.native.js.map +1 -1
  153. package/dist/jsx/ToastItemFrame.mjs +114 -0
  154. package/dist/jsx/ToastItemFrame.mjs.map +1 -0
  155. package/dist/jsx/ToastItemFrame.native.js +148 -0
  156. package/dist/jsx/ToastItemFrame.native.js.map +1 -0
  157. package/dist/jsx/ToastPortal.mjs +8 -5
  158. package/dist/jsx/ToastPortal.mjs.map +1 -1
  159. package/dist/jsx/ToastPortal.native.js +27 -22
  160. package/dist/jsx/ToastPortal.native.js.map +1 -1
  161. package/dist/jsx/ToastProvider.mjs +71 -69
  162. package/dist/jsx/ToastProvider.mjs.map +1 -1
  163. package/dist/jsx/ToastProvider.native.js +108 -106
  164. package/dist/jsx/ToastProvider.native.js.map +1 -1
  165. package/dist/jsx/ToastState.mjs +285 -0
  166. package/dist/jsx/ToastState.mjs.map +1 -0
  167. package/dist/jsx/ToastState.native.js +324 -0
  168. package/dist/jsx/ToastState.native.js.map +1 -0
  169. package/dist/jsx/ToastViewport.mjs +238 -199
  170. package/dist/jsx/ToastViewport.mjs.map +1 -1
  171. package/dist/jsx/ToastViewport.native.js +302 -274
  172. package/dist/jsx/ToastViewport.native.js.map +1 -1
  173. package/dist/jsx/Toaster.mjs +51 -0
  174. package/dist/jsx/Toaster.mjs.map +1 -0
  175. package/dist/jsx/Toaster.native.js +91 -0
  176. package/dist/jsx/Toaster.native.js.map +1 -0
  177. package/dist/jsx/constants.mjs +2 -2
  178. package/dist/jsx/constants.mjs.map +1 -1
  179. package/dist/jsx/constants.native.js +14 -12
  180. package/dist/jsx/constants.native.js.map +1 -1
  181. package/dist/jsx/createNativeToast.mjs +29 -24
  182. package/dist/jsx/createNativeToast.mjs.map +1 -1
  183. package/dist/jsx/createNativeToast.native.js +42 -30
  184. package/dist/jsx/createNativeToast.native.js.map +1 -1
  185. package/dist/jsx/dispatchNativeToast.mjs +22 -0
  186. package/dist/jsx/dispatchNativeToast.mjs.map +1 -0
  187. package/dist/jsx/dispatchNativeToast.native.js +52 -0
  188. package/dist/jsx/dispatchNativeToast.native.js.map +1 -0
  189. package/dist/jsx/index.native.js +7 -5
  190. package/dist/jsx/types.native.js +7 -5
  191. package/dist/jsx/useAnimatedDragGesture.mjs +178 -0
  192. package/dist/jsx/useAnimatedDragGesture.mjs.map +1 -0
  193. package/dist/jsx/useAnimatedDragGesture.native.js +224 -0
  194. package/dist/jsx/useAnimatedDragGesture.native.js.map +1 -0
  195. package/dist/jsx/useReducedMotion.mjs +38 -0
  196. package/dist/jsx/useReducedMotion.mjs.map +1 -0
  197. package/dist/jsx/useReducedMotion.native.js +83 -0
  198. package/dist/jsx/useReducedMotion.native.js.map +1 -0
  199. package/dist/jsx/useToastAnimations.mjs +258 -0
  200. package/dist/jsx/useToastAnimations.mjs.map +1 -0
  201. package/dist/jsx/useToastAnimations.native.js +304 -0
  202. package/dist/jsx/useToastAnimations.native.js.map +1 -0
  203. package/dist/jsx/v2.mjs +6 -0
  204. package/dist/jsx/v2.mjs.map +1 -0
  205. package/dist/jsx/v2.native.js +39 -0
  206. package/dist/jsx/v2.native.js.map +1 -0
  207. package/package.json +43 -24
  208. package/src/Toast.tsx +2 -2
  209. package/src/ToastComposable.tsx +1380 -0
  210. package/src/ToastImpl.tsx +15 -3
  211. package/src/ToastItemFrame.tsx +136 -0
  212. package/src/ToastPortal.tsx +2 -2
  213. package/src/ToastProvider.tsx +8 -1
  214. package/src/ToastState.ts +398 -0
  215. package/src/ToastViewport.tsx +6 -5
  216. package/src/Toaster.tsx +181 -0
  217. package/src/createNativeToast.native.tsx +4 -0
  218. package/src/createNativeToast.tsx +18 -24
  219. package/src/dispatchNativeToast.ts +43 -0
  220. package/src/useAnimatedDragGesture.native.ts +255 -0
  221. package/src/useAnimatedDragGesture.ts +319 -0
  222. package/src/useReducedMotion.ts +59 -0
  223. package/src/useToastAnimations.ts +377 -0
  224. package/src/v2.ts +31 -0
  225. package/types/Toast.d.ts +34 -34
  226. package/types/Toast.d.ts.map +1 -0
  227. package/types/ToastAnnounce.d.ts +4 -4
  228. package/types/ToastAnnounce.d.ts.map +1 -0
  229. package/types/ToastComposable.d.ts +199 -0
  230. package/types/ToastComposable.d.ts.map +1 -0
  231. package/types/ToastImperative.d.ts +3 -3
  232. package/types/ToastImperative.d.ts.map +1 -0
  233. package/types/ToastImpl.d.ts +11 -11
  234. package/types/ToastImpl.d.ts.map +1 -0
  235. package/types/ToastItemFrame.d.ts +25 -0
  236. package/types/ToastItemFrame.d.ts.map +1 -0
  237. package/types/ToastPortal.d.ts +1 -1
  238. package/types/ToastPortal.d.ts.map +1 -0
  239. package/types/ToastProvider.d.ts +4 -4
  240. package/types/ToastProvider.d.ts.map +1 -0
  241. package/types/ToastState.d.ts +179 -0
  242. package/types/ToastState.d.ts.map +1 -0
  243. package/types/ToastViewport.d.ts +10 -10
  244. package/types/ToastViewport.d.ts.map +1 -0
  245. package/types/Toaster.d.ts +112 -0
  246. package/types/Toaster.d.ts.map +1 -0
  247. package/types/constants.d.ts.map +1 -0
  248. package/types/createNativeToast.d.ts +5 -0
  249. package/types/createNativeToast.d.ts.map +1 -0
  250. package/types/createNativeToast.native.d.ts +1 -0
  251. package/types/createNativeToast.native.d.ts.map +1 -0
  252. package/types/dispatchNativeToast.d.ts +12 -0
  253. package/types/dispatchNativeToast.d.ts.map +1 -0
  254. package/types/index.d.ts.map +1 -0
  255. package/types/types.d.ts.map +1 -0
  256. package/types/useAnimatedDragGesture.d.ts +33 -0
  257. package/types/useAnimatedDragGesture.d.ts.map +1 -0
  258. package/types/useAnimatedDragGesture.native.d.ts +33 -0
  259. package/types/useAnimatedDragGesture.native.d.ts.map +1 -0
  260. package/types/useReducedMotion.d.ts +6 -0
  261. package/types/useReducedMotion.d.ts.map +1 -0
  262. package/types/useToastAnimations.d.ts +50 -0
  263. package/types/useToastAnimations.d.ts.map +1 -0
  264. package/types/v2.d.ts +10 -0
  265. package/types/v2.d.ts.map +1 -0
  266. package/v2/index.cjs +2 -0
  267. package/v2/index.js +2 -0
  268. package/v2/index.native.cjs +2 -0
  269. package/v2/index.native.js +2 -0
  270. package/LICENSE +0 -21
@@ -0,0 +1,895 @@
1
+ import { AnimatePresence } from "@hanzogui/animate-presence";
2
+ import { isWeb } from "@hanzogui/constants";
3
+ import { getGestureHandler } from "@hanzogui/native";
4
+ import { createStyledContext, styled, Theme, useConfiguration, useEvent, useThemeName, View } from "@hanzogui/core";
5
+ import { withStaticProperties } from "@hanzogui/helpers";
6
+ import { Portal } from "@hanzogui/portal";
7
+ import { XStack, YStack } from "@hanzogui/stacks";
8
+ import { SizableText } from "@hanzogui/text";
9
+ import * as React from "react";
10
+ import { ToastState } from "./ToastState.mjs";
11
+ import { dispatchNativeToast } from "./dispatchNativeToast.mjs";
12
+ import { useAnimatedDragGesture } from "./useAnimatedDragGesture.mjs";
13
+ import { useToastAnimations } from "./useToastAnimations.mjs";
14
+ import { useReducedMotion } from "./useReducedMotion.mjs";
15
+ import { DefaultCloseIcon, ToastActionFrame, ToastCloseFrame, ToastItemFrame, ToastPositionWrapper } from "./ToastItemFrame.mjs";
16
+ import { jsx, jsxs } from "react/jsx-runtime";
17
+ const VISIBLE_TOASTS_AMOUNT = 4;
18
+ const VIEWPORT_OFFSET = 16;
19
+ const TOAST_GAP = 14;
20
+ const TOAST_LIFETIME = 4e3;
21
+ const FIXED_TOAST_HEIGHT = 72;
22
+ const TIME_BEFORE_UNMOUNT = 200;
23
+ const DEFAULT_HOTKEY = ["altKey", "KeyT"];
24
+ const ToastContext = createStyledContext({}, "Toast__");
25
+ const useToastContext = ToastContext.useStyledContext;
26
+ const ToastItemContext = React.createContext(null);
27
+ function useToastItemContext() {
28
+ const ctx = React.useContext(ToastItemContext);
29
+ if (!ctx) {
30
+ throw new Error("useToastItemContext must be used within Toast.Item or Toast.List");
31
+ }
32
+ return ctx;
33
+ }
34
+ function resolveSwipeDirection(direction, position) {
35
+ if (direction !== "auto") return direction;
36
+ const [yPosition, xPosition] = position.split("-");
37
+ if (!isWeb) {
38
+ return yPosition === "top" ? "up" : "down";
39
+ }
40
+ if (xPosition === "left") return "left";
41
+ if (xPosition === "right") return "right";
42
+ return "horizontal";
43
+ }
44
+ const ToastRoot = React.forwardRef(function ToastRoot2(props, _ref) {
45
+ const {
46
+ children,
47
+ position = "bottom-right",
48
+ duration = TOAST_LIFETIME,
49
+ gap = TOAST_GAP,
50
+ visibleToasts = VISIBLE_TOASTS_AMOUNT,
51
+ swipeDirection: swipeDirectionProp = "auto",
52
+ swipeThreshold = 50,
53
+ toastHeight = FIXED_TOAST_HEIGHT,
54
+ closeButton = false,
55
+ expand = false,
56
+ theme: themeProp,
57
+ reducedMotion: reducedMotionProp,
58
+ native = false,
59
+ burntOptions,
60
+ notificationOptions,
61
+ icons
62
+ } = props;
63
+ const reducedMotion = useReducedMotion(reducedMotionProp);
64
+ const [toasts, setToasts] = React.useState([]);
65
+ const [heights, setHeights] = React.useState({});
66
+ const [localExpanded, setExpanded] = React.useState(false);
67
+ const expanded = expand || localExpanded;
68
+ const [interacting, setInteracting] = React.useState(false);
69
+ const heightsLockedRef = React.useRef(false);
70
+ const prevExpandedRef = React.useRef(expanded);
71
+ React.useLayoutEffect(() => {
72
+ if (prevExpandedRef.current !== expanded) {
73
+ heightsLockedRef.current = true;
74
+ prevExpandedRef.current = expanded;
75
+ }
76
+ const timer = setTimeout(() => {
77
+ heightsLockedRef.current = false;
78
+ }, 350);
79
+ return () => clearTimeout(timer);
80
+ }, [expanded]);
81
+ const setToastHeight = React.useCallback((toastId, height) => {
82
+ if (heightsLockedRef.current) return;
83
+ const rounded = Math.round(height);
84
+ setHeights(prev => {
85
+ const existing = prev[toastId];
86
+ if (existing != null && Math.abs(existing - rounded) <= 2) return prev;
87
+ return {
88
+ ...prev,
89
+ [toastId]: rounded
90
+ };
91
+ });
92
+ }, []);
93
+ const removeToastHeight = React.useCallback(toastId => {
94
+ setHeights(prev => {
95
+ if (!(toastId in prev)) return prev;
96
+ const next = {
97
+ ...prev
98
+ };
99
+ delete next[toastId];
100
+ return next;
101
+ });
102
+ }, []);
103
+ const dismissCooldownRef = React.useRef(false);
104
+ const dismissCooldownTimerRef = React.useRef(null);
105
+ const triggerDismissCooldown = React.useCallback(() => {
106
+ dismissCooldownRef.current = true;
107
+ if (dismissCooldownTimerRef.current) {
108
+ clearTimeout(dismissCooldownTimerRef.current);
109
+ }
110
+ dismissCooldownTimerRef.current = setTimeout(() => {
111
+ dismissCooldownRef.current = false;
112
+ }, 800);
113
+ }, []);
114
+ const isInDismissCooldown = React.useCallback(() => dismissCooldownRef.current, []);
115
+ const burntOptionsRef = React.useRef(burntOptions);
116
+ const notificationOptionsRef = React.useRef(notificationOptions);
117
+ React.useEffect(() => {
118
+ burntOptionsRef.current = burntOptions;
119
+ }, [burntOptions]);
120
+ React.useEffect(() => {
121
+ notificationOptionsRef.current = notificationOptions;
122
+ }, [notificationOptions]);
123
+ React.useEffect(() => {
124
+ return ToastState.subscribe(toast => {
125
+ if (toast.dismiss) {
126
+ setToasts(toasts2 => toasts2.map(t => t.id === toast.id ? {
127
+ ...t,
128
+ delete: true
129
+ } : t));
130
+ return;
131
+ }
132
+ if (native) {
133
+ const handled = dispatchNativeToast(toast, {
134
+ duration,
135
+ burntOptions: burntOptionsRef.current,
136
+ notificationOptions: notificationOptionsRef.current
137
+ });
138
+ if (handled) return;
139
+ }
140
+ setToasts(toasts2 => {
141
+ const idx = toasts2.findIndex(t => t.id === toast.id);
142
+ if (idx !== -1) {
143
+ return [...toasts2.slice(0, idx), {
144
+ ...toasts2[idx],
145
+ ...toast
146
+ }, ...toasts2.slice(idx + 1)];
147
+ }
148
+ return [toast, ...toasts2];
149
+ });
150
+ });
151
+ }, [native, duration]);
152
+ const prevToastCountRef = React.useRef(toasts.length);
153
+ React.useEffect(() => {
154
+ const prevCount = prevToastCountRef.current;
155
+ prevToastCountRef.current = toasts.length;
156
+ if (toasts.length <= 1 && !dismissCooldownRef.current) {
157
+ setExpanded(false);
158
+ } else if (toasts.length > prevCount && expanded) {
159
+ setExpanded(false);
160
+ }
161
+ }, [toasts.length, expanded]);
162
+ const removeToast = React.useCallback(toastToRemove => {
163
+ setToasts(toasts2 => {
164
+ if (!toasts2.find(t => t.id === toastToRemove.id)?.delete) {
165
+ ToastState.dismiss(toastToRemove.id);
166
+ }
167
+ return toasts2.filter(({
168
+ id
169
+ }) => id !== toastToRemove.id);
170
+ });
171
+ }, []);
172
+ const swipeDirection = resolveSwipeDirection(swipeDirectionProp, position);
173
+ const currentTheme = useThemeName();
174
+ const resolvedTheme = themeProp === "system" || !themeProp ? currentTheme?.includes("dark") ? "dark" : "light" : themeProp;
175
+ const contextValue = {
176
+ toasts,
177
+ heights,
178
+ setToastHeight,
179
+ removeToastHeight,
180
+ expanded,
181
+ setExpanded,
182
+ interacting,
183
+ setInteracting,
184
+ triggerDismissCooldown,
185
+ isInDismissCooldown,
186
+ removeToast,
187
+ position,
188
+ duration,
189
+ gap,
190
+ visibleToasts,
191
+ swipeDirection,
192
+ swipeThreshold,
193
+ toastHeight,
194
+ closeButton,
195
+ reducedMotion,
196
+ native,
197
+ burntOptions,
198
+ notificationOptions,
199
+ icons
200
+ };
201
+ return /* @__PURE__ */jsx(ToastContext.Provider, {
202
+ ...contextValue,
203
+ children: /* @__PURE__ */jsx(Theme, {
204
+ name: resolvedTheme,
205
+ children
206
+ })
207
+ });
208
+ });
209
+ const ToastViewportFrame = styled(View, {
210
+ name: "ToastViewport",
211
+ variants: {
212
+ unstyled: {
213
+ false: {
214
+ position: isWeb ? "fixed" : "absolute",
215
+ zIndex: 1e5,
216
+ pointerEvents: "box-none",
217
+ maxWidth: "100%",
218
+ ...(isWeb && {
219
+ width: 356
220
+ }),
221
+ minHeight: 1
222
+ }
223
+ }
224
+ },
225
+ defaultVariants: {
226
+ unstyled: process.env.GUI_HEADLESS === "1"
227
+ }
228
+ });
229
+ const ToastViewport = ToastViewportFrame.styleable(function ToastViewport2(props, ref) {
230
+ const {
231
+ offset = VIEWPORT_OFFSET,
232
+ hotkey = DEFAULT_HOTKEY,
233
+ label = "Notifications",
234
+ portalToRoot = true,
235
+ portalZIndex = Number.MAX_SAFE_INTEGER,
236
+ children,
237
+ ...rest
238
+ } = props;
239
+ const ctx = useToastContext();
240
+ const listRef = React.useRef(null);
241
+ const hoverTimeoutRef = React.useRef(null);
242
+ const hoverCooldownRef = React.useRef(false);
243
+ const deferredCollapseRef = React.useRef(null);
244
+ const mouseInsideRef = React.useRef(false);
245
+ const [yPosition, xPosition] = ctx.position.split("-");
246
+ const {
247
+ insets: safeInsets
248
+ } = useConfiguration();
249
+ const offsetStyles = React.useMemo(() => {
250
+ const styles = {};
251
+ const defaultOffset = typeof offset === "number" ? offset : VIEWPORT_OFFSET;
252
+ const offsetObj = typeof offset === "object" ? offset : {
253
+ top: defaultOffset,
254
+ right: defaultOffset,
255
+ bottom: defaultOffset,
256
+ left: defaultOffset
257
+ };
258
+ const safeTop = safeInsets?.top ?? 0;
259
+ const safeBottom = safeInsets?.bottom ?? 0;
260
+ const topOffset = safeTop > 0 ? safeTop : offsetObj.top ?? defaultOffset;
261
+ const bottomOffset = safeBottom > 0 ? safeBottom : offsetObj.bottom ?? defaultOffset;
262
+ if (yPosition === "top") styles.top = topOffset;else styles.bottom = bottomOffset;
263
+ if (isWeb) {
264
+ if (xPosition === "left") styles.left = offsetObj.left ?? defaultOffset;else if (xPosition === "right") styles.right = offsetObj.right ?? defaultOffset;else {
265
+ styles.left = "50%";
266
+ styles.transform = "translateX(-50%)";
267
+ }
268
+ } else {
269
+ styles.left = offsetObj.left ?? defaultOffset;
270
+ styles.right = offsetObj.right ?? defaultOffset;
271
+ }
272
+ return styles;
273
+ }, [offset, yPosition, xPosition]);
274
+ React.useEffect(() => {
275
+ if (!isWeb) return;
276
+ const handleKeyDown = event => {
277
+ const isHotkeyPressed = hotkey.length > 0 && hotkey.every(key => event[key] || event.code === key);
278
+ if (isHotkeyPressed) {
279
+ ctx.setExpanded(true);
280
+ listRef.current?.focus();
281
+ }
282
+ };
283
+ document.addEventListener("keydown", handleKeyDown);
284
+ return () => document.removeEventListener("keydown", handleKeyDown);
285
+ }, [hotkey]);
286
+ if (ctx.toasts.length === 0) return null;
287
+ const hotkeyLabel = hotkey.join("+").replace(/Key/g, "").replace(/Digit/g, "");
288
+ const content = /* @__PURE__ */jsx(ToastViewportFrame, {
289
+ ref: listRef,
290
+ "aria-label": `${label} ${hotkeyLabel}`,
291
+ tabIndex: -1,
292
+ "aria-live": "polite",
293
+ style: offsetStyles,
294
+ "data-y-position": yPosition,
295
+ "data-x-position": xPosition,
296
+ ...(isWeb ? {
297
+ onMouseEnter: () => {
298
+ mouseInsideRef.current = true;
299
+ if (deferredCollapseRef.current) {
300
+ clearTimeout(deferredCollapseRef.current);
301
+ deferredCollapseRef.current = null;
302
+ }
303
+ if (ctx.toasts.length > 1 && !ctx.interacting && !hoverCooldownRef.current) {
304
+ hoverTimeoutRef.current = setTimeout(() => ctx.setExpanded(true), 50);
305
+ }
306
+ },
307
+ onMouseLeave: () => {
308
+ mouseInsideRef.current = false;
309
+ if (hoverTimeoutRef.current) {
310
+ clearTimeout(hoverTimeoutRef.current);
311
+ hoverTimeoutRef.current = null;
312
+ }
313
+ if (!ctx.interacting && !ctx.isInDismissCooldown()) {
314
+ ctx.setExpanded(false);
315
+ } else if (ctx.isInDismissCooldown()) {
316
+ if (deferredCollapseRef.current) {
317
+ clearTimeout(deferredCollapseRef.current);
318
+ }
319
+ deferredCollapseRef.current = setTimeout(() => {
320
+ deferredCollapseRef.current = null;
321
+ if (!mouseInsideRef.current) {
322
+ ctx.setExpanded(false);
323
+ }
324
+ }, 1200);
325
+ }
326
+ },
327
+ onPointerDown: () => {
328
+ if (hoverTimeoutRef.current) {
329
+ clearTimeout(hoverTimeoutRef.current);
330
+ hoverTimeoutRef.current = null;
331
+ }
332
+ ctx.setInteracting(true);
333
+ },
334
+ onPointerUp: () => ctx.setInteracting(false),
335
+ onPointerCancel: () => ctx.setInteracting(false)
336
+ } : {
337
+ onPress: () => {
338
+ if (ctx.toasts.length > 1) {
339
+ ctx.setExpanded(prev => !prev);
340
+ }
341
+ }
342
+ }),
343
+ ...(isWeb && {
344
+ onFocus: event => {
345
+ if (!event.currentTarget.contains(event.relatedTarget)) {
346
+ if (ctx.toasts.length > 1) {
347
+ ctx.setExpanded(true);
348
+ }
349
+ ctx.setInteracting(true);
350
+ }
351
+ },
352
+ onBlur: event => {
353
+ if (!event.currentTarget.contains(event.relatedTarget)) {
354
+ ctx.setInteracting(false);
355
+ if (!ctx.isInDismissCooldown()) {
356
+ ctx.setExpanded(false);
357
+ }
358
+ }
359
+ }
360
+ }),
361
+ ...rest,
362
+ children
363
+ });
364
+ if (portalToRoot) {
365
+ return /* @__PURE__ */jsx(Portal, {
366
+ zIndex: portalZIndex,
367
+ children: content
368
+ });
369
+ }
370
+ return content;
371
+ });
372
+ function ToastList({
373
+ renderItem
374
+ }) {
375
+ const ctx = useToastContext();
376
+ const maxRender = ctx.toasts.length;
377
+ return /* @__PURE__ */jsx(AnimatePresence, {
378
+ children: ctx.toasts.slice(0, maxRender).map((toast, index) => {
379
+ const handleClose = () => {
380
+ if (toast.dismissible === false) return;
381
+ toast.onDismiss?.(toast);
382
+ ctx.removeToast(toast);
383
+ };
384
+ const itemContextValue = {
385
+ toast,
386
+ handleClose
387
+ };
388
+ if (!renderItem) {
389
+ return /* @__PURE__ */jsx(ToastItemContext.Provider, {
390
+ value: itemContextValue,
391
+ children: /* @__PURE__ */jsx(ToastItemInner, {
392
+ toast,
393
+ index,
394
+ children: /* @__PURE__ */jsx(DefaultToastContent, {
395
+ toast
396
+ })
397
+ })
398
+ }, toast.id);
399
+ }
400
+ return /* @__PURE__ */jsx(ToastItemContext.Provider, {
401
+ value: itemContextValue,
402
+ children: renderItem({
403
+ toast,
404
+ index,
405
+ handleClose
406
+ })
407
+ }, toast.id);
408
+ })
409
+ });
410
+ }
411
+ function DefaultToastContent({
412
+ toast
413
+ }) {
414
+ const ctx = useToastContext();
415
+ const {
416
+ handleClose
417
+ } = useToastItemContext();
418
+ const toastType = toast.type ?? "default";
419
+ const dismissible = toast.dismissible !== false;
420
+ const title = typeof toast.title === "function" ? toast.title() : toast.title;
421
+ const description = typeof toast.description === "function" ? toast.description() : toast.description;
422
+ return /* @__PURE__ */jsxs(XStack, {
423
+ alignItems: "flex-start",
424
+ gap: "$3",
425
+ children: [/* @__PURE__ */jsx(ToastIcon, {}), /* @__PURE__ */jsxs(YStack, {
426
+ flex: 1,
427
+ gap: "$1",
428
+ children: [title && /* @__PURE__ */jsx(ToastTitle, {
429
+ children: title
430
+ }), description && /* @__PURE__ */jsx(ToastDescription, {
431
+ children: description
432
+ }), (toast.action || toast.cancel) && /* @__PURE__ */jsxs(XStack, {
433
+ gap: "$2",
434
+ marginTop: "$2",
435
+ children: [toast.cancel && /* @__PURE__ */jsx(ToastActionFrame, {
436
+ backgroundColor: "transparent",
437
+ onPress: e => {
438
+ toast.cancel?.onClick?.(e);
439
+ handleClose();
440
+ },
441
+ children: /* @__PURE__ */jsx(SizableText, {
442
+ size: "$2",
443
+ color: "$color11",
444
+ children: toast.cancel.label
445
+ })
446
+ }), toast.action && /* @__PURE__ */jsx(ToastActionFrame, {
447
+ backgroundColor: "$color12",
448
+ hoverStyle: {
449
+ backgroundColor: "$color11"
450
+ },
451
+ pressStyle: {
452
+ backgroundColor: "$color10"
453
+ },
454
+ onPress: e => {
455
+ toast.action?.onClick?.(e);
456
+ if (!e.defaultPrevented) {
457
+ handleClose();
458
+ }
459
+ },
460
+ children: /* @__PURE__ */jsx(SizableText, {
461
+ size: "$2",
462
+ fontWeight: "600",
463
+ color: "$background",
464
+ children: toast.action.label
465
+ })
466
+ })]
467
+ })]
468
+ }), ctx.closeButton && dismissible && /* @__PURE__ */jsx(ToastClose, {})]
469
+ });
470
+ }
471
+ function DragWrapper({
472
+ animatedStyle,
473
+ gestureHandlers,
474
+ gesture,
475
+ AnimatedView,
476
+ dragRef,
477
+ children
478
+ }) {
479
+ if (isWeb) {
480
+ return /* @__PURE__ */jsx("div", {
481
+ ref: dragRef,
482
+ style: {
483
+ flex: 1,
484
+ display: "flex",
485
+ flexDirection: "column",
486
+ userSelect: "none",
487
+ WebkitUserSelect: "none",
488
+ touchAction: "none",
489
+ cursor: "default"
490
+ },
491
+ ...gestureHandlers,
492
+ children
493
+ });
494
+ }
495
+ if (gesture) {
496
+ const gh = getGestureHandler();
497
+ const GestureDetector = gh.state.GestureDetector;
498
+ if (GestureDetector) {
499
+ return /* @__PURE__ */jsx(GestureDetector, {
500
+ gesture,
501
+ children: /* @__PURE__ */jsx(View, {
502
+ style: {
503
+ flex: 1
504
+ },
505
+ ...{
506
+ collapsable: false
507
+ },
508
+ children: /* @__PURE__ */jsx(AnimatedView, {
509
+ style: [{
510
+ flex: 1
511
+ }, animatedStyle],
512
+ children
513
+ })
514
+ })
515
+ });
516
+ }
517
+ }
518
+ return /* @__PURE__ */jsx(AnimatedView, {
519
+ style: [{
520
+ flex: 1
521
+ }, animatedStyle],
522
+ ...gestureHandlers,
523
+ children
524
+ });
525
+ }
526
+ const ToastItemInner = ToastItemFrame.styleable(function ToastItem(props, ref) {
527
+ const {
528
+ toast,
529
+ index,
530
+ children,
531
+ ...rest
532
+ } = props;
533
+ const ctx = useToastContext();
534
+ const [mounted, setMounted] = React.useState(false);
535
+ const [removed, setRemoved] = React.useState(false);
536
+ const [swipeOut, setSwipeOut] = React.useState(false);
537
+ const [offsetBeforeRemove, setOffsetBeforeRemove] = React.useState(0);
538
+ const swipeExitYRef = React.useRef(null);
539
+ const closeTimerRef = React.useRef(null);
540
+ const closeTimerStartRef = React.useRef(0);
541
+ const lastPauseTimeRef = React.useRef(0);
542
+ const remainingTimeRef = React.useRef(toast.duration ?? ctx.duration);
543
+ const isFront = index === 0;
544
+ const isVisible = index < ctx.visibleToasts;
545
+ const toastType = toast.type ?? "default";
546
+ const dismissible = toast.dismissible !== false;
547
+ const duration = toast.duration ?? ctx.duration;
548
+ const [yPosition] = ctx.position.split("-");
549
+ const isTop = yPosition === "top";
550
+ const expandedOffset = isWeb ? (() => {
551
+ let totalHeight = 0;
552
+ let activeCount = 0;
553
+ for (let i = 0; i < index; i++) {
554
+ const toastId = ctx.toasts[i]?.id;
555
+ if (toastId == null) continue;
556
+ const h = ctx.heights[toastId];
557
+ if (h === 0) continue;
558
+ totalHeight += h ?? ctx.toastHeight;
559
+ activeCount++;
560
+ }
561
+ return totalHeight + activeCount * ctx.gap;
562
+ })() : index * (ctx.toastHeight + ctx.gap);
563
+ const expandedOffsetRef = React.useRef(expandedOffset);
564
+ expandedOffsetRef.current = expandedOffset;
565
+ const isExpandedRef = React.useRef(ctx.expanded);
566
+ isExpandedRef.current = ctx.expanded;
567
+ const startTimer = React.useCallback(() => {
568
+ if (duration === Number.POSITIVE_INFINITY || toastType === "loading") return;
569
+ closeTimerStartRef.current = Date.now();
570
+ closeTimerRef.current = setTimeout(() => {
571
+ toast.onAutoClose?.(toast);
572
+ setRemoved(true);
573
+ setTimeout(() => ctx.removeToast(toast), TIME_BEFORE_UNMOUNT);
574
+ }, remainingTimeRef.current);
575
+ }, [duration, toastType, toast, ctx.removeToast]);
576
+ const pauseTimer = useEvent(() => {
577
+ if (closeTimerRef.current) {
578
+ clearTimeout(closeTimerRef.current);
579
+ }
580
+ if (lastPauseTimeRef.current < closeTimerStartRef.current) {
581
+ const elapsed = Date.now() - closeTimerStartRef.current;
582
+ remainingTimeRef.current = Math.max(0, remainingTimeRef.current - elapsed);
583
+ }
584
+ lastPauseTimeRef.current = Date.now();
585
+ });
586
+ const resumeTimer = useEvent(() => {
587
+ if (ctx.expanded || ctx.interacting) return;
588
+ remainingTimeRef.current = duration;
589
+ startTimer();
590
+ });
591
+ React.useEffect(() => {
592
+ setMounted(true);
593
+ }, []);
594
+ React.useEffect(() => {
595
+ if (toast.delete) {
596
+ setRemoved(true);
597
+ if (isExpandedRef.current) {
598
+ setOffsetBeforeRemove(expandedOffsetRef.current);
599
+ }
600
+ setTimeout(() => ctx.removeToast(toast), TIME_BEFORE_UNMOUNT);
601
+ }
602
+ }, [toast.delete, toast, ctx.removeToast]);
603
+ React.useEffect(() => {
604
+ if (ctx.expanded || ctx.interacting) {
605
+ pauseTimer();
606
+ } else {
607
+ startTimer();
608
+ }
609
+ return () => {
610
+ if (closeTimerRef.current) clearTimeout(closeTimerRef.current);
611
+ };
612
+ }, [ctx.expanded, ctx.interacting, startTimer]);
613
+ React.useEffect(() => {
614
+ remainingTimeRef.current = duration;
615
+ }, [duration]);
616
+ const {
617
+ setDragOffset,
618
+ springBack,
619
+ animateOut,
620
+ animatedStyle,
621
+ AnimatedView,
622
+ dragRef
623
+ } = useToastAnimations({
624
+ reducedMotion: ctx.reducedMotion,
625
+ swipeAxis: ctx.swipeDirection === "up" || ctx.swipeDirection === "down" || ctx.swipeDirection === "vertical" ? "vertical" : "horizontal"
626
+ });
627
+ const {
628
+ isDragging,
629
+ gestureHandlers,
630
+ gesture
631
+ } = useAnimatedDragGesture({
632
+ direction: ctx.swipeDirection,
633
+ threshold: ctx.swipeThreshold,
634
+ disabled: !dismissible || toastType === "loading",
635
+ expanded: ctx.expanded,
636
+ onDragStart: pauseTimer,
637
+ onDragMove: setDragOffset,
638
+ onDismiss: (exitDirection, velocity) => {
639
+ ctx.triggerDismissCooldown();
640
+ setSwipeOut(true);
641
+ toast.onDismiss?.(toast);
642
+ swipeExitYRef.current = isExpandedRef.current ? isTop ? expandedOffsetRef.current : -expandedOffsetRef.current : isFront ? 0 : isTop ? ctx.gap * index : -ctx.gap * index;
643
+ setRemoved(true);
644
+ ctx.removeToast(toast);
645
+ animateOut(exitDirection, velocity);
646
+ },
647
+ onCancel: () => {
648
+ springBack(() => {
649
+ resumeTimer();
650
+ });
651
+ }
652
+ });
653
+ const handleLayout = React.useCallback(event => {
654
+ if (!isWeb) return;
655
+ if (removed) return;
656
+ if (!ctx.expanded && index !== 0) return;
657
+ const {
658
+ height
659
+ } = event.nativeEvent.layout;
660
+ ctx.setToastHeight(toast.id, height);
661
+ }, [toast.id, ctx.setToastHeight, index, ctx.expanded, removed]);
662
+ React.useEffect(() => {
663
+ if (!isWeb) return;
664
+ return () => {
665
+ ctx.removeToastHeight(toast.id);
666
+ };
667
+ }, [toast.id, ctx.removeToastHeight]);
668
+ const handleClose = React.useCallback(() => {
669
+ if (!dismissible) return;
670
+ ctx.triggerDismissCooldown();
671
+ toast.onDismiss?.(toast);
672
+ setRemoved(true);
673
+ if (isExpandedRef.current) {
674
+ setOffsetBeforeRemove(expandedOffsetRef.current);
675
+ }
676
+ setTimeout(() => ctx.removeToast(toast), TIME_BEFORE_UNMOUNT);
677
+ }, [dismissible, toast, ctx.removeToast, ctx.triggerDismissCooldown]);
678
+ const itemContextValue = React.useMemo(() => ({
679
+ toast,
680
+ handleClose
681
+ }), [toast, handleClose]);
682
+ let frontToastHeight = -1;
683
+ if (isWeb) {
684
+ for (const t of ctx.toasts) {
685
+ const h = ctx.heights[t.id];
686
+ if (h != null && h > 0) {
687
+ frontToastHeight = h;
688
+ break;
689
+ }
690
+ }
691
+ }
692
+ const stackScale = !ctx.expanded && !isFront ? 1 - index * 0.05 : 1;
693
+ const activeExpandedOffset = removed ? offsetBeforeRemove : expandedOffset;
694
+ const stackY = ctx.expanded ? isTop ? activeExpandedOffset : -activeExpandedOffset : isFront ? 0 : isTop ? ctx.gap * index : -ctx.gap * index;
695
+ const computedOpacity = removed && !swipeOut ? 0 : index >= ctx.visibleToasts ? 0 : 1;
696
+ const computedZIndex = removed ? 0 : ctx.visibleToasts - index + 1;
697
+ const computedHeight = isWeb ? ctx.expanded ? ctx.heights[toast.id] || void 0 : !isFront && frontToastHeight > 0 ? frontToastHeight : void 0 : void 0;
698
+ const computedPointerEvents = index >= ctx.visibleToasts ? "none" : "auto";
699
+ const gapFillerHeight = ctx.expanded ? ctx.gap + 1 : 0;
700
+ const dataAttributes = {
701
+ "data-mounted": mounted ? "true" : "false",
702
+ "data-removed": removed ? "true" : "false",
703
+ "data-swipe-out": swipeOut ? "true" : "false",
704
+ "data-visible": isVisible ? "true" : "false",
705
+ "data-front": isFront ? "true" : "false",
706
+ "data-index": String(index),
707
+ "data-type": toastType,
708
+ "data-expanded": ctx.expanded ? "true" : "false"
709
+ };
710
+ return /* @__PURE__ */jsx(ToastPositionWrapper, {
711
+ ref,
712
+ testID: rest.testID,
713
+ accessibilityLabel: rest.accessibilityLabel,
714
+ ...dataAttributes,
715
+ transition: isDragging || ctx.reducedMotion ? void 0 : removed ? "200ms" : "400ms",
716
+ animateOnly: isWeb ? ["transform", "opacity", "height"] : ["transform", "opacity"],
717
+ y: stackY,
718
+ scale: stackScale,
719
+ opacity: computedOpacity,
720
+ zIndex: computedZIndex,
721
+ height: computedHeight,
722
+ overflow: "visible",
723
+ pointerEvents: computedPointerEvents,
724
+ top: isTop ? 0 : void 0,
725
+ bottom: isTop ? void 0 : 0,
726
+ ...(isWeb && !isFront && {
727
+ style: {
728
+ transformOrigin: isTop ? "top center" : "bottom center"
729
+ }
730
+ }),
731
+ enterStyle: ctx.reducedMotion ? {
732
+ opacity: 0
733
+ } : {
734
+ opacity: 0,
735
+ y: isTop ? -80 : 80
736
+ },
737
+ exitStyle: ctx.reducedMotion ? {
738
+ opacity: 0
739
+ } : swipeOut ? {
740
+ opacity: 0,
741
+ y: swipeExitYRef.current ?? stackY,
742
+ scale: stackScale
743
+ } : {
744
+ opacity: 0,
745
+ y: stackY,
746
+ scale: stackScale
747
+ },
748
+ children: /* @__PURE__ */jsx(DragWrapper, {
749
+ animatedStyle,
750
+ gestureHandlers,
751
+ gesture,
752
+ AnimatedView,
753
+ dragRef,
754
+ children: /* @__PURE__ */jsxs(ToastItemFrame, {
755
+ role: "status",
756
+ "aria-live": "polite",
757
+ "aria-atomic": true,
758
+ tabIndex: 0,
759
+ onLayout: handleLayout,
760
+ ...(isWeb && {
761
+ onKeyDown: event => {
762
+ if (event.key === "Escape" && dismissible) {
763
+ const current = event.currentTarget;
764
+ const container = current.closest("[aria-label]");
765
+ if (container) {
766
+ const focusables = container.querySelectorAll('[tabindex="0"]');
767
+ const arr = Array.from(focusables);
768
+ const idx = arr.indexOf(current);
769
+ const next = arr[idx + 1] || arr[idx - 1];
770
+ next?.focus();
771
+ }
772
+ handleClose();
773
+ }
774
+ }
775
+ }),
776
+ ...rest,
777
+ children: [ctx.expanded && gapFillerHeight > 0 && /* @__PURE__ */jsx(View, {
778
+ position: "absolute",
779
+ left: 0,
780
+ right: 0,
781
+ height: gapFillerHeight,
782
+ pointerEvents: "auto",
783
+ ...(isTop ? {
784
+ top: "100%"
785
+ } : {
786
+ bottom: "100%"
787
+ })
788
+ }), /* @__PURE__ */jsx(ToastItemContext.Provider, {
789
+ value: itemContextValue,
790
+ children
791
+ })]
792
+ })
793
+ })
794
+ });
795
+ });
796
+ const ToastTitle = styled(SizableText, {
797
+ name: "ToastTitle",
798
+ variants: {
799
+ unstyled: {
800
+ false: {
801
+ color: "$color",
802
+ fontWeight: "600",
803
+ size: "$4"
804
+ }
805
+ }
806
+ },
807
+ defaultVariants: {
808
+ unstyled: process.env.GUI_HEADLESS === "1"
809
+ }
810
+ });
811
+ const ToastDescription = styled(SizableText, {
812
+ name: "ToastDescription",
813
+ variants: {
814
+ unstyled: {
815
+ false: {
816
+ color: "$color11",
817
+ size: "$2"
818
+ }
819
+ }
820
+ },
821
+ defaultVariants: {
822
+ unstyled: process.env.GUI_HEADLESS === "1"
823
+ }
824
+ });
825
+ const ToastClose = ToastCloseFrame.styleable(function ToastClose2(props, ref) {
826
+ let handleClose;
827
+ try {
828
+ const itemCtx = useToastItemContext();
829
+ handleClose = itemCtx.handleClose;
830
+ } catch {}
831
+ const ctx = useToastContext();
832
+ return /* @__PURE__ */jsx(ToastCloseFrame, {
833
+ ref,
834
+ "aria-label": "Close toast",
835
+ onPress: handleClose,
836
+ ...props,
837
+ children: props.children ?? ctx.icons?.close ?? /* @__PURE__ */jsx(DefaultCloseIcon, {})
838
+ });
839
+ });
840
+ const ToastAction = ToastActionFrame.styleable(function ToastAction2(props, ref) {
841
+ return /* @__PURE__ */jsx(ToastActionFrame, {
842
+ ref,
843
+ ...props
844
+ });
845
+ });
846
+ function ToastIcon(props) {
847
+ const ctx = useToastContext();
848
+ let toast;
849
+ try {
850
+ const itemCtx = useToastItemContext();
851
+ toast = itemCtx.toast;
852
+ } catch {
853
+ return null;
854
+ }
855
+ if (!toast) return null;
856
+ if (toast.icon !== void 0) {
857
+ return /* @__PURE__ */jsx(View, {
858
+ flexShrink: 0,
859
+ marginTop: "$0.5",
860
+ children: toast.icon
861
+ });
862
+ }
863
+ const toastType = toast.type ?? "default";
864
+ const icon = ctx.icons?.[toastType] ?? null;
865
+ if (!icon) return null;
866
+ return /* @__PURE__ */jsx(View, {
867
+ flexShrink: 0,
868
+ marginTop: "$0.5",
869
+ children: icon
870
+ });
871
+ }
872
+ function useToasts() {
873
+ const ctx = useToastContext();
874
+ return {
875
+ toasts: ctx.toasts,
876
+ expanded: ctx.expanded,
877
+ position: ctx.position
878
+ };
879
+ }
880
+ function useToastItem() {
881
+ return useToastItemContext();
882
+ }
883
+ ToastRoot.displayName = "Toast";
884
+ const Toast = withStaticProperties(ToastRoot, {
885
+ Viewport: ToastViewport,
886
+ List: ToastList,
887
+ Item: ToastItemInner,
888
+ Title: ToastTitle,
889
+ Description: ToastDescription,
890
+ Close: ToastClose,
891
+ Action: ToastAction,
892
+ Icon: ToastIcon
893
+ });
894
+ export { Toast, useToastItem, useToasts };
895
+ //# sourceMappingURL=ToastComposable.mjs.map