@flux-ui/components 3.0.0-next.35 → 3.0.0-next.38

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 (330) hide show
  1. package/dist/component/FluxActionBar.vue.d.ts +17 -17
  2. package/dist/component/FluxActionPane.vue.d.ts +7 -7
  3. package/dist/component/FluxActionStack.vue.d.ts +11 -15
  4. package/dist/component/{FluxAutoGrid.vue.d.ts → FluxAdaptiveGroup.vue.d.ts} +6 -3
  5. package/dist/component/FluxAdaptiveSlot.vue.d.ts +35 -0
  6. package/dist/component/FluxAspectRatio.vue.d.ts +3 -3
  7. package/dist/component/FluxBadgeStack.vue.d.ts +3 -3
  8. package/dist/component/FluxButtonGroup.vue.d.ts +3 -3
  9. package/dist/component/FluxButtonStack.vue.d.ts +3 -3
  10. package/dist/component/FluxCalendar.vue.d.ts +3 -3
  11. package/dist/component/FluxCalendarEvent.vue.d.ts +3 -3
  12. package/dist/component/FluxCheckbox.vue.d.ts +2 -1
  13. package/dist/component/FluxClickablePane.vue.d.ts +5 -5
  14. package/dist/component/FluxColorSelect.vue.d.ts +1 -0
  15. package/dist/component/{FluxPaneDeck.vue.d.ts → FluxColumn.vue.d.ts} +5 -5
  16. package/dist/component/FluxComment.vue.d.ts +3 -3
  17. package/dist/component/FluxContainer.vue.d.ts +3 -3
  18. package/dist/component/FluxDivider.vue.d.ts +5 -3
  19. package/dist/component/FluxDropZone.vue.d.ts +8 -7
  20. package/dist/component/FluxExpandableGroup.vue.d.ts +3 -3
  21. package/dist/component/FluxFader.vue.d.ts +3 -3
  22. package/dist/component/FluxFaderItem.vue.d.ts +3 -3
  23. package/dist/component/FluxFilter.vue.d.ts +3 -3
  24. package/dist/component/FluxFilterBar.vue.d.ts +3 -3
  25. package/dist/component/FluxFilterBase.vue.d.ts +4 -4
  26. package/dist/component/FluxFilterWindow.vue.d.ts +13 -17
  27. package/dist/component/FluxFlyout.vue.d.ts +19 -21
  28. package/dist/component/FluxForm.vue.d.ts +3 -3
  29. package/dist/component/FluxFormColumn.vue.d.ts +3 -3
  30. package/dist/component/FluxFormDateInput.vue.d.ts +18 -24
  31. package/dist/component/FluxFormDateRangeInput.vue.d.ts +18 -21
  32. package/dist/component/FluxFormDateTimeInput.vue.d.ts +18 -24
  33. package/dist/component/FluxFormField.vue.d.ts +7 -7
  34. package/dist/component/FluxFormGrid.vue.d.ts +3 -3
  35. package/dist/component/FluxFormInput.vue.d.ts +2 -9
  36. package/dist/component/FluxFormInputAddition.vue.d.ts +3 -3
  37. package/dist/component/FluxFormInputGroup.vue.d.ts +3 -3
  38. package/dist/component/FluxFormPinInput.vue.d.ts +2 -4
  39. package/dist/component/FluxFormRangeSlider.vue.d.ts +18 -2
  40. package/dist/component/FluxFormRow.vue.d.ts +3 -3
  41. package/dist/component/FluxFormSection.vue.d.ts +3 -3
  42. package/dist/component/FluxFormSelect.vue.d.ts +2 -4
  43. package/dist/component/FluxFormSelectAsync.vue.d.ts +2 -4
  44. package/dist/component/FluxFormSlider.vue.d.ts +11 -2
  45. package/dist/component/FluxFormTextArea.vue.d.ts +2 -6
  46. package/dist/component/FluxFormTimeZonePicker.vue.d.ts +2 -4
  47. package/dist/component/FluxFormTreeViewSelect.vue.d.ts +15 -37
  48. package/dist/component/FluxGallery.vue.d.ts +3 -3
  49. package/dist/component/FluxGrid.vue.d.ts +3 -3
  50. package/dist/component/FluxGridColumn.vue.d.ts +3 -3
  51. package/dist/component/FluxIcon.vue.d.ts +1 -0
  52. package/dist/component/FluxInfo.vue.d.ts +3 -3
  53. package/dist/component/FluxInfoStack.vue.d.ts +3 -3
  54. package/dist/component/FluxLayerPane.vue.d.ts +20 -0
  55. package/dist/component/FluxLayerPaneSecondary.vue.d.ts +20 -0
  56. package/dist/component/FluxMenu.vue.d.ts +3 -3
  57. package/dist/component/FluxMenuCollapsible.vue.d.ts +47 -0
  58. package/dist/component/FluxMenuGroup.vue.d.ts +3 -3
  59. package/dist/component/FluxMenuItem.vue.d.ts +5 -3
  60. package/dist/component/FluxMenuOptions.vue.d.ts +3 -3
  61. package/dist/component/FluxNotice.vue.d.ts +5 -5
  62. package/dist/component/FluxNoticeStack.vue.d.ts +3 -3
  63. package/dist/component/FluxOverflowBar.vue.d.ts +4 -4
  64. package/dist/component/FluxPane.vue.d.ts +5 -5
  65. package/dist/component/FluxPaneBody.vue.d.ts +3 -3
  66. package/dist/component/FluxPaneFooter.vue.d.ts +3 -3
  67. package/dist/component/FluxPaneGroup.vue.d.ts +3 -3
  68. package/dist/component/FluxPaneHeader.vue.d.ts +6 -6
  69. package/dist/component/FluxPaneIllustration.vue.d.ts +5 -5
  70. package/dist/component/FluxPressable.vue.d.ts +3 -3
  71. package/dist/component/FluxPrompt.vue.d.ts +3 -17
  72. package/dist/component/FluxRoot.vue.d.ts +3 -3
  73. package/dist/component/FluxRow.vue.d.ts +23 -0
  74. package/dist/component/FluxSegmentedControl.vue.d.ts +3 -2
  75. package/dist/component/FluxSplitButton.vue.d.ts +5 -5
  76. package/dist/component/FluxStack.vue.d.ts +3 -3
  77. package/dist/component/FluxStepper.vue.d.ts +6 -6
  78. package/dist/component/FluxStepperStep.vue.d.ts +3 -3
  79. package/dist/component/FluxTab.vue.d.ts +3 -3
  80. package/dist/component/FluxTabBar.vue.d.ts +3 -3
  81. package/dist/component/FluxTabBarItem.vue.d.ts +5 -7
  82. package/dist/component/FluxTableActions.vue.d.ts +3 -3
  83. package/dist/component/FluxTableBar.vue.d.ts +3 -3
  84. package/dist/component/FluxTableCell.vue.d.ts +5 -5
  85. package/dist/component/FluxTableHeader.vue.d.ts +3 -3
  86. package/dist/component/FluxTableRow.vue.d.ts +3 -3
  87. package/dist/component/FluxTabs.vue.d.ts +6 -6
  88. package/dist/component/FluxTagStack.vue.d.ts +3 -3
  89. package/dist/component/FluxTimeline.vue.d.ts +3 -3
  90. package/dist/component/FluxTimelineItem.vue.d.ts +3 -3
  91. package/dist/component/FluxToggle.vue.d.ts +2 -3
  92. package/dist/component/FluxToolbar.vue.d.ts +3 -3
  93. package/dist/component/FluxToolbarGroup.vue.d.ts +3 -3
  94. package/dist/component/FluxWindow.vue.d.ts +3 -3
  95. package/dist/component/index.d.ts +7 -2
  96. package/dist/component/primitive/Anchor.vue.d.ts +3 -3
  97. package/dist/component/primitive/AnchorPopup.vue.d.ts +3 -3
  98. package/dist/component/primitive/CoordinatePicker.vue.d.ts +1 -0
  99. package/dist/component/primitive/DialogLayout.vue.d.ts +28 -0
  100. package/dist/component/primitive/FilterOptionBase.vue.d.ts +2 -2
  101. package/dist/component/primitive/SelectBase.vue.d.ts +19 -37
  102. package/dist/component/primitive/SliderThumb.vue.d.ts +4 -0
  103. package/dist/component/primitive/TreeNodeRenderer.vue.d.ts +30 -0
  104. package/dist/component/primitive/index.d.ts +2 -0
  105. package/dist/composable/index.d.ts +1 -0
  106. package/dist/composable/private/index.d.ts +8 -0
  107. package/dist/composable/private/useAsyncFilterOptions.d.ts +14 -0
  108. package/dist/composable/private/useDateFlyout.d.ts +10 -0
  109. package/dist/composable/private/useDropdownPopup.d.ts +27 -0
  110. package/dist/composable/private/useFilterOption.d.ts +12 -0
  111. package/dist/composable/useAdaptiveGroupInjection.d.ts +2 -0
  112. package/dist/data/di.d.ts +11 -0
  113. package/dist/data/filter.d.ts +4 -17
  114. package/dist/data/i18n.d.ts +17 -0
  115. package/dist/data/timeZones.d.ts +3 -0
  116. package/dist/index.css +372 -331
  117. package/dist/index.d.ts +1 -1
  118. package/dist/index.js +7116 -6286
  119. package/dist/index.js.map +1 -1
  120. package/dist/transition/FluxAutoHeightTransition.vue.d.ts +5 -3
  121. package/dist/transition/FluxAutoWidthTransition.vue.d.ts +5 -3
  122. package/dist/transition/FluxBreakthroughTransition.vue.d.ts +5 -3
  123. package/dist/transition/FluxFadeTransition.vue.d.ts +5 -3
  124. package/dist/transition/FluxOverlayTransition.vue.d.ts +5 -3
  125. package/dist/transition/FluxRouteTransition.vue.d.ts +5 -3
  126. package/dist/transition/FluxSlideOverTransition.vue.d.ts +5 -3
  127. package/dist/transition/FluxTooltipTransition.vue.d.ts +5 -3
  128. package/dist/transition/FluxVerticalWindowTransition.vue.d.ts +5 -3
  129. package/dist/transition/FluxWindowTransition.vue.d.ts +5 -3
  130. package/package.json +19 -23
  131. package/src/component/FluxActionBar.vue +9 -8
  132. package/src/component/FluxActionPane.vue +4 -3
  133. package/src/component/FluxActionStack.vue +2 -2
  134. package/src/component/FluxAdaptiveGroup.vue +112 -0
  135. package/src/component/FluxAdaptiveSlot.vue +159 -0
  136. package/src/component/FluxAlert.vue +8 -17
  137. package/src/component/FluxAnimatedColors.vue +1 -1
  138. package/src/component/FluxAspectRatio.vue +2 -1
  139. package/src/component/FluxBadge.vue +5 -1
  140. package/src/component/FluxBadgeStack.vue +2 -1
  141. package/src/component/FluxButtonGroup.vue +2 -1
  142. package/src/component/FluxButtonStack.vue +2 -1
  143. package/src/component/FluxCalendar.vue +8 -1
  144. package/src/component/FluxCalendarEvent.vue +2 -1
  145. package/src/component/FluxCheckbox.vue +33 -6
  146. package/src/component/FluxChip.vue +1 -0
  147. package/src/component/FluxClickablePane.vue +3 -2
  148. package/src/component/FluxColorPicker.vue +8 -1
  149. package/src/component/FluxColorSelect.vue +25 -4
  150. package/src/component/{FluxAutoGrid.vue → FluxColumn.vue} +5 -8
  151. package/src/component/FluxComment.vue +2 -2
  152. package/src/component/FluxConfirm.vue +8 -17
  153. package/src/component/FluxContainer.vue +3 -2
  154. package/src/component/FluxDataTable.vue +3 -1
  155. package/src/component/FluxDivider.vue +7 -3
  156. package/src/component/FluxDropZone.vue +22 -8
  157. package/src/component/FluxExpandable.vue +3 -2
  158. package/src/component/FluxExpandableGroup.vue +2 -2
  159. package/src/component/FluxFader.vue +2 -2
  160. package/src/component/FluxFaderItem.vue +2 -1
  161. package/src/component/FluxFilter.vue +2 -1
  162. package/src/component/FluxFilterBar.vue +3 -2
  163. package/src/component/FluxFilterBase.vue +17 -9
  164. package/src/component/FluxFilterOption.vue +3 -14
  165. package/src/component/FluxFilterOptionAsync.vue +17 -60
  166. package/src/component/FluxFilterOptions.vue +3 -25
  167. package/src/component/FluxFilterOptionsAsync.vue +9 -73
  168. package/src/component/FluxFilterWindow.vue +1 -1
  169. package/src/component/FluxFlyout.vue +13 -11
  170. package/src/component/FluxForm.vue +2 -1
  171. package/src/component/FluxFormColumn.vue +2 -1
  172. package/src/component/FluxFormDateInput.vue +9 -22
  173. package/src/component/FluxFormDateRangeInput.vue +20 -15
  174. package/src/component/FluxFormDateTimeInput.vue +17 -20
  175. package/src/component/FluxFormField.vue +4 -4
  176. package/src/component/FluxFormGrid.vue +2 -1
  177. package/src/component/FluxFormInput.vue +11 -10
  178. package/src/component/FluxFormInputAddition.vue +2 -1
  179. package/src/component/FluxFormInputGroup.vue +3 -2
  180. package/src/component/FluxFormPinInput.vue +14 -6
  181. package/src/component/FluxFormRangeSlider.vue +12 -2
  182. package/src/component/FluxFormRow.vue +2 -1
  183. package/src/component/FluxFormSection.vue +4 -3
  184. package/src/component/FluxFormSelect.vue +11 -4
  185. package/src/component/FluxFormSelectAsync.vue +14 -8
  186. package/src/component/FluxFormSlider.vue +8 -2
  187. package/src/component/FluxFormTextArea.vue +12 -7
  188. package/src/component/FluxFormTimeZonePicker.vue +13 -626
  189. package/src/component/FluxFormTreeViewSelect.vue +51 -79
  190. package/src/component/FluxGallery.vue +2 -1
  191. package/src/component/FluxGrid.vue +3 -2
  192. package/src/component/FluxGridColumn.vue +2 -1
  193. package/src/component/FluxIcon.vue +4 -2
  194. package/src/component/FluxInfo.vue +2 -1
  195. package/src/component/FluxInfoStack.vue +3 -2
  196. package/src/component/FluxLayerPane.vue +16 -0
  197. package/src/component/FluxLayerPaneSecondary.vue +16 -0
  198. package/src/component/FluxLegend.vue +9 -9
  199. package/src/component/FluxMenu.vue +2 -2
  200. package/src/component/FluxMenuCollapsible.vue +187 -0
  201. package/src/component/FluxMenuGroup.vue +2 -1
  202. package/src/component/FluxMenuItem.vue +9 -1
  203. package/src/component/FluxMenuOptions.vue +1 -1
  204. package/src/component/FluxNotice.vue +7 -2
  205. package/src/component/FluxNoticeStack.vue +2 -1
  206. package/src/component/FluxOverflowBar.vue +3 -3
  207. package/src/component/FluxPagination.vue +1 -0
  208. package/src/component/FluxPane.vue +3 -2
  209. package/src/component/FluxPaneBody.vue +2 -1
  210. package/src/component/FluxPaneFooter.vue +2 -1
  211. package/src/component/FluxPaneGroup.vue +2 -1
  212. package/src/component/FluxPaneHeader.vue +7 -6
  213. package/src/component/FluxPaneIllustration.vue +3 -3
  214. package/src/component/FluxPaneMedia.vue +1 -1
  215. package/src/component/FluxPercentageBar.vue +3 -1
  216. package/src/component/FluxPressable.vue +2 -1
  217. package/src/component/FluxProgressBar.vue +2 -1
  218. package/src/component/FluxPrompt.vue +16 -27
  219. package/src/component/FluxRemove.vue +4 -0
  220. package/src/component/FluxRoot.vue +2 -2
  221. package/src/component/FluxRow.vue +24 -0
  222. package/src/component/FluxSegmentedControl.vue +51 -4
  223. package/src/component/FluxSnackbar.vue +36 -12
  224. package/src/component/FluxSplitButton.vue +3 -2
  225. package/src/component/FluxStack.vue +4 -3
  226. package/src/component/FluxStepper.vue +3 -3
  227. package/src/component/FluxStepperStep.vue +2 -1
  228. package/src/component/FluxTab.vue +2 -1
  229. package/src/component/FluxTabBar.vue +3 -3
  230. package/src/component/FluxTableActions.vue +2 -1
  231. package/src/component/FluxTableBar.vue +2 -1
  232. package/src/component/FluxTableCell.vue +4 -3
  233. package/src/component/FluxTableHeader.vue +4 -2
  234. package/src/component/FluxTableRow.vue +2 -1
  235. package/src/component/FluxTabs.vue +15 -6
  236. package/src/component/FluxTag.vue +5 -1
  237. package/src/component/FluxTagStack.vue +2 -1
  238. package/src/component/FluxTimeline.vue +2 -1
  239. package/src/component/FluxTimelineItem.vue +2 -1
  240. package/src/component/FluxToggle.vue +20 -5
  241. package/src/component/FluxToolbar.vue +2 -1
  242. package/src/component/FluxToolbarGroup.vue +2 -1
  243. package/src/component/FluxTooltip.vue +1 -1
  244. package/src/component/FluxTreeView.vue +9 -35
  245. package/src/component/FluxWindow.vue +2 -2
  246. package/src/component/index.ts +7 -2
  247. package/src/component/primitive/Anchor.vue +3 -1
  248. package/src/component/primitive/AnchorPopup.vue +3 -3
  249. package/src/component/primitive/CoordinatePicker.vue +2 -1
  250. package/src/component/primitive/CoordinatePickerThumb.vue +2 -0
  251. package/src/component/primitive/DialogLayout.vue +44 -0
  252. package/src/component/primitive/SelectBase.vue +22 -28
  253. package/src/component/primitive/SliderBase.vue +0 -1
  254. package/src/component/primitive/SliderThumb.vue +9 -0
  255. package/src/component/primitive/TreeNodeRenderer.vue +77 -0
  256. package/src/component/primitive/index.ts +2 -0
  257. package/src/composable/index.ts +1 -0
  258. package/src/composable/private/index.ts +8 -0
  259. package/src/composable/private/useAsyncFilterOptions.ts +70 -0
  260. package/src/composable/private/useCommandPalette.ts +1 -1
  261. package/src/composable/private/useDateFlyout.ts +34 -0
  262. package/src/composable/private/useDropdownPopup.ts +99 -0
  263. package/src/composable/private/useFilterOption.ts +59 -0
  264. package/src/composable/useAdaptiveGroupInjection.ts +6 -0
  265. package/src/css/component/Action.module.scss +2 -2
  266. package/src/css/component/AdaptiveSlot.module.scss +25 -0
  267. package/src/css/component/Avatar.module.scss +10 -11
  268. package/src/css/component/Badge.module.scss +4 -4
  269. package/src/css/component/Button.module.scss +4 -16
  270. package/src/css/component/Calendar.module.scss +4 -4
  271. package/src/css/component/Chip.module.scss +6 -10
  272. package/src/css/component/Color.module.scss +1 -1
  273. package/src/css/component/DatePicker.module.scss +1 -1
  274. package/src/css/component/Expandable.module.scss +5 -5
  275. package/src/css/component/Fader.module.scss +2 -1
  276. package/src/css/component/Flyout.module.scss +1 -1
  277. package/src/css/component/FocalPoint.module.scss +1 -1
  278. package/src/css/component/Form.module.scss +56 -10
  279. package/src/css/component/Item.module.scss +4 -4
  280. package/src/css/component/LayerPane.module.scss +40 -0
  281. package/src/css/component/Layout.module.scss +11 -4
  282. package/src/css/component/Legend.module.scss +2 -2
  283. package/src/css/component/Menu.module.scss +59 -11
  284. package/src/css/component/Notice.module.scss +7 -7
  285. package/src/css/component/Overlay.module.scss +2 -2
  286. package/src/css/component/Pane.module.scss +10 -23
  287. package/src/css/component/PercentageBar.module.scss +1 -1
  288. package/src/css/component/Remove.module.scss +1 -1
  289. package/src/css/component/SegmentedControl.module.scss +1 -0
  290. package/src/css/component/Snackbar.module.scss +1 -1
  291. package/src/css/component/Statistic.module.scss +2 -2
  292. package/src/css/component/Stepper.module.scss +1 -1
  293. package/src/css/component/Tab.module.scss +11 -15
  294. package/src/css/component/Table.module.scss +13 -13
  295. package/src/css/component/Timeline.module.scss +2 -2
  296. package/src/css/component/Toolbar.module.scss +3 -3
  297. package/src/css/component/Tooltip.module.scss +3 -4
  298. package/src/css/component/Transition.module.scss +1 -1
  299. package/src/css/component/TreeView.module.scss +2 -15
  300. package/src/css/component/TreeViewSelect.module.scss +1 -15
  301. package/src/css/component/base/Button.module.scss +6 -7
  302. package/src/css/component/base/Effect.module.scss +2 -1
  303. package/src/css/component/primitive/Slider.module.scss +6 -7
  304. package/src/css/component/primitive/TreeNode.module.scss +19 -0
  305. package/src/css/mixin/button-active.scss +6 -0
  306. package/src/css/mixin/focus-ring.scss +1 -1
  307. package/src/css/mixin/index.scss +1 -0
  308. package/src/css/typography.scss +3 -2
  309. package/src/css/variables.scss +7 -2
  310. package/src/data/di.ts +13 -0
  311. package/src/data/filter.ts +24 -28
  312. package/src/data/i18n.ts +17 -0
  313. package/src/data/store.ts +46 -11
  314. package/src/data/timeZones.ts +619 -0
  315. package/src/index.ts +2 -0
  316. package/src/transition/FluxAutoHeightTransition.vue +5 -0
  317. package/src/transition/FluxAutoWidthTransition.vue +5 -0
  318. package/src/transition/FluxBreakthroughTransition.vue +5 -0
  319. package/src/transition/FluxFadeTransition.vue +5 -0
  320. package/src/transition/FluxOverlayTransition.vue +5 -0
  321. package/src/transition/FluxRouteTransition.vue +5 -0
  322. package/src/transition/FluxSlideOverTransition.vue +5 -0
  323. package/src/transition/FluxTooltipTransition.vue +5 -0
  324. package/src/transition/FluxVerticalWindowTransition.vue +5 -0
  325. package/src/transition/FluxWindowTransition.vue +5 -0
  326. package/dist/0db98648.svg +0 -3
  327. package/src/component/FluxPaneDeck.vue +0 -24
  328. package/src/css/component/base/Grid.module.scss +0 -8
  329. package/src/image/avatar-mask.svg +0 -3
  330. package/tsconfig.json +0 -7
