@keboola/design 11.2.0 → 11.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 (233) hide show
  1. package/AGENTS.md +25 -14
  2. package/CHANGELOG.md +254 -0
  3. package/COMPONENT-API.md +1 -1
  4. package/dist/{AIKit-DiS0CVOW.js → AIKit-DaFT7p92.js} +23 -22
  5. package/dist/AIKit-DaFT7p92.js.map +1 -0
  6. package/dist/{Alert-DfZq9kGe.js → Alert-CseY3yAj.js} +3 -3
  7. package/dist/{Alert-DfZq9kGe.js.map → Alert-CseY3yAj.js.map} +1 -1
  8. package/dist/{AlertModal-Dp_XuJBW.js → AlertModal-DQAGpsEy.js} +3 -3
  9. package/dist/{AlertModal-Dp_XuJBW.js.map → AlertModal-DQAGpsEy.js.map} +1 -1
  10. package/dist/{AppShell-B5GQN6Zs.js → AppShell-BUoxM3fv.js} +29 -10
  11. package/dist/AppShell-BUoxM3fv.js.map +1 -0
  12. package/dist/{BrandEditor-DyzgfVkl.js → BrandEditor-BnTLMRMp.js} +6 -6
  13. package/dist/{BrandEditor-DyzgfVkl.js.map → BrandEditor-BnTLMRMp.js.map} +1 -1
  14. package/dist/{BrandLogo-CJkRd0F8.js → BrandLogo-V2pRUAeO.js} +2 -2
  15. package/dist/{BrandLogo-CJkRd0F8.js.map → BrandLogo-V2pRUAeO.js.map} +1 -1
  16. package/dist/{Breadcrumb-Frst8MTA.js → Breadcrumb-CQTPn_KB.js} +3 -3
  17. package/dist/{Breadcrumb-Frst8MTA.js.map → Breadcrumb-CQTPn_KB.js.map} +1 -1
  18. package/dist/{Button-6xBX0nNl.js → Button-CPsEQuTN.js} +2 -2
  19. package/dist/{Button-6xBX0nNl.js.map → Button-CPsEQuTN.js.map} +1 -1
  20. package/dist/{Card-BAoZ35CV.js → Card-Cd5HSBmv.js} +2 -2
  21. package/dist/{Card-BAoZ35CV.js.map → Card-Cd5HSBmv.js.map} +1 -1
  22. package/dist/{Checkbox-GJ8-srt4.js → Checkbox-5VNCcV7E.js} +3 -3
  23. package/dist/{Checkbox-GJ8-srt4.js.map → Checkbox-5VNCcV7E.js.map} +1 -1
  24. package/dist/{Clipboard-CBJZiviP.js → Clipboard-B7rckqV_.js} +2 -2
  25. package/dist/{Clipboard-CBJZiviP.js.map → Clipboard-B7rckqV_.js.map} +1 -1
  26. package/dist/{ClipboardButton-ClcluT0C.js → ClipboardButton-CQ6Aewpg.js} +3 -3
  27. package/dist/{ClipboardButton-ClcluT0C.js.map → ClipboardButton-CQ6Aewpg.js.map} +1 -1
  28. package/dist/{CodeEditor-DyaN-Ij2.js → CodeEditor-CUse8znx.js} +237 -95
  29. package/dist/CodeEditor-CUse8znx.js.map +1 -0
  30. package/dist/{ColorInput-B8z4j4Y_.js → ColorInput-Q1D9Vcc_.js} +3 -3
  31. package/dist/{ColorInput-B8z4j4Y_.js.map → ColorInput-Q1D9Vcc_.js.map} +1 -1
  32. package/dist/{ColorModeSwitch-dZFZyqy1.js → ColorModeSwitch-B5PXCVqB.js} +3 -3
  33. package/dist/{ColorModeSwitch-dZFZyqy1.js.map → ColorModeSwitch-B5PXCVqB.js.map} +1 -1
  34. package/dist/{Combobox-Dgm6Z4ib.js → Combobox-CyoRA7oY.js} +5 -5
  35. package/dist/Combobox-CyoRA7oY.js.map +1 -0
  36. package/dist/{Command-C0aZfVTq.js → Command-Ds68v2rX.js} +3 -3
  37. package/dist/{Command-C0aZfVTq.js.map → Command-Ds68v2rX.js.map} +1 -1
  38. package/dist/{CopyField-BJ96zvXs.js → CopyField-DI66uY_g.js} +2 -2
  39. package/dist/{CopyField-BJ96zvXs.js.map → CopyField-DI66uY_g.js.map} +1 -1
  40. package/dist/{DateInput-B3UdzRfW.js → DateInput-BPj2pzsn.js} +4 -4
  41. package/dist/{DateInput-B3UdzRfW.js.map → DateInput-BPj2pzsn.js.map} +1 -1
  42. package/dist/{DatePicker-Dw3DpbUh.js → DatePicker-DyEGuW9m.js} +2 -2
  43. package/dist/{DatePicker-Dw3DpbUh.js.map → DatePicker-DyEGuW9m.js.map} +1 -1
  44. package/dist/{DateRangeInput-DTuySEiq.js → DateRangeInput-u9DxNbHW.js} +4 -4
  45. package/dist/{DateRangeInput-DTuySEiq.js.map → DateRangeInput-u9DxNbHW.js.map} +1 -1
  46. package/dist/{DateRangePicker-DCmMHg4s.js → DateRangePicker-CYYhX6S7.js} +6 -6
  47. package/dist/{DateRangePicker-DCmMHg4s.js.map → DateRangePicker-CYYhX6S7.js.map} +1 -1
  48. package/dist/{DropdownMenu-t90tVw6l.js → DropdownMenu-DpMEcyCq.js} +2 -2
  49. package/dist/{DropdownMenu-t90tVw6l.js.map → DropdownMenu-DpMEcyCq.js.map} +1 -1
  50. package/dist/{FieldItem-D-h1NeBo.js → FieldItem-qQKGU9lF.js} +3 -3
  51. package/dist/{FieldItem-D-h1NeBo.js.map → FieldItem-qQKGU9lF.js.map} +1 -1
  52. package/dist/{FieldItem-CAPj9lj3.d.ts → FieldItem-vhIJW4pj.d.ts} +2 -10
  53. package/dist/{FileUpload-BRv0TaZk.js → FileUpload-C336MVnU.js} +2 -2
  54. package/dist/{FileUpload-BRv0TaZk.js.map → FileUpload-C336MVnU.js.map} +1 -1
  55. package/dist/{Form-DHvcFoEi.js → Form-CTygENDc.js} +8 -8
  56. package/dist/{Form-DHvcFoEi.js.map → Form-CTygENDc.js.map} +1 -1
  57. package/dist/{FormGroup-C41n65cE.js → FormGroup-BnwP0jNu.js} +3 -3
  58. package/dist/{FormGroup-C41n65cE.js.map → FormGroup-BnwP0jNu.js.map} +1 -1
  59. package/dist/{FullScreenModal-Cb3PGgh4.js → FullScreenModal-j-M4aPFd.js} +3 -3
  60. package/dist/{FullScreenModal-Cb3PGgh4.js.map → FullScreenModal-j-M4aPFd.js.map} +1 -1
  61. package/dist/{HoverCard-WfDkLK1s.js → HoverCard-yQq-O49c.js} +2 -2
  62. package/dist/{HoverCard-WfDkLK1s.js.map → HoverCard-yQq-O49c.js.map} +1 -1
  63. package/dist/{InputGroup-CdTq8H7c.js → InputGroup-D7zlmqPB.js} +3 -3
  64. package/dist/{InputGroup-CdTq8H7c.js.map → InputGroup-D7zlmqPB.js.map} +1 -1
  65. package/dist/{Kbd-CxHAo1oo.js → Kbd-D6LpR7G2.js} +2 -2
  66. package/dist/{Kbd-CxHAo1oo.js.map → Kbd-D6LpR7G2.js.map} +1 -1
  67. package/dist/{MermaidDiagram-ChL3WIQT.js → MermaidDiagram-JlvuGcY-.js} +6 -87
  68. package/dist/MermaidDiagram-JlvuGcY-.js.map +1 -0
  69. package/dist/{Modal-wqG8nJiK.js → Modal-o4ATIexE.js} +3 -3
  70. package/dist/{Modal-wqG8nJiK.js.map → Modal-o4ATIexE.js.map} +1 -1
  71. package/dist/{MultiActionButtonGroup-BiIIubiL.js → MultiActionButtonGroup-GTeFk-L8.js} +3 -3
  72. package/dist/{MultiActionButtonGroup-BiIIubiL.js.map → MultiActionButtonGroup-GTeFk-L8.js.map} +1 -1
  73. package/dist/{Navbar-BfaPeLUL.js → Navbar-CAQs4BZz.js} +2 -2
  74. package/dist/{Navbar-BfaPeLUL.js.map → Navbar-CAQs4BZz.js.map} +1 -1
  75. package/dist/{PageToolbar-OQg3mPF-.js → PageToolbar-bG2YtSa3.js} +3 -3
  76. package/dist/{PageToolbar-OQg3mPF-.js.map → PageToolbar-bG2YtSa3.js.map} +1 -1
  77. package/dist/{Pagination-Cjfda8KG.js → Pagination-BB3X7ooY.js} +2 -2
  78. package/dist/{Pagination-Cjfda8KG.js.map → Pagination-BB3X7ooY.js.map} +1 -1
  79. package/dist/{Popconfirm-D7_vfxFd.js → Popconfirm-C2Ky5hJO.js} +3 -3
  80. package/dist/{Popconfirm-D7_vfxFd.js.map → Popconfirm-C2Ky5hJO.js.map} +1 -1
  81. package/dist/{Popover-CzeHjvrB.js → Popover-DsbI2HKu.js} +2 -2
  82. package/dist/{Popover-CzeHjvrB.js.map → Popover-DsbI2HKu.js.map} +1 -1
  83. package/dist/{RadioGroup-sIveSsNa.js → RadioGroup-BMxuZEbT.js} +3 -3
  84. package/dist/{RadioGroup-sIveSsNa.js.map → RadioGroup-BMxuZEbT.js.map} +1 -1
  85. package/dist/{Search-3UiqNZRj.js → Search-DFeECt5D.js} +2 -2
  86. package/dist/{Search-3UiqNZRj.js.map → Search-DFeECt5D.js.map} +1 -1
  87. package/dist/{SearchInput-C7dF_Ir-.js → SearchInput-CCpdUego.js} +3 -3
  88. package/dist/{SearchInput-C7dF_Ir-.js.map → SearchInput-CCpdUego.js.map} +1 -1
  89. package/dist/{SectionNav-8NoTOKO8.js → SectionNav-Bw_MVL0_.js} +4 -4
  90. package/dist/{SectionNav-8NoTOKO8.js.map → SectionNav-Bw_MVL0_.js.map} +1 -1
  91. package/dist/{Select-Is0VkePH.js → Select-D6IZVvwL.js} +5 -5
  92. package/dist/Select-D6IZVvwL.js.map +1 -0
  93. package/dist/{Sheet-Dw9BDvjI.js → Sheet-BIzs2K2H.js} +3 -3
  94. package/dist/{Sheet-Dw9BDvjI.js.map → Sheet-BIzs2K2H.js.map} +1 -1
  95. package/dist/{Sidebar-Dcb4rinA.js → Sidebar-r1TW4g_b.js} +5 -5
  96. package/dist/{Sidebar-Dcb4rinA.js.map → Sidebar-r1TW4g_b.js.map} +1 -1
  97. package/dist/{Slider-BOPfMOMm.js → Slider-CjxyfEty.js} +3 -3
  98. package/dist/{Slider-BOPfMOMm.js.map → Slider-CjxyfEty.js.map} +1 -1
  99. package/dist/{Switch-CX2A0v50.js → Switch-BueTV03C.js} +2 -2
  100. package/dist/{Switch-CX2A0v50.js.map → Switch-BueTV03C.js.map} +1 -1
  101. package/dist/{Tabs-UMQuDoW8.js → Tabs-l72-WuhK.js} +2 -2
  102. package/dist/{Tabs-UMQuDoW8.js.map → Tabs-l72-WuhK.js.map} +1 -1
  103. package/dist/{TextInput-CMuN1WfY.js → TextInput-DhdRk8qm.js} +3 -3
  104. package/dist/{TextInput-CMuN1WfY.js.map → TextInput-DhdRk8qm.js.map} +1 -1
  105. package/dist/{ThemeProvider-QncUrfJn.js → ThemeProvider-DZfGdf1v.js} +5 -4
  106. package/dist/{ThemeProvider-QncUrfJn.js.map → ThemeProvider-DZfGdf1v.js.map} +1 -1
  107. package/dist/{TimePicker-D9zktB8A.js → TimePicker-B6d2rAbX.js} +2 -2
  108. package/dist/{TimePicker-D9zktB8A.js.map → TimePicker-B6d2rAbX.js.map} +1 -1
  109. package/dist/{Toast-DQSbs3oA.js → Toast-CxXUulYN.js} +2 -2
  110. package/dist/{Toast-DQSbs3oA.js.map → Toast-CxXUulYN.js.map} +1 -1
  111. package/dist/{ZoomableSvg-CZEu6sAq.js → ZoomableSvg-CNIzRHKH.js} +4 -4
  112. package/dist/{ZoomableSvg-CZEu6sAq.js.map → ZoomableSvg-CNIzRHKH.js.map} +1 -1
  113. package/dist/{context-KxxeMHbR.js → context-BrNtMc1H.js} +3 -33
  114. package/dist/context-BrNtMc1H.js.map +1 -0
  115. package/dist/defaults-CTfvj2KB.js +34 -0
  116. package/dist/defaults-CTfvj2KB.js.map +1 -0
  117. package/dist/editors.d.ts +12 -2
  118. package/dist/editors.js +20 -12
  119. package/dist/editors.js.map +1 -1
  120. package/dist/flint.d.ts +15 -0
  121. package/dist/flint.js +212 -0
  122. package/dist/flint.js.map +1 -0
  123. package/dist/index.d.ts +49 -7
  124. package/dist/index.js +57 -55
  125. package/dist/internal/blocks/AIKit.js +1 -1
  126. package/dist/internal/blocks/AppShell.js +2 -2
  127. package/dist/internal/blocks/BrandEditor.js +1 -1
  128. package/dist/internal/blocks/ChartPanel.js +1 -1
  129. package/dist/internal/blocks/ClipboardButton.js +1 -1
  130. package/dist/internal/blocks/ColorInput.js +1 -1
  131. package/dist/internal/blocks/ColorModeSwitch.js +1 -1
  132. package/dist/internal/blocks/Command.js +1 -1
  133. package/dist/internal/blocks/CopyField.js +1 -1
  134. package/dist/internal/blocks/DateInput.js +1 -1
  135. package/dist/internal/blocks/DateRangeInput.js +1 -1
  136. package/dist/{DiagramSkeleton-lwBS2YBa.js → internal/blocks/DiagramShared/DiagramSkeleton.js} +3 -3
  137. package/dist/internal/blocks/DiagramShared/DiagramSkeleton.js.map +1 -0
  138. package/dist/internal/blocks/EmptyConfigurationActionCard.js +1 -1
  139. package/dist/internal/blocks/ErrorState.js +1 -1
  140. package/dist/internal/blocks/ExportMenu.js +3 -3
  141. package/dist/internal/blocks/Form/connectors/MultiComboboxField.js +1 -1
  142. package/dist/internal/blocks/Form.js +1 -1
  143. package/dist/internal/blocks/FormGroup.js +1 -1
  144. package/dist/internal/blocks/MultiActionButtonGroup.js +1 -1
  145. package/dist/internal/blocks/MultiCombobox.js +4 -3
  146. package/dist/internal/blocks/MultiCombobox.js.map +1 -1
  147. package/dist/internal/blocks/NumberInput.js +1 -1
  148. package/dist/internal/blocks/PageToolbar.js +1 -1
  149. package/dist/internal/blocks/PasswordInput.js +2 -2
  150. package/dist/internal/blocks/SearchInput.js +1 -1
  151. package/dist/internal/blocks/SearchInputWithNavigation.js +3 -3
  152. package/dist/internal/blocks/SectionNav.js +1 -1
  153. package/dist/internal/blocks/SplitButton.js +2 -2
  154. package/dist/internal/blocks/StatCard.js +1 -1
  155. package/dist/internal/blocks/TextInput.js +1 -1
  156. package/dist/internal/blocks/Textarea.js +1 -1
  157. package/dist/internal/blocks/TimeInput.js +3 -3
  158. package/dist/internal/components/Alert.js +1 -1
  159. package/dist/internal/components/AlertModal.js +1 -1
  160. package/dist/internal/components/Avatar.js +1 -1
  161. package/dist/internal/components/BrandLogo.js +1 -1
  162. package/dist/internal/components/Breadcrumb.js +1 -1
  163. package/dist/internal/components/Button.js +1 -1
  164. package/dist/internal/components/Card.js +1 -1
  165. package/dist/internal/components/Checkbox.js +1 -1
  166. package/dist/internal/components/Clipboard.js +1 -1
  167. package/dist/internal/components/CollapsiblePanel.js +1 -1
  168. package/dist/internal/components/Combobox.js +1 -1
  169. package/dist/internal/components/DatePicker.js +1 -1
  170. package/dist/internal/components/DateRangePicker.js +1 -1
  171. package/dist/internal/components/DropdownMenu.js +1 -1
  172. package/dist/internal/components/FileUpload.js +1 -1
  173. package/dist/internal/components/FullScreenModal.js +1 -1
  174. package/dist/internal/components/HoverCard.js +1 -1
  175. package/dist/internal/components/InputGroup.js +1 -1
  176. package/dist/internal/components/Kbd.js +1 -1
  177. package/dist/internal/components/Modal.js +1 -1
  178. package/dist/internal/components/Navbar.js +1 -1
  179. package/dist/internal/components/Pagination.js +1 -1
  180. package/dist/internal/components/Popconfirm.js +1 -1
  181. package/dist/internal/components/Popover.js +1 -1
  182. package/dist/internal/components/RadioGroup.js +1 -1
  183. package/dist/internal/components/Search.js +1 -1
  184. package/dist/internal/components/Select.js +1 -1
  185. package/dist/internal/components/Sheet.js +1 -1
  186. package/dist/internal/components/Sidebar.js +1 -1
  187. package/dist/internal/components/Slider.js +1 -1
  188. package/dist/internal/components/Switch.js +1 -1
  189. package/dist/internal/components/Tabs.js +1 -1
  190. package/dist/internal/components/ThemeProvider.js +3 -2
  191. package/dist/internal/components/TimePicker.js +1 -1
  192. package/dist/internal/components/Toast.js +2 -2
  193. package/dist/internal/components/Tooltip.js +1 -1
  194. package/dist/internal/components/Truncated.js +16 -8
  195. package/dist/internal/components/Truncated.js.map +1 -1
  196. package/dist/internal/components/ZoomableSvg.js +1 -1
  197. package/dist/internal/utils.js +1 -1
  198. package/dist/markdown-editor.js +7 -7
  199. package/dist/mermaid.js +1 -1
  200. package/dist/rjsf.js +11 -11
  201. package/dist/{styles-DSUP_-9Z.js → styles-BAFscjSV.js} +4 -3
  202. package/dist/styles-BAFscjSV.js.map +1 -0
  203. package/dist/styles.css +1 -1
  204. package/dist/svgTransforms-C9njt92h.js +89 -0
  205. package/dist/svgTransforms-C9njt92h.js.map +1 -0
  206. package/dist/testing.js +3 -2
  207. package/dist/testing.js.map +1 -1
  208. package/dist/{themeTokens-BNg98Mu9.js → themeTokens-7T1AFLhq.js} +13 -6
  209. package/dist/{themeTokens-BNg98Mu9.js.map → themeTokens-7T1AFLhq.js.map} +1 -1
  210. package/dist/{toast-CjkURw0M.js → toast-BweSoKn3.js} +3 -3
  211. package/dist/toast-BweSoKn3.js.map +1 -0
  212. package/dist/types-BPcAjMG0.d.ts +10 -0
  213. package/dist/{useColorSchemeState-CYqcUfSH.js → useColorSchemeState-BJEk6esG.js} +2 -2
  214. package/dist/{useColorSchemeState-CYqcUfSH.js.map → useColorSchemeState-BJEk6esG.js.map} +1 -1
  215. package/dist/{utils-D0c5VAyF.js → utils-B-g7d_Jb.js} +2 -2
  216. package/dist/{utils-D0c5VAyF.js.map → utils-B-g7d_Jb.js.map} +1 -1
  217. package/dist/vega.d.ts +46 -0
  218. package/dist/vega.js +26 -0
  219. package/dist/vega.js.map +1 -0
  220. package/dist/vegaTheme-FBXgAdHK.js +146 -0
  221. package/dist/vegaTheme-FBXgAdHK.js.map +1 -0
  222. package/package.json +26 -7
  223. package/src/styles.css +27 -4
  224. package/dist/AIKit-DiS0CVOW.js.map +0 -1
  225. package/dist/AppShell-B5GQN6Zs.js.map +0 -1
  226. package/dist/CodeEditor-DyaN-Ij2.js.map +0 -1
  227. package/dist/Combobox-Dgm6Z4ib.js.map +0 -1
  228. package/dist/DiagramSkeleton-lwBS2YBa.js.map +0 -1
  229. package/dist/MermaidDiagram-ChL3WIQT.js.map +0 -1
  230. package/dist/Select-Is0VkePH.js.map +0 -1
  231. package/dist/context-KxxeMHbR.js.map +0 -1
  232. package/dist/styles-DSUP_-9Z.js.map +0 -1
  233. package/dist/toast-CjkURw0M.js.map +0 -1
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CodeEditor-CUse8znx.js","names":["cmPlaceholder","placeholder"],"sources":["../src/components/CodeEditor/ButtonToolbar.tsx","../src/components/CodeEditor/modes/dbt.ts","../src/components/CodeEditor/modes/jsonnet.ts","../src/components/CodeEditor/diffWash.ts","../src/components/CodeEditor/syntaxPalette.ts","../src/components/CodeEditor/helpers.ts","../src/components/CodeEditor/editorChrome.ts","../src/components/CodeEditor/search.ts","../src/components/CodeEditor/ToggleComponentHelp.tsx","../src/components/CodeEditor/tokenTheme.ts","../src/components/CodeEditor/tooltips.ts","../src/components/CodeEditor/variableCompletion.ts","../src/components/CodeEditor/CodeEditor.tsx"],"sourcesContent":["import type { ReactNode } from 'react';\n\nimport { ClipboardButton } from '../../blocks/ClipboardButton';\n\n// Floats over the top-right corner of the editor it is rendered into — private to\n// `CodeEditor`, which is the `relative` ancestor it positions against. `right-3`\n// leaves room for the scrollbar track, whose width the browser owns and no token\n// here describes.\nexport const ButtonToolbar = ({ value, children }: { value?: string; children?: ReactNode }) => {\n if (!value && !children) return null;\n\n return (\n <div className=\"tw:absolute tw:right-3 tw:top-1 tw:z-10 tw:flex tw:gap-0.5 tw:overflow-visible tw:rounded tw:border tw:border-solid tw:border-border tw:!bg-background tw:p-px tw:shadow-sm\">\n {!!value && <ClipboardButton size=\"icon-xs\" variant=\"invisible\" text={value} />}\n {children}\n </div>\n );\n};\n","import type { Completion, CompletionContext, CompletionResult } from '@codemirror/autocomplete';\nimport { simpleMode } from '@codemirror/legacy-modes/mode/simple-mode';\n\n// A dbt step is `dbt <command> [<subcommand>] [arguments, flags and selectors]`,\n// and the vocabulary below is grouped by the slot it belongs to — both to colour\n// it and to decide what is worth offering where.\nconst COMMANDS = [\n 'run-operation',\n 'run',\n 'test',\n 'seed',\n 'snapshot',\n 'list',\n 'ls',\n 'compile',\n 'build',\n 'deps',\n 'docs',\n 'source',\n];\nconst SUBCOMMANDS: Record<string, string[]> = { docs: ['generate'], source: ['freshness'] };\nconst ARGUMENTS = ['--select', '--exclude', '--selector', '--defer', '--resource-type', '-s'];\n// The arguments whose value is a graph selector, and so the only ones a selector\n// method has anything to attach to.\nconst SELECTORS = ['--select', '--exclude', '-s'];\nconst METHODS = [\n 'path:',\n 'source:',\n 'tag:',\n 'package:',\n 'config:',\n 'test_type:',\n 'test_name:',\n 'state:',\n 'exposure:',\n 'metric:',\n 'result:',\n 'source_status:',\n 'column_name:',\n];\nconst FLAGS = [\n '--fail-fast',\n '--warn-error',\n '--favor-state',\n '--vars',\n '--models',\n '--threads',\n '--profiles-dir',\n '--profile',\n '--full-refresh',\n];\n\n// A subcommand only ever highlights together with its command, so `dbt docs` stays\n// unpainted until `generate` follows it.\nconst COMMAND_PHRASES = COMMANDS.flatMap((command) => {\n const subcommands = SUBCOMMANDS[command];\n\n return subcommands ? subcommands.map((subcommand) => `${command} ${subcommand}`) : [command];\n});\n\n// Alternation is first-match, so a word that prefixes another has to come first\n// (`run-operation` before `run`, `--profiles-dir` before `--profile`). Sorting by\n// length keeps that true however the lists above are written.\nconst alternation = (list: string[]) => [...list].sort((a, b) => b.length - a.length).join('|');\n\n// Every keyword follows whitespace, so the leading run is part of the match.\n// Commands and arguments end on a word boundary; methods and flags carry their\n// own terminator (`:`) or need none.\nconst word = (list: string[]) => new RegExp(`^\\\\s+(?:${alternation(list)})\\\\b`, 'i');\nconst prefix = (list: string[]) => new RegExp(`^\\\\s+(?:${alternation(list)})`, 'i');\n\n// The word being completed: letters, digits, `_`, `-` and the `:` a selector\n// method ends with. Whitespace stays out of it, so a two-word label like `docs\n// generate` cannot stretch the match back across the words before the cursor.\nconst WORD = /[\\w:-]*$/;\n\nconst asOptions = (list: string[], type: string): Completion[] =>\n list.map((label) => ({ label, type }));\n\n// `type` drives the popup icon, so each group carries the one that matches the\n// colour the mode paints it in.\nconst DBT: Completion[] = [{ label: 'dbt', type: 'keyword' }];\nconst COMMAND_OPTIONS = asOptions(COMMANDS, 'keyword');\nconst SUBCOMMAND_OPTIONS: Record<string, Completion[]> = Object.fromEntries(\n Object.entries(SUBCOMMANDS).map(([command, subcommands]) => [\n command,\n asOptions(subcommands, 'keyword'),\n ]),\n);\nconst ARGUMENT_OPTIONS = asOptions(ARGUMENTS, 'variable');\nconst FLAG_OPTIONS = asOptions(FLAGS, 'constant');\nconst METHOD_OPTIONS = asOptions(METHODS, 'property');\n\n// Which slice of the vocabulary the cursor's slot can hold, given the words\n// already finished ahead of it. Offering the whole vocabulary everywhere proposes\n// `dbt` mid-command and a selector method with no selector to attach to.\nconst optionsAfter = (words: string[]): Completion[] => {\n const [step, command, ...rest] = words;\n\n if (step === undefined) return DBT;\n if (step.toLowerCase() !== 'dbt') return [];\n if (command === undefined) return COMMAND_OPTIONS;\n\n const subcommands = SUBCOMMAND_OPTIONS[command.toLowerCase()];\n if (subcommands && rest.length === 0) return subcommands;\n\n // A selector argument takes any number of space-separated values, so what\n // decides the slot is the last argument, not whether a selector appeared at all:\n // `--select tag:a tag:b` keeps offering methods, `--select a --profile p` stops.\n const lastArgument = rest.filter((it) => it.startsWith('-')).at(-1);\n const selecting = lastArgument !== undefined && SELECTORS.includes(lastArgument.toLowerCase());\n\n return selecting\n ? [...ARGUMENT_OPTIONS, ...FLAG_OPTIONS, ...METHOD_OPTIONS]\n : [...ARGUMENT_OPTIONS, ...FLAG_OPTIONS];\n};\n\nconst complete = (context: CompletionContext): CompletionResult | null => {\n const typed = context.matchBefore(WORD);\n\n // `WORD` also matches the empty string, so without this the popup would open on\n // every space. Asking for completions explicitly still opens it there.\n if (!typed?.text && !context.explicit) return null;\n\n const from = typed?.from ?? context.pos;\n const line = context.state.doc.lineAt(from);\n const options = optionsAfter(\n line.text\n .slice(0, from - line.from)\n .split(/\\s+/)\n .filter(Boolean),\n );\n\n return options.length > 0 ? { from, options, validFor: WORD } : null;\n};\n\nexport const dbt = simpleMode({\n languageData: {\n // `toggleComment` is a no-op without these, so Mod-/ silently does nothing.\n commentTokens: { line: '--', block: { open: '/*', close: '*/' } },\n autocomplete: complete,\n },\n start: [\n { regex: /\"(?:[^\\\\]|\\\\.)*?(?:\"|$)/, token: 'string' },\n // Word-bounded, so `dbtX` is not a dbt step whose first word happens to\n // colour — the same thing the completion source asks of it.\n { regex: /dbt\\b/, token: 'keyword', sol: true },\n { regex: word(COMMAND_PHRASES), token: 'keyword' },\n { regex: word(ARGUMENTS), token: 'variableName' },\n { regex: prefix(METHODS), token: 'propertyName' },\n { regex: prefix(FLAGS), token: 'attributeName' },\n { regex: /(?:@|\\*|,|\\+\\d+|\\d+\\+|\\+)/, token: 'operator' },\n { regex: /'.*'/, token: 'string' },\n { regex: /true|false/, token: 'atom' },\n ],\n});\n","import type { StreamParser } from '@codemirror/language';\n\n/**\n * Ported from google/codemirror-mode-jsonnet (Apache-2.0), the mode written by\n * the language's own authors, which was never taken past CodeMirror 5.\n * CodeMirror 5 style names are replaced by their CodeMirror 6 highlight tags:\n * `string-2` is `escape`, `error` is `invalid`.\n *\n * Every pattern is anchored and hoisted. `StringStream.match` slices the rest of\n * the line and, without `^`, scans all of it for a match it then discards unless\n * it started at the cursor — so an unanchored probe costs the whole remaining\n * line, and this tokenizer makes up to twenty of them per token.\n */\n\nconst COMMENT_END = /^\\*\\//;\nconst COMMENT_START = /^\\/\\/|^#/;\nconst C_COMMENT_START = /^\\/\\*/;\nconst TEXT_BLOCK = /^\\|\\|\\|/;\nconst TEXT_BLOCK_END = /^\\s*\\|\\|\\|/;\nconst RAW_DOUBLE = /^\"\"/;\nconst RAW_SINGLE = /^''/;\nconst CLOSE_DOUBLE = /^\"/;\nconst CLOSE_SINGLE = /^'/;\nconst ESCAPE = /^\\\\[\\\\\"'/bfnrt0]/;\nconst UNICODE_ESCAPE = /^\\\\u[0-9a-fA-F]{4}/;\nconst BACKSLASH = /^\\\\/;\nconst IMPORT = /^import(?:str)?\\s*(@?)([\"'])/;\nconst QUOTE = /^(@?)([\"'])/;\nconst ROOT = /^\\$/;\nconst NUMBER = /^(?:\\.\\d+|\\d+\\.?\\d*)(?:e[-+]?\\d+)?/i;\nconst OPERATOR = /^[-+/*=<>!&~^|$%]+/;\nconst IDENTIFIER = /^[a-zA-Z_][a-zA-Z0-9_]*/;\n\nconst KEYWORDS: Record<string, 'keyword' | 'atom'> = {\n local: 'keyword',\n self: 'keyword',\n super: 'keyword',\n assert: 'keyword',\n function: 'keyword',\n if: 'keyword',\n then: 'keyword',\n else: 'keyword',\n for: 'keyword',\n in: 'keyword',\n tailstrict: 'keyword',\n error: 'keyword',\n true: 'atom',\n false: 'atom',\n null: 'atom',\n};\n\ntype State = {\n cComment: boolean;\n textBlock: boolean;\n textBlockIndent: number | null;\n string: boolean;\n importString: boolean;\n stringSingle: boolean;\n stringRaw: boolean;\n};\n\nexport const jsonnet: StreamParser<State> = {\n name: 'jsonnet',\n\n // `toggleComment` is a no-op without these, so Mod-/ silently does nothing.\n languageData: { commentTokens: { line: '//', block: { open: '/*', close: '*/' } } },\n\n startState: () => ({\n cComment: false,\n textBlock: false,\n textBlockIndent: null,\n string: false,\n importString: false,\n stringSingle: false,\n stringRaw: false,\n }),\n\n token: (stream, state) => {\n if (state.cComment) {\n if (stream.match(COMMENT_END)) {\n state.cComment = false;\n return 'comment';\n }\n stream.next();\n return 'comment';\n }\n\n // A `|||` block runs from its own first content line to the first line\n // indented less than that — so the closing `|||` has to be recognised\n // before the indent is measured, or a block closed at column 0 never ends.\n if (state.textBlock) {\n if (state.textBlockIndent == null) {\n if (stream.match(TEXT_BLOCK_END)) {\n state.textBlock = false;\n return 'string';\n }\n state.textBlockIndent = stream.indentation();\n }\n if (stream.indentation() >= state.textBlockIndent) {\n stream.skipToEnd();\n return 'string';\n }\n if (stream.match(TEXT_BLOCK_END)) {\n state.textBlock = false;\n return 'string';\n }\n stream.next();\n return 'invalid';\n }\n\n // Quoted and `@`-raw strings, single or double, plain or after an import.\n if (state.string || state.importString) {\n const style = state.string ? 'string' : 'meta';\n\n if (state.stringRaw) {\n if (stream.match(state.stringSingle ? RAW_SINGLE : RAW_DOUBLE)) return 'escape';\n } else {\n if (stream.match(ESCAPE)) return 'escape';\n if (stream.match(UNICODE_ESCAPE)) return 'escape';\n if (stream.match(BACKSLASH)) return 'invalid';\n }\n\n if (stream.match(state.stringSingle ? CLOSE_SINGLE : CLOSE_DOUBLE)) {\n state.string = false;\n state.importString = false;\n return style;\n }\n\n stream.next();\n return style;\n }\n\n if (stream.match(COMMENT_START)) {\n stream.skipToEnd();\n return 'comment';\n }\n if (stream.match(C_COMMENT_START)) {\n state.cComment = true;\n return 'comment';\n }\n\n // An import opens a string that is styled as meta rather than as content.\n const imported = stream.match(IMPORT);\n if (Array.isArray(imported)) {\n state.importString = true;\n state.stringRaw = imported[1] === '@';\n state.stringSingle = imported[2] === \"'\";\n return 'meta';\n }\n\n const quoted = stream.match(QUOTE);\n if (Array.isArray(quoted)) {\n state.string = true;\n state.stringRaw = quoted[1] === '@';\n state.stringSingle = quoted[2] === \"'\";\n return 'string';\n }\n\n if (stream.match(TEXT_BLOCK)) {\n state.textBlock = true;\n state.textBlockIndent = null;\n return 'string';\n }\n\n if (stream.match(ROOT)) return 'keyword';\n if (stream.match(NUMBER)) return 'number';\n if (stream.match(OPERATOR)) return 'operator';\n\n // Consumed whole so that a keyword's prefix (`locally`) is not styled.\n const identifier = stream.match(IDENTIFIER);\n if (Array.isArray(identifier)) return KEYWORDS[identifier[0]] ?? null;\n\n stream.next();\n return null;\n },\n};\n","import type { ResolvedColorScheme } from '../ThemeProvider/types';\n\n/**\n * Alpha suffixes for the dark-scheme diff and state tints.\n *\n * - The line fill stays subtle enough for the `foreground` text to read; the gutter sits a step\n * stronger so the scan-lane is still obvious next to it.\n * - `DARK_LINE_ALPHA` also carries the run-state and search washes in `highlighting.ts` and\n * `search.ts`, which are static base themes and so append the suffix themselves.\n */\nexport const DARK_LINE_ALPHA = '29'; /* 16% */\nconst DARK_GUTTER_ALPHA = '47'; /* 28% */\n\n/**\n * The two diff fills, per scheme: light keeps the opaque pastel, dark tints the same `500` hue at\n * low alpha over whatever token surface is behind it.\n *\n * - Its own module, importing nothing, so `MergeEditor` can share it without reaching into\n * `CodeEditor/helpers.ts` and pulling the language modes and the CodeMirror runtime with it.\n * - Shared by the unified merge wash in `helpers.ts` and `buildDiffHighlightTheme` in\n * `MergeEditor/decorations.ts`, so the two views cannot drift apart on the alphas.\n * - Callers pass the hue and the pastel; which one is used is this function's business.\n */\nexport const buildDiffWash = (scheme: ResolvedColorScheme) => {\n const dark = scheme === 'dark';\n\n return {\n line: (hue: string, pastel: string) => (dark ? `${hue}${DARK_LINE_ALPHA}` : pastel),\n gutter: (hue: string, pastel: string) => (dark ? `${hue}${DARK_GUTTER_ALPHA}` : pastel),\n };\n};\n","import { tags } from '@lezer/highlight';\n\nimport colors from '@keboola/tailwind-config/colors';\n\nimport type { ResolvedColorScheme } from '../ThemeProvider/types';\n\n/**\n * The tag colours layered over the stock github palette, per colour scheme.\n *\n * - Its own module, importing nothing but the tag vocabulary and the ramps, so\n * `scripts/contrast-audit.ts` can measure the palette without pulling the language modes and the\n * CodeMirror runtime into a build script.\n * - Later entries win over the stock rule for the same tag — both `githubLightInit` and\n * `githubDarkInit` concatenate these after their own.\n * - `foreground` is the caller's, because it is a live `--*` token rather than a ramp step: the\n * theme passes `resolveToken('foreground')`, the audit passes the scheme's channel value.\n * - Every ramp step here is a light/dark pair, and each pair is chosen against **two** surfaces —\n * the theme's `background` setting is the page, but `variant=\"field\"` paints on `muted`, which\n * the theme never sees. Ratios in the comments are quoted `background` / `muted`.\n */\nexport const buildSyntaxPalette = (scheme: ResolvedColorScheme, foreground: string) => {\n const dark = scheme === 'dark';\n\n return [\n // Plain identifiers, quoted identifiers (`\"a column\"`) and brackets carry no colour of their\n // own, matching github.com's own rendering — stock github lumps brackets in with comments.\n { tag: [tags.name, tags.special(tags.string), tags.bracket], color: foreground },\n // Functions — light `600` 6.13 / 5.84, dark `300` 9.62 / 7.80.\n { tag: tags.standard(tags.name), color: dark ? colors.purple[300] : colors.purple[600] },\n // Special vars — light `800` 7.26 / 6.92, dark `300` 13.49 / 10.94.\n { tag: tags.special(tags.name), color: dark ? colors.cyan[300] : colors.cyan[800] },\n // Strings — light `800` 7.23 / 6.89, dark `300` 13.53 / 10.97.\n { tag: tags.string, color: dark ? colors.warning[300] : colors.warning[800] },\n // The four below re-target stock light colours that sit below AA, each to the nearest step of\n // our own ramp in the same hue. Dark needs none of them — `githubDarkStyle` clears AA on every\n // surface — so under dark they fall through to it.\n //\n // Ratios are `background` / `muted`; `CONTRAST-AUDIT.md` carries all four surfaces and the\n // stock values these replace.\n ...(dark\n ? []\n : [\n // Keywords — 5.96 / 5.69, from 4.38 / 4.18.\n { tag: [tags.keyword, tags.typeName, tags.typeOperator], color: colors.error[550] },\n // Comments — 6.44 / 6.15, from 4.61 / 4.40.\n { tag: tags.comment, color: colors.neutral[500] },\n // Markdown quotes — 7.15 / 6.82, from 4.43 / 4.22.\n { tag: tags.quote, color: colors.green[900] },\n // Lex errors — 7.81 / 7.45. The stock red clears both of these and fails the read-only\n // wash at 4.44, the darkest of the four surfaces an editor paints on.\n { tag: tags.invalid, color: colors.error[700] },\n ]),\n // Dark only, because `githubDarkStyle` carries no `escape` rule where the light array does.\n // The jsonnet mode emits it for `\\n` and `\\uXXXX`; unpainted, those fall back to `foreground`\n // and stop being distinguishable from the amber string body they sit in. `blue[300]` is\n // 10.97 / 8.90 and reads as \"special, inside a string\" against that amber.\n ...(dark ? [{ tag: [tags.escape, tags.url, tags.link], color: colors.blue[300] }] : []),\n ];\n};\n","import { javascript } from '@codemirror/lang-javascript';\nimport { json, jsonParseLinter } from '@codemirror/lang-json';\nimport { python } from '@codemirror/lang-python';\nimport { MSSQL, MySQL, PLSQL, PostgreSQL, StandardSQL } from '@codemirror/lang-sql';\nimport { StreamLanguage } from '@codemirror/language';\nimport { r } from '@codemirror/legacy-modes/mode/r';\nimport { shell } from '@codemirror/legacy-modes/mode/shell';\nimport { toml } from '@codemirror/legacy-modes/mode/toml';\nimport type { LintSource } from '@codemirror/lint';\nimport { linter } from '@codemirror/lint';\nimport { githubDarkInit, githubLightInit } from '@uiw/codemirror-theme-github';\nimport type { BasicSetupOptions } from '@uiw/react-codemirror';\n\nimport { getSqlLanguageSupport } from '@keboola/codemirror-lang-sql';\nimport colors from '@keboola/tailwind-config/colors';\n\nimport { resolveToken } from '../../utils/themeTokens';\nimport type { ResolvedColorScheme } from '../ThemeProvider/types';\n\nimport { dbt } from './modes/dbt';\nimport { jsonnet } from './modes/jsonnet';\nimport { buildDiffWash } from './diffWash';\nimport { buildSyntaxPalette } from './syntaxPalette';\n\n// The MIME vocabulary callers pass. Kept as a const so the runtime whitelist and\n// the type stay one list — an annotated `LANGUAGE_MODE[]` copy elsewhere silently\n// drifts, since the type checker accepts a short one.\nexport const LANGUAGE_MODES = [\n 'application/json',\n 'text/plain',\n 'text/x-python',\n 'text/x-sql',\n 'text/x-mysql',\n 'text/x-pgsql',\n 'text/x-mssql',\n // Snowflake, under a historical name — these strings are a published prop contract.\n 'text/x-sfsql',\n 'text/x-bqsql',\n 'text/x-plsql',\n 'text/x-rsrc',\n 'text/x-sh',\n 'text/x-toml',\n 'text/jsonnet',\n 'text/x-dbt',\n 'text/javascript',\n 'text/typescript',\n] as const;\n\nexport type LANGUAGE_MODE = (typeof LANGUAGE_MODES)[number];\n\nexport const isLanguageMode = (mode: string): mode is LANGUAGE_MODE =>\n (LANGUAGE_MODES as readonly string[]).includes(mode);\n\n// `readOnly` reaches CodeMirror as `contenteditable`, so the two states are only\n// addressable through it. Exported because `fieldChrome` overrides the read-only\n// wash below by re-declaring the same key — which only works while the strings\n// match exactly.\nexport const READ_ONLY_EDITOR = '&.cm-editor:has(.cm-content[contenteditable=\"false\"])';\nexport const EDITABLE_EDITOR = '&.cm-editor:has(.cm-content[contenteditable=\"true\"])';\n\n/**\n * Editor chrome and the unified merge (diff) wash.\n *\n * - Chrome surfaces (selection, read-only wash) resolve from live `--*` tokens, so they re-skin\n * with brand and colour scheme. Fallback channels mirror the light-mode token values for SSR /\n * no-provider parity.\n * - Diff colours stay categorical — fixed across brands, because added/removed is meaning, not\n * chrome — but each is a light/dark pair from `buildDiffWash`, shared with\n * `buildDiffHighlightTheme` in `MergeEditor/decorations.ts`.\n * - This wash reaches only `CodeEditor`'s *unified* merge view — the one a `previousValue` turns on.\n * `MergePane` builds its own theme from scratch.\n */\nexport const buildBaseThemeStyles = (scheme: ResolvedColorScheme) => {\n const { line, gutter } = buildDiffWash(scheme);\n const dark = scheme === 'dark';\n\n return {\n '*': { lineHeight: '20px' },\n '*::selection': {\n backgroundColor: resolveToken('primary', '31 143 255'),\n color: `${resolveToken('primary-foreground', '255 255 255')} !important`,\n },\n // The recessed wash. `secondary` sits a step darker than `muted` in light but a step *lighter*\n // in dark, where it would take the palette's tightest colour (`comment`) to 4.27:1 — so dark\n // asks for `muted` (4.89:1). The inversion is a token-system quirk, not an editor one.\n [READ_ONLY_EDITOR]: {\n backgroundColor: dark\n ? resolveToken('muted', '38 38 45')\n : resolveToken('secondary', '226 232 240'),\n },\n [`${READ_ONLY_EDITOR} .cm-gutters`]: {\n backgroundColor: resolveToken('border', '229 231 235'),\n },\n '&.cm-editor .cm-scroller': { overflowAnchor: 'none' },\n '&.cm-editor, &.cm-editor .cm-scroller': {\n minHeight: '100%',\n flexGrow: 1,\n alignItems: 'stretch !important',\n outline: 'none',\n },\n '.cm-gutter.cm-foldGutter': { display: 'none !important' },\n '.cm-gutter.cm-lineNumbers': { paddingLeft: '20px', paddingRight: '6px' },\n '.cm-gutters': { height: 'auto' },\n\n // merge (diff) view\n '&[class*=\"cm-merge-\"] .cm-deletedLine': {\n backgroundColor: line(colors.error[500], colors.error[100]),\n },\n '&[class*=\"cm-merge-\"] .cm-changedLine': {\n backgroundColor: line(colors.green[500], colors.green[100]),\n },\n '&[class*=\"cm-merge-\"] .cm-deletedLineGutter': {\n backgroundColor: gutter(colors.error[500], colors.error[200]),\n },\n '&[class*=\"cm-merge-\"] .cm-changedLineGutter': {\n backgroundColor: gutter(colors.green[500], colors.green[200]),\n },\n '&[class*=\"cm-merge-\"] .cm-deletedText': {\n background: gutter(colors.error[500], colors.error[200]),\n },\n '&[class*=\"cm-merge-\"] .cm-changedText': {\n background: gutter(colors.green[500], colors.green[200]),\n },\n // The container and its gutter follow the page, not the diff — a fixed white here would be the\n // whole editor as a light slab under dark.\n '&[class*=\"cm-merge-\"]': {\n backgroundColor: `${resolveToken('background', '249 250 251')} !important`,\n },\n '&[class*=\"cm-merge-\"] .cm-gutters': {\n backgroundColor: `${resolveToken('muted', '241 245 249')} !important`,\n },\n '.cm-changeGutter': { position: 'absolute', zIndex: -1, width: '100%', paddingLeft: 0 },\n '&[class*=\"cm-merge-\"] .cm-changedLine,&[class*=\"cm-merge-\"] .cm-line, &[class*=\"cm-merge-\"] .cm-deletedChunk':\n { paddingLeft: 0 },\n };\n};\n\n// Dead whatever the editor does with them: `buildBaseThemeStyles` hides the fold\n// gutter outright, and `buildCustomTheme` paints the active line transparent.\n//\n// `autocompletion` is off because both editors install their own and a second instance\n// is not a no-op: `CodeEditor` gates its copy on `readOnly` and on `withCompletions`,\n// and `SqlEditor` passes options through `installExtensions`, which basicSetup's\n// option-less copy would compete with.\nconst ALWAYS_OFF = {\n autocompletion: false,\n drawSelection: false,\n foldGutter: false,\n foldKeymap: false,\n highlightActiveLine: false,\n highlightActiveLineGutter: false,\n} as const;\n\n// `basicSetup` enables everything it is not told to skip, so a viewer would\n// otherwise install bracket closing and keybindings for commands a read-only\n// document rejects. Search stays — Mod-f is useful on a viewer. Same reasoning\n// as `shouldLintJson` below.\n//\n// `history` stays too, though a viewer can never add an entry: a caller that\n// flips `readOnly` mid-session reconfigures the view, and a reconfigure discards\n// state fields the new configuration doesn't have. Leaving it out saves nothing\n// and costs the editable session its undo stack.\nexport const buildBasicSetup = (readOnly: boolean): BasicSetupOptions => ({\n ...ALWAYS_OFF,\n ...(readOnly\n ? {\n closeBrackets: false,\n closeBracketsKeymap: false,\n lintKeymap: false,\n indentOnInput: false,\n rectangularSelection: false,\n dropCursor: false,\n highlightSelectionMatches: false,\n }\n : null),\n});\n\n/**\n * The syntax theme, per colour scheme.\n *\n * - The stock github palette is picked by scheme: `githubDarkInit` under dark, `githubLightInit`\n * otherwise. One palette cannot serve both — the light set scores 1.14:1 to 4.31:1 on the two\n * dark surfaces, so 10 of its 11 colours failed AA there (UT-5194).\n * - `githubDarkInit` also passes `dark: true` to `EditorView.theme`, which sets the\n * `EditorView.darkTheme` facet. That is what makes the `&dark` rules apply — CodeMirror's own\n * base theme (cursor, selection layer, panels, buttons) and ours (`search.ts`,\n * `highlighting.ts`) both key off it, so they follow the scheme without a second signal.\n * - Chrome (surface, gutter, selection, caret) resolves from live `--*` tokens, so it re-skins with\n * the brand too. Fallback channels mirror the light-mode token values, for SSR and jsdom.\n * - `caret` and `selectionMatch` are pinned because the two initialisers disagree on them, and the\n * branch would otherwise change values nothing here chose. The caret follows `foreground`; before\n * the facet was set, CodeMirror's own default painted it black on the dark page, so it was\n * invisible. `selectionMatch` is a 10% `primary` tint, which beats each initialiser's own value\n * on the token it hurts most: 3.82:1 against the light default's 3.29, 5.40:1 against the dark\n * default's 3.57. Any occurrence wash costs contrast — this is the cheapest one, and it is the\n * same in both schemes.\n * - `styles` comes from `buildSyntaxPalette`, which lives apart so the audit script can measure it.\n *\n * Those overrides exist because the github theme paints every `name`-family tag one colour, and in\n * SQL nearly every token is a name — identifiers, function calls and `$variables` all drowned\n * together, and a keyword that doubles as a function (`create or REPLACE`) read as a value\n * (UT-5024). Instead: identifiers and brackets carry no colour, functions and special vars get\n * their own hues, and amber is unique to string literals — in JSON that shifts string values from\n * navy to amber, the one visible non-SQL change.\n */\nexport const buildCustomTheme = (scheme: ResolvedColorScheme) => {\n const foreground = resolveToken('foreground', '30 41 59');\n const init = scheme === 'dark' ? githubDarkInit : githubLightInit;\n\n return init({\n settings: {\n fontFamily: `'SFMono-Regular', 'Menlo', 'Monaco', 'Consolas', 'Liberation Mono', 'Courier New'`,\n background: resolveToken('background', '249 250 251'),\n foreground,\n caret: foreground,\n gutterBackground: resolveToken('muted', '241 245 249'),\n gutterForeground: resolveToken('muted-foreground', '100 116 139'),\n gutterBorder: 'transparent',\n lineHighlight: 'transparent',\n selection: resolveToken('primary', '31 143 255'),\n selectionMatch: resolveToken('primary', '31 143 255', 0.1),\n },\n styles: buildSyntaxPalette(scheme, foreground),\n });\n};\n\nexport const getLanguageMode = (mode?: LANGUAGE_MODE) => {\n switch (mode) {\n case undefined:\n case 'application/json':\n return json();\n case 'text/x-python':\n return python();\n case 'text/x-sql':\n return getSqlLanguageSupport(StandardSQL);\n case 'text/x-mysql':\n return getSqlLanguageSupport(MySQL);\n case 'text/x-pgsql':\n return getSqlLanguageSupport(PostgreSQL);\n case 'text/x-mssql':\n return getSqlLanguageSupport(MSSQL);\n case 'text/x-sfsql':\n return getSqlLanguageSupport('snowflake');\n case 'text/x-bqsql':\n return getSqlLanguageSupport('bigquery');\n case 'text/x-plsql':\n return getSqlLanguageSupport(PLSQL);\n case 'text/x-rsrc':\n return StreamLanguage.define(r);\n case 'text/x-sh':\n return StreamLanguage.define(shell);\n case 'text/x-toml':\n return StreamLanguage.define(toml);\n case 'text/jsonnet':\n return StreamLanguage.define(jsonnet);\n case 'text/x-dbt':\n return StreamLanguage.define(dbt);\n case 'text/javascript':\n return javascript({ jsx: true });\n case 'text/typescript':\n return javascript({ jsx: true, typescript: true });\n // No language — `text/plain` lands here, and so does any mode added to\n // LANGUAGE_MODES without an arm above. Unstyled text is the safe degradation;\n // a `json()` default would colour unrelated content as if it were JSON.\n default:\n return [];\n }\n};\n\n// The JSON parse linter is only useful on an editable editor — a read-only one\n// can't act on the errors, so running it is wasted work and its underlines are\n// noise (e.g. non-strict JSON shown read-only in Kai chat).\nexport const shouldLintJson = (mode: LANGUAGE_MODE | undefined, readOnly: boolean): boolean =>\n mode === 'application/json' && !readOnly;\n\n/**\n * Wraps a lint source so a blank document produces no diagnostics.\n *\n * `jsonParseLinter` reports \"Unexpected end of input\" for empty content, which is right for a file and\n * wrong for an *optional* form field: it starts empty, and clearing it is how its value is removed.\n * Left unwrapped, every such field opens with a red gutter marker contradicting its own validation —\n * `CodeEditorField` puts six of them on one screen.\n *\n * Exported for its test: the wrapper is the behaviour worth pinning, and it needs no editor to exercise.\n */\nexport const skipBlankDocument =\n (source: LintSource): LintSource =>\n (view) =>\n view.state.doc.toString().trim() === '' ? [] : source(view);\n\n/**\n * The JSON linter, optionally blind to a blank document.\n *\n * - `allowBlankDocument` is opt-in, and only `CodeEditorField` opts in (from `!required`). Suppressing\n * the marker by default would break callers that treat empty as invalid *and* say so nowhere else:\n * `ex-generic/JsonConfiguration.tsx`, `flows/TaskParamsModalContent.tsx` and\n * `stream/PayloadTest.tsx` all gate their button on `isValidJsonConfig`, which is `false` for `''`,\n * with no `disabledReason` — so the gutter marker is the only thing explaining a dead button.\n * - Not derivable from `variant`: `ex-generic/FunctionControl.tsx` is `variant=\"field\"` and empty is\n * an error there too. Whether blank is valid is the *field's* contract, not the control's shape.\n */\nexport const buildJsonLinter = (allowBlankDocument: boolean) => {\n const source = jsonParseLinter();\n\n return linter(allowBlankDocument ? skipBlankDocument(source) : source);\n};\n","import colors from '@keboola/tailwind-config/colors';\n\nimport { resolveToken } from '../../utils/themeTokens';\nimport type { ResolvedColorScheme } from '../ThemeProvider/types';\n\nimport { EDITABLE_EDITOR, READ_ONLY_EDITOR } from './helpers';\n\n/**\n * The parts of an editor's outer chrome that differ between presets; how they\n * reach CodeMirror's selectors lives once in `buildChromeStyles`.\n */\nexport type EditorChrome = {\n surface: string;\n borderColor: string;\n readOnlySurface: string;\n readOnlyBorderColor: string;\n /** `null` for a preset with no hover affordance — form inputs have none. */\n hoverBorderColor: string | null;\n focusBorderColor: string;\n focusRing: string;\n radius: string;\n paddingY: string;\n /** `null` leaves CodeMirror's own 6px/2px line inset alone. */\n paddingX: { left: string; right: string } | null;\n};\n\n/**\n * Mirrors `InputGroup` at the sizing each design language gives a `TextInput`,\n * so an editor dropped into a form reads as one of its fields.\n *\n * The legacy preset reads the neutral ramp because the legacy `secondary`\n * variant does. No semantic token holds that grey, and the nearest one\n * (`--muted`) is a few points off — which is the \"almost, but not quite, the\n * input next to it\" mismatch this preset exists to remove.\n *\n * That ramp is fixed, so the legacy preset needs its own scheme pair — a legacy brand and the dark\n * scheme are independent choices, and `neutral[100]` under dark is a light slab: `foreground` on it\n * is 1.09:1 and the darkest syntax colour 2.69:1. Dark mirrors the same two steps from the other\n * end of the ramp (`800` / `900`, 5.00:1 and 6.14:1 for that colour).\n */\nexport const buildInputChrome = (isArgo: boolean, scheme: ResolvedColorScheme): EditorChrome => {\n const dark = scheme === 'dark';\n const legacySurface = dark ? colors.neutral[800] : colors.neutral[100];\n const legacyReadOnly = dark ? colors.neutral[900] : colors.neutral[150];\n\n return {\n surface: isArgo ? resolveToken('muted', '241 245 249') : legacySurface,\n borderColor: isArgo ? resolveToken('input', '203 213 225') : legacySurface,\n readOnlySurface: isArgo ? resolveToken('muted', '241 245 249') : legacyReadOnly,\n readOnlyBorderColor: isArgo ? resolveToken('input', '203 213 225') : legacyReadOnly,\n hoverBorderColor: null,\n focusBorderColor: isArgo\n ? resolveToken('primary', '37 99 235')\n : resolveToken('ring', '31 143 255'),\n focusRing: `0 0 0 4px ${resolveToken('ring', '31 143 255', isArgo ? 0.5 : 0.3)}`,\n radius: isArgo ? 'var(--radius-lg, 0.25rem)' : '0.25rem',\n // 2px border + 2×this + `.cm-content`'s own 4px + a 20px line, against the\n // height a one-line `TextInput` has: argo forces `sizing: 'medium'` (36px),\n // legacy leaves it at `default` (40px).\n paddingY: isArgo ? '3px' : '5px',\n // Tops `.cm-line`'s 6px/2px up to the 16px an input's text is inset by.\n paddingX: { left: '10px', right: '14px' },\n };\n};\n\n/** The SQL workspace's notebook cell: a white canvas, not a form control. */\nexport const buildCanvasChrome = (): EditorChrome => ({\n surface: resolveToken('card', '255 255 255'),\n borderColor: 'transparent',\n readOnlySurface: resolveToken('muted', '241 245 249'),\n readOnlyBorderColor: 'transparent',\n hoverBorderColor: resolveToken('ring', '31 143 255'),\n focusBorderColor: resolveToken('ring', '31 143 255'),\n focusRing: `0 0 0 4px ${resolveToken('ring', '31 143 255', 0.3)}`,\n radius: '8px',\n paddingY: '8px',\n paddingX: null,\n});\n\n/**\n * Spread over `buildBaseThemeStyles()` — never used alone. The read-only keys\n * are the base's own, so they replace its wash instead of landing beside it.\n */\nexport const buildChromeStyles = (chrome: EditorChrome) => ({\n '&.cm-editor': {\n border: `solid 1px ${chrome.borderColor}`,\n borderRadius: chrome.radius,\n backgroundColor: chrome.surface,\n paddingTop: chrome.paddingY,\n paddingBottom: chrome.paddingY,\n },\n '&.cm-editor :is(.cm-gutters,.cm-scroller)': { backgroundColor: chrome.surface },\n\n ...(chrome.paddingX\n ? {\n // Only without a gutter: there the editor reads as a one-line input and\n // its text should start where a neighbouring `TextInput`'s does. With a\n // gutter, the gutter owns the left edge.\n '&.cm-editor:not(:has(.cm-gutters)) .cm-content': {\n paddingLeft: chrome.paddingX.left,\n paddingRight: chrome.paddingX.right,\n },\n }\n : null),\n\n ...(chrome.hoverBorderColor\n ? { [`${EDITABLE_EDITOR}:hover`]: { borderColor: chrome.hoverBorderColor } }\n : null),\n [`${EDITABLE_EDITOR}:focus-within`]: {\n borderColor: chrome.focusBorderColor,\n boxShadow: chrome.focusRing,\n },\n\n [READ_ONLY_EDITOR]: {\n backgroundColor: chrome.readOnlySurface,\n borderColor: chrome.readOnlyBorderColor,\n },\n [`${READ_ONLY_EDITOR} .cm-gutters`]: { backgroundColor: chrome.readOnlySurface },\n [`${READ_ONLY_EDITOR} .cm-scroller`]: { backgroundColor: chrome.readOnlySurface },\n});\n","import { StateEffect, StateField, type Text } from '@codemirror/state';\nimport {\n Decoration,\n type DecorationSet,\n EditorView,\n ViewPlugin,\n type ViewUpdate,\n} from '@codemirror/view';\n\nimport colors from '@keboola/tailwind-config/colors';\n\nimport { escapeStringRegexp } from '../../utils/escapeStringRegexp';\n\nimport { DARK_LINE_ALPHA } from './diffWash';\n\n// Represents a single search match in the editor\ntype SearchMatch = {\n /** Start position in document */\n from: number;\n /** End position in document */\n to: number;\n /** Text content of the match */\n text: string;\n /** Local match index within this editor (0-based) */\n localIndex: number;\n};\n\n// Effect to update search state\nconst setSearchEffect = StateEffect.define<{\n query: string;\n selectedMatchIndex?: number;\n}>();\n\n// State to track current search matches\ntype SearchState = {\n query: string;\n selectedMatchIndex?: number;\n matches: SearchMatch[];\n decorations: DecorationSet;\n};\n\n// Find all matches in the document\nfunction findMatches(doc: Text, query: string): SearchMatch[] {\n if (!query) return [];\n\n const text = doc.toString();\n\n try {\n const regex = new RegExp(escapeStringRegexp(query), 'gi');\n\n return Array.from(text.matchAll(regex)).map((match, index) => {\n const from = match.index!;\n const to = from + match[0].length;\n\n return { from, to, text: match[0], localIndex: index };\n });\n } catch (e) {\n // Invalid regex - return no matches\n console.warn('Invalid search regex:', e);\n return [];\n }\n}\n\n// Create decorations for search matches\nfunction createDecorations(matches: SearchMatch[], selectedLocalIndex?: number): DecorationSet {\n const decorations = matches.map((match) => {\n const isSelected = match.localIndex === selectedLocalIndex;\n\n const decoration = Decoration.mark({\n class: isSelected ? 'cm-searchMatch-selected' : 'cm-searchMatch',\n });\n\n return decoration.range(match.from, match.to);\n });\n\n return Decoration.set(decorations, true);\n}\n\n// StateField to manage search state\nconst searchField = StateField.define<SearchState>({\n create() {\n return {\n query: '',\n selectedMatchIndex: undefined,\n matches: [],\n decorations: Decoration.none,\n };\n },\n\n update(state, tr) {\n let newState = state;\n\n // Handle search effect\n for (const effect of tr.effects) {\n if (!effect.is(setSearchEffect)) {\n continue;\n }\n\n const { query, selectedMatchIndex } = effect.value;\n\n // Find matches\n const matches = findMatches(tr.state.doc, query);\n\n // Create decorations\n const decorations = createDecorations(matches, selectedMatchIndex);\n\n newState = {\n query,\n selectedMatchIndex,\n matches,\n decorations,\n };\n }\n\n // Map decorations through document changes\n if (tr.docChanged && newState.query) {\n const matches = findMatches(tr.state.doc, newState.query);\n const decorations = createDecorations(matches, newState.selectedMatchIndex);\n\n newState = {\n ...newState,\n matches,\n decorations,\n };\n }\n\n return newState;\n },\n\n provide: (field) => EditorView.decorations.from(field, (state) => state.decorations),\n});\n\n// View plugin to handle scrolling to selected match\nconst searchViewPlugin = ViewPlugin.fromClass(\n class {\n private lastSelectedIndex?: number;\n\n update(update: ViewUpdate) {\n const state = update.state.field(searchField);\n\n // Scroll to selected match when it changes\n if (\n state.selectedMatchIndex !== undefined &&\n state.selectedMatchIndex !== this.lastSelectedIndex\n ) {\n const match = state.matches[state.selectedMatchIndex];\n\n if (match) {\n requestAnimationFrame(() => {\n update.view.dispatch({\n effects: EditorView.scrollIntoView(match.from, { y: 'center' }),\n });\n });\n }\n\n this.lastSelectedIndex = state.selectedMatchIndex;\n }\n\n // Reset if no selection\n if (state.selectedMatchIndex === undefined) {\n this.lastSelectedIndex = undefined;\n }\n }\n },\n);\n\n/**\n * Match and current-match fills, per colour scheme.\n *\n * - `&dark` is how a *static* base theme follows the scheme, without becoming a\n * `useThemedExtension` builder and a second entry in its never-evicting cache. It applies\n * whenever the `EditorView.darkTheme` facet is set — see `buildBaseThemeStyles`' callers, which\n * set it explicitly.\n * - Light text is `blue[700]`: 5.42:1 on the fill, and 6.29:1 for white on the current match.\n * - Dark tints `blue[500]` for the plain match, with `blue[200]` text: 11.10:1 on the page surface,\n * 8.86:1 on the `variant=\"field\"` one. The current match keeps a solid `blue[500]` and takes\n * `neutral[900]` as its text (5.78:1) — white on it is 2.55:1, since the token that reads as\n * \"strong\" in light is a light colour.\n */\nconst searchTheme = EditorView.baseTheme({\n '.cm-searchMatch': {\n backgroundColor: colors.blue[100],\n },\n '.cm-searchMatch > span': {\n color: `${colors.blue[700]} !important`,\n },\n '.cm-searchMatch-selected': {\n backgroundColor: colors.blue[700],\n },\n '.cm-searchMatch-selected > span': {\n color: `${colors.white} !important`,\n },\n\n '&dark .cm-searchMatch': {\n backgroundColor: `${colors.blue[500]}${DARK_LINE_ALPHA}`,\n },\n '&dark .cm-searchMatch > span': {\n color: `${colors.blue[200]} !important`,\n },\n '&dark .cm-searchMatch-selected': {\n backgroundColor: colors.blue[500],\n },\n '&dark .cm-searchMatch-selected > span': {\n color: `${colors.neutral[900]} !important`,\n },\n});\n\nexport function searchExtension() {\n return [searchField, searchViewPlugin, searchTheme];\n}\n\nexport function updateSearch(view: EditorView, query: string, selectedMatchIndex?: number) {\n view.dispatch({ effects: setSearchEffect.of({ query, selectedMatchIndex }) });\n}\n","import { isMac } from '../../utils';\nimport { Kbd } from '../Kbd';\n\nexport const ToggleComponentHelp = () => (\n <div>\n Use <Kbd>{isMac ? 'Command+/' : 'Ctrl+/'}</Kbd> to toggle comments.\n </div>\n);\n","import { type Extension } from '@codemirror/state';\n\nimport type { ResolvedColorScheme } from '../ThemeProvider/types';\nimport { useThemeAttributes } from '../ThemeProvider/useThemeAttributes';\n\n// Cached across component instances, not just across renders. A CodeMirror theme\n// extension carries its own StyleModule, and mounting an EditorView appends its\n// rules to a document-level stylesheet — which invalidates style for the whole\n// document. Sharing one module per theme keeps the stylesheet a constant size no\n// matter how many editors mount.\nconst themeCache = new Map<string, Extension>();\n\n/**\n * Memoize a CodeMirror theme/extension built from `resolveToken`, shared across\n * every instance that passes the same `cacheKey` and rebuilt whenever the active\n * brand / light-dark mode changes. `build` reads live `--*` values off `<html>`,\n * so the active theme is an invisible dependency a deps array can't see.\n *\n * `build` receives the scheme those values were read under, for the theme values\n * that are a light/dark *pair* rather than a token lookup (a categorical diff\n * wash has no semantic token, but an opaque light pastel still has to become a\n * low-alpha tint under dark). It comes from the same read that produced the key,\n * so a builder cannot resolve one scheme's colours under the other one's key.\n *\n * `cacheKey` is the extension's full identity: anything the builder closes over\n * must be part of it (e.g. `` `merge-pane:${deleted}` ``), or instances built\n * from different inputs would share one theme.\n */\nexport const useThemedExtension = (\n cacheKey: string,\n build: (scheme: ResolvedColorScheme) => Extension,\n): Extension => {\n const { scheme, cacheKey: themeKey } = useThemeAttributes();\n const key = `${themeKey} ${cacheKey}`;\n\n // The module-level cache is the memo; reading and filling it during render is\n // idempotent and keyed only on values already stable for the render.\n let cached = themeCache.get(key);\n if (!cached) {\n cached = build(scheme);\n themeCache.set(key, cached);\n }\n\n return cached;\n};\n","import { useMemo } from 'react';\nimport { Compartment, type Extension } from '@codemirror/state';\nimport { tooltips, ViewPlugin } from '@codemirror/view';\n\n// A `position: fixed` box is laid out against the viewport — and so escapes\n// every scroll container above it — only while no ancestor claims the job of\n// being its containing block. This encodes the CSS rule for who claims it\n// rather than the subset this repo happens to use today; `contain` and\n// `will-change` take value lists, so those two are matched loosely.\n//\n// `content-visibility` is absent on purpose: it implies containment without\n// saying so through `contain`, and it is handled below as a clipper — which is\n// the stronger of the two properties for our purposes.\nconst establishesFixedContainingBlock = (style: CSSStyleDeclaration) =>\n style.transform !== 'none' ||\n style.translate !== 'none' ||\n style.rotate !== 'none' ||\n style.scale !== 'none' ||\n style.perspective !== 'none' ||\n style.filter !== 'none' ||\n style.backdropFilter !== 'none' ||\n /\\b(paint|layout|strict|content)\\b/.test(style.contain) ||\n /\\b(transform|perspective|filter|contain)\\b/.test(style.willChange);\n\n// Crops its content, so hosting the tooltip inside it would not help. Paint\n// containment — which `content-visibility: auto` turns on without ever showing\n// up in computed `contain` — crops even a fixed-position descendant, and so\n// does a mask.\nconst crops = (style: CSSStyleDeclaration) =>\n style.overflowX !== 'visible' ||\n style.overflowY !== 'visible' ||\n style.maskImage !== 'none' ||\n style.contentVisibility !== 'visible' ||\n /\\b(paint|strict|content)\\b/.test(style.contain);\n\n/**\n * Where a tooltip can hang without being cropped, or `null` for \"wherever\n * CodeMirror would put it anyway\".\n *\n * Two ancestors matter, and they are not the same ancestor. The **outermost\n * cropper** is the one to get above — landing anywhere below it leaves the\n * tooltip inside the box doing the cropping. The **containing block** is where\n * the search can stop, because from there upwards `position: fixed` is measured\n * against that element and nothing higher can crop it.\n *\n * `document.body` and `<html>` are not treated as croppers: a fixed box whose\n * containing block is the viewport is not clipped by their overflow, and\n * hosting outside `<body>` would drop the tooltip out of the app's stacking and\n * pointer-events scope for no gain.\n */\nconst findTooltipHost = (from: HTMLElement) => {\n let outermostCropper: HTMLElement | null = null;\n\n for (let node = from.parentElement; node && node !== document.body; node = node.parentElement) {\n const style = getComputedStyle(node);\n\n if (crops(style)) {\n outermostCropper = node;\n } else if (establishesFixedContainingBlock(style)) {\n return outermostCropper?.parentElement ?? node;\n }\n }\n\n return outermostCropper?.parentElement ?? null;\n};\n\n/**\n * `tooltips()`, re-hosted so the completion popup is never cropped.\n *\n * CodeMirror hangs tooltips inside the editor and lets `position: fixed` carry\n * them past its edges. That holds only while the viewport is their containing\n * block — a modal centred with a translate, a sheet sliding in, or a box under\n * paint containment takes that job, and then every scroller, mask and contained\n * box in between crops the popup instead. A tall editor hides the damage; a\n * one-line one shows a sliver of an unreadable list.\n *\n * The two shapes this has to survive in production are a `Modal`, whose body\n * scrolls and carries the argo fade mask, and kbc-ui's SQL editor, which wraps\n * every code block in `content-visibility: auto` to keep long scripts cheap.\n *\n * Hosting the layer above the outermost cropper clears all of that while keeping\n * the popup inside the modal's stacking, focus and pointer-events scope — which\n * `document.body` would not: the popup would sit behind the modal, and Radix\n * leaves the body `pointer-events: none` while a dialog is open.\n *\n * Both editors install this, and it is the only place either of them configures\n * a tooltip host. Keep it that way: CodeMirror's tooltip config takes the first\n * contributor that names a parent, so a second mechanism would not compose with\n * this one — it would silently win or lose on extension order.\n */\nconst tooltipsExtension = (): Extension => {\n // The resolved host lives in a compartment, not in an appended config: React\n // hands CodeMirror a new extension array whenever the editor's props move,\n // which dispatches a full reconfigure. That replaces appended config, while\n // compartment contents are carried over.\n const layer = new Compartment();\n\n return [\n layer.of(tooltips()),\n ViewPlugin.define((view) => {\n // Deferred on two counts: a plugin cannot dispatch while the view it\n // belongs to is still being built, and reading computed styles here would\n // force a style and layout flush in the middle of the commit that inserted\n // the editor. The lookup is one-shot — an ancestor that gains a transform\n // afterwards is not picked up.\n const scheduled = setTimeout(() => {\n if (!view.dom.isConnected) return;\n\n const parent = findTooltipHost(view.dom);\n if (parent) view.dispatch({ effects: layer.reconfigure(tooltips({ parent })) });\n });\n\n return { destroy: () => clearTimeout(scheduled) };\n }),\n ];\n};\n\n/**\n * The extension above, built once per editor. Rebuilding it would hand\n * CodeMirror a fresh compartment and plugin on every reconfigure, dropping the\n * host it had already resolved — so it is only ever reached through this hook.\n */\nexport const useTooltipsExtension = () => useMemo(tooltipsExtension, []);\n","import type { Completion, CompletionContext, CompletionSource } from '@codemirror/autocomplete';\n\nimport { useStableCallback } from '../../hooks/useStableCallback';\n\nexport type EditorVariable = { name: string; value?: string };\n\n// Keywords come by the hundred from the language, so a variable would otherwise rank\n// below every one of them that shares a prefix.\nconst BOOST = 2000;\n\n// One brace or two, because `closeBrackets` turns a typed `{` into `{}` and a caret\n// that has only opened the placeholder is still asking for a variable. One charset\n// for the name throughout: a second, narrower one would start the range mid-name on\n// anything it disagreed about, and a range that starts mid-name never matches.\nconst NAME = String.raw`[\\w-]*`;\nconst AT_CARET = new RegExp(String.raw`(?:\\{{1,2} ?)?${NAME}$`);\nconst NAME_AT_END = new RegExp(`${NAME}$`);\nconst OPENING = /\\{{1,2} ?$/;\nconst CLOSING = /^ ?\\}{1,2}/;\n\n/**\n * Completes a mustache-style `{{name}}` placeholder.\n */\nexport const completeVariables = (variables: EditorVariable[] = []): CompletionSource => {\n if (variables.length === 0) return () => null;\n\n const options: Completion[] = variables.map(({ name, value }) => ({\n // The bare name: `SqlEditor` filters prefix-only while `CodeEditor` filters\n // fuzzily, and this is the only spelling both accept whether or not the caret\n // has typed the braces. The braces are `displayLabel`, which is what renders.\n label: name,\n displayLabel: `{{${name}}}`,\n detail: value,\n type: 'variable',\n boost: BOOST,\n apply: (view, completion, from, to) => {\n const { doc } = view.state;\n const line = doc.lineAt(from);\n const insert = `{{${completion.label}}}`;\n\n // The range covers the name alone, so the braces around it are found rather\n // than assumed — `closeBrackets` may have added a closing one nobody typed.\n const opening = OPENING.exec(doc.sliceString(line.from, from));\n const closing = CLOSING.exec(doc.sliceString(to, line.to));\n const start = opening ? from - opening[0].length : from;\n const end = closing ? to + closing[0].length : to;\n\n view.dispatch({\n changes: { from: start, to: end, insert },\n selection: { anchor: start + insert.length },\n });\n },\n }));\n\n return (context: CompletionContext) => {\n const match = context.matchBefore(AT_CARET);\n\n if (!match?.text) return null;\n\n const [name = ''] = NAME_AT_END.exec(match.text) ?? [];\n\n return { from: match.to - name.length, options };\n };\n};\n\n/**\n * The completion source both editors install, with an identity that never moves.\n *\n * Both hold it inside the memo that keys their whole extension tree, and callers\n * build the list inline — a config row mapped to `{ name, value }` in a store\n * selector, so a fresh array arrives on every store push. Because CodeMirror asks\n * the source for options rather than reading them up front, holding it steady costs\n * nothing: a completion request always reaches the latest render's variables.\n */\nexport const useVariableCompletion = (variables: EditorVariable[] = []): CompletionSource =>\n useStableCallback(completeVariables(variables));\n","import { useEffect, useLayoutEffect, useMemo, useRef } from 'react';\nimport type { KeyboardEvent, ReactNode } from 'react';\nimport type { CompletionSource } from '@codemirror/autocomplete';\nimport { autocompletion, completeAnyWord } from '@codemirror/autocomplete';\nimport { unifiedMergeView } from '@codemirror/merge';\nimport { EditorView, keymap, placeholder as cmPlaceholder } from '@codemirror/view';\nimport CodeMirror, {\n EditorState,\n type Extension,\n type ReactCodeMirrorRef,\n} from '@uiw/react-codemirror';\n\nimport { keyCodes } from '../../constants/keyCodes';\nimport { useStableCallback } from '../../hooks/useStableCallback';\nimport { cn } from '../../utils';\nimport { HelpBlock } from '../HelpBlock';\nimport { useArgoDesign } from '../ThemeProvider/context';\n\nimport { ButtonToolbar } from './ButtonToolbar';\nimport { buildChromeStyles, buildInputChrome } from './editorChrome';\nimport type { LANGUAGE_MODE } from './helpers';\nimport {\n buildBaseThemeStyles,\n buildBasicSetup,\n buildCustomTheme,\n buildJsonLinter,\n getLanguageMode,\n shouldLintJson,\n} from './helpers';\nimport { searchExtension, updateSearch } from './search';\nimport { ToggleComponentHelp } from './ToggleComponentHelp';\nimport { useThemedExtension } from './tokenTheme';\nimport { useTooltipsExtension } from './tooltips';\nimport { type EditorVariable, useVariableCompletion } from './variableCompletion';\n\ntype Props = {\n value: string;\n previousValue?: string;\n /**\n * `'field'` draws the chrome an `InputGroup` draws — surface, border, radius,\n * focus ring, read-only wash — for an editor that is one control among others\n * in a form. It sizes to its content, so don't pin its height.\n *\n * `'plain'` (the default) is the full-bleed surface of an editor that *is* the\n * panel: a modal body, a chat block, a fixed-height viewer already framed by\n * whatever contains it.\n */\n variant?: 'plain' | 'field';\n mode?: LANGUAGE_MODE;\n placeholder?: string;\n /** Names the editable region for screen readers — the editor has no visible label of its own. */\n ariaLabel?: string;\n /**\n * Names the editable region from an existing element, for when the label is already on screen.\n * Prefer this over `ariaLabel` inside a form — `CodeEditorField` passes the field's own label id.\n */\n ariaLabelledBy?: string;\n /** Links the editable region to help / error text. Space-delimited idref list. */\n ariaDescribedBy?: string;\n /** Marks the editable region invalid. Visual error styling is the caller's (`variant=\"field\"`). */\n ariaInvalid?: boolean;\n ariaRequired?: boolean;\n /**\n * Treats a blank document as valid instead of a parse error (JSON modes only).\n *\n * - Off by default: for a standalone editor \"Unexpected end of input\" is correct, and at several\n * call sites the gutter marker is the only thing explaining a Save button that\n * `isValidJsonConfig('') === false` has already disabled.\n * - `CodeEditorField` turns it on for a field that is not `required`, where an empty document is\n * how the value is removed.\n */\n allowBlankDocument?: boolean;\n /**\n * Fires when focus leaves the editable region — what a form connector needs to mark its field\n * blurred, which is the gate errors are revealed on.\n *\n * - Bound as a CodeMirror DOM handler on the content node, not on the wrapper: the wrapper is not\n * what gets focused.\n * - Installed only when passed, so an editor without it keeps the extension set it had.\n */\n onBlur?: () => void;\n /**\n * Highlights every occurrence and scrolls the selected one into view. The find\n * UI is the caller's — pass the query it holds, and omit both props entirely to\n * leave the search extension uninstalled.\n */\n searchQuery?: string;\n searchMatchIndex?: number;\n readOnly?: boolean;\n /**\n * Refuses edits while leaving the editor looking and behaving as it did — for a\n * transient lock such as an in-flight save, where a keystroke landing mid-request\n * would be overwritten by the response. `readOnly` is the wrong prop for that:\n * it turns the editor into a viewer, greying the surface and taking the lint\n * marks and completions with it.\n */\n inputLocked?: boolean;\n /**\n * A flat list of completions, offered everywhere in the document. One word per\n * label: CodeMirror derives the pattern for the word being completed from the\n * labels' characters, so a space in one widens it across whitespace and the\n * editor offers nothing past the first word of a line. A phrase belongs in\n * `completionSource`.\n *\n * Compared by identity, like `completionSource` — hand the editor a stable array.\n */\n autocompletions?: string[];\n /**\n * Completions that depend on where the cursor is — a column list offered only\n * after its table, say. Wins over both `autocompletions` and `completeAny`,\n * which stay the right props for a list that is the same everywhere in the\n * document and for having no list at all. Like them, it opens on typing.\n *\n * Compared by identity: build it in a `useMemo` or the editor rebuilds its whole\n * extension tree on every render.\n */\n completionSource?: CompletionSource;\n /**\n * Configuration variables, completed into `{{name}}`. Independent of\n * `completionSource`: both are offered, so a caller keeps its own completions and\n * gets variables spelled the way the rest of the platform writes them.\n */\n variables?: EditorVariable[];\n /**\n * Whether the completion popup runs at all.\n *\n * - `false` silences every source, the *language's* own vocabulary included.\n * - For a field highlighted as a language nobody authors there: pasted `.env` and a\n * cURL command sit in shell mode for its colours, and shell's `ls`, `sudo`, `vim`\n * are noise over content we cannot predict.\n */\n withCompletions?: boolean;\n extraKeys?: Record<string, () => void>;\n withToggleCommentHint?: boolean;\n withAutofocus?: boolean;\n withLineNumbers?: boolean;\n withLineWrapping?: boolean;\n withCollapseUnchanged?: boolean;\n withCopyButton?: boolean;\n completeAny?: boolean;\n help?: ReactNode;\n helpPostfix?: ReactNode;\n /**\n * Extra actions for the toolbar that floats over the editor's top-right corner,\n * beside the copy button. The toolbar is a 28px chip, so pass `size=\"icon-xs\"`\n * buttons — a default-sized one grows the chip and de-aligns the copy button.\n */\n renderAdditionalButtons?: (value?: string) => ReactNode;\n className?: string;\n} & (\n | { readOnly: true; onChange?: never }\n // `boolean` rather than `false`: a field the user's permissions may lock still\n // needs its handler for the case where they can edit.\n | { readOnly?: boolean; onChange: (value: string) => void }\n);\n\nconst emptyObject = {};\n\nexport const CodeEditor = ({\n value,\n previousValue,\n onChange,\n variant = 'plain',\n mode = 'application/json',\n placeholder = '',\n ariaLabel,\n ariaLabelledBy,\n ariaDescribedBy,\n ariaInvalid,\n ariaRequired,\n allowBlankDocument = false,\n onBlur,\n searchQuery,\n searchMatchIndex,\n readOnly = false,\n inputLocked = false,\n autocompletions,\n completionSource,\n variables,\n withCompletions = true,\n extraKeys = emptyObject,\n withToggleCommentHint = false,\n withAutofocus = false,\n withLineNumbers = true,\n withLineWrapping = true,\n withCollapseUnchanged = false,\n withCopyButton = false,\n completeAny = false,\n help = null,\n helpPostfix = null,\n renderAdditionalButtons,\n className,\n}: Props) => {\n // CodeMirror rebuilds and re-resolves the whole extension tree whenever the\n // change handler's identity moves, and callers pass inline arrows.\n const handleChange = useStableCallback((next: string) => onChange?.(next));\n const handleBlur = useStableCallback(() => onBlur?.());\n\n // Themes re-resolve their `--*` tokens on brand / light-dark change. The\n // syntax palette is keyed without a component prefix so `SqlEditor` — which\n // builds it from the same `buildCustomTheme` — shares this one module.\n // Presence, not truthiness: a caller that searches always passes the prop, so\n // the extension set stays stable while the query changes.\n const withSearch = searchQuery !== undefined;\n // Same presence-not-truthiness reasoning as `withSearch`: gate the handler extension on the prop\n // being passed at all, so every existing caller keeps the extension set it had.\n const withBlur = onBlur !== undefined;\n const editorRef = useRef<ReactCodeMirrorRef>(null);\n\n // One object so the extension list has a single dependency instead of five, and `null` when nothing\n // is set so the extension is left out entirely rather than added empty.\n const contentAria = useMemo(() => {\n const attributes: Record<string, string> = {};\n if (ariaLabel !== undefined) attributes['aria-label'] = ariaLabel;\n if (ariaLabelledBy !== undefined) attributes['aria-labelledby'] = ariaLabelledBy;\n if (ariaDescribedBy !== undefined) attributes['aria-describedby'] = ariaDescribedBy;\n // Stringified because `contentAttributes` writes DOM attributes, where `aria-invalid=\"false\"` and\n // an absent attribute mean the same thing but `false` would be dropped by a truthiness check.\n if (ariaInvalid !== undefined) attributes['aria-invalid'] = String(ariaInvalid);\n if (ariaRequired !== undefined) attributes['aria-required'] = String(ariaRequired);\n return Object.keys(attributes).length > 0 ? attributes : null;\n }, [ariaLabel, ariaLabelledBy, ariaDescribedBy, ariaInvalid, ariaRequired]);\n\n useEffect(() => {\n const view = editorRef.current?.view;\n if (view && withSearch) updateSearch(view, searchQuery, searchMatchIndex);\n }, [withSearch, searchQuery, searchMatchIndex]);\n\n // A view created while a query is already set — a remount, a tab switch —\n // starts with no highlights unless the search is applied as it is built.\n const handleCreateEditor = useStableCallback((view: EditorView) => {\n if (searchQuery) updateSearch(view, searchQuery, searchMatchIndex);\n });\n\n // Same reasoning as `onChange` above, one level out: callers build this object\n // inline, so keying the extensions on it would reconfigure the editor on every\n // parent render. Only the set of bound keys can change what the keymap *is* —\n // the handlers behind them are read when the key is actually pressed.\n const extraKeysRef = useRef(extraKeys);\n useLayoutEffect(() => {\n extraKeysRef.current = extraKeys;\n });\n\n const boundKeysSignature = Object.keys(extraKeys).join('\\n');\n const boundKeys = useMemo(\n () => boundKeysSignature.split('\\n').filter(Boolean),\n [boundKeysSignature],\n );\n\n const tooltipLayer = useTooltipsExtension();\n\n // `languageData.of` takes a function CodeMirror calls per completion request, so\n // the source is built here rather than inside it — otherwise every keystroke that\n // opens the popup rebuilds an option per variable.\n const variableCompletion = useVariableCompletion(variables);\n\n const customTheme = useThemedExtension('editor:syntax', buildCustomTheme);\n\n // The brand decides which `InputGroup` the field chrome has to match, so it is\n // part of the theme's identity — `useThemedExtension` caches per key across\n // every instance, and the theme signal it keys on carries only `<html>`.\n const isArgo = useArgoDesign();\n const isField = variant === 'field';\n const baseTheme = useThemedExtension(\n isField ? `code-editor:field:${isArgo ? 'argo' : 'legacy'}` : 'code-editor:chrome',\n (scheme) =>\n // `dark` sets `EditorView.darkTheme`, which is what activates every `&dark` rule — ours in\n // `search.ts` / `highlighting.ts`, and CodeMirror's own for the cursor, selection layer and\n // panels. Declared here rather than inherited from whichever github palette\n // `buildCustomTheme` picked, so swapping that palette cannot silently turn them all off.\n EditorView.theme(\n {\n ...buildBaseThemeStyles(scheme),\n ...(isField ? buildChromeStyles(buildInputChrome(isArgo, scheme)) : null),\n },\n { dark: scheme === 'dark' },\n ),\n );\n\n const commonExtensions: Extension[] = useMemo(() => {\n const callerCompletions =\n completionSource ??\n (completeAny ? completeAnyWord : autocompletions?.length ? autocompletions : null);\n\n // An empty list is left out: CodeMirror wraps a list in `completeFromList`, which\n // answers an empty result rather than none, so the editor would run a source that\n // can never match on every keystroke.\n const completionEntries = [\n ...(callerCompletions ? [{ autocomplete: callerCompletions }] : []),\n { autocomplete: variableCompletion },\n ];\n\n return [\n getLanguageMode(mode),\n shouldLintJson(mode, readOnly) ? buildJsonLinter(allowBlankDocument) : [],\n withLineWrapping ? EditorView.lineWrapping : [],\n EditorState.languageData.of(() => completionEntries),\n keymap.of(\n boundKeys.map((key) => ({\n key,\n run: () => {\n extraKeysRef.current[key]?.();\n return true;\n },\n })),\n ),\n readOnly || !withCompletions\n ? []\n : [\n // The only `autocompletion()` an editor gets — `buildBasicSetup` turns\n // basicSetup's own off. Not gated on the completion props: that hid what the\n // *language* supplies — dbt's vocabulary, Snowflake's keywords — behind a\n // shortcut, and macOS leaves no usable one. With nothing to offer no popup\n // opens anyway, so only `withCompletions={false}` asks for silence.\n autocompletion(),\n ],\n // Every a11y attribute goes onto the *content* node, not the wrapper: CodeMirror's\n // `div[role=\"textbox\"]` is what gets focused, so it is the only element AT will read them from.\n contentAria ? EditorView.contentAttributes.of(contentAria) : [],\n withBlur ? EditorView.domEventHandlers({ blur: handleBlur }) : [],\n withSearch ? searchExtension() : [],\n tooltipLayer,\n baseTheme,\n ];\n }, [\n autocompletions,\n completionSource,\n variableCompletion,\n completeAny,\n withCompletions,\n boundKeys,\n mode,\n readOnly,\n allowBlankDocument,\n withLineWrapping,\n baseTheme,\n contentAria,\n withBlur,\n handleBlur,\n withSearch,\n tooltipLayer,\n ]);\n\n const extensions = useMemo(() => {\n return [\n ...commonExtensions,\n cmPlaceholder(placeholder),\n EditorView.editable.of(!readOnly),\n // The lock is this facet and nothing else. `contenteditable` is what the\n // read-only wash keys off, and `basicSetup` is what holds the undo history,\n // so leaving both alone is what makes the lock invisible.\n EditorState.readOnly.of(readOnly || inputLocked),\n previousValue\n ? unifiedMergeView({\n original: previousValue,\n mergeControls: false,\n highlightChanges: false,\n collapseUnchanged: withCollapseUnchanged ? {} : undefined,\n })\n : [],\n ];\n }, [commonExtensions, placeholder, readOnly, inputLocked, previousValue, withCollapseUnchanged]);\n\n const config = useMemo(() => {\n return {\n ...buildBasicSetup(readOnly),\n lineNumbers: withLineNumbers,\n // Mod-f opens CodeMirror's own panel, which would run a second query and a\n // second match count over the same document beside the caller's input.\n ...(withSearch ? { searchKeymap: false } : null),\n };\n }, [withLineNumbers, readOnly, withSearch]);\n\n return (\n // oxlint-disable-next-line jsx-a11y/no-static-element-interactions\n <div\n data-variant={variant}\n className={cn(\n // Scoped to the box CodeMirror renders into rather than to every child, so\n // the toolbar below does not have to undo all three in `!important`.\n 'tw:relative tw:flex tw:min-h-0 tw:flex-col tw:[&_.cm-mergeViewEditor]:overflow-visible tw:[&_.cm-mergeViewEditors]:h-full tw:[&_.cm-mergeView]:h-full tw:[&_>.cm-theme]:h-full',\n // A field's `.cm-editor` is rounded, so the square box behind it would show\n // at the corners, and `overflow-auto` would crop the focus ring — a shadow\n // painted outside the editor's own box.\n isField\n ? 'tw:[&_>.cm-theme]:overflow-visible tw:[&_>.cm-theme]:bg-transparent'\n : 'tw:[&_>.cm-theme]:overflow-auto tw:[&_>.cm-theme]:bg-background',\n className,\n )}\n onKeyDown={(event: KeyboardEvent) => {\n if (event.key === keyCodes.ESCAPE) {\n event.stopPropagation();\n }\n }}\n >\n <ButtonToolbar value={withCopyButton ? value : undefined}>\n {renderAdditionalButtons?.(value)}\n </ButtonToolbar>\n <CodeMirror\n ref={editorRef}\n onCreateEditor={handleCreateEditor}\n theme={customTheme}\n value={value}\n onChange={handleChange}\n extensions={extensions}\n autoFocus={withAutofocus}\n basicSetup={config}\n />\n {!readOnly && (withToggleCommentHint || help || helpPostfix) && (\n <HelpBlock className=\"tw:mt-2 tw:flex tw:flex-wrap tw:gap-1\">\n {help}\n {withToggleCommentHint ? <ToggleComponentHelp /> : null}\n {helpPostfix}\n </HelpBlock>\n )}\n </div>\n );\n};\n"],"mappings":"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"}
@@ -1,8 +1,8 @@
1
1
  import { cn } from "./classNames-BzrkDnOD.js";
