@zendir/ui 0.5.0 → 0.6.1

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 (391) hide show
  1. package/CHANGELOG.md +419 -386
  2. package/README.md +640 -631
  3. package/dist/_virtual/_rolldown/runtime.js +13 -0
  4. package/dist/index.js +17 -221
  5. package/dist/react/3d/CesiumCaptureSource.d.ts +0 -1
  6. package/dist/react/3d/CesiumCaptureSource.js +364 -283
  7. package/dist/react/3d/CesiumCaptureSource.js.map +1 -1
  8. package/dist/react/3d/ZenSpace3D.d.ts +2 -3
  9. package/dist/react/3d/ZenSpace3D.js +1681 -1237
  10. package/dist/react/3d/ZenSpace3D.js.map +1 -1
  11. package/dist/react/3d/ZenSpace3DCesium.d.ts +0 -1
  12. package/dist/react/3d/ZenSpace3DCesium.js +513 -560
  13. package/dist/react/3d/ZenSpace3DCesium.js.map +1 -1
  14. package/dist/react/3d/ZenSpace3DShaders.js +61 -66
  15. package/dist/react/3d/ZenSpace3DShaders.js.map +1 -1
  16. package/dist/react/3d/ZenSpace3DTypes.d.ts +19 -20
  17. package/dist/react/3d/ZenSpace3DUtils.d.ts +0 -1
  18. package/dist/react/3d/ZenSpace3DUtils.js +37 -24
  19. package/dist/react/3d/ZenSpace3DUtils.js.map +1 -1
  20. package/dist/react/3d/capturePngAnalysis.js +42 -36
  21. package/dist/react/3d/capturePngAnalysis.js.map +1 -1
  22. package/dist/react/3d/index.d.ts +3 -3
  23. package/dist/react/3d/index.js +5 -53
  24. package/dist/react/3d/threeLoader.d.ts +1 -1
  25. package/dist/react/3d/threeLoader.js +23 -18
  26. package/dist/react/3d/threeLoader.js.map +1 -1
  27. package/dist/react/astro/ClassificationBanner.d.ts +2 -3
  28. package/dist/react/astro/ClassificationBanner.js +95 -79
  29. package/dist/react/astro/ClassificationBanner.js.map +1 -1
  30. package/dist/react/astro/GlobalStatusBar.d.ts +0 -1
  31. package/dist/react/astro/GlobalStatusBar.js +157 -163
  32. package/dist/react/astro/GlobalStatusBar.js.map +1 -1
  33. package/dist/react/astro/MissionClock.d.ts +7 -8
  34. package/dist/react/astro/MissionClock.js +377 -400
  35. package/dist/react/astro/MissionClock.js.map +1 -1
  36. package/dist/react/astro/MonitoringIcon.d.ts +1 -2
  37. package/dist/react/astro/MonitoringIcon.js +422 -358
  38. package/dist/react/astro/MonitoringIcon.js.map +1 -1
  39. package/dist/react/astro/Notification.d.ts +1 -2
  40. package/dist/react/astro/Notification.js +229 -126
  41. package/dist/react/astro/Notification.js.map +1 -1
  42. package/dist/react/astro/Progress.d.ts +0 -1
  43. package/dist/react/astro/Progress.js +199 -141
  44. package/dist/react/astro/Progress.js.map +1 -1
  45. package/dist/react/astro/SimulationControls.d.ts +3 -4
  46. package/dist/react/astro/SimulationControls.js +596 -650
  47. package/dist/react/astro/SimulationControls.js.map +1 -1
  48. package/dist/react/astro/StatusIndicator.d.ts +0 -1
  49. package/dist/react/astro/StatusIndicator.js +236 -170
  50. package/dist/react/astro/StatusIndicator.js.map +1 -1
  51. package/dist/react/astro/UnifiedTimeline.d.ts +9 -10
  52. package/dist/react/astro/UnifiedTimeline.js +2345 -2392
  53. package/dist/react/astro/UnifiedTimeline.js.map +1 -1
  54. package/dist/react/astro/index.d.ts +5 -5
  55. package/dist/react/astro/index.js +1 -25
  56. package/dist/react/cards/AccessCard.d.ts +0 -1
  57. package/dist/react/cards/AccessCard.js +471 -405
  58. package/dist/react/cards/AccessCard.js.map +1 -1
  59. package/dist/react/cards/OrbitCard.d.ts +0 -1
  60. package/dist/react/cards/OrbitCard.js +487 -364
  61. package/dist/react/cards/OrbitCard.js.map +1 -1
  62. package/dist/react/cards/SpacecraftCard.d.ts +0 -1
  63. package/dist/react/cards/SpacecraftCard.js +813 -925
  64. package/dist/react/cards/SpacecraftCard.js.map +1 -1
  65. package/dist/react/cards/TelemetryCard.d.ts +0 -1
  66. package/dist/react/cards/TelemetryCard.js +1055 -732
  67. package/dist/react/cards/TelemetryCard.js.map +1 -1
  68. package/dist/react/cards/TelemetryStreamCard.d.ts +0 -1
  69. package/dist/react/cards/TelemetryStreamCard.js +323 -297
  70. package/dist/react/cards/TelemetryStreamCard.js.map +1 -1
  71. package/dist/react/cards/index.d.ts +1 -1
  72. package/dist/react/cards/index.js +1 -8
  73. package/dist/react/charts/GroundTrackMap.d.ts +6 -7
  74. package/dist/react/charts/GroundTrackMap.js +1377 -1256
  75. package/dist/react/charts/GroundTrackMap.js.map +1 -1
  76. package/dist/react/charts/GroundTrackMapLeaflet.d.ts +1 -2
  77. package/dist/react/charts/GroundTrackMapLeaflet.js +1065 -987
  78. package/dist/react/charts/GroundTrackMapLeaflet.js.map +1 -1
  79. package/dist/react/charts/groundTrackMapLeafletTiles.js +34 -25
  80. package/dist/react/charts/groundTrackMapLeafletTiles.js.map +1 -1
  81. package/dist/react/charts/groundTrackMapLeafletUtils.js +70 -61
  82. package/dist/react/charts/groundTrackMapLeafletUtils.js.map +1 -1
  83. package/dist/react/charts/index.d.ts +1 -1
  84. package/dist/react/charts/index.js +7 -100
  85. package/dist/react/charts/unified/AstroChart.d.ts +1 -2
  86. package/dist/react/charts/unified/AstroChart.js +1331 -1411
  87. package/dist/react/charts/unified/AstroChart.js.map +1 -1
  88. package/dist/react/charts/unified/PowerOverviewChart.d.ts +3 -3
  89. package/dist/react/charts/unified/PowerOverviewChart.js +495 -478
  90. package/dist/react/charts/unified/PowerOverviewChart.js.map +1 -1
  91. package/dist/react/charts/unified/domain.d.ts +12 -13
  92. package/dist/react/charts/unified/domain.js +3999 -3145
  93. package/dist/react/charts/unified/domain.js.map +1 -1
  94. package/dist/react/charts/unified/generators.d.ts +3 -4
  95. package/dist/react/charts/unified/generators.js +561 -498
  96. package/dist/react/charts/unified/generators.js.map +1 -1
  97. package/dist/react/charts/unified/index.d.ts +1 -1
  98. package/dist/react/charts/unified/presets.d.ts +14 -15
  99. package/dist/react/charts/unified/presets.js +857 -994
  100. package/dist/react/charts/unified/presets.js.map +1 -1
  101. package/dist/react/charts/unified/sync.d.ts +2 -3
  102. package/dist/react/charts/unified/sync.js +229 -195
  103. package/dist/react/charts/unified/sync.js.map +1 -1
  104. package/dist/react/charts/unified/theme.d.ts +11 -12
  105. package/dist/react/charts/unified/theme.js +606 -642
  106. package/dist/react/charts/unified/theme.js.map +1 -1
  107. package/dist/react/charts/unified/types.d.ts +32 -33
  108. package/dist/react/charts/unified/useChartStream.d.ts +1 -2
  109. package/dist/react/charts/unified/useChartStream.js +203 -216
  110. package/dist/react/charts/unified/useChartStream.js.map +1 -1
  111. package/dist/react/chatgpt/AppCard.d.ts +1 -2
  112. package/dist/react/chatgpt/index.d.ts +7 -7
  113. package/dist/react/chatgpt/index.js +160 -139
  114. package/dist/react/chatgpt/index.js.map +1 -1
  115. package/dist/react/context/CategoryContext.d.ts +0 -1
  116. package/dist/react/context/CategoryContext.js +78 -29
  117. package/dist/react/context/CategoryContext.js.map +1 -1
  118. package/dist/react/context/DisplaySettingsContext.d.ts +1 -2
  119. package/dist/react/context/DisplaySettingsContext.js +205 -156
  120. package/dist/react/context/DisplaySettingsContext.js.map +1 -1
  121. package/dist/react/context/SpatialSelectionContext.d.ts +0 -1
  122. package/dist/react/context/SpatialSelectionContext.js +36 -7
  123. package/dist/react/context/SpatialSelectionContext.js.map +1 -1
  124. package/dist/react/core/data/DataTable.d.ts +3 -4
  125. package/dist/react/core/data/DataTable.js +473 -440
  126. package/dist/react/core/data/DataTable.js.map +1 -1
  127. package/dist/react/core/data/DataValue.d.ts +4 -5
  128. package/dist/react/core/data/DataValue.js +605 -571
  129. package/dist/react/core/data/DataValue.js.map +1 -1
  130. package/dist/react/core/data/propertyConfig.d.ts +1 -2
  131. package/dist/react/core/data/propertyConfig.js +446 -382
  132. package/dist/react/core/data/propertyConfig.js.map +1 -1
  133. package/dist/react/core/display/AstroIcon.d.ts +4 -5
  134. package/dist/react/core/display/AstroIcon.js +339 -429
  135. package/dist/react/core/display/AstroIcon.js.map +1 -1
  136. package/dist/react/core/display/Badge.d.ts +2 -3
  137. package/dist/react/core/display/Badge.js +131 -131
  138. package/dist/react/core/display/Badge.js.map +1 -1
  139. package/dist/react/core/display/CardHeader.d.ts +0 -1
  140. package/dist/react/core/display/CardHeader.js +398 -311
  141. package/dist/react/core/display/CardHeader.js.map +1 -1
  142. package/dist/react/core/display/Container.d.ts +2 -3
  143. package/dist/react/core/display/Container.js +640 -668
  144. package/dist/react/core/display/Container.js.map +1 -1
  145. package/dist/react/core/display/CopyButton.d.ts +1 -2
  146. package/dist/react/core/display/CopyButton.js +158 -101
  147. package/dist/react/core/display/CopyButton.js.map +1 -1
  148. package/dist/react/core/display/GlassCard.d.ts +3 -4
  149. package/dist/react/core/display/GlassCard.js +416 -369
  150. package/dist/react/core/display/GlassCard.js.map +1 -1
  151. package/dist/react/core/display/HeaderIconWithStatus.d.ts +0 -1
  152. package/dist/react/core/display/HeaderIconWithStatus.js +152 -152
  153. package/dist/react/core/display/HeaderIconWithStatus.js.map +1 -1
  154. package/dist/react/core/display/Icon.d.ts +2 -3
  155. package/dist/react/core/display/Icon.js +172 -143
  156. package/dist/react/core/display/Icon.js.map +1 -1
  157. package/dist/react/core/display/Typography.d.ts +24 -25
  158. package/dist/react/core/display/Typography.js +360 -178
  159. package/dist/react/core/display/Typography.js.map +1 -1
  160. package/dist/react/core/feedback/ConfirmDialog.d.ts +1 -2
  161. package/dist/react/core/feedback/ConfirmDialog.js +343 -304
  162. package/dist/react/core/feedback/ConfirmDialog.js.map +1 -1
  163. package/dist/react/core/feedback/Dialog.d.ts +2 -3
  164. package/dist/react/core/feedback/Dialog.js +189 -197
  165. package/dist/react/core/feedback/Dialog.js.map +1 -1
  166. package/dist/react/core/feedback/Toast.d.ts +2 -3
  167. package/dist/react/core/feedback/Toast.js +346 -207
  168. package/dist/react/core/feedback/Toast.js.map +1 -1
  169. package/dist/react/core/index.d.ts +26 -26
  170. package/dist/react/core/index.js +7 -119
  171. package/dist/react/core/inputs/Button.d.ts +2 -3
  172. package/dist/react/core/inputs/Button.js +281 -304
  173. package/dist/react/core/inputs/Button.js.map +1 -1
  174. package/dist/react/core/inputs/Checkbox.d.ts +2 -3
  175. package/dist/react/core/inputs/Checkbox.js +139 -127
  176. package/dist/react/core/inputs/Checkbox.js.map +1 -1
  177. package/dist/react/core/inputs/Input.d.ts +3 -4
  178. package/dist/react/core/inputs/Input.js +277 -285
  179. package/dist/react/core/inputs/Input.js.map +1 -1
  180. package/dist/react/core/inputs/LimitsBar.d.ts +1 -2
  181. package/dist/react/core/inputs/LimitsBar.js +271 -196
  182. package/dist/react/core/inputs/LimitsBar.js.map +1 -1
  183. package/dist/react/core/inputs/NumberInput.d.ts +2 -3
  184. package/dist/react/core/inputs/NumberInput.js +531 -503
  185. package/dist/react/core/inputs/NumberInput.js.map +1 -1
  186. package/dist/react/core/inputs/PinInput.d.ts +2 -3
  187. package/dist/react/core/inputs/PinInput.js +224 -207
  188. package/dist/react/core/inputs/PinInput.js.map +1 -1
  189. package/dist/react/core/inputs/Select.d.ts +1 -2
  190. package/dist/react/core/inputs/Select.js +298 -299
  191. package/dist/react/core/inputs/Select.js.map +1 -1
  192. package/dist/react/core/inputs/Toggle.d.ts +2 -3
  193. package/dist/react/core/inputs/Toggle.js +142 -148
  194. package/dist/react/core/inputs/Toggle.js.map +1 -1
  195. package/dist/react/core/layout/Box.d.ts +3 -4
  196. package/dist/react/core/layout/Box.js +118 -122
  197. package/dist/react/core/layout/Box.js.map +1 -1
  198. package/dist/react/core/layout/Center.d.ts +0 -1
  199. package/dist/react/core/layout/Center.js +45 -32
  200. package/dist/react/core/layout/Center.js.map +1 -1
  201. package/dist/react/core/layout/Divider.d.ts +1 -2
  202. package/dist/react/core/layout/Divider.js +112 -106
  203. package/dist/react/core/layout/Divider.js.map +1 -1
  204. package/dist/react/core/layout/Flex.d.ts +4 -5
  205. package/dist/react/core/layout/Flex.js +120 -124
  206. package/dist/react/core/layout/Flex.js.map +1 -1
  207. package/dist/react/core/layout/Grid.d.ts +5 -6
  208. package/dist/react/core/layout/Grid.js +131 -138
  209. package/dist/react/core/layout/Grid.js.map +1 -1
  210. package/dist/react/core/layout/Spacer.d.ts +0 -1
  211. package/dist/react/core/layout/Spacer.js +36 -29
  212. package/dist/react/core/layout/Spacer.js.map +1 -1
  213. package/dist/react/core/layout/Stack.d.ts +4 -5
  214. package/dist/react/core/layout/Stack.js +127 -70
  215. package/dist/react/core/layout/Stack.js.map +1 -1
  216. package/dist/react/core/layout/responsive.d.ts +1 -2
  217. package/dist/react/core/layout/responsive.js +25 -19
  218. package/dist/react/core/layout/responsive.js.map +1 -1
  219. package/dist/react/core/layout/useBreakpoint.d.ts +1 -1
  220. package/dist/react/core/layout/useBreakpoint.js +119 -66
  221. package/dist/react/core/layout/useBreakpoint.js.map +1 -1
  222. package/dist/react/core/navigation/AppBar.d.ts +1 -2
  223. package/dist/react/core/navigation/AppBar.js +827 -805
  224. package/dist/react/core/navigation/AppBar.js.map +1 -1
  225. package/dist/react/core/navigation/Pagination.d.ts +2 -3
  226. package/dist/react/core/navigation/Pagination.js +207 -187
  227. package/dist/react/core/navigation/Pagination.js.map +1 -1
  228. package/dist/react/core/navigation/SideNav.d.ts +5 -6
  229. package/dist/react/core/navigation/SideNav.js +855 -629
  230. package/dist/react/core/navigation/SideNav.js.map +1 -1
  231. package/dist/react/core/navigation/Tabs.d.ts +0 -1
  232. package/dist/react/core/navigation/Tabs.js +113 -119
  233. package/dist/react/core/navigation/Tabs.js.map +1 -1
  234. package/dist/react/core/overlays/Popover.d.ts +2 -3
  235. package/dist/react/core/overlays/Popover.js +303 -282
  236. package/dist/react/core/overlays/Popover.js.map +1 -1
  237. package/dist/react/core/overlays/SidePanel.d.ts +1 -2
  238. package/dist/react/core/overlays/SidePanel.js +217 -212
  239. package/dist/react/core/overlays/SidePanel.js.map +1 -1
  240. package/dist/react/core/overlays/Tooltip.d.ts +1 -2
  241. package/dist/react/core/overlays/Tooltip.js +170 -176
  242. package/dist/react/core/overlays/Tooltip.js.map +1 -1
  243. package/dist/react/core/widgets/ActivityPlanner.d.ts +0 -1
  244. package/dist/react/core/widgets/ActivityPlanner.js +855 -517
  245. package/dist/react/core/widgets/ActivityPlanner.js.map +1 -1
  246. package/dist/react/core/widgets/Capture.d.ts +2 -3
  247. package/dist/react/core/widgets/Capture.js +965 -779
  248. package/dist/react/core/widgets/Capture.js.map +1 -1
  249. package/dist/react/core/widgets/ChatPanel.d.ts +16 -17
  250. package/dist/react/core/widgets/ChatPanel.js +1734 -1034
  251. package/dist/react/core/widgets/ChatPanel.js.map +1 -1
  252. package/dist/react/core/widgets/ColorPickerPanel.d.ts +0 -1
  253. package/dist/react/core/widgets/ColorPickerPanel.js +298 -287
  254. package/dist/react/core/widgets/ColorPickerPanel.js.map +1 -1
  255. package/dist/react/core/widgets/CommandBuilder.d.ts +2 -3
  256. package/dist/react/core/widgets/CommandBuilder.js +624 -516
  257. package/dist/react/core/widgets/CommandBuilder.js.map +1 -1
  258. package/dist/react/core/widgets/ConnectionForm.d.ts +2 -3
  259. package/dist/react/core/widgets/ConnectionForm.js +528 -492
  260. package/dist/react/core/widgets/ConnectionForm.js.map +1 -1
  261. package/dist/react/core/widgets/FileExplorer.d.ts +3 -4
  262. package/dist/react/core/widgets/FileExplorer.js +617 -505
  263. package/dist/react/core/widgets/FileExplorer.js.map +1 -1
  264. package/dist/react/core/widgets/HexViewer.d.ts +2 -3
  265. package/dist/react/core/widgets/HexViewer.js +1353 -1091
  266. package/dist/react/core/widgets/HexViewer.js.map +1 -1
  267. package/dist/react/core/widgets/ImageFrame.d.ts +1 -2
  268. package/dist/react/core/widgets/ImageFrame.js +230 -193
  269. package/dist/react/core/widgets/ImageFrame.js.map +1 -1
  270. package/dist/react/core/widgets/ImageGallery.d.ts +2 -1
  271. package/dist/react/core/widgets/ImageGallery.js +380 -314
  272. package/dist/react/core/widgets/ImageGallery.js.map +1 -1
  273. package/dist/react/core/widgets/ImagePanel.d.ts +0 -1
  274. package/dist/react/core/widgets/ImagePanel.js +110 -101
  275. package/dist/react/core/widgets/ImagePanel.js.map +1 -1
  276. package/dist/react/core/widgets/LogViewer.d.ts +2 -3
  277. package/dist/react/core/widgets/LogViewer.js +711 -607
  278. package/dist/react/core/widgets/LogViewer.js.map +1 -1
  279. package/dist/react/core/widgets/MessageStream.d.ts +3 -4
  280. package/dist/react/core/widgets/MessageStream.js +514 -444
  281. package/dist/react/core/widgets/MessageStream.js.map +1 -1
  282. package/dist/react/core/widgets/MissionCalendar.d.ts +3 -4
  283. package/dist/react/core/widgets/MissionCalendar.js +1488 -1020
  284. package/dist/react/core/widgets/MissionCalendar.js.map +1 -1
  285. package/dist/react/core/widgets/PacketViewer.d.ts +2 -3
  286. package/dist/react/core/widgets/PacketViewer.js +550 -421
  287. package/dist/react/core/widgets/PacketViewer.js.map +1 -1
  288. package/dist/react/core/widgets/capture-placeholder.png.js +6 -5
  289. package/dist/react/core/widgets/capture-placeholder.png.js.map +1 -1
  290. package/dist/react/hooks/index.d.ts +5 -5
  291. package/dist/react/hooks/useAccessWindows.d.ts +0 -1
  292. package/dist/react/hooks/useCompactMode.d.ts +1 -1
  293. package/dist/react/hooks/useCompactMode.js +104 -58
  294. package/dist/react/hooks/useCompactMode.js.map +1 -1
  295. package/dist/react/hooks/useGroundTrackHistory.d.ts +0 -1
  296. package/dist/react/hooks/useSimulationScene.d.ts +1 -2
  297. package/dist/react/hooks/useSimulationScene.js +481 -374
  298. package/dist/react/hooks/useSimulationScene.js.map +1 -1
  299. package/dist/react/index.d.ts +3 -3
  300. package/dist/react/panels/LayerControlPanel.d.ts +1 -2
  301. package/dist/react/panels/LayerControlPanel.js +223 -180
  302. package/dist/react/panels/LayerControlPanel.js.map +1 -1
  303. package/dist/react/panels/ObjectInventoryPanel.d.ts +2 -3
  304. package/dist/react/panels/ObjectInventoryPanel.js +315 -250
  305. package/dist/react/panels/ObjectInventoryPanel.js.map +1 -1
  306. package/dist/react/panels/index.d.ts +1 -1
  307. package/dist/react/panels/index.js +1 -6
  308. package/dist/react/shared/ErrorBoundary.d.ts +1 -2
  309. package/dist/react/shared/ErrorBoundary.js +170 -139
  310. package/dist/react/shared/ErrorBoundary.js.map +1 -1
  311. package/dist/react/shared/Skeleton.d.ts +1 -2
  312. package/dist/react/shared/Skeleton.js +300 -301
  313. package/dist/react/shared/Skeleton.js.map +1 -1
  314. package/dist/react/theme/ThemeProvider.d.ts +2 -321
  315. package/dist/react/theme/ThemeProvider.js +313 -939
  316. package/dist/react/theme/ThemeProvider.js.map +1 -1
  317. package/dist/react/theme/cardAccent.d.ts +1 -2
  318. package/dist/react/theme/cardAccent.js +196 -126
  319. package/dist/react/theme/cardAccent.js.map +1 -1
  320. package/dist/react/theme/config.d.ts +0 -1
  321. package/dist/react/theme/config.js +47 -25
  322. package/dist/react/theme/config.js.map +1 -1
  323. package/dist/react/theme/index.d.ts +2 -2
  324. package/dist/react/theme/index.js +1 -16
  325. package/dist/react/theme/types.d.ts +332 -0
  326. package/dist/react/theme/types.js +39 -0
  327. package/dist/react/theme/types.js.map +1 -0
  328. package/dist/react/types.d.ts +8 -8
  329. package/dist/react/types.js +147 -47
  330. package/dist/react/types.js.map +1 -1
  331. package/dist/react/utils/categoryPalette.d.ts +0 -1
  332. package/dist/react/utils/categoryPalette.js +91 -102
  333. package/dist/react/utils/categoryPalette.js.map +1 -1
  334. package/dist/react/utils/index.d.ts +5 -5
  335. package/dist/react/utils/index.js +457 -371
  336. package/dist/react/utils/index.js.map +1 -1
  337. package/dist/react/visualizations/EclipseTimerCard.d.ts +0 -1
  338. package/dist/react/visualizations/LinkBudgetCard.d.ts +0 -1
  339. package/dist/react/visualizations/NavBallCard.d.ts +0 -1
  340. package/dist/react/visualizations/PropulsionCard.d.ts +1 -2
  341. package/dist/react/visualizations/SensorFootprintCard.d.ts +1 -2
  342. package/dist/react/visualizations/ThermalHeatmapCard.d.ts +0 -1
  343. package/dist/react/visualizations/index.d.ts +3 -3
  344. package/dist/react.d.ts +2 -1
  345. package/dist/react.js +17 -221
  346. package/dist/shaders/atmosphere.frag.js +6 -5
  347. package/dist/shaders/atmosphere.frag.js.map +1 -1
  348. package/dist/shaders/atmosphere.vert.js +6 -5
  349. package/dist/shaders/atmosphere.vert.js.map +1 -1
  350. package/dist/shaders/stars.frag.js +6 -5
  351. package/dist/shaders/stars.frag.js.map +1 -1
  352. package/dist/shaders/stars.vert.js +6 -5
  353. package/dist/shaders/stars.vert.js.map +1 -1
  354. package/dist/style.css +26 -3
  355. package/dist/tokens/core.d.ts +159 -0
  356. package/dist/tokens/core.js +144 -0
  357. package/dist/tokens/core.js.map +1 -0
  358. package/dist/tokens/css-vars.d.ts +213 -2
  359. package/dist/tokens/css-vars.js +590 -227
  360. package/dist/tokens/css-vars.js.map +1 -1
  361. package/dist/tokens/index.d.ts +31 -228
  362. package/dist/tokens/index.js +281 -366
  363. package/dist/tokens/index.js.map +1 -1
  364. package/dist/tokens/palettes/astro.d.ts +129 -0
  365. package/dist/tokens/palettes/astro.js +112 -0
  366. package/dist/tokens/palettes/astro.js.map +1 -0
  367. package/dist/tokens/palettes/index.d.ts +288 -0
  368. package/dist/tokens/palettes/index.js +35 -0
  369. package/dist/tokens/palettes/index.js.map +1 -0
  370. package/dist/tokens/palettes/tailwind.d.ts +324 -0
  371. package/dist/tokens/palettes/tailwind.js +201 -0
  372. package/dist/tokens/palettes/tailwind.js.map +1 -0
  373. package/dist/tokens/palettes/zendir.d.ts +126 -0
  374. package/dist/tokens/palettes/zendir.js +92 -0
  375. package/dist/tokens/palettes/zendir.js.map +1 -0
  376. package/dist/tokens/themes.d.ts +30 -0
  377. package/dist/tokens/themes.js +704 -0
  378. package/dist/tokens/themes.js.map +1 -0
  379. package/dist/tokens/tokens.css +533 -155
  380. package/dist/types/index.d.ts +2 -2
  381. package/package.json +310 -313
  382. package/dist/index.js.map +0 -1
  383. package/dist/react/3d/index.js.map +0 -1
  384. package/dist/react/astro/index.js.map +0 -1
  385. package/dist/react/cards/index.js.map +0 -1
  386. package/dist/react/charts/index.js.map +0 -1
  387. package/dist/react/core/index.js.map +0 -1
  388. package/dist/react/panels/index.js.map +0 -1
  389. package/dist/react/theme/astro-tokens.d.ts +0 -153
  390. package/dist/react/theme/index.js.map +0 -1
  391. package/dist/react.js.map +0 -1