@@ -9,7 +9,10 @@
9
9
  isSearchable && $style.isSearchable
10
10
  )"
11
11
  :id="id"
12
+ role="combobox"
12
13
  :aria-disabled="disabled ? true : undefined"
14
+ :aria-expanded="isPopupOpen"
15
+ aria-haspopup="listbox"
13
16
  tabindex="0"
14
17
  tag-name="div"
15
18
  @click="toggle()"
@@ -133,13 +136,12 @@
133
136
  <script
134
137
  lang="ts"
135
138
  setup>
136
- import { useClickOutside } from '@basmilius/common';
137
139
  import { unrefTemplateElement } from '@flux-ui/internals';
138
140
  import type { FluxFormSelectOption, FluxFormSelectOptions } from '@flux-ui/types';
139
141
  import { clsx } from 'clsx';
140
142
  import { type ComponentPublicInstance, computed, nextTick, ref, toRef, unref, useTemplateRef, watch } from 'vue';
141
143
  import { useDisabled, useFormFieldInjection } from '$flux/composable';
142
- import { useTranslate } from '$flux/composable/private';
144
+ import { useDropdownPopup, useTranslate } from '$flux/composable/private';
143
145
  import { isFluxFormSelectGroup, isFluxFormSelectOption } from '$flux/data';