2
- import { createChangeInputEvent } from "./utils-D0c5VAyF.js";
2
+ import { createChangeInputEvent } from "./utils-B-g7d_Jb.js";
3
3
  import { mergeRefs } from "./internal/utils/mergeRefs.js";
4
4
  import { Pipette, X } from "./icons-Cek151jC.js";
5
- import { InputGroup } from "./InputGroup-CdTq8H7c.js";
5
+ import { InputGroup } from "./InputGroup-D7zlmqPB.js";
6
6
  import { useControllableState } from "./useControllableState-M6494mCT.js";
7
7
  import { useRef } from "react";
8
8
  import { jsx, jsxs } from "react/jsx-runtime";
@@ -177,4 +177,4 @@ const ColorInput = ({ ref, state, variant, focusVariant, sizing, className, valu
177
177
  //#endregion
178
178
  export { ColorInput };
179
179
 
180
- //# sourceMappingURL=ColorInput-B8z4j4Y_.js.map
180
+ //# sourceMappingURL=ColorInput-Q1D9Vcc_.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ColorInput-B8z4j4Y_.js","names":[],"sources":["../src/blocks/ColorInput/utils.ts","../src/blocks/ColorInput/ColorPicker.tsx","../src/blocks/ColorInput/ColorInput.tsx"],"sourcesContent":["import type { ComponentProps } from 'react';\n\nconst HEX_CHARSET = /^[0-9a-fA-F]+$/;\n// `#` + 3, 4, 6, or 8 hex digits — every length CSS accepts as a hex color.\nconst COMPLETE_HEX_PATTERN = /^#(?:[0-9a-fA-F]{3,4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/;\n// Longest hex body CSS accepts (`#rrggbbaa` without the hash).\nconst MAX_HEX_BODY_LENGTH = 8;\n// Native <input type=\"color\"> default when fed anything unparseable.\nconst PICKER_FALLBACK = '#000000';\n\nconst extractHexBody = (value: unknown): string | null => {\n if (typeof value !== 'string') return null;\n const trimmed = value.trim();\n if (trimmed === '') return null;\n return trimmed.startsWith('#') ? trimmed.slice(1) : trimmed;\n};\n\nexport const isCompleteHexColor = (value: string): boolean => COMPLETE_HEX_PATTERN.test(value);\n\n// @see https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/showPicker\nexport const showPicker = (input: HTMLInputElement) => {\n const isShowPickerSupported = 'showPicker' in HTMLInputElement.prototype;\n isShowPickerSupported ? input.showPicker() : input.click();\n};\n\n/**\n * Coerces free-form text into a partial hex color for the visible text\n * input. Allows up to 8 hex digits to support `#rrggbbaa` (RGBA / alpha).\n *\n * Behaviour:\n * - empty / null / undefined / non-string → `''`\n * - trims surrounding whitespace\n * - prepends `#` when the user types raw hex without it\n * - keeps only the leading run of valid hex digits, dropping the rest\n * - caps total length at `# + 8` hex digits\n * - returns `''` when no valid hex digits remain (e.g. bare `#`, `zz`) so\n * the input doesn't sit on a lonely `#`\n *\n * Note: the result may be a *prefix* (e.g. `#a`, `#ab`) that is not yet a\n * valid CSS color — gate any rendering on `isCompleteHexColor`.\n */\nexport const coerceHexInputValue = (value?: string | null): string => {\n const body = extractHexBody(value);\n if (body === null) return '';\n const [validBody] = body.match(/^[0-9a-fA-F]+/) ?? [];\n if (!validBody) return '';\n return `#${validBody.slice(0, MAX_HEX_BODY_LENGTH)}`;\n};\n\n/**\n * Coerces any value into the strict lowercase `#rrggbb` form required by the\n * native `<input type=\"color\">`. Anything the picker can't render is\n * collapsed to `#000000`.\n *\n * - 3-digit shorthand (`#abc`) → expanded to 6 digits (`#aabbcc`)\n * - 4/8-digit RGBA → alpha channel is dropped\n * - invalid characters, wrong length, or non-string types → `#000000`\n *\n * The native picker silently lowercases its value; we lowercase here too so\n * controlled consumers see the same string round-trip.\n */\nexport const coerceColorPickerValue = (value: ComponentProps<'input'>['value'] | null) => {\n const body = extractHexBody(value);\n if (body === null || !HEX_CHARSET.test(body)) return PICKER_FALLBACK;\n\n if (body.length === 3 || body.length === 4) {\n const [r, g, b] = body;\n return `#${r}${r}${g}${g}${b}${b}`.toLowerCase();\n }\n if (body.length === 6 || body.length === 8) {\n return `#${body.slice(0, 6).toLowerCase()}`;\n }\n return PICKER_FALLBACK;\n};\n","import { type ComponentProps, type ComponentRef, useRef } from 'react';\n\nimport { InputGroup } from '../../components/InputGroup';\nimport { Pipette } from '../../icons';\n\nimport { coerceColorPickerValue, showPicker } from './utils';\n\ntype Props = Omit<ComponentProps<'input'>, 'type'>;\n\nexport const ColorPicker = ({ value, disabled, readOnly, ...props }: Props) => {\n const pickerRef = useRef<ComponentRef<'input'>>(null);\n\n const handleOpenPicker = () => {\n if (!pickerRef.current) return;\n showPicker(pickerRef.current);\n };\n\n return (\n <div className=\"tw:relative\">\n <input\n {...props}\n ref={pickerRef}\n type=\"color\"\n value={coerceColorPickerValue(value)}\n tabIndex={-1}\n aria-hidden\n className=\"tw:pointer-events-none tw:absolute tw:left-0 tw:top-full tw:size-0 tw:opacity-0\"\n disabled={disabled}\n readOnly={readOnly}\n />\n <InputGroup.Button\n onMouseDown={(event) => event.preventDefault()}\n disabled={disabled || readOnly}\n onClick={handleOpenPicker}\n aria-label=\"Pick color\"\n >\n <Pipette className=\"tw:size-4\" />\n </InputGroup.Button>\n </div>\n );\n};\n","import { useRef } from 'react';\nimport type {\n ChangeEventHandler,\n ComponentProps,\n ComponentRef,\n FocusEventHandler,\n MouseEventHandler,\n} from 'react';\n\nimport { InputGroup } from '../../components/InputGroup';\nimport { useControllableState } from '../../hooks/useControllableState';\nimport { X } from '../../icons';\nimport { cn, createChangeInputEvent, mergeRefs } from '../../utils';\n\nimport { ColorPicker } from './ColorPicker';\nimport { coerceHexInputValue, isCompleteHexColor } from './utils';\n\ntype InputGroupProps = Pick<\n ComponentProps<typeof InputGroup>,\n 'variant' | 'focusVariant' | 'state' | 'sizing'\n>;\n\ntype InputGroupInputProps = Omit<ComponentProps<typeof InputGroup.Input>, 'value' | 'defaultValue'>;\n\ntype Props = InputGroupProps &\n InputGroupInputProps & {\n value?: string | null;\n defaultValue?: string | null;\n onValueChange?: (value: string) => void;\n onValueBlur?: (value: string) => void;\n allowClear?: boolean;\n };\n\nexport const ColorInput = ({\n ref,\n\n // group props\n state,\n variant,\n focusVariant,\n sizing,\n className,\n\n // own props\n value: valueProp,\n onValueChange,\n onValueBlur,\n onChange,\n onBlur,\n defaultValue,\n allowClear = false,\n\n // input props\n disabled,\n readOnly,\n ...restInputProps\n}: Props) => {\n const inputRef = useRef<ComponentRef<'input'>>(null);\n\n const [value, setValue] = useControllableState<string>({\n // A `null` controlled value stays controlled (coerced to ''); `undefined` is uncontrolled.\n prop: valueProp === null ? '' : valueProp,\n defaultProp: defaultValue ?? '',\n onChange: onValueChange,\n });\n\n const isControlled = valueProp !== undefined;\n\n const canClear = allowClear && !!value && !disabled && !readOnly;\n const swatchColor = coerceHexInputValue(value);\n const isValidSwatch = isCompleteHexColor(swatchColor);\n\n // Preserve raw text while the user is typing — sanitise on blur.\n const handleChange: ChangeEventHandler<HTMLInputElement> = (event) => {\n setValue(event.target.value);\n onChange?.(event);\n };\n\n const handleBlur: FocusEventHandler<HTMLInputElement> = (event) => {\n const newValue = event.target.value;\n const sanitizedNewValue = coerceHexInputValue(newValue);\n\n if (sanitizedNewValue !== newValue) {\n // In controlled mode, let the parent decide whether to apply the\n // sanitised value via `onValueChange` — don't fight its `value` prop.\n if (!isControlled) event.target.value = sanitizedNewValue;\n setValue(sanitizedNewValue);\n }\n\n onValueBlur?.(sanitizedNewValue);\n onBlur?.(event);\n };\n\n const handlePickerChange: ChangeEventHandler<HTMLInputElement> = (event) => {\n setValue(coerceHexInputValue(event.target.value));\n onChange?.(event);\n };\n\n const handleClear: MouseEventHandler<HTMLButtonElement> = () => {\n if (!inputRef.current) return;\n inputRef.current.value = '';\n setValue('');\n onChange?.(createChangeInputEvent(inputRef.current));\n };\n\n return (\n <InputGroup\n state={state}\n variant={variant}\n sizing={sizing}\n focusVariant={focusVariant}\n className={className}\n >\n <InputGroup.Addon\n align=\"inline-start\"\n className={cn(\n { 'tw:-ml-7 tw:opacity-0': !value },\n 'tw:transition-[opacity,margin]',\n 'tw:ease-linear',\n 'tw:duration-200',\n )}\n >\n <div\n style={isValidSwatch ? { background: swatchColor } : undefined}\n className={cn(\n 'tw:size-5',\n 'tw:shrink-0',\n 'tw:rounded-sm',\n 'tw:border',\n 'tw:border-solid',\n 'tw:border-neutral-300',\n {\n 'tw:bg-[linear-gradient(to_top_right,transparent_calc(50%_-_1px),theme(colors.red.300)_calc(50%_-_1px),theme(colors.red.300)_calc(50%_+_1px),transparent_calc(50%_+_1px))]':\n !isValidSwatch,\n },\n )}\n />\n </InputGroup.Addon>\n\n <InputGroup.Input\n {...restInputProps}\n type=\"text\"\n ref={mergeRefs(ref ?? null, inputRef)}\n value={value}\n onChange={handleChange}\n onBlur={handleBlur}\n disabled={disabled}\n readOnly={readOnly}\n />\n\n <InputGroup.Addon align=\"inline-end\">\n {canClear && (\n <InputGroup.Button\n // prevents input focus stealing\n onMouseDown={(event) => event.preventDefault()}\n onClick={handleClear}\n aria-label=\"Clear color\"\n >\n <X className=\"tw:size-4\" />\n </InputGroup.Button>\n )}\n <ColorPicker\n disabled={disabled}\n readOnly={readOnly}\n value={value}\n onChange={handlePickerChange}\n />\n </InputGroup.Addon>\n </InputGroup>\n );\n};\n"],"mappings":"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"}
1
+ {"version":3,"file":"ColorInput-Q1D9Vcc_.js","names":[],"sources":["../src/blocks/ColorInput/utils.ts","../src/blocks/ColorInput/ColorPicker.tsx","../src/blocks/ColorInput/ColorInput.tsx"],"sourcesContent":["import type { ComponentProps } from 'react';\n\nconst HEX_CHARSET = /^[0-9a-fA-F]+$/;\n// `#` + 3, 4, 6, or 8 hex digits — every length CSS accepts as a hex color.\nconst COMPLETE_HEX_PATTERN = /^#(?:[0-9a-fA-F]{3,4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/;\n// Longest hex body CSS accepts (`#rrggbbaa` without the hash).\nconst MAX_HEX_BODY_LENGTH = 8;\n// Native <input type=\"color\"> default when fed anything unparseable.\nconst PICKER_FALLBACK = '#000000';\n\nconst extractHexBody = (value: unknown): string | null => {\n if (typeof value !== 'string') return null;\n const trimmed = value.trim();\n if (trimmed === '') return null;\n return trimmed.startsWith('#') ? trimmed.slice(1) : trimmed;\n};\n\nexport const isCompleteHexColor = (value: string): boolean => COMPLETE_HEX_PATTERN.test(value);\n\n// @see https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/showPicker\nexport const showPicker = (input: HTMLInputElement) => {\n const isShowPickerSupported = 'showPicker' in HTMLInputElement.prototype;\n isShowPickerSupported ? input.showPicker() : input.click();\n};\n\n/**\n * Coerces free-form text into a partial hex color for the visible text\n * input. Allows up to 8 hex digits to support `#rrggbbaa` (RGBA / alpha).\n *\n * Behaviour:\n * - empty / null / undefined / non-string → `''`\n * - trims surrounding whitespace\n * - prepends `#` when the user types raw hex without it\n * - keeps only the leading run of valid hex digits, dropping the rest\n * - caps total length at `# + 8` hex digits\n * - returns `''` when no valid hex digits remain (e.g. bare `#`, `zz`) so\n * the input doesn't sit on a lonely `#`\n *\n * Note: the result may be a *prefix* (e.g. `#a`, `#ab`) that is not yet a\n * valid CSS color — gate any rendering on `isCompleteHexColor`.\n */\nexport const coerceHexInputValue = (value?: string | null): string => {\n const body = extractHexBody(value);\n if (body === null) return '';\n const [validBody] = body.match(/^[0-9a-fA-F]+/) ?? [];\n if (!validBody) return '';\n return `#${validBody.slice(0, MAX_HEX_BODY_LENGTH)}`;\n};\n\n/**\n * Coerces any value into the strict lowercase `#rrggbb` form required by the\n * native `<input type=\"color\">`. Anything the picker can't render is\n * collapsed to `#000000`.\n *\n * - 3-digit shorthand (`#abc`) → expanded to 6 digits (`#aabbcc`)\n * - 4/8-digit RGBA → alpha channel is dropped\n * - invalid characters, wrong length, or non-string types → `#000000`\n *\n * The native picker silently lowercases its value; we lowercase here too so\n * controlled consumers see the same string round-trip.\n */\nexport const coerceColorPickerValue = (value: ComponentProps<'input'>['value'] | null) => {\n const body = extractHexBody(value);\n if (body === null || !HEX_CHARSET.test(body)) return PICKER_FALLBACK;\n\n if (body.length === 3 || body.length === 4) {\n const [r, g, b] = body;\n return `#${r}${r}${g}${g}${b}${b}`.toLowerCase();\n }\n if (body.length === 6 || body.length === 8) {\n return `#${body.slice(0, 6).toLowerCase()}`;\n }\n return PICKER_FALLBACK;\n};\n","import { type ComponentProps, type ComponentRef, useRef } from 'react';\n\nimport { InputGroup } from '../../components/InputGroup';\nimport { Pipette } from '../../icons';\n\nimport { coerceColorPickerValue, showPicker } from './utils';\n\ntype Props = Omit<ComponentProps<'input'>, 'type'>;\n\nexport const ColorPicker = ({ value, disabled, readOnly, ...props }: Props) => {\n const pickerRef = useRef<ComponentRef<'input'>>(null);\n\n const handleOpenPicker = () => {\n if (!pickerRef.current) return;\n showPicker(pickerRef.current);\n };\n\n return (\n <div className=\"tw:relative\">\n <input\n {...props}\n ref={pickerRef}\n type=\"color\"\n value={coerceColorPickerValue(value)}\n tabIndex={-1}\n aria-hidden\n className=\"tw:pointer-events-none tw:absolute tw:left-0 tw:top-full tw:size-0 tw:opacity-0\"\n disabled={disabled}\n readOnly={readOnly}\n />\n <InputGroup.Button\n onMouseDown={(event) => event.preventDefault()}\n disabled={disabled || readOnly}\n onClick={handleOpenPicker}\n aria-label=\"Pick color\"\n >\n <Pipette className=\"tw:size-4\" />\n </InputGroup.Button>\n </div>\n );\n};\n","import { useRef } from 'react';\nimport type {\n ChangeEventHandler,\n ComponentProps,\n ComponentRef,\n FocusEventHandler,\n MouseEventHandler,\n} from 'react';\n\nimport { InputGroup } from '../../components/InputGroup';\nimport { useControllableState } from '../../hooks/useControllableState';\nimport { X } from '../../icons';\nimport { cn, createChangeInputEvent, mergeRefs } from '../../utils';\n\nimport { ColorPicker } from './ColorPicker';\nimport { coerceHexInputValue, isCompleteHexColor } from './utils';\n\ntype InputGroupProps = Pick<\n ComponentProps<typeof InputGroup>,\n 'variant' | 'focusVariant' | 'state' | 'sizing'\n>;\n\ntype InputGroupInputProps = Omit<ComponentProps<typeof InputGroup.Input>, 'value' | 'defaultValue'>;\n\ntype Props = InputGroupProps &\n InputGroupInputProps & {\n value?: string | null;\n defaultValue?: string | null;\n onValueChange?: (value: string) => void;\n onValueBlur?: (value: string) => void;\n allowClear?: boolean;\n };\n\nexport const ColorInput = ({\n ref,\n\n // group props\n state,\n variant,\n focusVariant,\n sizing,\n className,\n\n // own props\n value: valueProp,\n onValueChange,\n onValueBlur,\n onChange,\n onBlur,\n defaultValue,\n allowClear = false,\n\n // input props\n disabled,\n readOnly,\n ...restInputProps\n}: Props) => {\n const inputRef = useRef<ComponentRef<'input'>>(null);\n\n const [value, setValue] = useControllableState<string>({\n // A `null` controlled value stays controlled (coerced to ''); `undefined` is uncontrolled.\n prop: valueProp === null ? '' : valueProp,\n defaultProp: defaultValue ?? '',\n onChange: onValueChange,\n });\n\n const isControlled = valueProp !== undefined;\n\n const canClear = allowClear && !!value && !disabled && !readOnly;\n const swatchColor = coerceHexInputValue(value);\n const isValidSwatch = isCompleteHexColor(swatchColor);\n\n // Preserve raw text while the user is typing — sanitise on blur.\n const handleChange: ChangeEventHandler<HTMLInputElement> = (event) => {\n setValue(event.target.value);\n onChange?.(event);\n };\n\n const handleBlur: FocusEventHandler<HTMLInputElement> = (event) => {\n const newValue = event.target.value;\n const sanitizedNewValue = coerceHexInputValue(newValue);\n\n if (sanitizedNewValue !== newValue) {\n // In controlled mode, let the parent decide whether to apply the\n // sanitised value via `onValueChange` — don't fight its `value` prop.\n if (!isControlled) event.target.value = sanitizedNewValue;\n setValue(sanitizedNewValue);\n }\n\n onValueBlur?.(sanitizedNewValue);\n onBlur?.(event);\n };\n\n const handlePickerChange: ChangeEventHandler<HTMLInputElement> = (event) => {\n setValue(coerceHexInputValue(event.target.value));\n onChange?.(event);\n };\n\n const handleClear: MouseEventHandler<HTMLButtonElement> = () => {\n if (!inputRef.current) return;\n inputRef.current.value = '';\n setValue('');\n onChange?.(createChangeInputEvent(inputRef.current));\n };\n\n return (\n <InputGroup\n state={state}\n variant={variant}\n sizing={sizing}\n focusVariant={focusVariant}\n className={className}\n >\n <InputGroup.Addon\n align=\"inline-start\"\n className={cn(\n { 'tw:-ml-7 tw:opacity-0': !value },\n 'tw:transition-[opacity,margin]',\n 'tw:ease-linear',\n 'tw:duration-200',\n )}\n >\n <div\n style={isValidSwatch ? { background: swatchColor } : undefined}\n className={cn(\n 'tw:size-5',\n 'tw:shrink-0',\n 'tw:rounded-sm',\n 'tw:border',\n 'tw:border-solid',\n 'tw:border-neutral-300',\n {\n 'tw:bg-[linear-gradient(to_top_right,transparent_calc(50%_-_1px),theme(colors.red.300)_calc(50%_-_1px),theme(colors.red.300)_calc(50%_+_1px),transparent_calc(50%_+_1px))]':\n !isValidSwatch,\n },\n )}\n />\n </InputGroup.Addon>\n\n <InputGroup.Input\n {...restInputProps}\n type=\"text\"\n ref={mergeRefs(ref ?? null, inputRef)}\n value={value}\n onChange={handleChange}\n onBlur={handleBlur}\n disabled={disabled}\n readOnly={readOnly}\n />\n\n <InputGroup.Addon align=\"inline-end\">\n {canClear && (\n <InputGroup.Button\n // prevents input focus stealing\n onMouseDown={(event) => event.preventDefault()}\n onClick={handleClear}\n aria-label=\"Clear color\"\n >\n <X className=\"tw:size-4\" />\n </InputGroup.Button>\n )}\n <ColorPicker\n disabled={disabled}\n readOnly={readOnly}\n value={value}\n onChange={handlePickerChange}\n />\n </InputGroup.Addon>\n </InputGroup>\n );\n};\n"],"mappings":";;;;;;;;;AAEA,MAAM,cAAc;AAEpB,MAAM,uBAAuB;AAE7B,MAAM,sBAAsB;AAE5B,MAAM,kBAAkB;AAExB,MAAM,kBAAkB,UAAkC;CACxD,IAAI,OAAO,UAAU,UAAU,OAAO;CACtC,MAAM,UAAU,MAAM,KAAK;CAC3B,IAAI,YAAY,IAAI,OAAO;CAC3B,OAAO,QAAQ,WAAW,GAAG,IAAI,QAAQ,MAAM,CAAC,IAAI;AACtD;AAEA,MAAa,sBAAsB,UAA2B,qBAAqB,KAAK,KAAK;AAG7F,MAAa,cAAc,UAA4B;CAErD,gBAD8C,iBAAiB,YACvC,MAAM,WAAW,IAAI,MAAM,MAAM;AAC3D;;;;;;;;;;;;;;;;;AAkBA,MAAa,uBAAuB,UAAkC;CACpE,MAAM,OAAO,eAAe,KAAK;CACjC,IAAI,SAAS,MAAM,OAAO;CAC1B,MAAM,CAAC,aAAa,KAAK,MAAM,eAAe,KAAK,CAAC;CACpD,IAAI,CAAC,WAAW,OAAO;CACvB,OAAO,IAAI,UAAU,MAAM,GAAG,mBAAmB;AACnD;;;;;;;;;;;;;AAcA,MAAa,0BAA0B,UAAmD;CACxF,MAAM,OAAO,eAAe,KAAK;CACjC,IAAI,SAAS,QAAQ,CAAC,YAAY,KAAK,IAAI,GAAG,OAAO;CAErD,IAAI,KAAK,WAAW,KAAK,KAAK,WAAW,GAAG;EAC1C,MAAM,CAAC,GAAG,GAAG,KAAK;EAClB,OAAO,IAAI,IAAI,IAAI,IAAI,IAAI,IAAI,IAAI,YAAY;CACjD;CACA,IAAI,KAAK,WAAW,KAAK,KAAK,WAAW,GACvC,OAAO,IAAI,KAAK,MAAM,GAAG,CAAC,CAAC,CAAC,YAAY;CAE1C,OAAO;AACT;;;AChEA,MAAa,eAAe,EAAE,OAAO,UAAU,UAAU,GAAG,YAAmB;CAC7E,MAAM,YAAY,OAA8B,IAAI;CAEpD,MAAM,yBAAyB;EAC7B,IAAI,CAAC,UAAU,SAAS;EACxB,WAAW,UAAU,OAAO;CAC9B;CAEA,OACE,qBAAC,OAAD;EAAK,WAAU;EAAf,UAAA,CACE,oBAAC,SAAD;GACE,GAAI;GACJ,KAAK;GACL,MAAK;GACL,OAAO,uBAAuB,KAAK;GACnC,UAAU;GACV,eAAA;GACA,WAAU;GACA;GACA;EACX,CAAA,GACD,oBAAC,WAAW,QAAZ;GACE,cAAc,UAAU,MAAM,eAAe;GAC7C,UAAU,YAAY;GACtB,SAAS;GACT,cAAW;GAEX,UAAA,oBAAC,SAAD,EAAS,WAAU,YAAa,CAAA;EACf,CAAA,CAChB;;AAET;;;ACPA,MAAa,cAAc,EACzB,KAGA,OACA,SACA,cACA,QACA,WAGA,OAAO,WACP,eACA,aACA,UACA,QACA,cACA,aAAa,OAGb,UACA,UACA,GAAG,qBACQ;CACX,MAAM,WAAW,OAA8B,IAAI;CAEnD,MAAM,CAAC,OAAO,YAAY,qBAA6B;EAErD,MAAM,cAAc,OAAO,KAAK;EAChC,aAAa,gBAAgB;EAC7B,UAAU;CACZ,CAAC;CAED,MAAM,eAAe,cAAc,KAAA;CAEnC,MAAM,WAAW,cAAc,CAAC,CAAC,SAAS,CAAC,YAAY,CAAC;CACxD,MAAM,cAAc,oBAAoB,KAAK;CAC7C,MAAM,gBAAgB,mBAAmB,WAAW;CAGpD,MAAM,gBAAsD,UAAU;EACpE,SAAS,MAAM,OAAO,KAAK;EAC3B,WAAW,KAAK;CAClB;CAEA,MAAM,cAAmD,UAAU;EACjE,MAAM,WAAW,MAAM,OAAO;EAC9B,MAAM,oBAAoB,oBAAoB,QAAQ;EAEtD,IAAI,sBAAsB,UAAU;GAGlC,IAAI,CAAC,cAAc,MAAM,OAAO,QAAQ;GACxC,SAAS,iBAAiB;EAC5B;EAEA,cAAc,iBAAiB;EAC/B,SAAS,KAAK;CAChB;CAEA,MAAM,sBAA4D,UAAU;EAC1E,SAAS,oBAAoB,MAAM,OAAO,KAAK,CAAC;EAChD,WAAW,KAAK;CAClB;CAEA,MAAM,oBAA0D;EAC9D,IAAI,CAAC,SAAS,SAAS;EACvB,SAAS,QAAQ,QAAQ;EACzB,SAAS,EAAE;EACX,WAAW,uBAAuB,SAAS,OAAO,CAAC;CACrD;CAEA,OACE,qBAAC,YAAD;EACS;EACE;EACD;EACM;EACH;EALb,UAAA;GAOE,oBAAC,WAAW,OAAZ;IACE,OAAM;IACN,WAAW,GACT,EAAE,yBAAyB,CAAC,MAAM,GAClC,kCACA,kBACA,iBACF;IAEA,UAAA,oBAAC,OAAD;KACE,OAAO,gBAAgB,EAAE,YAAY,YAAY,IAAI,KAAA;KACrD,WAAW,GACT,aACA,eACA,iBACA,aACA,mBACA,yBACA,EACE,6KACE,CAAC,cACL,CACF;IACD,CAAA;GACe,CAAA;GAElB,oBAAC,WAAW,OAAZ;IACE,GAAI;IACJ,MAAK;IACL,KAAK,UAAU,OAAO,MAAM,QAAQ;IAC7B;IACP,UAAU;IACV,QAAQ;IACE;IACA;GACX,CAAA;GAED,qBAAC,WAAW,OAAZ;IAAkB,OAAM;IAAxB,UAAA,CACG,YACC,oBAAC,WAAW,QAAZ;KAEE,cAAc,UAAU,MAAM,eAAe;KAC7C,SAAS;KACT,cAAW;KAEX,UAAA,oBAAC,GAAD,EAAG,WAAU,YAAa,CAAA;IACT,CAAA,GAErB,oBAAC,aAAD;KACY;KACA;KACH;KACP,UAAU;IACX,CAAA,CACe;;EACR;;AAEhB"}
@@ -1,6 +1,6 @@
1
1
  import { Monitor, Moon, Sun } from "./icons-Cek151jC.js";
2
- import { Button } from "./Button-6xBX0nNl.js";
3
- import { DropdownMenu } from "./DropdownMenu-t90tVw6l.js";
2
+ import { Button } from "./Button-CPsEQuTN.js";
3
+ import { DropdownMenu } from "./DropdownMenu-DpMEcyCq.js";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
  //#region src/blocks/ColorModeSwitch/ColorModeSwitch.tsx
6
6
  const OPTIONS = [
@@ -74,4 +74,4 @@ const ColorModeSwitch = ({ value, onValueChange, size = "small", className }) =>
74
74
  //#endregion
75
75
  export { ColorModeSwitch };
76
76
 
77
- //# sourceMappingURL=ColorModeSwitch-dZFZyqy1.js.map
77
+ //# sourceMappingURL=ColorModeSwitch-B5PXCVqB.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ColorModeSwitch-dZFZyqy1.js","names":[],"sources":["../src/blocks/ColorModeSwitch/ColorModeSwitch.tsx"],"sourcesContent":["import { Button } from '../../components/Button';\nimport { DropdownMenu } from '../../components/DropdownMenu';\nimport type { ColorScheme } from '../../components/ThemeProvider';\nimport type { LucideIcon } from '../../icons';\nimport { Monitor, Moon, Sun } from '../../icons';\n\ntype Props = {\n /** The active color scheme. Controlled — pair with `onValueChange`. */\n value: ColorScheme;\n /** Called with the chosen scheme when the user picks a menu item. */\n onValueChange: (value: ColorScheme) => void;\n /** Trigger button size. Defaults to `small`. */\n size?: 'small' | 'medium';\n className?: string;\n};\n\nconst OPTIONS: { value: ColorScheme; label: string; icon: LucideIcon }[] = [\n { value: 'light', label: 'Light', icon: Sun },\n { value: 'dark', label: 'Dark', icon: Moon },\n { value: 'system', label: 'System', icon: Monitor },\n];\n\nconst triggerSizeMap = { small: 'icon-sm', medium: 'icon' } as const;\n\n/**\n * Light / dark / system control — a single icon-only `Button` (showing the active\n * scheme) that opens a `DropdownMenu` of the three options. Composed, not a new\n * primitive. **Controlled:** it renders `value` and reports changes; it does not\n * own the state. `ThemeProvider.colorScheme` is a controlled prop, so wire this to\n * wherever that state lives:\n *\n * ```tsx\n * const [scheme, setScheme] = useState<ColorScheme>('system');\n * <ThemeProvider colorScheme={scheme}>…</ThemeProvider>\n * <ColorModeSwitch value={scheme} onValueChange={setScheme} />\n * ```\n *\n * The menu uses `DropdownMenu.RadioGroup` for single-select semantics; the active\n * item is marked as checked. The trigger's `aria-label` names the current scheme.\n */\nexport const ColorModeSwitch = ({ value, onValueChange, size = 'small', className }: Props) => {\n const active = OPTIONS.find((option) => option.value === value);\n const ActiveIcon = active?.icon ?? Monitor;\n const activeLabel = active?.label ?? 'System';\n\n return (\n <DropdownMenu>\n <DropdownMenu.Trigger asChild>\n <Button\n type=\"button\"\n variant=\"outline\"\n size={triggerSizeMap[size]}\n aria-label={`Color mode: ${activeLabel}`}\n title={`Color mode: ${activeLabel}`}\n className={className}\n >\n <ActiveIcon className=\"tw:size-4\" />\n </Button>\n </DropdownMenu.Trigger>\n <DropdownMenu.Content align=\"end\">\n <DropdownMenu.RadioGroup value={value} onValueChange={onValueChange}>\n {OPTIONS.map(({ value: option, label, icon: Icon }) => (\n <DropdownMenu.RadioItem\n key={option}\n value={option}\n icon={<Icon />}\n indicator=\"check\"\n indicatorAlign=\"end\"\n closeOnSelect\n >\n {label}\n </DropdownMenu.RadioItem>\n ))}\n </DropdownMenu.RadioGroup>\n </DropdownMenu.Content>\n </DropdownMenu>\n );\n};\n"],"mappings":";;;;;AAgBA,MAAM,UAAqE;CACzE;EAAE,OAAO;EAAS,OAAO;EAAS,MAAM;CAAI;CAC5C;EAAE,OAAO;EAAQ,OAAO;EAAQ,MAAM;CAAK;CAC3C;EAAE,OAAO;EAAU,OAAO;EAAU,MAAM;CAAQ;AACpD;AAEA,MAAM,iBAAiB;CAAE,OAAO;CAAW,QAAQ;AAAO;;;;;;;;;;;;;;;;;AAkB1D,MAAa,mBAAmB,EAAE,OAAO,eAAe,OAAO,SAAS,gBAAuB;CAC7F,MAAM,SAAS,QAAQ,MAAM,WAAW,OAAO,UAAU,KAAK;CAC9D,MAAM,aAAa,QAAQ,QAAQ;CACnC,MAAM,cAAc,QAAQ,SAAS;CAErC,OACE,qBAAC,cAAD,EAAA,UAAA,CACE,oBAAC,aAAa,SAAd;EAAsB,SAAA;EACpB,UAAA,oBAAC,QAAD;GACE,MAAK;GACL,SAAQ;GACR,MAAM,eAAe;GACrB,cAAY,eAAe;GAC3B,OAAO,eAAe;GACX;GAEX,UAAA,oBAAC,YAAD,EAAY,WAAU,YAAa,CAAA;EAC7B,CAAA;CACY,CAAA,GACtB,oBAAC,aAAa,SAAd;EAAsB,OAAM;EAC1B,UAAA,oBAAC,aAAa,YAAd;GAAgC;GAAsB;GACnD,UAAA,QAAQ,KAAK,EAAE,OAAO,QAAQ,OAAO,MAAM,WAC1C,oBAAC,aAAa,WAAd;IAEE,OAAO;IACP,MAAM,oBAAC,MAAD,CAAO,CAAA;IACb,WAAU;IACV,gBAAe;IACf,eAAA;IAEC,UAAA;GACqB,GARjB,MAQiB,CACzB;EACsB,CAAA;CACL,CAAA,CACV,EAAA,CAAA;AAElB"}
1
+ {"version":3,"file":"ColorModeSwitch-B5PXCVqB.js","names":[],"sources":["../src/blocks/ColorModeSwitch/ColorModeSwitch.tsx"],"sourcesContent":["import { Button } from '../../components/Button';\nimport { DropdownMenu } from '../../components/DropdownMenu';\nimport type { ColorScheme } from '../../components/ThemeProvider';\nimport type { LucideIcon } from '../../icons';\nimport { Monitor, Moon, Sun } from '../../icons';\n\ntype Props = {\n /** The active color scheme. Controlled — pair with `onValueChange`. */\n value: ColorScheme;\n /** Called with the chosen scheme when the user picks a menu item. */\n onValueChange: (value: ColorScheme) => void;\n /** Trigger button size. Defaults to `small`. */\n size?: 'small' | 'medium';\n className?: string;\n};\n\nconst OPTIONS: { value: ColorScheme; label: string; icon: LucideIcon }[] = [\n { value: 'light', label: 'Light', icon: Sun },\n { value: 'dark', label: 'Dark', icon: Moon },\n { value: 'system', label: 'System', icon: Monitor },\n];\n\nconst triggerSizeMap = { small: 'icon-sm', medium: 'icon' } as const;\n\n/**\n * Light / dark / system control — a single icon-only `Button` (showing the active\n * scheme) that opens a `DropdownMenu` of the three options. Composed, not a new\n * primitive. **Controlled:** it renders `value` and reports changes; it does not\n * own the state. `ThemeProvider.colorScheme` is a controlled prop, so wire this to\n * wherever that state lives:\n *\n * ```tsx\n * const [scheme, setScheme] = useState<ColorScheme>('system');\n * <ThemeProvider colorScheme={scheme}>…</ThemeProvider>\n * <ColorModeSwitch value={scheme} onValueChange={setScheme} />\n * ```\n *\n * The menu uses `DropdownMenu.RadioGroup` for single-select semantics; the active\n * item is marked as checked. The trigger's `aria-label` names the current scheme.\n */\nexport const ColorModeSwitch = ({ value, onValueChange, size = 'small', className }: Props) => {\n const active = OPTIONS.find((option) => option.value === value);\n const ActiveIcon = active?.icon ?? Monitor;\n const activeLabel = active?.label ?? 'System';\n\n return (\n <DropdownMenu>\n <DropdownMenu.Trigger asChild>\n <Button\n type=\"button\"\n variant=\"outline\"\n size={triggerSizeMap[size]}\n aria-label={`Color mode: ${activeLabel}`}\n title={`Color mode: ${activeLabel}`}\n className={className}\n >\n <ActiveIcon className=\"tw:size-4\" />\n </Button>\n </DropdownMenu.Trigger>\n <DropdownMenu.Content align=\"end\">\n <DropdownMenu.RadioGroup value={value} onValueChange={onValueChange}>\n {OPTIONS.map(({ value: option, label, icon: Icon }) => (\n <DropdownMenu.RadioItem\n key={option}\n value={option}\n icon={<Icon />}\n indicator=\"check\"\n indicatorAlign=\"end\"\n closeOnSelect\n >\n {label}\n </DropdownMenu.RadioItem>\n ))}\n </DropdownMenu.RadioGroup>\n </DropdownMenu.Content>\n </DropdownMenu>\n );\n};\n"],"mappings":";;;;;AAgBA,MAAM,UAAqE;CACzE;EAAE,OAAO;EAAS,OAAO;EAAS,MAAM;CAAI;CAC5C;EAAE,OAAO;EAAQ,OAAO;EAAQ,MAAM;CAAK;CAC3C;EAAE,OAAO;EAAU,OAAO;EAAU,MAAM;CAAQ;AACpD;AAEA,MAAM,iBAAiB;CAAE,OAAO;CAAW,QAAQ;AAAO;;;;;;;;;;;;;;;;;AAkB1D,MAAa,mBAAmB,EAAE,OAAO,eAAe,OAAO,SAAS,gBAAuB;CAC7F,MAAM,SAAS,QAAQ,MAAM,WAAW,OAAO,UAAU,KAAK;CAC9D,MAAM,aAAa,QAAQ,QAAQ;CACnC,MAAM,cAAc,QAAQ,SAAS;CAErC,OACE,qBAAC,cAAD,EAAA,UAAA,CACE,oBAAC,aAAa,SAAd;EAAsB,SAAA;EACpB,UAAA,oBAAC,QAAD;GACE,MAAK;GACL,SAAQ;GACR,MAAM,eAAe;GACrB,cAAY,eAAe;GAC3B,OAAO,eAAe;GACX;GAEX,UAAA,oBAAC,YAAD,EAAY,WAAU,YAAa,CAAA;EAC7B,CAAA;CACY,CAAA,GACtB,oBAAC,aAAa,SAAd;EAAsB,OAAM;EAC1B,UAAA,oBAAC,aAAa,YAAd;GAAgC;GAAsB;GACnD,UAAA,QAAQ,KAAK,EAAE,OAAO,QAAQ,OAAO,MAAM,WAC1C,oBAAC,aAAa,WAAd;IAEE,OAAO;IACP,MAAM,oBAAC,MAAD,CAAO,CAAA;IACb,WAAU;IACV,gBAAe;IACf,eAAA;IAEC,UAAA;GACqB,GARjB,MAQiB,CACzB;EACsB,CAAA;CACL,CAAA,CACV,EAAA,CAAA;AAElB"}
@@ -1,7 +1,7 @@
1
1
  import { cn } from "./classNames-BzrkDnOD.js";
2
- import { useArgoDesign } from "./context-KxxeMHbR.js";
2
+ import { useArgoDesign } from "./context-BrNtMc1H.js";
3
3
  import { Check, ChevronDown, Plus, X } from "./icons-Cek151jC.js";
4
- import { InputGroup } from "./InputGroup-CdTq8H7c.js";
4
+ import { InputGroup } from "./InputGroup-D7zlmqPB.js";
5
5
  import { Badge } from "./Badge-Ch26CXoP.js";
6
6
  import { useEffect, useRef, useState } from "react";
7
7
  import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
@@ -153,7 +153,7 @@ const ComboboxItemIndicator = ({ ref, className, variant = "check", ...props })
153
153
  return /* @__PURE__ */ jsx(Combobox.ItemIndicator, {
154
154
  ...props,
155
155
  ref,
156
- className: cn("tw:pointer-events-none", "tw:absolute", "tw:right-2", "tw:group-data-[variant=default]/combobox-content:right-4", "tw:size-4", "tw:group-data-[highlighted]/combobox-item:text-accent-foreground", "tw:group-data-[variant=default]/combobox-content:group-data-[highlighted]/combobox-item:text-foreground", className),
156
+ className: cn("tw:pointer-events-none", "tw:absolute", "tw:right-2", "tw:group-data-[variant=default]/combobox-content:right-4", "tw:size-4", "tw:group-data-[highlighted]/combobox-item:text-accent-foreground", "tw:group-data-[variant=default]/combobox-content:group-data-[highlighted]/combobox-item:text-secondary-foreground", className),
157
157
  render: /* @__PURE__ */ jsx(Check, {})
158
158
  });
159
159
  };
@@ -163,7 +163,7 @@ const ComboboxItem = ({ ref, className, children, icon, indicator: variant = "ch
163
163
  ...props,
164
164
  ref,
165
165
  "data-slot": "combobox-item",
166
- className: cn("tw:group/combobox-item", "tw:relative", "tw:flex", "tw:flex-1", "tw:items-center", "tw:gap-2", "tw:py-2", "tw:px-2", "tw:group-data-[variant=default]/combobox-content:px-4", "tw:rounded-lg", "tw:group-data-[variant=default]/combobox-content:rounded-none", "tw:text-sm", "tw:select-none", "tw:cursor-default", "tw:outline-hidden", "tw:data-[highlighted]:bg-accent", "tw:group-data-[variant=default]/combobox-content:data-[highlighted]:bg-neutral-100", "tw:data-[highlighted]:text-accent-foreground", "tw:group-data-[variant=default]/combobox-content:data-[highlighted]:text-foreground", "tw:data-disabled:pointer-events-none", "tw:data-disabled:opacity-50", "tw:[&_svg]:pointer-events-none", "tw:[&_svg]:shrink-0", "tw:[&_svg]:text-muted-foreground", "tw:[&_svg:not([class*='size-'])]:size-4", className),
166
+ className: cn("tw:group/combobox-item", "tw:relative", "tw:flex", "tw:flex-1", "tw:items-center", "tw:gap-2", "tw:py-2", "tw:px-2", "tw:group-data-[variant=default]/combobox-content:px-4", "tw:rounded-lg", "tw:group-data-[variant=default]/combobox-content:rounded-none", "tw:text-sm", "tw:select-none", "tw:cursor-default", "tw:outline-hidden", "tw:data-[highlighted]:bg-accent", "tw:group-data-[variant=default]/combobox-content:data-[highlighted]:bg-secondary", "tw:data-[highlighted]:text-accent-foreground", "tw:group-data-[variant=default]/combobox-content:data-[highlighted]:text-secondary-foreground", "tw:data-disabled:pointer-events-none", "tw:data-disabled:opacity-50", "tw:[&_svg]:pointer-events-none", "tw:[&_svg]:shrink-0", "tw:[&_svg]:text-muted-foreground", "tw:[&_svg:not([class*='size-'])]:size-4", className),
167
167
  children: [
168
168
  /* @__PURE__ */ jsx(ComboboxItemIndicator, { variant }),
169
169
  icon,
@@ -440,4 +440,4 @@ Combobox$1.Chips = ComboboxChips;
440
440
  //#endregion
441
441
  export { Combobox$1 as Combobox, createCreatableItem, defaultGroupToLabel, defaultItemToDisabled, defaultItemToIcon, defaultItemToLabel, defaultQueryToCreateLabel, defaultToCreateValue, isCreatableItem, isGroupItem, isGroupItems, isLabeledItem, toLabel };
442
442
 
443
- //# sourceMappingURL=Combobox-Dgm6Z4ib.js.map
443
+ //# sourceMappingURL=Combobox-CyoRA7oY.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Combobox-CyoRA7oY.js","names":["BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","BaseCombobox","Combobox","BaseCombobox"],"sources":["../src/components/Combobox/utils.ts","../src/components/Combobox/ComboboxChips.tsx","../src/components/Combobox/ComboboxContent.tsx","../src/components/Combobox/ComboboxEmpty.tsx","../src/components/Combobox/ComboboxInput.tsx","../src/components/Combobox/ComboboxInputGroup.tsx","../src/components/Combobox/ComboboxItemIndicator.tsx","../src/components/Combobox/ComboboxItem.tsx","../src/components/Combobox/ComboboxList.tsx","../src/components/Combobox/ComboboxRoot.tsx","../src/components/Combobox/ComboboxSeparator.tsx","../src/components/Combobox/Group/ComboboxGroup.tsx","../src/components/Combobox/Group/ComboboxGroupLabel.tsx","../src/components/Combobox/Group/ComboboxCollection.tsx","../src/components/Combobox/Combobox.tsx"],"sourcesContent":["import type { CreatableItem, Group, InternalItems, LabeledItem, SelectAllItem } from './types';\n\nconst isPlainObject = (item: unknown): item is Record<string, unknown> =>\n item !== null && typeof item === 'object';\n\nconst isNumber = (item: unknown): item is number => typeof item === 'number';\nconst isString = (item: unknown): item is string => typeof item === 'string';\n\nexport const isLabeledItem = (item: unknown): item is LabeledItem =>\n isPlainObject(item) && Reflect.has(item, 'label') && Reflect.has(item, 'value');\n\nconst isInternalItem = (item: unknown): item is InternalItems =>\n isLabeledItem(item) && '__marker' in item;\n\nexport const isSelectAllItem = (item: unknown): item is SelectAllItem =>\n isInternalItem(item) && item.__marker === 'selectAll';\n\nexport const isCreatableItem = (item: unknown): item is CreatableItem => {\n return isInternalItem(item) && item.__marker === 'creatable';\n};\n\nexport const isGroupItem = <Item>(itemOrGroup: Item | Group<Item>): itemOrGroup is Group<Item> =>\n itemOrGroup !== null && typeof itemOrGroup === 'object' && Reflect.has(itemOrGroup, 'items');\n\nexport const isGroupItems = <Item, GroupShape extends Group<Item> = Group<Item>>(\n items: readonly (Item | GroupShape)[],\n): items is GroupShape[] => {\n if (!Array.isArray(items)) return false;\n if (items.length === 0) return false; // Base UI treats an empty items array as non-grouped, so we must too for consistency\n return isGroupItem(items[0]); // Base UI only checks the first item to determine if it's a group or not, so we do the same for consistency\n};\n\nexport const defaultItemToLabel = <Item>(item: Item) => {\n if (isNumber(item) || isString(item)) return item;\n if (!isLabeledItem(item))\n throw new Error(\n 'Combobox: Item does not have a `label` field. Pass `itemToLabel` for custom item shapes.',\n );\n\n return item.label;\n};\n\n/** Display string for an item — mirrors base-ui's own default logic. */\nexport const toLabel = (item: unknown): string => {\n if (isString(item)) return item;\n if (isLabeledItem(item)) {\n if (item.label) return item.label;\n if (item.value) return item.value;\n }\n return String(item);\n};\n\n/** Equality key for an item — prefers .value for stable identity. */\nexport const toValueKey = (item: unknown): string => {\n if (isString(item)) return item;\n if (isLabeledItem(item)) {\n if (item.value) return item.value;\n if (item.label) return item.label;\n }\n return String(item);\n};\n\nexport const defaultItemToIcon = <Item>(item: Item) =>\n isLabeledItem(item) ? item.icon : undefined;\n\nexport const defaultItemToDisabled = <Item>(item: Item) =>\n isLabeledItem(item) ? (item.disabled ?? false) : false;\n\nexport const defaultGroupToLabel = () => undefined;\n\n// Internal markers ------------------------------------------------------------\n// Both `selectAll` and `creatable` are LabeledItem-shaped sentinels that we\n// inject into the items list passed to Base UI. They carry a `__marker`\n// discriminator so consumer code (and user-supplied callbacks) can't collide\n// with them by accident.\n\nexport const selectAllItem: SelectAllItem = {\n __marker: 'selectAll',\n value: '__select_all__',\n label: 'Select All',\n};\n\nexport const createCreatableItem = (query: string): CreatableItem => ({\n __marker: 'creatable',\n value: query,\n label: query,\n});\n\nexport const defaultToCreateValue = <Value>(\n query: string,\n value: Value | undefined,\n queryToCreateValue?: (query: string) => Value,\n): Value => {\n if (queryToCreateValue) return queryToCreateValue(query);\n if (value === undefined) return query as Value;\n if (isString(value)) return query as Value;\n if (isLabeledItem(value)) return { value: query, label: query } as Value;\n throw new Error(\n 'Combobox: Cannot infer item shape for `allowCreate`. Pass `queryToCreateValue` for custom item shapes.',\n );\n};\n\nexport const defaultQueryToCreateLabel = (query: string) => `Create \"${query}\"`;\n","import type { ComponentProps, ReactNode } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { X } from '../../icons';\nimport { Badge } from '../Badge';\n\nimport { defaultItemToLabel } from './utils';\n\ntype BadgeColor = ComponentProps<typeof Badge>['color'];\ntype BadgeVariant = ComponentProps<typeof Badge>['variant'];\n\ntype Props<Value> = {\n maxVisible?: number;\n itemToChipLabel?: (item: Value) => ReactNode;\n itemToChipColor?: (item: Value) => BadgeColor;\n variant?: BadgeVariant;\n};\n\nexport const ComboboxChips = <Value,>({\n maxVisible = 3,\n itemToChipLabel = defaultItemToLabel,\n itemToChipColor,\n variant = 'pill',\n}: Props<Value>) => (\n <BaseCombobox.Value>\n {(values: Value[]) => {\n if (!values.length) return null;\n\n const visible = values.slice(0, maxVisible);\n const overflow = values.slice(maxVisible);\n\n return (\n <>\n {visible.map((value: Value, index) => (\n <BaseCombobox.Chip\n // oxlint-disable-next-line react/no-array-index-key\n key={index}\n render={\n <Badge.Root\n color={itemToChipColor?.(value)}\n className=\"tw:max-w-40\"\n variant={variant}\n />\n }\n >\n <Badge.Label>{itemToChipLabel(value)}</Badge.Label>\n <Badge.Addon variant=\"inline\" align=\"inline-end\">\n <BaseCombobox.ChipRemove\n render={\n <Badge.Button aria-label=\"Remove value\">\n <X className=\"tw:size-3\" />\n </Badge.Button>\n }\n />\n </Badge.Addon>\n </BaseCombobox.Chip>\n ))}\n\n {overflow.length > 0 && (\n <Badge.Root variant=\"pill\">\n <Badge.Label>+{overflow.length}</Badge.Label>\n </Badge.Root>\n )}\n </>\n );\n }}\n </BaseCombobox.Value>\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../utils';\nimport { useArgoDesign } from '../ThemeProvider/context';\n\ntype PortalProps = ComponentProps<typeof BaseCombobox.Portal>;\ntype PositionerProps = ComponentProps<typeof BaseCombobox.Positioner>;\ntype PopupProps = Omit<ComponentProps<typeof BaseCombobox.Popup>, 'className'> & {\n className?: string;\n};\n\ntype Variant = 'default' | 'argo';\n\ntype Props = PopupProps &\n Pick<PositionerProps, 'side' | 'align' | 'sideOffset' | 'alignOffset' | 'anchor'> &\n Pick<PortalProps, 'container'>;\n\nexport const ComboboxContent = ({\n ref,\n align = 'start',\n side = 'bottom',\n sideOffset = 4,\n alignOffset,\n anchor,\n container,\n className,\n children,\n ...popupProps\n}: Props) => {\n const effectiveVariant: Variant = useArgoDesign() ? 'argo' : 'default';\n return (\n <BaseCombobox.Portal container={container}>\n <BaseCombobox.Positioner\n align={align}\n side={side}\n sideOffset={sideOffset}\n alignOffset={alignOffset}\n anchor={anchor}\n className=\"tw:isolate tw:z-[1055] tailwindcss-preflight\"\n >\n <BaseCombobox.Popup\n ref={ref}\n data-chips={!!anchor}\n data-variant={effectiveVariant}\n className={cn(\n 'tw:!pointer-events-auto',\n 'tw:group/combobox-content',\n 'tw:relative',\n 'tw:flex tw:flex-col tw:overflow-hidden',\n\n // sizing\n 'tw:max-h-[var(--available-height)]',\n 'tw:w-[var(--anchor-width)]',\n 'tw:max-w-[var(--available-width)]',\n 'tw:origin-[var(--transform-origin)]',\n 'tw:data-[chips=true]:min-w-[var(--anchor-width)]',\n\n // appearance\n 'tw:rounded-lg',\n 'tw:data-[variant=default]:rounded',\n\n 'tw:bg-popover',\n 'tw:text-popover-foreground',\n 'tw:shadow-md',\n 'tw:ring-1',\n 'tw:ring-foreground/10',\n 'tw:duration-100',\n\n // open animation\n 'data-open:animate-in',\n 'data-open:fade-in-0',\n 'data-open:zoom-in-95',\n\n // closed animation\n 'data-closed:animate-out',\n 'data-closed:fade-out-0',\n 'data-closed:zoom-out-95',\n\n // position animations\n 'tw:data-[side=bottom]:slide-in-from-top-2',\n 'tw:data-[side=top]:slide-in-from-bottom-2',\n 'tw:data-[side=left]:slide-in-from-right-2',\n 'tw:data-[side=right]:slide-in-from-left-2',\n 'tw:data-[side=inline-start]:slide-in-from-right-2',\n 'tw:data-[side=inline-end]:slide-in-from-left-2',\n className,\n )}\n {...popupProps}\n >\n {children}\n </BaseCombobox.Popup>\n </BaseCombobox.Positioner>\n </BaseCombobox.Portal>\n );\n};\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../utils';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.Empty>, 'className'> & {\n className?: string;\n};\n\nexport const ComboboxEmpty = ({ ref, className, ...props }: Props) => (\n <BaseCombobox.Empty\n ref={ref}\n className={cn(\n 'tw:hidden',\n 'tw:group-data-[empty]/combobox-content:flex',\n 'tw:justify-center',\n 'tw:items-center',\n 'tw:text-center',\n 'tw:px-2',\n 'tw:text-muted-foreground',\n 'tw:py-6',\n className,\n )}\n {...props}\n />\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { InputGroup } from '../InputGroup';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.Input>, 'render'>;\n\nexport const ComboboxInput = ({ ref, ...props }: Props) => (\n <BaseCombobox.Input {...props} ref={ref} render={<InputGroup.Input />} />\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { InputGroup } from '../InputGroup';\n\ntype InputGroupProps = Pick<\n ComponentProps<typeof InputGroup>,\n 'variant' | 'focusVariant' | 'sizing' | 'state'\n>;\n\ntype Props = InputGroupProps &\n Omit<ComponentProps<typeof BaseCombobox.InputGroup>, 'render' | 'className'> & {\n className?: string;\n };\n\nexport const ComboboxInputGroup = ({\n ref,\n state,\n variant,\n sizing,\n focusVariant,\n className,\n ...props\n}: Props) => (\n <BaseCombobox.InputGroup\n {...props}\n ref={ref}\n render={\n <InputGroup\n state={state}\n variant={variant}\n focusVariant={focusVariant}\n sizing={sizing}\n className={className}\n />\n }\n />\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { Check } from '../../icons';\nimport { cn } from '../../utils';\n\ntype Variant = 'check' | 'checkbox';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.ItemIndicator>, 'className' | 'children'> & {\n className?: string;\n variant?: Variant;\n};\n\nexport const ComboboxItemIndicator = ({ ref, className, variant = 'check', ...props }: Props) => {\n if (variant === 'checkbox') {\n return (\n <BaseCombobox.ItemIndicator\n ref={ref}\n keepMounted\n className={cn(\n 'tw:group/combobox-item-indicator',\n\n 'tw:inline-flex',\n 'tw:items-center',\n 'tw:justify-center',\n 'tw:size-4',\n 'tw:shrink-0',\n\n 'tw:rounded',\n 'tw:border',\n 'tw:border-input',\n 'tw:bg-background',\n\n 'tw:data-[selected]:bg-primary',\n 'tw:data-[selected]:border-primary',\n className,\n )}\n {...props}\n >\n <Check\n className={cn(\n 'tw:hidden',\n 'tw:size-3',\n 'tw:stroke-[4px]',\n 'tw:!text-primary-foreground',\n 'tw:group-data-[selected]/combobox-item-indicator:block',\n )}\n />\n </BaseCombobox.ItemIndicator>\n );\n }\n\n return (\n <BaseCombobox.ItemIndicator\n {...props}\n ref={ref}\n className={cn(\n 'tw:pointer-events-none',\n 'tw:absolute',\n 'tw:right-2',\n\n 'tw:group-data-[variant=default]/combobox-content:right-4',\n // `render={<Check />}` makes the icon the indicator element itself (not a descendant), so a\n // `[&_svg]` rule never matches it — size it directly or Lucide renders at its 24px default.\n 'tw:size-4',\n 'tw:group-data-[highlighted]/combobox-item:text-accent-foreground',\n 'tw:group-data-[variant=default]/combobox-content:group-data-[highlighted]/combobox-item:text-secondary-foreground',\n className,\n )}\n render={<Check />}\n />\n );\n};\n","import type { ComponentProps, ReactNode } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../utils';\n\nimport { ComboboxItemIndicator } from './ComboboxItemIndicator';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.Item>, 'className'> & {\n className?: string;\n icon?: ReactNode;\n indicator?: ComponentProps<typeof ComboboxItemIndicator>['variant'];\n};\n\nexport const ComboboxItem = ({\n ref,\n className,\n children,\n icon,\n indicator: variant = 'check',\n ...props\n}: Props) => (\n <BaseCombobox.Item\n {...props}\n ref={ref}\n data-slot=\"combobox-item\"\n className={cn(\n 'tw:group/combobox-item',\n // layout\n 'tw:relative',\n 'tw:flex',\n 'tw:flex-1',\n 'tw:items-center',\n 'tw:gap-2',\n\n // spacing\n 'tw:py-2',\n 'tw:px-2',\n 'tw:group-data-[variant=default]/combobox-content:px-4',\n 'tw:rounded-lg',\n 'tw:group-data-[variant=default]/combobox-content:rounded-none',\n\n // typography\n 'tw:text-sm',\n 'tw:select-none',\n 'tw:cursor-default',\n 'tw:outline-hidden',\n\n // highlighted (keyboard / hover)\n 'tw:data-[highlighted]:bg-accent',\n // The legacy highlight is a neutral step, not the argo accent.\n //\n // - `secondary` carries its own foreground, so fill and ink move together.\n // - `muted` is unusable: in dark it equals `popover`, so the band would disappear\n // into the listbox.\n 'tw:group-data-[variant=default]/combobox-content:data-[highlighted]:bg-secondary',\n 'tw:data-[highlighted]:text-accent-foreground',\n 'tw:group-data-[variant=default]/combobox-content:data-[highlighted]:text-secondary-foreground',\n\n // disabled\n 'tw:data-disabled:pointer-events-none',\n 'tw:data-disabled:opacity-50',\n\n // child svg defaults\n 'tw:[&_svg]:pointer-events-none',\n 'tw:[&_svg]:shrink-0',\n 'tw:[&_svg]:text-muted-foreground',\n \"tw:[&_svg:not([class*='size-'])]:size-4\",\n className,\n )}\n >\n {<ComboboxItemIndicator variant={variant} />}\n {icon}\n <span className=\"tw:truncate\">{children}</span>\n </BaseCombobox.Item>\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../utils';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.List>, 'className'> & {\n className?: string;\n};\n\nexport const ComboboxList = ({ ref, className, ...props }: Props) => (\n <BaseCombobox.List\n ref={ref}\n className={cn(\n 'tw:no-scrollbar',\n 'tw:scroll-py-1',\n 'tw:overflow-y-auto',\n 'tw:overscroll-contain',\n 'tw:min-h-0',\n 'tw:flex-1',\n\n 'tw:p-2',\n 'tw:data-[empty]:p-0',\n 'tw:group-data-[variant=default]/combobox-content:p-0',\n className,\n )}\n {...props}\n />\n);\n","import { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nexport const ComboboxRoot = <Value, Multiple extends boolean | undefined = false>(\n props: BaseCombobox.Root.Props<Value, Multiple>,\n) => <BaseCombobox.Root {...props} />;\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../utils';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.Separator>, 'className'> & {\n className?: string;\n};\n\nexport const ComboboxSeparator = ({ ref, className, ...props }: Props) => (\n <BaseCombobox.Separator\n ref={ref}\n className={cn('tw:mx-2 tw:my-1 tw:h-px tw:bg-border', className)}\n {...props}\n />\n);\n","import type { ComponentProps } from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../../utils';\n\ntype Props = Omit<ComponentProps<typeof BaseCombobox.Group>, 'className'> & {\n className?: string;\n};\n\nexport const ComboboxGroup = ({ ref, className, children, ...props }: Props) => (\n <BaseCombobox.Group\n ref={ref}\n className={cn('tw:flex tw:flex-col tw:gap-0.5', className)}\n {...props}\n >\n {children}\n </BaseCombobox.Group>\n);\n","import { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\nimport { cn } from '../../../utils';\n\ntype Props = Omit<BaseCombobox.GroupLabel.Props, 'className'> & {\n className?: string;\n};\n\nexport const ComboboxGroupLabel = ({ ref, className, ...props }: Props) => (\n <BaseCombobox.GroupLabel\n {...props}\n ref={ref}\n className={cn(\n // Base (argo variant) — soft gray section label.\n 'tw:px-2',\n 'tw:py-1.5',\n 'tw:text-xs',\n 'tw:font-medium',\n 'tw:leading-none',\n 'tw:text-muted-foreground',\n\n 'tw:group-data-[variant=default]/combobox-content:uppercase',\n 'tw:group-data-[variant=default]/combobox-content:font-semibold',\n 'tw:group-data-[variant=default]/combobox-content:tracking-wider',\n 'tw:group-data-[variant=default]/combobox-content:text-[11px]',\n 'tw:group-data-[variant=default]/combobox-content:text-black',\n 'tw:group-data-[variant=default]/combobox-content:pt-2',\n 'tw:group-data-[variant=default]/combobox-content:px-4',\n\n className,\n )}\n />\n);\n","import { Combobox as BaseCombobox } from '@base-ui/react/combobox';\n\ntype Props = BaseCombobox.Collection.Props;\n\nexport const ComboboxCollection = ({ ...props }: Props) => (\n <BaseCombobox.Collection data-slot=\"combobox-collection\" {...props} />\n);\n","import {\n type ComponentProps,\n type CSSProperties,\n type ReactNode,\n useEffect,\n useRef,\n useState,\n} from 'react';\nimport { Combobox as BaseCombobox } from '@base-ui/react/combobox';\nimport { useVirtualizer } from '@tanstack/react-virtual';\n\nimport { ChevronDown, Plus, X } from '../../icons';\nimport { InputGroup } from '../InputGroup';\n\nimport { ComboboxChips } from './ComboboxChips';\nimport { ComboboxContent } from './ComboboxContent';\nimport { ComboboxEmpty } from './ComboboxEmpty';\nimport { ComboboxInput } from './ComboboxInput';\nimport { ComboboxInputGroup } from './ComboboxInputGroup';\nimport { ComboboxItem } from './ComboboxItem';\nimport { ComboboxList } from './ComboboxList';\nimport { ComboboxRoot } from './ComboboxRoot';\nimport { ComboboxSeparator } from './ComboboxSeparator';\nimport { ComboboxCollection, ComboboxGroup, ComboboxGroupLabel } from './Group';\nimport type { Group } from './types';\nimport {\n createCreatableItem,\n defaultGroupToLabel,\n defaultItemToDisabled,\n defaultItemToIcon,\n defaultItemToLabel,\n defaultQueryToCreateLabel,\n defaultToCreateValue,\n isCreatableItem,\n isGroupItem,\n isGroupItems,\n toLabel,\n toValueKey,\n} from './utils';\n\n// Above this many (ungrouped) items, the list is windowed with `@tanstack/react-virtual` so only\n// the visible rows hit the DOM. Base UI keeps keyboard nav + filtering working against the full\n// `items` set (via `virtualized`), so search is unaffected.\nconst VIRTUALIZE_THRESHOLD = 30;\nconst ESTIMATED_ROW_HEIGHT = 40;\nconst ESTIMATED_LIST_HEIGHT = 320;\n\ntype ComboboxProps<Value> = BaseCombobox.Root.Props<Value, false>;\ntype ComboboxInputProps = ComponentProps<typeof ComboboxInput>;\ntype ComboboxInputGroupProps = ComponentProps<typeof ComboboxInputGroup>;\ntype ComboboxItemProps = ComponentProps<typeof ComboboxItem>;\n\ntype Indicator = NonNullable<ComboboxItemProps['indicator']>;\n\ntype PublicComboboxInputProps = Pick<ComboboxInputProps, 'placeholder' | 'id'> &\n Pick<ComboboxInputGroupProps, 'variant' | 'focusVariant' | 'sizing' | 'state' | 'className'>;\n\ntype PublicComboboxProps<Value> = Pick<\n ComboboxProps<Value>,\n | 'disabled'\n | 'inputRef'\n | 'value'\n | 'defaultValue'\n | 'onValueChange'\n | 'itemToStringLabel'\n | 'itemToStringValue'\n | 'filter'\n | 'onOpenChangeComplete'\n | 'isItemEqualToValue'\n>;\n\ntype CreatableProps<Value> = {\n allowCreate?: boolean;\n queryToCreateLabel?: (query: string) => ReactNode;\n queryToCreateValue?: (query: string) => Value;\n /**\n * Gate on the typed query for `allowCreate`.\n *\n * - Returning `false` hides the create row, so the empty state shows instead.\n * - Only called for a non-empty query that matches no existing item.\n * - Reach for it when a free-form value has a format (an email address, a URL, an identifier).\n */\n canCreate?: (query: string) => boolean;\n};\n\ntype Props<Value, GroupShape extends Group<Value> = Group<Value>> = PublicComboboxInputProps &\n PublicComboboxProps<Value> &\n CreatableProps<Value> & {\n items?: readonly (Value | GroupShape)[];\n\n // root specific\n allowClear?: boolean;\n empty?: ReactNode;\n indicator?: Indicator;\n prefix?: ReactNode;\n /**\n * Window the list with a virtualizer so large option sets stay fast. Opt-in — defaults to\n * `false` to keep behavior unchanged for existing call sites (every option stays in the DOM).\n * Pass `'auto'` to virtualize only ungrouped lists longer than {@link VIRTUALIZE_THRESHOLD},\n * or `true` to force it. Grouped lists are never virtualized.\n */\n virtualized?: boolean | 'auto';\n\n // item specific\n /** `query` is the current search text — pass it to `MarkedText` to highlight the match. */\n itemToLabel?: (item: Value, query: string) => ReactNode;\n itemToIcon?: (item: Value) => ReactNode;\n itemToDisabled?: (item: Value) => boolean;\n\n // group specific\n groupToLabel?: (group: GroupShape) => ReactNode;\n };\n\nexport const Combobox = <Value, GroupShape extends Group<Value> = Group<Value>>({\n // root props\n items: _itemsProp,\n value,\n defaultValue,\n onValueChange,\n itemToStringLabel: itemToStringLabelProp,\n itemToStringValue,\n disabled,\n filter,\n inputRef,\n onOpenChangeComplete,\n isItemEqualToValue: isItemEqualToValueProp,\n\n // input props\n variant,\n sizing,\n focusVariant,\n state,\n placeholder,\n allowClear,\n id,\n className,\n\n // own props\n empty = 'No items',\n indicator,\n prefix,\n virtualized = false,\n\n // creatable\n allowCreate,\n queryToCreateValue,\n queryToCreateLabel = defaultQueryToCreateLabel,\n canCreate,\n\n // own item props\n itemToDisabled = defaultItemToDisabled,\n itemToLabel = defaultItemToLabel,\n itemToIcon = defaultItemToIcon,\n groupToLabel = defaultGroupToLabel,\n}: Props<Value, GroupShape>) => {\n const closeReasonRef = useRef<'outside-click' | 'item-press' | 'creatable-item-press' | 'none'>(\n 'none',\n );\n const [inputValue, setInputValue] = useState(() => {\n const initial = value !== undefined ? value : defaultValue;\n if (initial == null) return '';\n return itemToStringLabelProp?.(initial) ?? toLabel(initial);\n });\n\n // Bumped on every selection so the sync effect below re-runs even when the owner leaves `value`\n // untouched.\n const [selections, setSelections] = useState(0);\n\n // Snap the input back to the controlled value's label.\n //\n // - Runs on a new `value` and after every selection, so a selection the owner does not adopt\n // cannot leave the input showing something the value does not say.\n // - `value` pinned to `null` is the \"adder\" shape: each pick is consumed by the owner and the\n // input clears, ready for the next one.\n // - Uncontrolled comboboxes (`value === undefined`) keep Base UI's own input handling.\n useEffect(() => {\n if (value === undefined) return;\n const label = value === null ? '' : (itemToStringLabelProp?.(value) ?? toLabel(value));\n setInputValue((prev) => (prev === label ? prev : label));\n }, [value, selections]); // eslint-disable-line react-hooks/exhaustive-deps\n\n const selectedLabel =\n value == null ? undefined : (itemToStringLabelProp?.(value) ?? toLabel(value));\n // While the input still shows the current selection's label (nothing typed since the popup\n // opened), treat it as an empty query so the whole list stays browsable. Otherwise the combobox\n // filters down to just the selected item and you can't switch to a different, unrelated one\n // without clearing first.\n const isShowingSelection = selectedLabel !== undefined && inputValue === selectedLabel;\n const query = (isShowingSelection ? '' : inputValue).trim();\n const queryLower = query.toLowerCase();\n\n const itemsProp = _itemsProp ?? [];\n const sampleItem = itemsProp.flatMap((item) => (isGroupItem(item) ? item.items : [item]))[0];\n\n const [createdItems, setCreatedItems] = useState<Value[]>([]);\n\n const allItems = (() => {\n if (createdItems.length === 0) return itemsProp as (Value | GroupShape)[];\n if (isGroupItems(itemsProp))\n return [...itemsProp, { items: createdItems } as unknown as GroupShape];\n return [...itemsProp, ...createdItems];\n })();\n\n const items = (() => {\n if (!allowCreate || disabled) return allItems;\n if (!query) return allItems;\n const exactMatch = allItems\n .flatMap((item) => (isGroupItem(item) ? item.items : [item]))\n .some(\n (item) => (itemToStringLabelProp?.(item) ?? toLabel(item)).toLowerCase() === queryLower,\n );\n if (exactMatch) return allItems;\n if (canCreate && !canCreate(query)) return allItems;\n\n const creatable = isGroupItems(itemsProp)\n ? [{ items: [createCreatableItem(query)] }]\n : [createCreatableItem(query)];\n\n return [...allItems, ...creatable];\n })();\n\n const itemToStringLabel: ComboboxProps<Value>['itemToStringLabel'] = (value) => {\n if (isCreatableItem(value)) return value.value;\n return itemToStringLabelProp?.(value) ?? toLabel(value);\n };\n\n const wrappedFilter: ComboboxProps<Value>['filter'] = isShowingSelection\n ? () => true\n : !allowCreate || !filter\n ? filter\n : (item, ...args) => isCreatableItem(item) || filter(item, ...args);\n\n const wrappedItemToStringValue: ComboboxProps<Value>['itemToStringValue'] =\n !allowCreate || !itemToStringValue\n ? itemToStringValue\n : (item) => (isCreatableItem(item) ? item.value : itemToStringValue(item));\n\n const isItemEqualToValue: ComboboxProps<Value>['isItemEqualToValue'] = (a, b) => {\n if (isCreatableItem(a) || isCreatableItem(b)) return toValueKey(a) === toValueKey(b);\n return isItemEqualToValueProp?.(a, b) ?? Object.is(a, b);\n };\n\n const handleInputValueChange: NonNullable<ComboboxProps<Value>['onInputValueChange']> = (\n value,\n { reason },\n ) => {\n if (\n ['input-clear', 'none'].includes(reason) &&\n ['item-press', 'creatable-item-press'].includes(closeReasonRef.current)\n ) {\n closeReasonRef.current = 'none';\n return;\n }\n\n if (reason === 'none' && closeReasonRef.current == 'outside-click') {\n closeReasonRef.current = 'none';\n setInputValue(value);\n return;\n }\n\n setInputValue(value);\n };\n\n const handleOnOpenChangeComplete: NonNullable<ComboboxProps<Value>['onOpenChangeComplete']> = (\n open,\n ) => {\n onOpenChangeComplete?.(open);\n if (open) return;\n if (closeReasonRef.current !== 'none') return;\n closeReasonRef.current = 'outside-click';\n };\n\n const handleOnValueChange: ComboboxProps<Value>['onValueChange'] = (next, event) => {\n setSelections((count) => count + 1);\n\n if (isCreatableItem(next)) {\n const newValue = defaultToCreateValue(next.value, sampleItem, queryToCreateValue) as Value;\n closeReasonRef.current = 'creatable-item-press';\n setCreatedItems((prev) => [...prev, newValue]);\n onValueChange?.(newValue, event);\n return;\n }\n\n closeReasonRef.current = 'item-press';\n onValueChange?.(next, event);\n };\n\n // State-backed (not a ref) so a re-render fires when the popup mounts/remounts — Base UI unmounts\n // the list on close, and the virtualizer must re-observe the fresh element on each reopen or it\n // measures a stale/detached node and paints nothing.\n const [listElement, setListElement] = useState<HTMLDivElement | null>(null);\n // Base the decision on `allItems` (the real options) rather than `items`, which also holds the\n // transient creatable row — otherwise virtualization could toggle on/off as the user types.\n const isGrouped = isGroupItems(allItems);\n const shouldVirtualize =\n !isGrouped &&\n (virtualized === true || (virtualized === 'auto' && allItems.length > VIRTUALIZE_THRESHOLD));\n\n // In virtualized mode we pre-filter here and disable Base UI's filter with `null` (see the Root\n // `filter` prop — `undefined` would keep Base UI's default `contains`, which re-filters our items\n // with a different predicate and wrongly drives the empty state + keyboard nav). The creatable\n // row is always kept.\n const matchesQuery = (item: Value) => {\n if (isCreatableItem(item)) return true;\n if (!query) return true;\n if (filter) return !!filter(item, query, (value) => itemToStringLabel(value) ?? toLabel(value));\n return (itemToStringLabel(item) ?? toLabel(item)).toLowerCase().includes(queryLower);\n };\n\n const virtualItems = shouldVirtualize ? (items as Value[]).filter(matchesQuery) : [];\n\n const virtualizer = useVirtualizer({\n count: virtualItems.length,\n getScrollElement: () => listElement,\n estimateSize: () => ESTIMATED_ROW_HEIGHT,\n overscan: 12,\n enabled: shouldVirtualize,\n // Seed a viewport height so rows paint on the first frame. Without it the list measures 0 until\n // the ResizeObserver fires (a frame later), which renders an empty popup on open.\n initialRect: { width: 0, height: ESTIMATED_LIST_HEIGHT },\n });\n\n const renderItem = (item: Value, index?: number) => {\n if (isCreatableItem(item)) {\n return (\n <Combobox.Item index={index} value={item} icon={<Plus />}>\n {queryToCreateLabel(item.value)}\n </Combobox.Item>\n );\n }\n\n return (\n <Combobox.Item\n index={index}\n value={item}\n indicator={indicator}\n icon={itemToIcon(item)}\n disabled={itemToDisabled(item)}\n >\n {itemToLabel(item, query)}\n </Combobox.Item>\n );\n };\n\n const rowStyle = (offset: number): CSSProperties => ({\n position: 'absolute',\n top: 0,\n left: 0,\n width: '100%',\n transform: `translateY(${offset}px)`,\n });\n\n return (\n <BaseCombobox.Root<Value, false>\n items={shouldVirtualize ? virtualItems : items}\n // Base UI highlights nothing until ArrowDown, so Enter after typing would drop the query\n // silently — no selection, and the popup closes. Highlighting the first match makes Enter\n // commit it, including the creatable row when `allowCreate` is on.\n autoHighlight\n value={value}\n defaultValue={defaultValue}\n filter={shouldVirtualize ? null : wrappedFilter}\n onValueChange={handleOnValueChange}\n itemToStringLabel={itemToStringLabel}\n isItemEqualToValue={isItemEqualToValue}\n itemToStringValue={wrappedItemToStringValue}\n onOpenChangeComplete={handleOnOpenChangeComplete}\n disabled={disabled}\n inputRef={inputRef}\n inputValue={inputValue}\n onInputValueChange={handleInputValueChange}\n virtualized={shouldVirtualize}\n onItemHighlighted={(_, details) => {\n if (shouldVirtualize && details.reason === 'keyboard') {\n virtualizer.scrollToIndex(details.index);\n }\n }}\n >\n <ComboboxInputGroup\n variant={variant}\n sizing={sizing}\n state={state}\n focusVariant={focusVariant}\n className={className}\n >\n {prefix && <InputGroup.Addon align=\"inline-start\">{prefix}</InputGroup.Addon>}\n <ComboboxInput id={id} placeholder={placeholder} disabled={disabled} />\n <InputGroup.Addon align=\"inline-end\">\n {allowClear && (\n <InputGroup.Button asChild aria-label=\"Clear\" disabled={disabled}>\n <BaseCombobox.Clear>\n <X className=\"tw:size-4\" />\n </BaseCombobox.Clear>\n </InputGroup.Button>\n )}\n <InputGroup.Button disabled={disabled} asChild aria-label=\"Open combobox\">\n <BaseCombobox.Trigger>\n <ChevronDown className=\"tw:size-4\" />\n </BaseCombobox.Trigger>\n </InputGroup.Button>\n </InputGroup.Addon>\n </ComboboxInputGroup>\n <ComboboxContent>\n <ComboboxEmpty>{empty}</ComboboxEmpty>\n {shouldVirtualize ? (\n <ComboboxList ref={setListElement}>\n <div\n style={{\n position: 'relative',\n width: '100%',\n height: `${virtualizer.getTotalSize()}px`,\n }}\n >\n {virtualizer.getVirtualItems().map((row) => {\n const item = virtualItems[row.index];\n if (item === undefined) return null;\n return (\n <div\n key={row.key}\n data-index={row.index}\n ref={virtualizer.measureElement}\n style={rowStyle(row.start)}\n >\n {renderItem(item, row.index)}\n </div>\n );\n })}\n </div>\n </ComboboxList>\n ) : (\n <ComboboxList>\n {(itemOrGroup: Value | GroupShape) => {\n if (isCreatableItem(itemOrGroup))\n return (\n <Combobox.Item value={itemOrGroup} icon={<Plus />}>\n {queryToCreateLabel(itemOrGroup.value)}\n </Combobox.Item>\n );\n\n if (isGroupItem(itemOrGroup)) {\n const maybeCreatable = itemOrGroup.items[0];\n\n if (isCreatableItem(maybeCreatable)) {\n return (\n <Combobox.Item value={maybeCreatable} icon={<Plus />}>\n {queryToCreateLabel(maybeCreatable.value)}\n </Combobox.Item>\n );\n }\n\n const groupLabel = groupToLabel(itemOrGroup);\n\n return (\n <Combobox.Group items={itemOrGroup.items}>\n {groupLabel && <Combobox.GroupLabel>{groupLabel}</Combobox.GroupLabel>}\n {/* Don't forward `renderItem` by reference — the collection passes its\n group-local index, which ComboboxItem uses verbatim and breaks keyboard\n nav. Drop it so the item falls back to its own global list index. */}\n <Combobox.GroupList>{(item: Value) => renderItem(item)}</Combobox.GroupList>\n </Combobox.Group>\n );\n }\n\n return renderItem(itemOrGroup);\n }}\n </ComboboxList>\n )}\n </ComboboxContent>\n </BaseCombobox.Root>\n );\n};\n\n// Base\nCombobox.Root = ComboboxRoot;\nCombobox.InputGroup = ComboboxInputGroup;\nCombobox.Input = ComboboxInput;\nCombobox.Content = ComboboxContent;\nCombobox.List = ComboboxList;\nCombobox.Item = ComboboxItem;\nCombobox.Empty = ComboboxEmpty;\nCombobox.Value = BaseCombobox.Value;\nCombobox.Separator = ComboboxSeparator;\n\n// Group\nCombobox.Group = ComboboxGroup;\nCombobox.GroupLabel = ComboboxGroupLabel;\nCombobox.GroupList = ComboboxCollection;\n\n// Chips\nCombobox.Chips = ComboboxChips;\n"],"mappings":"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d;GACS;GACD;GACM;GACC;GACL;GACR,WAAU;GAEV,UAAA,oBAACA,SAAa,OAAd;IACO;IACL,cAAY,CAAC,CAAC;IACd,gBAAc;IACd,WAAW,GACT,2BACA,6BACA,eACA,0CAGA,sCACA,8BACA,qCACA,uCACA,oDAGA,iBACA,qCAEA,iBACA,8BACA,gBACA,aACA,yBACA,mBAGA,wBACA,uBACA,wBAGA,2BACA,0BACA,2BAGA,6CACA,6CACA,6CACA,6CACA,qDACA,kDACA,SACF;IACA,GAAI;IAEH;GACiB,CAAA;EACG,CAAA;CACN,CAAA;AAEzB;;;ACtFA,MAAa,iBAAiB,EAAE,KAAK,WAAW,GAAG,YACjD,oBAACC,SAAa,OAAd;CACO;CACL,WAAW,GACT,aACA,+CACA,qBACA,mBACA,kBACA,WACA,4BACA,WACA,SACF;CACA,GAAI;AACL,CAAA;;;ACjBH,MAAa,iBAAiB,EAAE,KAAK,GAAG,YACtC,oBAACC,SAAa,OAAd;CAAoB,GAAI;CAAY;CAAK,QAAQ,oBAAC,WAAW,OAAZ,CAAmB,CAAA;AAAI,CAAA;;;ACO1E,MAAa,sBAAsB,EACjC,KACA,OACA,SACA,QACA,cACA,WACA,GAAG,YAEH,oBAACC,SAAa,YAAd;CACE,GAAI;CACC;CACL,QACE,oBAAC,YAAD;EACS;EACE;EACK;EACN;EACG;CACZ,CAAA;AAEJ,CAAA;;;ACvBH,MAAa,yBAAyB,EAAE,KAAK,WAAW,UAAU,SAAS,GAAG,YAAmB;CAC/F,IAAI,YAAY,YACd,OACE,oBAACC,SAAa,eAAd;EACO;EACL,aAAA;EACA,WAAW,GACT,oCAEA,kBACA,mBACA,qBACA,aACA,eAEA,cACA,aACA,mBACA,oBAEA,iCACA,qCACA,SACF;EACA,GAAI;EAEJ,UAAA,oBAAC,OAAD,EACE,WAAW,GACT,aACA,aACA,mBACA,+BACA,wDACF,EACD,CAAA;CACyB,CAAA;CAIhC,OACE,oBAACA,SAAa,eAAd;EACE,GAAI;EACC;EACL,WAAW,GACT,0BACA,eACA,cAEA,4DAGA,aACA,oEACA,qHACA,SACF;EACA,QAAQ,oBAAC,OAA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"}
@@ -1,8 +1,8 @@
1
1
  import { cn } from "./classNames-BzrkDnOD.js";
2
- import { useArgoDesign } from "./context-KxxeMHbR.js";
2
+ import { useArgoDesign } from "./context-BrNtMc1H.js";
3
3
  import { Check, Circle } from "./icons-Cek151jC.js";
4
4
  import { ScrollArea } from "./internal/components/ScrollArea.js";
5
- import { TextInput } from "./TextInput-CMuN1WfY.js";
5
+ import { TextInput } from "./TextInput-DhdRk8qm.js";
6
6
  import { jsx, jsxs } from "react/jsx-runtime";
7
7
  import { Command, CommandInput, defaultFilter, useCommandState } from "cmdk";
8
8
  //#region src/blocks/Command/CommandContent.tsx
@@ -99,4 +99,4 @@ Command$1.Item = CommandItem;
99
99
  //#endregion
100
100
  export { Command$1 as Command, CommandGroup, CommandInput$1 as CommandInput, CommandItem, CommandList, defaultFilter, useCommandState };
101
101
 
102
- //# sourceMappingURL=Command-C0aZfVTq.js.map
102
+ //# sourceMappingURL=Command-Ds68v2rX.js.map