@@ -1,74 +1,131 @@
1
- import { jsx, jsxs } from "react/jsx-runtime";
2
- import React, { memo, forwardRef } from "react";
3
1
  import { useTheme } from "../../theme/ThemeProvider.js";
4
2
  import { useBreakpoint } from "./useBreakpoint.js";
5
3
  import { resolveResponsiveSpacing } from "./responsive.js";
6
- const Stack = memo(forwardRef(function Stack2({
7
- as: Component = "div",
8
- direction = "column",
9
- spacing = "md",
10
- align,
11
- justify,
12
- wrap,
13
- fullWidth = false,
14
- fullHeight = false,
15
- divider = false,
16
- style,
17
- children,
18
- ...rest
19
- }, ref) {
20
- const { tokens } = useTheme();
21
- const { breakpoint } = useBreakpoint();
22
- const resolvedSpacing = resolveResponsiveSpacing(spacing, breakpoint, tokens);
23
- const resolvedDirection = Array.isArray(direction) ? direction[Math.min(["base", "sm", "md", "lg", "xl", "xxl"].indexOf(breakpoint), direction.length - 1)] ?? direction[direction.length - 1] : direction;
24
- const isVertical = resolvedDirection === "column" || resolvedDirection === "column-reverse";
25
- const computedStyle = {
26
- display: "flex",
27
- flexDirection: resolvedDirection,
28
- ...divider || !resolvedSpacing ? {} : { gap: resolvedSpacing },
29
- alignItems: align,
30
- justifyContent: justify,
31
- flexWrap: wrap,
32
- ...fullWidth ? { width: "100%" } : {},
33
- ...fullHeight ? { height: "100%" } : {},
34
- ...style
35
- };
36
- if (divider) {
37
- const items = React.Children.toArray(children).filter(Boolean);
38
- const dividerStyle = isVertical ? {
39
- width: "100%",
40
- height: "1px",
41
- backgroundColor: tokens.colors.border.muted,
42
- flexShrink: 0,
43
- margin: `${resolvedSpacing} 0`
44
- } : {
45
- height: "100%",
46
- width: "1px",
47
- backgroundColor: tokens.colors.border.muted,
48
- flexShrink: 0,
49
- alignSelf: "stretch",
50
- margin: `0 ${resolvedSpacing}`
51
- };
52
- return /* @__PURE__ */ jsx(Component, { ref, style: computedStyle, ...rest, children: items.map((child, index) => /* @__PURE__ */ jsxs(React.Fragment, { children: [
53
- child,
54
- index < items.length - 1 && /* @__PURE__ */ jsx("div", { style: dividerStyle, "aria-hidden": "true" })
55
- ] }, index)) });
56
- }
57
- return /* @__PURE__ */ jsx(Component, { ref, style: computedStyle, ...rest, children });
4
+ import React, { forwardRef, memo } from "react";
5
+ import { jsx, jsxs } from "react/jsx-runtime";
6
+ //#region src/react/core/layout/Stack.tsx
7
+ /**
8
+ * @zendir/ui - Stack Layout Primitives
9
+ *
10
+ * Consistent spacing stacks — the most common layout pattern in operator dashboards.
11
+ * Stack, HStack, and VStack provide directional flex with uniform gaps.
12
+ *
13
+ * @example
14
+ * ```tsx
15
+ * // Vertical stack (default)
16
+ * <Stack spacing="md">
17
+ * <TelemetryCard />
18
+ * <LinkBudgetCard />
19
+ * <SpacecraftCard />
20
+ * </Stack>
21
+ *
22
+ * // Horizontal stack
23
+ * <HStack spacing="sm" align="center">
24
+ * <StatusIndicator status="normal" />
25
+ * <Body1>Connected</Body1>
26
+ * </HStack>
27
+ *
28
+ * // Responsive spacing
29
+ * <VStack spacing={['sm', 'md', 'lg']}>
30
+ * <Content />
31
+ * </VStack>
32
+ * ```
33
+ */
34
+ var Stack = memo(forwardRef(function Stack({ as: Component = "div", direction = "column", spacing = "md", align, justify, wrap, fullWidth = false, fullHeight = false, divider = false, style, children, ...rest }, ref) {
35
+ const { tokens } = useTheme();
36
+ const { breakpoint } = useBreakpoint();
37
+ const resolvedSpacing = resolveResponsiveSpacing(spacing, breakpoint, tokens);
38
+ const resolvedDirection = Array.isArray(direction) ? direction[Math.min([
39
+ "base",
40
+ "sm",
41
+ "md",
42
+ "lg",
43
+ "xl",
44
+ "xxl"
45
+ ].indexOf(breakpoint), direction.length - 1)] ?? direction[direction.length - 1] : direction;
46
+ const isVertical = resolvedDirection === "column" || resolvedDirection === "column-reverse";
47
+ const computedStyle = {
48
+ display: "flex",
49
+ flexDirection: resolvedDirection,
50
+ ...divider || !resolvedSpacing ? {} : { gap: resolvedSpacing },
51
+ alignItems: align,
52
+ justifyContent: justify,
53
+ flexWrap: wrap,
54
+ ...fullWidth ? { width: "100%" } : {},
55
+ ...fullHeight ? { height: "100%" } : {},
56
+ ...style
57
+ };
58
+ if (divider) {
59
+ const items = React.Children.toArray(children).filter(Boolean);
60
+ const dividerStyle = isVertical ? {
61
+ width: "100%",
62
+ height: "1px",
63
+ backgroundColor: tokens.colors.border.muted,
64
+ flexShrink: 0,
65
+ margin: `${resolvedSpacing} 0`
66
+ } : {
67
+ height: "100%",
68
+ width: "1px",
69
+ backgroundColor: tokens.colors.border.muted,
70
+ flexShrink: 0,
71
+ alignSelf: "stretch",
72
+ margin: `0 ${resolvedSpacing}`
73
+ };
74
+ return /* @__PURE__ */ jsx(Component, {
75
+ ref,
76
+ style: computedStyle,
77
+ ...rest,
78
+ children: items.map((child, index) => /* @__PURE__ */ jsxs(React.Fragment, { children: [child, index < items.length - 1 && /* @__PURE__ */ jsx("div", {
79
+ style: dividerStyle,
80
+ "aria-hidden": "true"
81
+ })] }, index))
82
+ });
83
+ }
84
+ return /* @__PURE__ */ jsx(Component, {
85
+ ref,
86
+ style: computedStyle,
87
+ ...rest,
88
+ children
89
+ });
90
+ }));
91
+ /**
92
+ * Horizontal Stack — `<Stack direction="row">` shorthand.
93
+ *
94
+ * @example
95
+ * ```tsx
96
+ * <HStack spacing="sm" align="center">
97
+ * <Icon name="satellite" />
98
+ * <Body1>SAT-1</Body1>
99
+ * <Badge status="normal">Nominal</Badge>
100
+ * </HStack>
101
+ * ```
102
+ */
103
+ var HStack = memo(forwardRef(function HStack(props, ref) {
104
+ return /* @__PURE__ */ jsx(Stack, {
105
+ ref,
106
+ direction: "row",
107
+ ...props
108
+ });
109
+ }));
110
+ /**
111
+ * Vertical Stack — `<Stack direction="column">` shorthand.
112
+ *
113
+ * @example
114
+ * ```tsx
115
+ * <VStack spacing="md">
116
+ * <TelemetryCard />
117
+ * <LinkBudgetCard />
118
+ * </VStack>
119
+ * ```
120
+ */
121
+ var VStack = memo(forwardRef(function VStack(props, ref) {
122
+ return /* @__PURE__ */ jsx(Stack, {
123
+ ref,
124
+ direction: "column",
125
+ ...props
126
+ });
58
127
  }));
59
- const HStack = memo(forwardRef(
60
- function HStack2(props, ref) {
61
- return /* @__PURE__ */ jsx(Stack, { ref, direction: "row", ...props });
62
- }
63
- ));
64
- const VStack = memo(forwardRef(
65
- function VStack2(props, ref) {
66
- return /* @__PURE__ */ jsx(Stack, { ref, direction: "column", ...props });
67
- }
68
- ));
69
- export {
70
- HStack,
71
- Stack,
72
- VStack
73
- };
74
- //# sourceMappingURL=Stack.js.map
128
+ //#endregion
129
+ export { HStack, Stack, Stack as default, VStack };
130
+
131
+ //# sourceMappingURL=Stack.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"Stack.js","sources":["../../../../src/react/core/layout/Stack.tsx"],"sourcesContent":["/**\r\n * @zendir/ui - Stack Layout Primitives\r\n * \r\n * Consistent spacing stacks — the most common layout pattern in operator dashboards.\r\n * Stack, HStack, and VStack provide directional flex with uniform gaps.\r\n * \r\n * @example\r\n * ```tsx\r\n * // Vertical stack (default)\r\n * <Stack spacing=\"md\">\r\n * <TelemetryCard />\r\n * <LinkBudgetCard />\r\n * <SpacecraftCard />\r\n * </Stack>\r\n * \r\n * // Horizontal stack\r\n * <HStack spacing=\"sm\" align=\"center\">\r\n * <StatusIndicator status=\"normal\" />\r\n * <Body1>Connected</Body1>\r\n * </HStack>\r\n * \r\n * // Responsive spacing\r\n * <VStack spacing={['sm', 'md', 'lg']}>\r\n * <Content />\r\n * </VStack>\r\n * ```\r\n */\r\n\r\nimport React, { memo, forwardRef } from 'react';\r\nimport { useTheme } from '../../theme';\r\nimport { useBreakpoint } from './useBreakpoint';\r\nimport { resolveResponsiveSpacing } from './responsive';\r\nimport type { ResponsiveValue } from './useBreakpoint';\r\nimport type { SpacingToken } from './responsive';\r\n\r\ntype SpacingInput = SpacingToken | string | number;\r\n\r\nexport interface StackProps extends React.HTMLAttributes<HTMLDivElement> {\r\n /** Element type to render */\r\n as?: React.ElementType;\r\n /** Stack direction */\r\n direction?: ResponsiveValue<'row' | 'column' | 'row-reverse' | 'column-reverse'>;\r\n /** Space between children (spacing token, px, or CSS string) */\r\n spacing?: ResponsiveValue<SpacingInput>;\r\n /** Align items (cross-axis) */\r\n align?: 'flex-start' | 'flex-end' | 'center' | 'baseline' | 'stretch';\r\n /** Justify content (main-axis) */\r\n justify?: 'flex-start' | 'flex-end' | 'center' | 'space-between' | 'space-around' | 'space-evenly';\r\n /** Flex wrap */\r\n wrap?: 'nowrap' | 'wrap' | 'wrap-reverse';\r\n /** Full width */\r\n fullWidth?: boolean;\r\n /** Full height */\r\n fullHeight?: boolean;\r\n /** Divider between items — renders a themed line */\r\n divider?: boolean;\r\n /** Children */\r\n children?: React.ReactNode;\r\n}\r\n\r\nexport const Stack = memo(forwardRef<HTMLDivElement, StackProps>(function Stack(\r\n {\r\n as: Component = 'div',\r\n direction = 'column',\r\n spacing = 'md',\r\n align,\r\n justify,\r\n wrap,\r\n fullWidth = false,\r\n fullHeight = false,\r\n divider = false,\r\n style,\r\n children,\r\n ...rest\r\n },\r\n ref\r\n): React.ReactElement {\r\n const { tokens } = useTheme();\r\n const { breakpoint } = useBreakpoint();\r\n \r\n const resolvedSpacing = resolveResponsiveSpacing(spacing, breakpoint, tokens);\r\n const resolvedDirection = Array.isArray(direction)\r\n ? (direction[Math.min(['base', 'sm', 'md', 'lg', 'xl', 'xxl'].indexOf(breakpoint), direction.length - 1)] ?? direction[direction.length - 1])\r\n : direction;\r\n const isVertical = resolvedDirection === 'column' || resolvedDirection === 'column-reverse';\r\n \r\n const computedStyle: React.CSSProperties = {\r\n display: 'flex',\r\n flexDirection: resolvedDirection as 'row' | 'column' | 'row-reverse' | 'column-reverse',\r\n ...(divider || !resolvedSpacing ? {} : { gap: resolvedSpacing }),\r\n alignItems: align,\r\n justifyContent: justify,\r\n flexWrap: wrap,\r\n ...(fullWidth ? { width: '100%' } : {}),\r\n ...(fullHeight ? { height: '100%' } : {}),\r\n ...style,\r\n };\r\n \r\n // If divider is enabled, interleave divider elements\r\n if (divider) {\r\n const items = React.Children.toArray(children).filter(Boolean);\r\n const dividerStyle: React.CSSProperties = isVertical\r\n ? {\r\n width: '100%',\r\n height: '1px',\r\n backgroundColor: tokens.colors.border.muted,\r\n flexShrink: 0,\r\n margin: `${resolvedSpacing} 0`,\r\n }\r\n : {\r\n height: '100%',\r\n width: '1px',\r\n backgroundColor: tokens.colors.border.muted,\r\n flexShrink: 0,\r\n alignSelf: 'stretch',\r\n margin: `0 ${resolvedSpacing}`,\r\n };\r\n \r\n return (\r\n <Component ref={ref} style={computedStyle} {...rest}>\r\n {items.map((child, index) => (\r\n <React.Fragment key={index}>\r\n {child}\r\n {index < items.length - 1 && <div style={dividerStyle} aria-hidden=\"true\" />}\r\n </React.Fragment>\r\n ))}\r\n </Component>\r\n );\r\n }\r\n \r\n return (\r\n <Component ref={ref} style={computedStyle} {...rest}>\r\n {children}\r\n </Component>\r\n );\r\n}));\r\n\r\n/**\r\n * Horizontal Stack — `<Stack direction=\"row\">` shorthand.\r\n * \r\n * @example\r\n * ```tsx\r\n * <HStack spacing=\"sm\" align=\"center\">\r\n * <Icon name=\"satellite\" />\r\n * <Body1>SAT-1</Body1>\r\n * <Badge status=\"normal\">Nominal</Badge>\r\n * </HStack>\r\n * ```\r\n */\r\nexport const HStack = memo(forwardRef<HTMLDivElement, Omit<StackProps, 'direction'>>(\r\n function HStack(props, ref) {\r\n return <Stack ref={ref} direction=\"row\" {...props} />;\r\n }\r\n));\r\n\r\n/**\r\n * Vertical Stack — `<Stack direction=\"column\">` shorthand.\r\n * \r\n * @example\r\n * ```tsx\r\n * <VStack spacing=\"md\">\r\n * <TelemetryCard />\r\n * <LinkBudgetCard />\r\n * </VStack>\r\n * ```\r\n */\r\nexport const VStack = memo(forwardRef<HTMLDivElement, Omit<StackProps, 'direction'>>(\r\n function VStack(props, ref) {\r\n return <Stack ref={ref} direction=\"column\" {...props} />;\r\n }\r\n));\r\n\r\nexport default Stack;\r\n"],"names":["Stack","HStack","VStack"],"mappings":";;;;;AA4DO,MAAM,QAAQ,KAAK,WAAuC,SAASA,OACxE;AAAA,EACE,IAAI,YAAY;AAAA,EAChB,YAAY;AAAA,EACZ,UAAU;AAAA,EACV;AAAA,EACA;AAAA,EACA;AAAA,EACA,YAAY;AAAA,EACZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV;AAAA,EACA;AAAA,EACA,GAAG;AACL,GACA,KACoB;AACpB,QAAM,EAAE,OAAA,IAAW,SAAA;AACnB,QAAM,EAAE,WAAA,IAAe,cAAA;AAEvB,QAAM,kBAAkB,yBAAyB,SAAS,YAAY,MAAM;AAC5E,QAAM,oBAAoB,MAAM,QAAQ,SAAS,IAC5C,UAAU,KAAK,IAAI,CAAC,QAAQ,MAAM,MAAM,MAAM,MAAM,KAAK,EAAE,QAAQ,UAAU,GAAG,UAAU,SAAS,CAAC,CAAC,KAAK,UAAU,UAAU,SAAS,CAAC,IACzI;AACJ,QAAM,aAAa,sBAAsB,YAAY,sBAAsB;AAE3E,QAAM,gBAAqC;AAAA,IACzC,SAAS;AAAA,IACT,eAAe;AAAA,IACf,GAAI,WAAW,CAAC,kBAAkB,CAAA,IAAK,EAAE,KAAK,gBAAA;AAAA,IAC9C,YAAY;AAAA,IACZ,gBAAgB;AAAA,IAChB,UAAU;AAAA,IACV,GAAI,YAAY,EAAE,OAAO,OAAA,IAAW,CAAA;AAAA,IACpC,GAAI,aAAa,EAAE,QAAQ,OAAA,IAAW,CAAA;AAAA,IACtC,GAAG;AAAA,EAAA;AAIL,MAAI,SAAS;AACX,UAAM,QAAQ,MAAM,SAAS,QAAQ,QAAQ,EAAE,OAAO,OAAO;AAC7D,UAAM,eAAoC,aACtC;AAAA,MACE,OAAO;AAAA,MACP,QAAQ;AAAA,MACR,iBAAiB,OAAO,OAAO,OAAO;AAAA,MACtC,YAAY;AAAA,MACZ,QAAQ,GAAG,eAAe;AAAA,IAAA,IAE5B;AAAA,MACE,QAAQ;AAAA,MACR,OAAO;AAAA,MACP,iBAAiB,OAAO,OAAO,OAAO;AAAA,MACtC,YAAY;AAAA,MACZ,WAAW;AAAA,MACX,QAAQ,KAAK,eAAe;AAAA,IAAA;AAGlC,WACE,oBAAC,WAAA,EAAU,KAAU,OAAO,eAAgB,GAAG,MAC5C,UAAA,MAAM,IAAI,CAAC,OAAO,UACjB,qBAAC,MAAM,UAAN,EACE,UAAA;AAAA,MAAA;AAAA,MACA,QAAQ,MAAM,SAAS,yBAAM,OAAA,EAAI,OAAO,cAAc,eAAY,OAAA,CAAO;AAAA,IAAA,KAFvD,KAGrB,CACD,GACH;AAAA,EAEJ;AAEA,6BACG,WAAA,EAAU,KAAU,OAAO,eAAgB,GAAG,MAC5C,UACH;AAEJ,CAAC,CAAC;AAcK,MAAM,SAAS,KAAK;AAAA,EACzB,SAASC,QAAO,OAAO,KAAK;AAC1B,+BAAQ,OAAA,EAAM,KAAU,WAAU,OAAO,GAAG,OAAO;AAAA,EACrD;AACF,CAAC;AAaM,MAAM,SAAS,KAAK;AAAA,EACzB,SAASC,QAAO,OAAO,KAAK;AAC1B,+BAAQ,OAAA,EAAM,KAAU,WAAU,UAAU,GAAG,OAAO;AAAA,EACxD;AACF,CAAC;"}
1
+ {"version":3,"file":"Stack.js","names":[],"sources":["../../../../src/react/core/layout/Stack.tsx"],"sourcesContent":["/**\r\n * @zendir/ui - Stack Layout Primitives\r\n *\r\n * Consistent spacing stacks — the most common layout pattern in operator dashboards.\r\n * Stack, HStack, and VStack provide directional flex with uniform gaps.\r\n *\r\n * @example\r\n * ```tsx\r\n * // Vertical stack (default)\r\n * <Stack spacing=\"md\">\r\n * <TelemetryCard />\r\n * <LinkBudgetCard />\r\n * <SpacecraftCard />\r\n * </Stack>\r\n *\r\n * // Horizontal stack\r\n * <HStack spacing=\"sm\" align=\"center\">\r\n * <StatusIndicator status=\"normal\" />\r\n * <Body1>Connected</Body1>\r\n * </HStack>\r\n *\r\n * // Responsive spacing\r\n * <VStack spacing={['sm', 'md', 'lg']}>\r\n * <Content />\r\n * </VStack>\r\n * ```\r\n */\r\n\r\nimport React, { memo, forwardRef } from \"react\";\r\nimport { useTheme } from \"../../theme\";\r\nimport { useBreakpoint } from \"./useBreakpoint\";\r\nimport { resolveResponsiveSpacing } from \"./responsive\";\r\nimport type { ResponsiveValue } from \"./useBreakpoint\";\r\nimport type { SpacingToken } from \"./responsive\";\r\n\r\ntype SpacingInput = SpacingToken | string | number;\r\n\r\nexport interface StackProps extends React.HTMLAttributes<HTMLDivElement> {\r\n /** Element type to render */\r\n as?: React.ElementType;\r\n /** Stack direction */\r\n direction?: ResponsiveValue<\r\n \"row\" | \"column\" | \"row-reverse\" | \"column-reverse\"\r\n >;\r\n /** Space between children (spacing token, px, or CSS string) */\r\n spacing?: ResponsiveValue<SpacingInput>;\r\n /** Align items (cross-axis) */\r\n align?: \"flex-start\" | \"flex-end\" | \"center\" | \"baseline\" | \"stretch\";\r\n /** Justify content (main-axis) */\r\n justify?:\r\n | \"flex-start\"\r\n | \"flex-end\"\r\n | \"center\"\r\n | \"space-between\"\r\n | \"space-around\"\r\n | \"space-evenly\";\r\n /** Flex wrap */\r\n wrap?: \"nowrap\" | \"wrap\" | \"wrap-reverse\";\r\n /** Full width */\r\n fullWidth?: boolean;\r\n /** Full height */\r\n fullHeight?: boolean;\r\n /** Divider between items — renders a themed line */\r\n divider?: boolean;\r\n /** Children */\r\n children?: React.ReactNode;\r\n}\r\n\r\nexport const Stack = memo(\r\n forwardRef<HTMLDivElement, StackProps>(function Stack(\r\n {\r\n as: Component = \"div\",\r\n direction = \"column\",\r\n spacing = \"md\",\r\n align,\r\n justify,\r\n wrap,\r\n fullWidth = false,\r\n fullHeight = false,\r\n divider = false,\r\n style,\r\n children,\r\n ...rest\r\n },\r\n ref,\r\n ): React.ReactElement {\r\n const { tokens } = useTheme();\r\n const { breakpoint } = useBreakpoint();\r\n\r\n const resolvedSpacing = resolveResponsiveSpacing(\r\n spacing,\r\n breakpoint,\r\n tokens,\r\n );\r\n const resolvedDirection = Array.isArray(direction)\r\n ? (direction[\r\n Math.min(\r\n [\"base\", \"sm\", \"md\", \"lg\", \"xl\", \"xxl\"].indexOf(breakpoint),\r\n direction.length - 1,\r\n )\r\n ] ?? direction[direction.length - 1])\r\n : direction;\r\n const isVertical =\r\n resolvedDirection === \"column\" || resolvedDirection === \"column-reverse\";\r\n\r\n const computedStyle: React.CSSProperties = {\r\n display: \"flex\",\r\n flexDirection: resolvedDirection as\r\n | \"row\"\r\n | \"column\"\r\n | \"row-reverse\"\r\n | \"column-reverse\",\r\n ...(divider || !resolvedSpacing ? {} : { gap: resolvedSpacing }),\r\n alignItems: align,\r\n justifyContent: justify,\r\n flexWrap: wrap,\r\n ...(fullWidth ? { width: \"100%\" } : {}),\r\n ...(fullHeight ? { height: \"100%\" } : {}),\r\n ...style,\r\n };\r\n\r\n // If divider is enabled, interleave divider elements\r\n if (divider) {\r\n const items = React.Children.toArray(children).filter(Boolean);\r\n const dividerStyle: React.CSSProperties = isVertical\r\n ? {\r\n width: \"100%\",\r\n height: \"1px\",\r\n backgroundColor: tokens.colors.border.muted,\r\n flexShrink: 0,\r\n margin: `${resolvedSpacing} 0`,\r\n }\r\n : {\r\n height: \"100%\",\r\n width: \"1px\",\r\n backgroundColor: tokens.colors.border.muted,\r\n flexShrink: 0,\r\n alignSelf: \"stretch\",\r\n margin: `0 ${resolvedSpacing}`,\r\n };\r\n\r\n return (\r\n <Component ref={ref} style={computedStyle} {...rest}>\r\n {items.map((child, index) => (\r\n <React.Fragment key={index}>\r\n {child}\r\n {index < items.length - 1 && (\r\n <div style={dividerStyle} aria-hidden=\"true\" />\r\n )}\r\n </React.Fragment>\r\n ))}\r\n </Component>\r\n );\r\n }\r\n\r\n return (\r\n <Component ref={ref} style={computedStyle} {...rest}>\r\n {children}\r\n </Component>\r\n );\r\n }),\r\n);\r\n\r\n/**\r\n * Horizontal Stack — `<Stack direction=\"row\">` shorthand.\r\n *\r\n * @example\r\n * ```tsx\r\n * <HStack spacing=\"sm\" align=\"center\">\r\n * <Icon name=\"satellite\" />\r\n * <Body1>SAT-1</Body1>\r\n * <Badge status=\"normal\">Nominal</Badge>\r\n * </HStack>\r\n * ```\r\n */\r\nexport const HStack = memo(\r\n forwardRef<HTMLDivElement, Omit<StackProps, \"direction\">>(\r\n function HStack(props, ref) {\r\n return <Stack ref={ref} direction=\"row\" {...props} />;\r\n },\r\n ),\r\n);\r\n\r\n/**\r\n * Vertical Stack — `<Stack direction=\"column\">` shorthand.\r\n *\r\n * @example\r\n * ```tsx\r\n * <VStack spacing=\"md\">\r\n * <TelemetryCard />\r\n * <LinkBudgetCard />\r\n * </VStack>\r\n * ```\r\n */\r\nexport const VStack = memo(\r\n forwardRef<HTMLDivElement, Omit<StackProps, \"direction\">>(\r\n function VStack(props, ref) {\r\n return <Stack ref={ref} direction=\"column\" {...props} />;\r\n },\r\n ),\r\n);\r\n\r\nexport default Stack;\r\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAoEA,IAAa,QAAQ,KACnB,WAAuC,SAAS,MAC9C,EACE,IAAI,YAAY,OAChB,YAAY,UACZ,UAAU,MACV,OACA,SACA,MACA,YAAY,OACZ,aAAa,OACb,UAAU,OACV,OACA,UACA,GAAG,QAEL,KACoB;CACpB,MAAM,EAAE,WAAW,SAAS;CAC5B,MAAM,EAAE,eAAe,cAAc;CAErC,MAAM,kBAAkB,yBACtB,SACA,YACA,MACF;CACA,MAAM,oBAAoB,MAAM,QAAQ,SAAS,IAC5C,UACC,KAAK,IACH;EAAC;EAAQ;EAAM;EAAM;EAAM;EAAM;CAAK,CAAC,CAAC,QAAQ,UAAU,GAC1D,UAAU,SAAS,CACrB,MACG,UAAU,UAAU,SAAS,KAClC;CACJ,MAAM,aACJ,sBAAsB,YAAY,sBAAsB;CAE1D,MAAM,gBAAqC;EACzC,SAAS;EACT,eAAe;EAKf,GAAI,WAAW,CAAC,kBAAkB,CAAC,IAAI,EAAE,KAAK,gBAAgB;EAC9D,YAAY;EACZ,gBAAgB;EAChB,UAAU;EACV,GAAI,YAAY,EAAE,OAAO,OAAO,IAAI,CAAC;EACrC,GAAI,aAAa,EAAE,QAAQ,OAAO,IAAI,CAAC;EACvC,GAAG;CACL;CAGA,IAAI,SAAS;EACX,MAAM,QAAQ,MAAM,SAAS,QAAQ,QAAQ,CAAC,CAAC,OAAO,OAAO;EAC7D,MAAM,eAAoC,aACtC;GACE,OAAO;GACP,QAAQ;GACR,iBAAiB,OAAO,OAAO,OAAO;GACtC,YAAY;GACZ,QAAQ,GAAG,gBAAgB;EAC7B,IACA;GACE,QAAQ;GACR,OAAO;GACP,iBAAiB,OAAO,OAAO,OAAO;GACtC,YAAY;GACZ,WAAW;GACX,QAAQ,KAAK;EACf;EAEJ,OACE,oBAAC,WAAD;GAAgB;GAAK,OAAO;GAAe,GAAI;aAC5C,MAAM,KAAK,OAAO,UACjB,qBAAC,MAAM,UAAP,EAAA,UAAA,CACG,OACA,QAAQ,MAAM,SAAS,KACtB,oBAAC,OAAD;IAAK,OAAO;IAAc,eAAY;GAAQ,CAAA,CAElC,EAAA,GALK,KAKL,CACjB;EACQ,CAAA;CAEf;CAEA,OACE,oBAAC,WAAD;EAAgB;EAAK,OAAO;EAAe,GAAI;EAC5C;CACQ,CAAA;AAEf,CAAC,CACH;;;;;;;;;;;;;AAcA,IAAa,SAAS,KACpB,WACE,SAAS,OAAO,OAAO,KAAK;CAC1B,OAAO,oBAAC,OAAD;EAAY;EAAK,WAAU;EAAM,GAAI;CAAQ,CAAA;AACtD,CACF,CACF;;;;;;;;;;;;AAaA,IAAa,SAAS,KACpB,WACE,SAAS,OAAO,OAAO,KAAK;CAC1B,OAAO,oBAAC,OAAD;EAAY;EAAK,WAAU;EAAS,GAAI;CAAQ,CAAA;AACzD,CACF,CACF"}
@@ -1,8 +1,7 @@
1
1
  import { ThemeTokens } from '../../theme';
2
2
  import { Breakpoint, ResponsiveValue } from './useBreakpoint';
3
-
4
3
  /** Spacing token names matching ThemeTokens.spacing */
5
- export type SpacingToken = 'xxs' | 'xs' | 'sm' | 'smd' | 'md' | 'mdl' | 'lg' | 'xl' | 'xxl';
4
+ export type SpacingToken = "xxs" | "xs" | "sm" | "smd" | "md" | "mdl" | "lg" | "xl" | "xxl";
6
5
  /** Value that can be a spacing token, a CSS string, or a number (px) */
7
6
  type SpacingInput = SpacingToken | string | number;
8
7
  /**
@@ -1,26 +1,32 @@
1
1
  import { resolveResponsiveValue } from "./useBreakpoint.js";
2
+ //#region src/react/core/layout/responsive.ts
3
+ /**
4
+ * Resolve a spacing value to a CSS string.
5
+ * - SpacingToken ('xs', 'sm', etc.) → looks up token value
6
+ * - number → converts to px string
7
+ * - string → passes through (e.g., '1rem', '50%')
8
+ */
2
9
  function resolveSpacing(value, tokens) {
3
- if (value === void 0 || value === null) return void 0;
4
- if (typeof value === "string" && value in tokens.spacing) {
5
- return tokens.spacing[value];
6
- }
7
- if (typeof value === "number") {
8
- return `${value}px`;
9
- }
10
- return value;
10
+ if (value === void 0 || value === null) return void 0;
11
+ if (typeof value === "string" && value in tokens.spacing) return tokens.spacing[value];
12
+ if (typeof value === "number") return `${value}px`;
13
+ return value;
11
14
  }
15
+ /**
16
+ * Resolve a responsive spacing value at the current breakpoint.
17
+ */
12
18
  function resolveResponsiveSpacing(value, breakpoint, tokens) {
13
- if (value === void 0 || value === null) return void 0;
14
- const resolved = Array.isArray(value) ? resolveResponsiveValue(value, breakpoint) : value;
15
- return resolveSpacing(resolved, tokens);
19
+ if (value === void 0 || value === null) return void 0;
20
+ return resolveSpacing(Array.isArray(value) ? resolveResponsiveValue(value, breakpoint) : value, tokens);
16
21
  }
22
+ /**
23
+ * Resolve a responsive value (non-spacing) at the current breakpoint.
24
+ */
17
25
  function resolveResponsive(value, breakpoint) {
18
- if (value === void 0 || value === null) return void 0;
19
- return Array.isArray(value) ? resolveResponsiveValue(value, breakpoint) : value;
26
+ if (value === void 0 || value === null) return void 0;
27
+ return Array.isArray(value) ? resolveResponsiveValue(value, breakpoint) : value;
20
28
  }
21
- export {
22
- resolveResponsive,
23
- resolveResponsiveSpacing,
24
- resolveSpacing
25
- };
26
- //# sourceMappingURL=responsive.js.map
29
+ //#endregion
30
+ export { resolveResponsive, resolveResponsiveSpacing, resolveSpacing };
31
+
32
+ //# sourceMappingURL=responsive.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"responsive.js","sources":["../../../../src/react/core/layout/responsive.ts"],"sourcesContent":["/**\r\n * @zendir/ui - Responsive Utilities\r\n * \r\n * Helpers for resolving responsive values and spacing tokens to CSS values.\r\n * Used internally by layout primitives (Box, Flex, Grid, Stack).\r\n */\r\n\r\nimport type { ThemeTokens } from '../../theme';\r\nimport type { Breakpoint, ResponsiveValue } from './useBreakpoint';\r\nimport { resolveResponsiveValue } from './useBreakpoint';\r\n\r\n/** Spacing token names matching ThemeTokens.spacing */\r\nexport type SpacingToken = 'xxs' | 'xs' | 'sm' | 'smd' | 'md' | 'mdl' | 'lg' | 'xl' | 'xxl';\r\n\r\n/** Value that can be a spacing token, a CSS string, or a number (px) */\r\ntype SpacingInput = SpacingToken | string | number;\r\n\r\n/**\r\n * Resolve a spacing value to a CSS string.\r\n * - SpacingToken ('xs', 'sm', etc.) → looks up token value\r\n * - number → converts to px string\r\n * - string → passes through (e.g., '1rem', '50%')\r\n */\r\nexport function resolveSpacing(\r\n value: SpacingInput | undefined,\r\n tokens: ThemeTokens\r\n): string | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n \r\n // Spacing token\r\n if (typeof value === 'string' && value in tokens.spacing) {\r\n return tokens.spacing[value as SpacingToken];\r\n }\r\n \r\n // Number → px\r\n if (typeof value === 'number') {\r\n return `${value}px`;\r\n }\r\n \r\n // CSS string passthrough\r\n return value;\r\n}\r\n\r\n/**\r\n * Resolve a responsive spacing value at the current breakpoint.\r\n */\r\nexport function resolveResponsiveSpacing(\r\n value: ResponsiveValue<SpacingInput> | undefined,\r\n breakpoint: Breakpoint,\r\n tokens: ThemeTokens\r\n): string | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n \r\n const resolved = Array.isArray(value)\r\n ? resolveResponsiveValue(value, breakpoint)\r\n : value;\r\n \r\n return resolveSpacing(resolved, tokens);\r\n}\r\n\r\n/**\r\n * Resolve a responsive value (non-spacing) at the current breakpoint.\r\n */\r\nexport function resolveResponsive<T>(\r\n value: ResponsiveValue<T> | undefined,\r\n breakpoint: Breakpoint\r\n): T | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n return Array.isArray(value)\r\n ? resolveResponsiveValue(value, breakpoint)\r\n : value;\r\n}\r\n"],"names":[],"mappings":";AAuBO,SAAS,eACd,OACA,QACoB;AACpB,MAAI,UAAU,UAAa,UAAU,KAAM,QAAO;AAGlD,MAAI,OAAO,UAAU,YAAY,SAAS,OAAO,SAAS;AACxD,WAAO,OAAO,QAAQ,KAAqB;AAAA,EAC7C;AAGA,MAAI,OAAO,UAAU,UAAU;AAC7B,WAAO,GAAG,KAAK;AAAA,EACjB;AAGA,SAAO;AACT;AAKO,SAAS,yBACd,OACA,YACA,QACoB;AACpB,MAAI,UAAU,UAAa,UAAU,KAAM,QAAO;AAElD,QAAM,WAAW,MAAM,QAAQ,KAAK,IAChC,uBAAuB,OAAO,UAAU,IACxC;AAEJ,SAAO,eAAe,UAAU,MAAM;AACxC;AAKO,SAAS,kBACd,OACA,YACe;AACf,MAAI,UAAU,UAAa,UAAU,KAAM,QAAO;AAClD,SAAO,MAAM,QAAQ,KAAK,IACtB,uBAAuB,OAAO,UAAU,IACxC;AACN;"}
1
+ {"version":3,"file":"responsive.js","names":[],"sources":["../../../../src/react/core/layout/responsive.ts"],"sourcesContent":["/**\r\n * @zendir/ui - Responsive Utilities\r\n *\r\n * Helpers for resolving responsive values and spacing tokens to CSS values.\r\n * Used internally by layout primitives (Box, Flex, Grid, Stack).\r\n */\r\n\r\nimport type { ThemeTokens } from \"../../theme\";\r\nimport type { Breakpoint, ResponsiveValue } from \"./useBreakpoint\";\r\nimport { resolveResponsiveValue } from \"./useBreakpoint\";\r\n\r\n/** Spacing token names matching ThemeTokens.spacing */\r\nexport type SpacingToken =\r\n | \"xxs\"\r\n | \"xs\"\r\n | \"sm\"\r\n | \"smd\"\r\n | \"md\"\r\n | \"mdl\"\r\n | \"lg\"\r\n | \"xl\"\r\n | \"xxl\";\r\n\r\n/** Value that can be a spacing token, a CSS string, or a number (px) */\r\ntype SpacingInput = SpacingToken | string | number;\r\n\r\n/**\r\n * Resolve a spacing value to a CSS string.\r\n * - SpacingToken ('xs', 'sm', etc.) → looks up token value\r\n * - number → converts to px string\r\n * - string → passes through (e.g., '1rem', '50%')\r\n */\r\nexport function resolveSpacing(\r\n value: SpacingInput | undefined,\r\n tokens: ThemeTokens,\r\n): string | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n\r\n // Spacing token\r\n if (typeof value === \"string\" && value in tokens.spacing) {\r\n return tokens.spacing[value as SpacingToken];\r\n }\r\n\r\n // Number → px\r\n if (typeof value === \"number\") {\r\n return `${value}px`;\r\n }\r\n\r\n // CSS string passthrough\r\n return value;\r\n}\r\n\r\n/**\r\n * Resolve a responsive spacing value at the current breakpoint.\r\n */\r\nexport function resolveResponsiveSpacing(\r\n value: ResponsiveValue<SpacingInput> | undefined,\r\n breakpoint: Breakpoint,\r\n tokens: ThemeTokens,\r\n): string | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n\r\n const resolved = Array.isArray(value)\r\n ? resolveResponsiveValue(value, breakpoint)\r\n : value;\r\n\r\n return resolveSpacing(resolved, tokens);\r\n}\r\n\r\n/**\r\n * Resolve a responsive value (non-spacing) at the current breakpoint.\r\n */\r\nexport function resolveResponsive<T>(\r\n value: ResponsiveValue<T> | undefined,\r\n breakpoint: Breakpoint,\r\n): T | undefined {\r\n if (value === undefined || value === null) return undefined;\r\n return Array.isArray(value)\r\n ? resolveResponsiveValue(value, breakpoint)\r\n : value;\r\n}\r\n"],"mappings":";;;;;;;;AAgCA,SAAgB,eACd,OACA,QACoB;CACpB,IAAI,UAAU,KAAA,KAAa,UAAU,MAAM,OAAO,KAAA;CAGlD,IAAI,OAAO,UAAU,YAAY,SAAS,OAAO,SAC/C,OAAO,OAAO,QAAQ;CAIxB,IAAI,OAAO,UAAU,UACnB,OAAO,GAAG,MAAM;CAIlB,OAAO;AACT;;;;AAKA,SAAgB,yBACd,OACA,YACA,QACoB;CACpB,IAAI,UAAU,KAAA,KAAa,UAAU,MAAM,OAAO,KAAA;CAMlD,OAAO,eAJU,MAAM,QAAQ,KAAK,IAChC,uBAAuB,OAAO,UAAU,IACxC,OAE4B,MAAM;AACxC;;;;AAKA,SAAgB,kBACd,OACA,YACe;CACf,IAAI,UAAU,KAAA,KAAa,UAAU,MAAM,OAAO,KAAA;CAClD,OAAO,MAAM,QAAQ,KAAK,IACtB,uBAAuB,OAAO,UAAU,IACxC;AACN"}
@@ -16,7 +16,7 @@
16
16
  * const { isMobile, isTablet, isDesktop, breakpoint, width } = useBreakpoint();
17
17
  * ```
18
18
  */
19
- export type Breakpoint = 'base' | 'sm' | 'md' | 'lg' | 'xl' | 'xxl';
19
+ export type Breakpoint = "base" | "sm" | "md" | "lg" | "xl" | "xxl";
20
20
  /** Responsive value: single value or [base, sm?, md?, lg?, xl?, xxl?] */
21
21
  export type ResponsiveValue<T> = T | [T, T?, T?, T?, T?, T?];
22
22
  export declare const BREAKPOINTS: {
@@ -1,73 +1,126 @@
1
- import { useState, useEffect, useMemo, useCallback } from "react";
2
- const BREAKPOINTS = {
3
- base: 0,
4
- sm: 640,
5
- md: 768,
6
- lg: 1024,
7
- xl: 1280,
8
- xxl: 1920
1
+ import { useCallback, useEffect, useMemo, useState } from "react";
2
+ //#region src/react/core/layout/useBreakpoint.ts
3
+ /**
4
+ * @zendir/ui - Responsive Breakpoint System
5
+ *
6
+ * Breakpoints aligned with Astro UX Design System responsive guidelines.
7
+ * Supports mission control displays (4K) down to mobile field devices.
8
+ *
9
+ * Breakpoints:
10
+ * - sm: 640px — Mobile landscape / small tablets
11
+ * - md: 768px — Tablets
12
+ * - lg: 1024px — Laptops / desktop
13
+ * - xl: 1280px — Large monitors
14
+ * - xxl: 1920px — Mission control displays (HD)
15
+ *
16
+ * @example
17
+ * ```tsx
18
+ * const { isMobile, isTablet, isDesktop, breakpoint, width } = useBreakpoint();
19
+ * ```
20
+ */
21
+ var BREAKPOINTS = {
22
+ base: 0,
23
+ sm: 640,
24
+ md: 768,
25
+ lg: 1024,
26
+ xl: 1280,
27
+ xxl: 1920
9
28
  };
10
- const BREAKPOINT_ORDER = ["base", "sm", "md", "lg", "xl", "xxl"];
29
+ var BREAKPOINT_ORDER = [
30
+ "base",
31
+ "sm",
32
+ "md",
33
+ "lg",
34
+ "xl",
35
+ "xxl"
36
+ ];
11
37
  function getBreakpoint(width) {
12
- if (width >= BREAKPOINTS.xxl) return "xxl";
13
- if (width >= BREAKPOINTS.xl) return "xl";
14
- if (width >= BREAKPOINTS.lg) return "lg";
15
- if (width >= BREAKPOINTS.md) return "md";
16
- if (width >= BREAKPOINTS.sm) return "sm";
17
- return "base";
38
+ if (width >= BREAKPOINTS.xxl) return "xxl";
39
+ if (width >= BREAKPOINTS.xl) return "xl";
40
+ if (width >= BREAKPOINTS.lg) return "lg";
41
+ if (width >= BREAKPOINTS.md) return "md";
42
+ if (width >= BREAKPOINTS.sm) return "sm";
43
+ return "base";
18
44
  }
45
+ /**
46
+ * Hook for responsive breakpoint detection.
47
+ *
48
+ * Uses matchMedia for efficient, debounce-free breakpoint tracking.
49
+ * Respects SSR by defaulting to 'lg' (desktop).
50
+ *
51
+ * @example
52
+ * ```tsx
53
+ * const { isMobile, isDesktop, breakpoint } = useBreakpoint();
54
+ *
55
+ * return (
56
+ * <Grid columns={isMobile ? 1 : 3}>
57
+ * ...
58
+ * </Grid>
59
+ * );
60
+ * ```
61
+ */
19
62
  function useBreakpoint() {
20
- const [width, setWidth] = useState(() => {
21
- if (typeof window !== "undefined") return window.innerWidth;
22
- return 1024;
23
- });
24
- useEffect(() => {
25
- if (typeof window === "undefined") return;
26
- let rafId;
27
- const handleResize = () => {
28
- cancelAnimationFrame(rafId);
29
- rafId = requestAnimationFrame(() => {
30
- setWidth(window.innerWidth);
31
- });
32
- };
33
- window.addEventListener("resize", handleResize, { passive: true });
34
- return () => {
35
- window.removeEventListener("resize", handleResize);
36
- cancelAnimationFrame(rafId);
37
- };
38
- }, []);
39
- const breakpoint = useMemo(() => getBreakpoint(width), [width]);
40
- const isAbove = useCallback((bp) => {
41
- return width >= BREAKPOINTS[bp];
42
- }, [width]);
43
- const isBelow = useCallback((bp) => {
44
- return width < BREAKPOINTS[bp];
45
- }, [width]);
46
- return useMemo(() => ({
47
- breakpoint,
48
- width,
49
- isMobile: width < BREAKPOINTS.md,
50
- isTablet: width >= BREAKPOINTS.md && width < BREAKPOINTS.lg,
51
- isDesktop: width >= BREAKPOINTS.lg,
52
- isWidescreen: width >= BREAKPOINTS.xxl,
53
- isAbove,
54
- isBelow
55
- }), [breakpoint, width, isAbove, isBelow]);
63
+ const [width, setWidth] = useState(() => {
64
+ if (typeof window !== "undefined") return window.innerWidth;
65
+ return 1024;
66
+ });
67
+ useEffect(() => {
68
+ if (typeof window === "undefined") return;
69
+ let rafId;
70
+ const handleResize = () => {
71
+ cancelAnimationFrame(rafId);
72
+ rafId = requestAnimationFrame(() => {
73
+ setWidth(window.innerWidth);
74
+ });
75
+ };
76
+ window.addEventListener("resize", handleResize, { passive: true });
77
+ return () => {
78
+ window.removeEventListener("resize", handleResize);
79
+ cancelAnimationFrame(rafId);
80
+ };
81
+ }, []);
82
+ const breakpoint = useMemo(() => getBreakpoint(width), [width]);
83
+ const isAbove = useCallback((bp) => {
84
+ return width >= BREAKPOINTS[bp];
85
+ }, [width]);
86
+ const isBelow = useCallback((bp) => {
87
+ return width < BREAKPOINTS[bp];
88
+ }, [width]);
89
+ return useMemo(() => ({
90
+ breakpoint,
91
+ width,
92
+ isMobile: width < BREAKPOINTS.md,
93
+ isTablet: width >= BREAKPOINTS.md && width < BREAKPOINTS.lg,
94
+ isDesktop: width >= BREAKPOINTS.lg,
95
+ isWidescreen: width >= BREAKPOINTS.xxl,
96
+ isAbove,
97
+ isBelow
98
+ }), [
99
+ breakpoint,
100
+ width,
101
+ isAbove,
102
+ isBelow
103
+ ]);
56
104
  }
105
+ /**
106
+ * Resolve a responsive value based on current breakpoint.
107
+ *
108
+ * Given `[1, 2, 3]` at breakpoint 'lg', returns 3.
109
+ * Falls back to the last defined value for higher breakpoints.
110
+ *
111
+ * @example
112
+ * resolveResponsiveValue([1, 2, 3], 'lg') // → 3
113
+ * resolveResponsiveValue([1, 2], 'xl') // → 2 (falls back to last defined)
114
+ * resolveResponsiveValue(5, 'md') // → 5 (non-array passthrough)
115
+ */
57
116
  function resolveResponsiveValue(value, breakpoint) {
58
- if (!Array.isArray(value)) return value;
59
- const index = BREAKPOINT_ORDER.indexOf(breakpoint);
60
- for (let i = Math.min(index, value.length - 1); i >= 0; i--) {
61
- if (value[i] !== void 0 && value[i] !== null) return value[i];
62
- }
63
- for (let i = 0; i < value.length; i++) {
64
- if (value[i] !== void 0 && value[i] !== null) return value[i];
65
- }
66
- return value[0];
117
+ if (!Array.isArray(value)) return value;
118
+ const index = BREAKPOINT_ORDER.indexOf(breakpoint);
119
+ for (let i = Math.min(index, value.length - 1); i >= 0; i--) if (value[i] !== void 0 && value[i] !== null) return value[i];
120
+ for (let i = 0; i < value.length; i++) if (value[i] !== void 0 && value[i] !== null) return value[i];
121
+ return value[0];
67
122
  }
68
- export {
69
- BREAKPOINTS,
70
- resolveResponsiveValue,
71
- useBreakpoint
72
- };
73
- //# sourceMappingURL=useBreakpoint.js.map
123
+ //#endregion
124
+ export { BREAKPOINTS, resolveResponsiveValue, useBreakpoint };
125
+
126
+ //# sourceMappingURL=useBreakpoint.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"useBreakpoint.js","sources":["../../../../src/react/core/layout/useBreakpoint.ts"],"sourcesContent":["/**\r\n * @zendir/ui - Responsive Breakpoint System\r\n * \r\n * Breakpoints aligned with Astro UX Design System responsive guidelines.\r\n * Supports mission control displays (4K) down to mobile field devices.\r\n * \r\n * Breakpoints:\r\n * - sm: 640px — Mobile landscape / small tablets\r\n * - md: 768px — Tablets\r\n * - lg: 1024px — Laptops / desktop\r\n * - xl: 1280px — Large monitors\r\n * - xxl: 1920px — Mission control displays (HD)\r\n * \r\n * @example\r\n * ```tsx\r\n * const { isMobile, isTablet, isDesktop, breakpoint, width } = useBreakpoint();\r\n * ```\r\n */\r\n\r\nimport { useState, useEffect, useCallback, useMemo } from 'react';\r\n\r\nexport type Breakpoint = 'base' | 'sm' | 'md' | 'lg' | 'xl' | 'xxl';\r\n\r\n/** Responsive value: single value or [base, sm?, md?, lg?, xl?, xxl?] */\r\nexport type ResponsiveValue<T> = T | [T, T?, T?, T?, T?, T?];\r\n\r\nexport const BREAKPOINTS = {\r\n base: 0,\r\n sm: 640,\r\n md: 768,\r\n lg: 1024,\r\n xl: 1280,\r\n xxl: 1920,\r\n} as const;\r\n\r\nconst BREAKPOINT_ORDER: Breakpoint[] = ['base', 'sm', 'md', 'lg', 'xl', 'xxl'];\r\n\r\nfunction getBreakpoint(width: number): Breakpoint {\r\n if (width >= BREAKPOINTS.xxl) return 'xxl';\r\n if (width >= BREAKPOINTS.xl) return 'xl';\r\n if (width >= BREAKPOINTS.lg) return 'lg';\r\n if (width >= BREAKPOINTS.md) return 'md';\r\n if (width >= BREAKPOINTS.sm) return 'sm';\r\n return 'base';\r\n}\r\n\r\nexport interface UseBreakpointReturn {\r\n /** Current breakpoint name */\r\n breakpoint: Breakpoint;\r\n /** Current viewport width in px */\r\n width: number;\r\n /** True when viewport < 768px (base, sm) */\r\n isMobile: boolean;\r\n /** True when viewport >= 768px and < 1024px */\r\n isTablet: boolean;\r\n /** True when viewport >= 1024px */\r\n isDesktop: boolean;\r\n /** True when viewport >= 1920px (mission control) */\r\n isWidescreen: boolean;\r\n /** Check if viewport is at or above a given breakpoint */\r\n isAbove: (bp: Breakpoint) => boolean;\r\n /** Check if viewport is below a given breakpoint */\r\n isBelow: (bp: Breakpoint) => boolean;\r\n}\r\n\r\n/**\r\n * Hook for responsive breakpoint detection.\r\n * \r\n * Uses matchMedia for efficient, debounce-free breakpoint tracking.\r\n * Respects SSR by defaulting to 'lg' (desktop).\r\n * \r\n * @example\r\n * ```tsx\r\n * const { isMobile, isDesktop, breakpoint } = useBreakpoint();\r\n * \r\n * return (\r\n * <Grid columns={isMobile ? 1 : 3}>\r\n * ...\r\n * </Grid>\r\n * );\r\n * ```\r\n */\r\nexport function useBreakpoint(): UseBreakpointReturn {\r\n const [width, setWidth] = useState(() => {\r\n if (typeof window !== 'undefined') return window.innerWidth;\r\n return 1024; // SSR default: desktop\r\n });\r\n\r\n useEffect(() => {\r\n if (typeof window === 'undefined') return;\r\n\r\n let rafId: number;\r\n const handleResize = () => {\r\n cancelAnimationFrame(rafId);\r\n rafId = requestAnimationFrame(() => {\r\n setWidth(window.innerWidth);\r\n });\r\n };\r\n\r\n window.addEventListener('resize', handleResize, { passive: true });\r\n return () => {\r\n window.removeEventListener('resize', handleResize);\r\n cancelAnimationFrame(rafId);\r\n };\r\n }, []);\r\n\r\n const breakpoint = useMemo(() => getBreakpoint(width), [width]);\r\n\r\n const isAbove = useCallback((bp: Breakpoint) => {\r\n return width >= BREAKPOINTS[bp];\r\n }, [width]);\r\n\r\n const isBelow = useCallback((bp: Breakpoint) => {\r\n return width < BREAKPOINTS[bp];\r\n }, [width]);\r\n\r\n return useMemo(() => ({\r\n breakpoint,\r\n width,\r\n isMobile: width < BREAKPOINTS.md,\r\n isTablet: width >= BREAKPOINTS.md && width < BREAKPOINTS.lg,\r\n isDesktop: width >= BREAKPOINTS.lg,\r\n isWidescreen: width >= BREAKPOINTS.xxl,\r\n isAbove,\r\n isBelow,\r\n }), [breakpoint, width, isAbove, isBelow]);\r\n}\r\n\r\n/**\r\n * Resolve a responsive value based on current breakpoint.\r\n * \r\n * Given `[1, 2, 3]` at breakpoint 'lg', returns 3.\r\n * Falls back to the last defined value for higher breakpoints.\r\n * \r\n * @example\r\n * resolveResponsiveValue([1, 2, 3], 'lg') // → 3\r\n * resolveResponsiveValue([1, 2], 'xl') // → 2 (falls back to last defined)\r\n * resolveResponsiveValue(5, 'md') // → 5 (non-array passthrough)\r\n */\r\nexport function resolveResponsiveValue<T>(value: ResponsiveValue<T>, breakpoint: Breakpoint): T {\r\n if (!Array.isArray(value)) return value;\r\n \r\n const index = BREAKPOINT_ORDER.indexOf(breakpoint);\r\n \r\n // Walk backwards from current breakpoint to find a defined value\r\n for (let i = Math.min(index, value.length - 1); i >= 0; i--) {\r\n if (value[i] !== undefined && value[i] !== null) return value[i] as T;\r\n }\r\n \r\n // Fallback: find first defined value in the responsive array.\r\n for (let i = 0; i < value.length; i++) {\r\n if (value[i] !== undefined && value[i] !== null) return value[i] as T;\r\n }\r\n\r\n return value[0] as T;\r\n}\r\n"],"names":[],"mappings":";AA0BO,MAAM,cAAc;AAAA,EACzB,MAAM;AAAA,EACN,IAAI;AAAA,EACJ,IAAI;AAAA,EACJ,IAAI;AAAA,EACJ,IAAI;AAAA,EACJ,KAAK;AACP;AAEA,MAAM,mBAAiC,CAAC,QAAQ,MAAM,MAAM,MAAM,MAAM,KAAK;AAE7E,SAAS,cAAc,OAA2B;AAChD,MAAI,SAAS,YAAY,IAAK,QAAO;AACrC,MAAI,SAAS,YAAY,GAAI,QAAO;AACpC,MAAI,SAAS,YAAY,GAAI,QAAO;AACpC,MAAI,SAAS,YAAY,GAAI,QAAO;AACpC,MAAI,SAAS,YAAY,GAAI,QAAO;AACpC,SAAO;AACT;AAsCO,SAAS,gBAAqC;AACnD,QAAM,CAAC,OAAO,QAAQ,IAAI,SAAS,MAAM;AACvC,QAAI,OAAO,WAAW,YAAa,QAAO,OAAO;AACjD,WAAO;AAAA,EACT,CAAC;AAED,YAAU,MAAM;AACd,QAAI,OAAO,WAAW,YAAa;AAEnC,QAAI;AACJ,UAAM,eAAe,MAAM;AACzB,2BAAqB,KAAK;AAC1B,cAAQ,sBAAsB,MAAM;AAClC,iBAAS,OAAO,UAAU;AAAA,MAC5B,CAAC;AAAA,IACH;AAEA,WAAO,iBAAiB,UAAU,cAAc,EAAE,SAAS,MAAM;AACjE,WAAO,MAAM;AACX,aAAO,oBAAoB,UAAU,YAAY;AACjD,2BAAqB,KAAK;AAAA,IAC5B;AAAA,EACF,GAAG,CAAA,CAAE;AAEL,QAAM,aAAa,QAAQ,MAAM,cAAc,KAAK,GAAG,CAAC,KAAK,CAAC;AAE9D,QAAM,UAAU,YAAY,CAAC,OAAmB;AAC9C,WAAO,SAAS,YAAY,EAAE;AAAA,EAChC,GAAG,CAAC,KAAK,CAAC;AAEV,QAAM,UAAU,YAAY,CAAC,OAAmB;AAC9C,WAAO,QAAQ,YAAY,EAAE;AAAA,EAC/B,GAAG,CAAC,KAAK,CAAC;AAEV,SAAO,QAAQ,OAAO;AAAA,IACpB;AAAA,IACA;AAAA,IACA,UAAU,QAAQ,YAAY;AAAA,IAC9B,UAAU,SAAS,YAAY,MAAM,QAAQ,YAAY;AAAA,IACzD,WAAW,SAAS,YAAY;AAAA,IAChC,cAAc,SAAS,YAAY;AAAA,IACnC;AAAA,IACA;AAAA,EAAA,IACE,CAAC,YAAY,OAAO,SAAS,OAAO,CAAC;AAC3C;AAaO,SAAS,uBAA0B,OAA2B,YAA2B;AAC9F,MAAI,CAAC,MAAM,QAAQ,KAAK,EAAG,QAAO;AAElC,QAAM,QAAQ,iBAAiB,QAAQ,UAAU;AAGjD,WAAS,IAAI,KAAK,IAAI,OAAO,MAAM,SAAS,CAAC,GAAG,KAAK,GAAG,KAAK;AAC3D,QAAI,MAAM,CAAC,MAAM,UAAa,MAAM,CAAC,MAAM,KAAM,QAAO,MAAM,CAAC;AAAA,EACjE;AAGA,WAAS,IAAI,GAAG,IAAI,MAAM,QAAQ,KAAK;AACrC,QAAI,MAAM,CAAC,MAAM,UAAa,MAAM,CAAC,MAAM,KAAM,QAAO,MAAM,CAAC;AAAA,EACjE;AAEA,SAAO,MAAM,CAAC;AAChB;"}
1
+ {"version":3,"file":"useBreakpoint.js","names":[],"sources":["../../../../src/react/core/layout/useBreakpoint.ts"],"sourcesContent":["/**\r\n * @zendir/ui - Responsive Breakpoint System\r\n *\r\n * Breakpoints aligned with Astro UX Design System responsive guidelines.\r\n * Supports mission control displays (4K) down to mobile field devices.\r\n *\r\n * Breakpoints:\r\n * - sm: 640px — Mobile landscape / small tablets\r\n * - md: 768px — Tablets\r\n * - lg: 1024px — Laptops / desktop\r\n * - xl: 1280px — Large monitors\r\n * - xxl: 1920px — Mission control displays (HD)\r\n *\r\n * @example\r\n * ```tsx\r\n * const { isMobile, isTablet, isDesktop, breakpoint, width } = useBreakpoint();\r\n * ```\r\n */\r\n\r\nimport { useState, useEffect, useCallback, useMemo } from \"react\";\r\n\r\nexport type Breakpoint = \"base\" | \"sm\" | \"md\" | \"lg\" | \"xl\" | \"xxl\";\r\n\r\n/** Responsive value: single value or [base, sm?, md?, lg?, xl?, xxl?] */\r\nexport type ResponsiveValue<T> = T | [T, T?, T?, T?, T?, T?];\r\n\r\nexport const BREAKPOINTS = {\r\n base: 0,\r\n sm: 640,\r\n md: 768,\r\n lg: 1024,\r\n xl: 1280,\r\n xxl: 1920,\r\n} as const;\r\n\r\nconst BREAKPOINT_ORDER: Breakpoint[] = [\"base\", \"sm\", \"md\", \"lg\", \"xl\", \"xxl\"];\r\n\r\nfunction getBreakpoint(width: number): Breakpoint {\r\n if (width >= BREAKPOINTS.xxl) return \"xxl\";\r\n if (width >= BREAKPOINTS.xl) return \"xl\";\r\n if (width >= BREAKPOINTS.lg) return \"lg\";\r\n if (width >= BREAKPOINTS.md) return \"md\";\r\n if (width >= BREAKPOINTS.sm) return \"sm\";\r\n return \"base\";\r\n}\r\n\r\nexport interface UseBreakpointReturn {\r\n /** Current breakpoint name */\r\n breakpoint: Breakpoint;\r\n /** Current viewport width in px */\r\n width: number;\r\n /** True when viewport < 768px (base, sm) */\r\n isMobile: boolean;\r\n /** True when viewport >= 768px and < 1024px */\r\n isTablet: boolean;\r\n /** True when viewport >= 1024px */\r\n isDesktop: boolean;\r\n /** True when viewport >= 1920px (mission control) */\r\n isWidescreen: boolean;\r\n /** Check if viewport is at or above a given breakpoint */\r\n isAbove: (bp: Breakpoint) => boolean;\r\n /** Check if viewport is below a given breakpoint */\r\n isBelow: (bp: Breakpoint) => boolean;\r\n}\r\n\r\n/**\r\n * Hook for responsive breakpoint detection.\r\n *\r\n * Uses matchMedia for efficient, debounce-free breakpoint tracking.\r\n * Respects SSR by defaulting to 'lg' (desktop).\r\n *\r\n * @example\r\n * ```tsx\r\n * const { isMobile, isDesktop, breakpoint } = useBreakpoint();\r\n *\r\n * return (\r\n * <Grid columns={isMobile ? 1 : 3}>\r\n * ...\r\n * </Grid>\r\n * );\r\n * ```\r\n */\r\nexport function useBreakpoint(): UseBreakpointReturn {\r\n const [width, setWidth] = useState(() => {\r\n if (typeof window !== \"undefined\") return window.innerWidth;\r\n return 1024; // SSR default: desktop\r\n });\r\n\r\n useEffect(() => {\r\n if (typeof window === \"undefined\") return;\r\n\r\n let rafId: number;\r\n const handleResize = () => {\r\n cancelAnimationFrame(rafId);\r\n rafId = requestAnimationFrame(() => {\r\n setWidth(window.innerWidth);\r\n });\r\n };\r\n\r\n window.addEventListener(\"resize\", handleResize, { passive: true });\r\n return () => {\r\n window.removeEventListener(\"resize\", handleResize);\r\n cancelAnimationFrame(rafId);\r\n };\r\n }, []);\r\n\r\n const breakpoint = useMemo(() => getBreakpoint(width), [width]);\r\n\r\n const isAbove = useCallback(\r\n (bp: Breakpoint) => {\r\n return width >= BREAKPOINTS[bp];\r\n },\r\n [width],\r\n );\r\n\r\n const isBelow = useCallback(\r\n (bp: Breakpoint) => {\r\n return width < BREAKPOINTS[bp];\r\n },\r\n [width],\r\n );\r\n\r\n return useMemo(\r\n () => ({\r\n breakpoint,\r\n width,\r\n isMobile: width < BREAKPOINTS.md,\r\n isTablet: width >= BREAKPOINTS.md && width < BREAKPOINTS.lg,\r\n isDesktop: width >= BREAKPOINTS.lg,\r\n isWidescreen: width >= BREAKPOINTS.xxl,\r\n isAbove,\r\n isBelow,\r\n }),\r\n [breakpoint, width, isAbove, isBelow],\r\n );\r\n}\r\n\r\n/**\r\n * Resolve a responsive value based on current breakpoint.\r\n *\r\n * Given `[1, 2, 3]` at breakpoint 'lg', returns 3.\r\n * Falls back to the last defined value for higher breakpoints.\r\n *\r\n * @example\r\n * resolveResponsiveValue([1, 2, 3], 'lg') // → 3\r\n * resolveResponsiveValue([1, 2], 'xl') // → 2 (falls back to last defined)\r\n * resolveResponsiveValue(5, 'md') // → 5 (non-array passthrough)\r\n */\r\nexport function resolveResponsiveValue<T>(\r\n value: ResponsiveValue<T>,\r\n breakpoint: Breakpoint,\r\n): T {\r\n if (!Array.isArray(value)) return value;\r\n\r\n const index = BREAKPOINT_ORDER.indexOf(breakpoint);\r\n\r\n // Walk backwards from current breakpoint to find a defined value\r\n for (let i = Math.min(index, value.length - 1); i >= 0; i--) {\r\n if (value[i] !== undefined && value[i] !== null) return value[i] as T;\r\n }\r\n\r\n // Fallback: find first defined value in the responsive array.\r\n for (let i = 0; i < value.length; i++) {\r\n if (value[i] !== undefined && value[i] !== null) return value[i] as T;\r\n }\r\n\r\n return value[0] as T;\r\n}\r\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AA0BA,IAAa,cAAc;CACzB,MAAM;CACN,IAAI;CACJ,IAAI;CACJ,IAAI;CACJ,IAAI;CACJ,KAAK;AACP;AAEA,IAAM,mBAAiC;CAAC;CAAQ;CAAM;CAAM;CAAM;CAAM;AAAK;AAE7E,SAAS,cAAc,OAA2B;CAChD,IAAI,SAAS,YAAY,KAAK,OAAO;CACrC,IAAI,SAAS,YAAY,IAAI,OAAO;CACpC,IAAI,SAAS,YAAY,IAAI,OAAO;CACpC,IAAI,SAAS,YAAY,IAAI,OAAO;CACpC,IAAI,SAAS,YAAY,IAAI,OAAO;CACpC,OAAO;AACT;;;;;;;;;;;;;;;;;;AAsCA,SAAgB,gBAAqC;CACnD,MAAM,CAAC,OAAO,YAAY,eAAe;EACvC,IAAI,OAAO,WAAW,aAAa,OAAO,OAAO;EACjD,OAAO;CACT,CAAC;CAED,gBAAgB;EACd,IAAI,OAAO,WAAW,aAAa;EAEnC,IAAI;EACJ,MAAM,qBAAqB;GACzB,qBAAqB,KAAK;GAC1B,QAAQ,4BAA4B;IAClC,SAAS,OAAO,UAAU;GAC5B,CAAC;EACH;EAEA,OAAO,iBAAiB,UAAU,cAAc,EAAE,SAAS,KAAK,CAAC;EACjE,aAAa;GACX,OAAO,oBAAoB,UAAU,YAAY;GACjD,qBAAqB,KAAK;EAC5B;CACF,GAAG,CAAC,CAAC;CAEL,MAAM,aAAa,cAAc,cAAc,KAAK,GAAG,CAAC,KAAK,CAAC;CAE9D,MAAM,UAAU,aACb,OAAmB;EAClB,OAAO,SAAS,YAAY;CAC9B,GACA,CAAC,KAAK,CACR;CAEA,MAAM,UAAU,aACb,OAAmB;EAClB,OAAO,QAAQ,YAAY;CAC7B,GACA,CAAC,KAAK,CACR;CAEA,OAAO,eACE;EACL;EACA;EACA,UAAU,QAAQ,YAAY;EAC9B,UAAU,SAAS,YAAY,MAAM,QAAQ,YAAY;EACzD,WAAW,SAAS,YAAY;EAChC,cAAc,SAAS,YAAY;EACnC;EACA;CACF,IACA;EAAC;EAAY;EAAO;EAAS;CAAO,CACtC;AACF;;;;;;;;;;;;AAaA,SAAgB,uBACd,OACA,YACG;CACH,IAAI,CAAC,MAAM,QAAQ,KAAK,GAAG,OAAO;CAElC,MAAM,QAAQ,iBAAiB,QAAQ,UAAU;CAGjD,KAAK,IAAI,IAAI,KAAK,IAAI,OAAO,MAAM,SAAS,CAAC,GAAG,KAAK,GAAG,KACtD,IAAI,MAAM,OAAO,KAAA,KAAa,MAAM,OAAO,MAAM,OAAO,MAAM;CAIhE,KAAK,IAAI,IAAI,GAAG,IAAI,MAAM,QAAQ,KAChC,IAAI,MAAM,OAAO,KAAA,KAAa,MAAM,OAAO,MAAM,OAAO,MAAM;CAGhE,OAAO,MAAM;AACf"}
@@ -1,6 +1,5 @@
1
1
  import { default as React, ReactNode } from 'react';
2
2
  import { ThemeVariant, ThemeMode } from '../../theme';
3
-
4
3
  export interface AppBarBranding {
5
4
  /** Logo image URL (takes precedence over text) */
6
5
  logoUrl?: string;
@@ -53,7 +52,7 @@ export interface AppBarProps {
53
52
  /** Let center slot grow to fill space and stay centered (e.g. simulation controls). */
54
53
  centerGrow?: boolean;
55
54
  /** Bar variant: default (52px) or dense (44px min height, tighter padding/gap). */
56
- variant?: 'default' | 'dense';
55
+ variant?: "default" | "dense";
57
56
  /** Callback when theme changes */
58
57
  onThemeChange?: (theme: ThemeVariant) => void;
59
58
  /** Callback when mode changes */