144
146
  import { FluxFadeTransition } from '$flux/transition';
145
147
  import FluxFormInput from '$flux/component/FluxFormInput.vue';
@@ -193,20 +195,27 @@
193
195
  const translate = useTranslate();
194
196
 
195
197
  const anchorRef = useTemplateRef<ComponentPublicInstance>('anchor');
196
- const anchorPopupRef = useTemplateRef('anchorPopup');
198
+ const anchorPopupRef = useTemplateRef<ComponentPublicInstance>('anchorPopup');
197
199
  const optionElementRefs = useTemplateRef<typeof FluxMenuItem[]>('optionElements');
198
200
  const searchInputElementRef = useTemplateRef<ComponentPublicInstance<typeof FluxFormInput>>('searchInputElement');
199
201
 
200
202
  const highlightedIndex = ref(INITIAL_HIGHLIGHTED_INDEX);
201
203
  const isKeyboardAction = ref(false);
202
- const isPopupOpen = ref(false);
203
204
 
204
205
  const focusElement = computed(() => unrefTemplateElement(searchInputElementRef) ?? unrefTemplateElement(anchorRef));
205
206
  const highlightedId = computed(() => unref(rawOptions)[unref(highlightedIndex)]?.value);
206
207
  const rawOptions = computed(() => options.map(group => group[1]).flat());
207
208
 
208
- useClickOutside([anchorRef, anchorPopupRef], isPopupOpen, () => isPopupOpen.value = false);
209
- useClickOutside(anchorRef, isPopupOpen, () => unref(focusElement)?.focus());
209
+ const {
210
+ isOpen: isPopupOpen,
211
+ toggle,
212
+ onKeyDownBase
213
+ } = useDropdownPopup({
214
+ anchorRef,
215
+ popupRef: anchorPopupRef,
216
+ focusElement,
217
+ disabled
218
+ });
210
219
 
211
220
  function deselect(id: string | number | null): void {
212
221
  emit('deselect', id);
@@ -217,7 +226,9 @@
217
226
  function select(id: string | number | null): void {
218
227
  emit('select', id);
219
228
 
220
- !isMultiple && (isPopupOpen.value = false);
229
+ if (!isMultiple) {
230
+ isPopupOpen.value = false;
231
+ }
221
232
 
222
233
  highlightedIndex.value = INITIAL_HIGHLIGHTED_INDEX;
223
234
  modelSearch.value = '';
@@ -225,14 +236,6 @@
225
236
  nextTick(() => unref(focusElement)?.focus());
226
237
  }
227
238
 
228
- function toggle(): void {
229
- if (unref(disabled)) {
230
- return;
231
- }
232
-
233
- isPopupOpen.value = !unref(isPopupOpen);
234
- }
235
-
236
239
  function onKeyDown(evt: KeyboardEvent): void {
237
240
  emit('keyDown', evt);
238
241
 
@@ -246,6 +249,10 @@
246
249
 
247
250
  isKeyboardAction.value = true;
248
251
 
252
+ if (onKeyDownBase(evt)) {
253
+ return;
254
+ }
255
+
249
256
  if (unref(highlightedIndex) === INITIAL_HIGHLIGHTED_INDEX && ['ArrowDown', 'ArrowUp'].includes(evt.key)) {
250
257
  const options = unref(optionElementRefs);
251
258
  const selectedIndex = options?.findIndex(o => 'isActive' in o.$props && o.$props.isActive);
@@ -277,14 +284,6 @@
277
284
  id && select(id);
278
285
  break;
279
286
 
280
- case 'Escape':
281
- isPopupOpen.value = false;
282
- break;
283
-
284
- case 'Tab':
285
- isPopupOpen.value = false;
286
- return;
287
-
288
287
  default:
289
288
  if (evt.key.length === 1) {
290
289
  highlightedIndex.value = unref(rawOptions).findIndex(o => o.label.toLowerCase().startsWith(evt.key.toLowerCase()));
@@ -314,11 +313,6 @@
314
313
  return;
315
314
  }
316
315
 
317
- nextTick(() => {
318
- const searchInput = unref(searchInputElementRef);
319
- searchInput?.focus();
320
- });
321
-
322
316
  nextTick(() => {
323
317
  const options = unref(optionElementRefs);
324
318
 
@@ -6,7 +6,6 @@
6
6
  disabled && $style.isDisabled,
7
7
  isDragging && $style.isDragging
8
8
  )"
9
- role="slider"
10
9
  :aria-disabled="disabled ? true : undefined"
11
10
  @pointerdown="onPointerDown">
12
11
  <FluxTicks
@@ -8,7 +8,12 @@
8
8
  :style="{
9
9
  left: `${position * 100}%`
10
10
  }"
11
+ role="slider"
11
12
  :aria-disabled="disabled ? true : undefined"
13
+ :aria-label="ariaLabel"
14
+ :aria-valuemax="ariaValuemax"
15
+ :aria-valuemin="ariaValuemin"
16
+ :aria-valuenow="ariaValuenow"
12
17
  :tabindex="disabled ? -1 : 0"
13
18
  type="button"
14
19
  @keydown="onKeyDown"
@@ -32,6 +37,10 @@
32
37
  const {
33
38
  disabled: componentDisabled
34
39
  } = defineProps<{
40
+ readonly ariaLabel?: string;
41
+ readonly ariaValuemax?: number;
42
+ readonly ariaValuemin?: number;
43
+ readonly ariaValuenow?: number;
35
44
  readonly disabled?: boolean;
36
45
  readonly isDragging?: boolean;
37
46
  readonly position: number;
@@ -0,0 +1,77 @@
1
+ <template>
2
+ <div :class="$style.treeNodeLineArea">
3
+ <span
4
+ v-for="(showLine, guideIndex) in node.lineGuides"
5
+ :key="`g-${guideIndex}`"
6
+ :class="[$style.treeIndent, showLine && $style.hasLine]"/>
7
+
8
+ <span
9
+ v-if="node.depth > 0"
10
+ :class="[$style.treeConnector, node.isLast && $style.isLast]"/>
11
+
12
+ <span
13
+ :class="$style.treeNodeExpand"
14
+ @click="onExpandClick($event)">
15
+ <FluxIcon
16
+ v-if="node.children?.length"
17
+ :name="expanded ? 'angle-down' : 'angle-right'"
18
+ :size="12"/>
19
+ </span>
20
+ </div>
21
+
22
+ <span
23
+ v-if="dotColor"
24
+ :class="$style.treeNodeColorDot"
25
+ :style="{ background: dotColor }"/>
26
+
27
+ <FluxIcon
28
+ v-if="node.icon"
29
+ :class="$style.treeNodeIcon"
30
+ :name="node.icon"
31
+ :size="16"/>
32
+
33
+ <span :class="$style.treeNodeLabel">{{ node.label }}</span>
34
+
35
+ <slot
36
+ name="trailing"
37
+ :node="node"/>
38
+ </template>
39
+
40
+ <script
41
+ lang="ts"
42
+ setup
43
+ generic="TOption extends TreeBaseOption">
44
+ import type { FluxColor } from '@flux-ui/types';
45
+ import { computed } from 'vue';
46
+ import type { TreeBaseOption, TreeFlatNode } from '$flux/composable/private';
47
+ import { getLevelColor } from '$flux/composable/private';
48
+ import FluxIcon from '$flux/component/FluxIcon.vue';
49
+ import $style from '$flux/css/component/primitive/TreeNode.module.scss';
50
+
51
+ const emit = defineEmits<{
52
+ expandClick: [MouseEvent];
53
+ }>();
54
+
55
+ const {
56
+ levelColors,
57
+ node
58
+ } = defineProps<{
59
+ readonly node: TreeFlatNode<TOption>;
60
+ readonly expanded: boolean;
61
+ readonly levelColors?: (FluxColor | string)[];
62
+ }>();
63
+
64
+ defineSlots<{
65
+ trailing?(props: { node: TreeFlatNode<TOption> }): any;
66
+ }>();
67
+
68
+ defineOptions({
69
+ inheritAttrs: false
70
+ });
71
+
72
+ const dotColor = computed(() => getLevelColor(node.depth, levelColors));
73
+
74
+ function onExpandClick(evt: MouseEvent): void {
75
+ emit('expandClick', evt);
76
+ }
77
+ </script>
@@ -1,5 +1,6 @@
1
1
  export { default as Anchor } from './Anchor.vue';
2
2
  export { default as AnchorPopup } from './AnchorPopup.vue';
3
+ export { default as DialogLayout } from './DialogLayout.vue';
3
4
  export { default as FilterBadge } from './FilterBadge.vue';
4
5
  export { default as FilterItem } from './FilterItem.vue';
5
6
  export { default as FilterOptionBase } from './FilterOptionBase.vue';
@@ -7,6 +8,7 @@ export { default as SelectBase } from './SelectBase.vue';
7
8
  export { default as SliderBase } from './SliderBase.vue';
8
9
  export { default as SliderThumb } from './SliderThumb.vue';
9
10
  export { default as SliderTrack } from './SliderTrack.vue';
11
+ export { default as TreeNodeRenderer } from './TreeNodeRenderer.vue';
10
12
 
11
13
  export { FilterMenuRenderer } from './FilterMenuRenderer';
12
14
  export { VNodeRenderer } from './VNodeRenderer';
@@ -1,6 +1,7 @@
1
1
  export { default as useBreakpoints } from './useBreakpoints';
2
2
  export { default as useDisabled } from './useDisabled';
3
3
 
4
+ export { default as useAdaptiveGroupInjection } from './useAdaptiveGroupInjection';
4
5
  export { default as useDisabledInjection } from './useDisabledInjection';
5
6
  export { default as useExpandableGroupInjection } from './useExpandableGroupInjection';
6
7
  export { default as useFilterInjection } from './useFilterInjection';
@@ -1,4 +1,12 @@
1
+ export { default as useAsyncFilterOptions } from './useAsyncFilterOptions';
2
+ export { default as useDateFlyout } from './useDateFlyout';
3
+ export { default as useDropdownPopup } from './useDropdownPopup';
4
+ export type { UseDropdownPopupOptions, UseDropdownPopupReturn } from './useDropdownPopup';
1
5
  export { default as useFormSelect } from './useFormSelect';
2
6
  export { default as useTranslate } from './useTranslate';
7
+ export { useCommandPalette } from './useCommandPalette';
8
+ export type { CommandPaletteGroup, CommandPaletteResultItem } from './useCommandPalette';
9
+ export { useFilterOptionMulti, useFilterOptionSingle } from './useFilterOption';
10
+ export type { FilterOptionMulti, FilterOptionSingle } from './useFilterOption';
3
11
  export { flattenAll, flattenVisible, getLevelColor, INITIAL_HIGHLIGHTED_INDEX, useTreeView } from './useTreeView';
4
12
  export type { TreeBaseOption, TreeFlatNode } from './useTreeView';
@@ -0,0 +1,70 @@
1
+ import { useDebouncedRef, useLoaded } from '@basmilius/common';
2
+ import type { FluxFilterOptionRow, FluxFilterValue } from '@flux-ui/types';
3
+ import { type ComputedRef, type ModelRef, computed, type Ref, ref, unref, watch } from 'vue';
4
+ import { isFluxFilterOptionItem } from '$flux/data';
5
+
6
+ type UseAsyncFilterOptionsParams = {
7
+ readonly currentValueIds: ComputedRef<FluxFilterValue[]>;
8
+ readonly modelSearch: ModelRef<string, string, string, string>;
9
+ fetchOptions(ids: FluxFilterValue[]): Promise<FluxFilterOptionRow[]>;
10
+ fetchRelevant(): Promise<FluxFilterOptionRow[]>;
11
+ fetchSearch(searchQuery: string): Promise<FluxFilterOptionRow[]>;
12
+ };
13
+
14
+ export default function ({
15
+ currentValueIds,
16
+ modelSearch,
17
+ fetchOptions: fetchOptionsProp,
18
+ fetchRelevant: fetchRelevantProp,
19
+ fetchSearch: fetchSearchProp
20
+ }: UseAsyncFilterOptionsParams) {
21
+ const {isLoading, loaded} = useLoaded();
22
+ const debouncedModelSearch = useDebouncedRef(modelSearch, 150) as unknown as Ref<string>;
23
+ const fetchOptions = computed(() => loaded(fetchOptionsProp));
24
+ const fetchRelevant = computed(() => loaded(fetchRelevantProp));
25
+ const fetchSearch = computed(() => loaded(fetchSearchProp));
26
+
27
+ const selectedOptions = ref<FluxFilterOptionRow[]>([]);
28
+ const visibleOptions = ref<FluxFilterOptionRow[]>([]);
29
+
30
+ const options = computed(() => {
31
+ const options: FluxFilterOptionRow[] = [];
32
+ const search = unref(modelSearch);
33
+ const selected = unref(selectedOptions);
34
+ const visible = unref(visibleOptions);
35
+
36
+ visible.forEach(vo => options.push(vo));
37
+
38
+ selected.forEach(so => {
39
+ if (isFluxFilterOptionItem(so) && visible.find(vo => isFluxFilterOptionItem(vo) && vo.value === so.value)) {
40
+ return;
41
+ }
42
+
43
+ if (isFluxFilterOptionItem(so) && !so.label.toLowerCase().includes(search.toLowerCase())) {
44
+ return;
45
+ }
46
+
47
+ options.push(so);
48
+ });
49
+
50
+ return options;
51
+ });
52
+
53
+ watch(currentValueIds, async ids => {
54
+ if (ids.length === 0) {
55
+ return;
56
+ }
57
+
58
+ selectedOptions.value = await unref(fetchOptions)(ids);
59
+ }, {immediate: true});
60
+
61
+ watch(debouncedModelSearch, async searchQuery => {
62
+ if (searchQuery.length > 0) {
63
+ visibleOptions.value = await unref(fetchSearch)(searchQuery);
64
+ } else {
65
+ visibleOptions.value = await unref(fetchRelevant)();
66
+ }
67
+ }, {immediate: true});
68
+
69
+ return {isLoading, options};
70
+ }
@@ -47,7 +47,7 @@ export function useCommandPalette(params: {
47
47
  const isTransitioningBack = ref(false);
48
48
  const savedState = ref<{ readonly search: string; readonly highlightedIndex: number; } | null>(null);
49
49
  const asyncResults = ref<Map<string, FluxCommandSourceItem[]>>(new Map());
50
- const debouncedSearch = useDebouncedRef(search, 300);
50
+ const debouncedSearch = useDebouncedRef(search, 300) as unknown as Ref<string>;
51
51
  let fetchGeneration = 0;
52
52
 
53
53
  const filteredItems = computed<CommandPaletteResultItem[]>(() => {
@@ -0,0 +1,34 @@
1
+ import { type ModelRef, type Ref, ref, unref, watch } from 'vue';
2
+
3
+ type FlyoutLike = {
4
+ close(): void;
5
+ };
6
+
7
+ type UseDateFlyoutOptions<T> = {
8
+ compareKey?(value: T | null): string | number | null | undefined;
9
+ transformIn?(value: T | null): T | null;
10
+ };
11
+
12
+ export default function <T>(
13
+ modelValue: ModelRef<T | null>,
14
+ flyoutRef: Readonly<Ref<FlyoutLike | null>>,
15
+ options: UseDateFlyoutOptions<T> = {}
16
+ ): Ref<T | null> {
17
+ const localValue = ref<T | null>(null) as Ref<T | null>;
18
+
19
+ watch(modelValue, value => {
20
+ localValue.value = options.transformIn ? options.transformIn(value) : value;
21
+ }, {immediate: true});
22
+
23
+ watch(localValue, value => {
24
+ unref(flyoutRef)?.close();
25
+
26
+ if (options.compareKey && options.compareKey(modelValue.value) === options.compareKey(value)) {
27
+ return;
28
+ }
29
+
30
+ modelValue.value = value;
31
+ });
32
+
33
+ return localValue;
34
+ }
@@ -0,0 +1,99 @@
1
+ import { useClickOutside } from '@basmilius/common';
2
+ import { unrefTemplateElement } from '@flux-ui/internals';
3
+ import { type ComponentPublicInstance, nextTick, ref, type Ref, unref, watch } from 'vue';
4
+
5
+ export type UseDropdownPopupOptions = {
6
+ readonly anchorRef: Readonly<Ref<ComponentPublicInstance | null | undefined>>;
7
+ readonly popupRef: Readonly<Ref<ComponentPublicInstance | null | undefined>>;
8
+ readonly focusElement: Readonly<Ref<HTMLElement | null | undefined>>;
9
+ readonly disabled?: Readonly<Ref<boolean>>;
10
+ readonly readonly?: Readonly<Ref<boolean>>;
11
+ readonly onOpen?: () => void;
12
+ readonly onClose?: () => void;
13
+ };
14
+
15
+ export type UseDropdownPopupReturn = {
16
+ readonly isOpen: Ref<boolean>;
17
+ readonly open: () => void;
18
+ readonly close: () => void;
19
+ readonly toggle: () => void;
20
+ readonly focusAnchor: () => void;
21
+ readonly onKeyDownBase: (evt: KeyboardEvent) => boolean;
22
+ };
23
+
24
+ /**
25
+ * Shared dropdown-popup infrastructure for select-like components. Manages:
26
+ * - open/close state
27
+ * - click-outside (close when clicking outside popup + anchor)
28
+ * - focus-back-to-anchor on close
29
+ * - focus-the-inner-focus-element on open
30
+ * - Escape/Tab keyboard handling
31
+ */
32
+ export default function useDropdownPopup(options: UseDropdownPopupOptions): UseDropdownPopupReturn {
33
+ const isOpen = ref(false);
34
+
35
+ function open(): void {
36
+ if (unref(options.disabled) || unref(options.readonly)) {
37
+ return;
38
+ }
39
+
40
+ isOpen.value = true;
41
+ }
42
+
43
+ function close(): void {
44
+ isOpen.value = false;
45
+ }
46
+
47
+ function toggle(): void {
48
+ if (unref(options.disabled) || unref(options.readonly)) {
49
+ return;
50
+ }
51
+
52
+ isOpen.value = !unref(isOpen);
53
+ }
54
+
55
+ function focusAnchor(): void {
56
+ nextTick(() => unrefTemplateElement(options.anchorRef)?.focus());
57
+ }
58
+
59
+ function onKeyDownBase(evt: KeyboardEvent): boolean {
60
+ if (evt.key === 'Escape' && unref(isOpen)) {
61
+ evt.preventDefault();
62
+ isOpen.value = false;
63
+ focusAnchor();
64
+ return true;
65
+ }
66
+
67
+ if (evt.key === 'Tab' && unref(isOpen)) {
68
+ isOpen.value = false;
69
+ return true;
70
+ }
71
+
72
+ return false;
73
+ }
74
+
75
+ if (typeof window !== 'undefined') {
76
+ useClickOutside([options.anchorRef, options.popupRef], isOpen, () => isOpen.value = false);
77
+ useClickOutside(options.anchorRef, isOpen, () => unref(options.focusElement)?.focus());
78
+ }
79
+
80
+ watch(isOpen, opened => {
81
+ if (!opened) {
82
+ options.onClose?.();
83
+ return;
84
+ }
85
+
86
+ nextTick(() => unref(options.focusElement)?.focus());
87
+
88
+ options.onOpen?.();
89
+ });
90
+
91
+ return {
92
+ isOpen,
93
+ open,
94
+ close,
95
+ toggle,
96
+ focusAnchor,
97
+ onKeyDownBase
98
+ };
99
+ }
@@ -0,0 +1,59 @@
1
+ import type { FluxFilterValue, FluxFilterValueSingle } from '@flux-ui/types';
2
+ import { type ComputedRef, computed, unref } from 'vue';
3
+ import { useFilterInjection } from '$flux/composable';
4
+
5
+ export type FilterOptionSingle = {
6
+ readonly currentValue: ComputedRef<FluxFilterValueSingle>;
7
+ onSelect(value: FluxFilterValue): void;
8
+ };
9
+
10
+ export type FilterOptionMulti = {
11
+ readonly currentValue: ComputedRef<FluxFilterValueSingle[]>;
12
+ onSelect(value: FluxFilterValueSingle): void;
13
+ };
14
+
15
+ export function useFilterOptionSingle(name: string): FilterOptionSingle {
16
+ const {back, state, setValue} = useFilterInjection();
17
+
18
+ const currentValue = computed(() => unref(state)[name] as FluxFilterValueSingle);
19
+
20
+ function onSelect(value: FluxFilterValue): void {
21
+ if (unref(currentValue) === value) {
22
+ setValue(name, null);
23
+ } else {
24
+ setValue(name, value);
25
+ }
26
+
27
+ back();
28
+ }
29
+
30
+ return {currentValue, onSelect};
31
+ }
32
+
33
+ export function useFilterOptionMulti(name: string): FilterOptionMulti {
34
+ const {state, setValue} = useFilterInjection();
35
+
36
+ const currentValue = computed<FluxFilterValueSingle[]>(() => {
37
+ const value = unref(state)[name];
38
+
39
+ if (Array.isArray(value)) {
40
+ return value;
41
+ }
42
+
43
+ return [];
44
+ });
45
+
46
+ function onSelect(value: FluxFilterValueSingle): void {
47
+ let values = Array.from(unref(currentValue));
48
+
49
+ if (values.includes(value)) {
50
+ values = values.filter(v => v !== value);
51
+ } else {
52
+ values.push(value);
53
+ }
54
+
55
+ setValue(name, values);
56
+ }
57
+
58
+ return {currentValue, onSelect};
59
+ }
@@ -0,0 +1,6 @@
1
+ import { inject } from 'vue';
2
+ import { FluxAdaptiveGroupInjectionKey } from '$flux/data';
3
+
4
+ export default function () {
5
+ return inject(FluxAdaptiveGroupInjectionKey, null);
6
+ }
@@ -57,7 +57,7 @@
57
57
  }
58
58
 
59
59
  .basePaneStructure > .actionBar {
60
- padding: 15px 21px;
60
+ padding: 12px 18px;
61
61
  background: var(--gray-50);
62
62
  border: 1px solid var(--gray-100);
63
63
  border-left: 0;
@@ -77,7 +77,7 @@
77
77
  }
78
78
 
79
79
  .paneHeader + .actionBar {
80
- margin-top: 21px;
80
+ margin-top: 18px;
81
81
  }
82
82
 
83
83
  .actionPane {
@@ -0,0 +1,25 @@
1
+ .adaptiveGroup {
2
+ display: flex;
3
+ overflow: hidden;
4
+ flex-flow: row nowrap;
5
+ gap: var(--gap, 9px);
6
+ min-width: 0;
7
+ }
8
+
9
+ .adaptiveSlot {
10
+ display: flex;
11
+ overflow: hidden;
12
+ flex-flow: row nowrap;
13
+ min-width: 0;
14
+ }
15
+
16
+ .adaptiveSlotMeasurer {
17
+ position: absolute;
18
+ top: 0;
19
+ left: 0;
20
+ display: flex;
21
+ visibility: hidden;
22
+ flex-flow: row nowrap;
23
+ width: max-content;
24
+ pointer-events: none;
25
+ }
@@ -6,7 +6,7 @@
6
6
  height: 1em;
7
7
  width: 1em;
8
8
  flex: 0 0 1em;
9
- border-radius: .5em;
9
+ border-radius: .3em;
10
10
  user-select: none;
11
11
  }
12
12
 
@@ -68,19 +68,18 @@
68
68
  backdrop-filter: blur(3px) saturate(180%);
69
69
 
70
70
  :local(.spinner) {
71
- --track: rgb(0 0 0 / .12);
71
+ --track: rgb(from var(--gray-950) r g b / .12);
72
72
  }
73
73
  }
74
74
 
75
75
  .avatarStatus {
76
76
  position: absolute;
77
77
  display: block;
78
- right: 0.0238095238em;
79
- bottom: 0.0238095238em;
80
- height: 0.285714286em;
81
- width: 0.285714286em;
82
- background: black;
83
- border-radius: 99px;
78
+ right: .021em;
79
+ bottom: .021em;
80
+ height: .27em;
81
+ width: .27em;
82
+ border-radius: var(--radius-full);
84
83
  }
85
84
 
86
85
  .avatarStatusGray {
@@ -134,8 +133,8 @@
134
133
 
135
134
  .statusAvatar .avatarFallback,
136
135
  .statusAvatar .avatarImage {
137
- mask: url('$flux/image/avatar-mask.svg') no-repeat center center / cover;
138
- -webkit-mask: url('$flux/image/avatar-mask.svg') no-repeat center center / cover;
136
+ mask: radial-gradient(circle .18em at calc(100% - 0.16em) calc(100% - 0.16em), transparent 100%, #000 100%);
137
+ -webkit-mask: radial-gradient(circle .18em at calc(100% - 0.16em) calc(100% - 0.16em), transparent 100%, #000 100%);
139
138
  }
140
139
 
141
140
  .persona {
@@ -148,7 +147,7 @@
148
147
  border-radius: var(--radius);
149
148
  cursor: pointer;
150
149
  text-align: left;
151
- transition: 180ms var(--swift-out);
150
+ transition: var(--transition-default);
152
151
  transition-property: background, mixin.focus-ring-transition-properties();
153
152
 
154
153
  @include mixin.focus-ring(2px);