@qw-ui/core 0.3.0-next.8 → 0.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.
- package/README.md +21 -37
- package/dist/action-sheet/action-sheet.d.ts +110 -0
- package/dist/action-sheet/index.d.ts +2 -0
- package/dist/action-sheet/index.js +2 -0
- package/dist/action-sheet-Cvcr1S_m.js +183 -0
- package/dist/action-sheet-Cvcr1S_m.js.map +1 -0
- package/dist/area-picker/area-picker.d.ts +113 -0
- package/dist/area-picker/index.d.ts +1 -0
- package/dist/area-picker/index.js +348 -0
- package/dist/area-picker/index.js.map +1 -0
- package/dist/aria-description-CimD2M_C.js +13 -0
- package/dist/aria-description-CimD2M_C.js.map +1 -0
- package/dist/aria-description.d.ts +2 -0
- package/dist/avatar/avatar-load.d.ts +76 -0
- package/dist/avatar/avatar.d.ts +22 -5
- package/dist/avatar/index.d.ts +1 -0
- package/dist/avatar/index.js +57 -18
- package/dist/avatar/index.js.map +1 -1
- package/dist/avatar-load-w9dq05oV.js +139 -0
- package/dist/avatar-load-w9dq05oV.js.map +1 -0
- package/dist/back-top/back-top.d.ts +77 -0
- package/dist/back-top/index.d.ts +1 -0
- package/dist/back-top/index.js +189 -0
- package/dist/back-top/index.js.map +1 -0
- package/dist/badge/badge.d.ts +85 -0
- package/dist/badge/index.d.ts +1 -0
- package/dist/badge/index.js +88 -0
- package/dist/badge/index.js.map +1 -0
- package/dist/button/button.d.ts +13 -0
- package/dist/button/index.js +3 -5
- package/dist/button/index.js.map +1 -1
- package/dist/calendar/calendar.d.ts +100 -0
- package/dist/calendar/index.d.ts +1 -0
- package/dist/calendar/index.js +2 -0
- package/dist/calendar-CmpK3stz.js +363 -0
- package/dist/calendar-CmpK3stz.js.map +1 -0
- package/dist/card/card.d.ts +68 -0
- package/dist/card/index.d.ts +2 -0
- package/dist/card/index.js +2 -0
- package/dist/card-DRtWa6Cr.js +107 -0
- package/dist/card-DRtWa6Cr.js.map +1 -0
- package/dist/cascader/cascader.d.ts +115 -0
- package/dist/cascader/index.d.ts +1 -0
- package/dist/cascader/index.js +2 -0
- package/dist/cascader-D-xMjs7P.js +333 -0
- package/dist/cascader-D-xMjs7P.js.map +1 -0
- package/dist/cell/cell.d.ts +41 -0
- package/dist/cell/index.d.ts +1 -0
- package/dist/cell/index.js +43 -0
- package/dist/cell/index.js.map +1 -0
- package/dist/check-list/check-list.d.ts +78 -0
- package/dist/check-list/index.d.ts +2 -0
- package/dist/check-list/index.js +2 -0
- package/dist/check-list-BvZHQt5w.js +60 -0
- package/dist/check-list-BvZHQt5w.js.map +1 -0
- package/dist/checkbox/checkbox.d.ts +59 -0
- package/dist/checkbox/index.d.ts +2 -0
- package/dist/checkbox/index.js +2 -0
- package/dist/checkbox-BlndJrz5.js +127 -0
- package/dist/checkbox-BlndJrz5.js.map +1 -0
- package/dist/checkbox-group/checkbox-group.d.ts +86 -0
- package/dist/checkbox-group/index.d.ts +3 -0
- package/dist/checkbox-group/index.js +2 -0
- package/dist/checkbox-group-gGfsTv-e.js +223 -0
- package/dist/checkbox-group-gGfsTv-e.js.map +1 -0
- package/dist/choice-group-C4c9m0qe.js +373 -0
- package/dist/choice-group-C4c9m0qe.js.map +1 -0
- package/dist/circle/circle.d.ts +97 -0
- package/dist/circle/index.d.ts +1 -0
- package/dist/circle/index.js +119 -0
- package/dist/circle/index.js.map +1 -0
- package/dist/collapse/collapse.d.ts +98 -0
- package/dist/collapse/index.d.ts +2 -0
- package/dist/collapse/index.js +2 -0
- package/dist/collapse-B969h7-H.js +226 -0
- package/dist/collapse-B969h7-H.js.map +1 -0
- package/dist/countdown/countdown.d.ts +114 -0
- package/dist/countdown/index.d.ts +1 -0
- package/dist/countdown/index.js +309 -0
- package/dist/countdown/index.js.map +1 -0
- package/dist/date-picker/date-picker.d.ts +168 -0
- package/dist/date-picker/index.d.ts +1 -0
- package/dist/date-picker/index.js +401 -0
- package/dist/date-picker/index.js.map +1 -0
- package/dist/descriptions/descriptions.d.ts +69 -0
- package/dist/descriptions/index.d.ts +1 -0
- package/dist/descriptions/index.js +86 -0
- package/dist/descriptions/index.js.map +1 -0
- package/dist/dialog/dialog.d.ts +61 -43
- package/dist/dialog/index.js +73 -19
- package/dist/dialog/index.js.map +1 -1
- package/dist/divider/divider.d.ts +18 -2
- package/dist/divider/index.js +20 -2
- package/dist/divider/index.js.map +1 -1
- package/dist/dropdown/dropdown.d.ts +172 -0
- package/dist/dropdown/index.d.ts +2 -0
- package/dist/dropdown/index.js +467 -0
- package/dist/dropdown/index.js.map +1 -0
- package/dist/ellipsis/ellipsis-layout.d.ts +34 -0
- package/dist/ellipsis/ellipsis.d.ts +88 -0
- package/dist/ellipsis/index.d.ts +2 -0
- package/dist/ellipsis/index.js +320 -0
- package/dist/ellipsis/index.js.map +1 -0
- package/dist/empty/empty-illustration.d.ts +3 -0
- package/dist/empty/empty.d.ts +43 -1
- package/dist/empty/index.js +2 -21
- package/dist/empty-CAgyvhUI.js +166 -0
- package/dist/empty-CAgyvhUI.js.map +1 -0
- package/dist/field/field.d.ts +95 -0
- package/dist/field/index.d.ts +2 -0
- package/dist/field/index.js +2 -0
- package/dist/field-DMHGIMZF.js +241 -0
- package/dist/field-DMHGIMZF.js.map +1 -0
- package/dist/floating-bubble/floating-bubble.d.ts +116 -0
- package/dist/floating-bubble/index.d.ts +1 -0
- package/dist/floating-bubble/index.js +333 -0
- package/dist/floating-bubble/index.js.map +1 -0
- package/dist/floating-panel/floating-panel.d.ts +80 -0
- package/dist/floating-panel/index.d.ts +2 -0
- package/dist/floating-panel/index.js +2 -0
- package/dist/floating-panel-Cbm5njBJ.js +363 -0
- package/dist/floating-panel-Cbm5njBJ.js.map +1 -0
- package/dist/footer/footer.d.ts +94 -0
- package/dist/footer/index.d.ts +1 -0
- package/dist/footer/index.js +154 -0
- package/dist/footer/index.js.map +1 -0
- package/dist/form/connect.d.ts +6 -0
- package/dist/form/form.d.ts +100 -0
- package/dist/form/ids.d.ts +14 -0
- package/dist/form/index.d.ts +13 -0
- package/dist/form/index.js +3 -0
- package/dist/form/methods.d.ts +5 -0
- package/dist/form/model.d.ts +24 -0
- package/dist/form/native.d.ts +25 -0
- package/dist/form/rules.d.ts +40 -0
- package/dist/form/ssr.d.ts +7 -0
- package/dist/form/types.d.ts +150 -0
- package/dist/form-BAGkIEMY.js +1354 -0
- package/dist/form-BAGkIEMY.js.map +1 -0
- package/dist/format-BDUY0C_c.js +89 -0
- package/dist/format-BDUY0C_c.js.map +1 -0
- package/dist/gesture-_SRHIvBm.js +30 -0
- package/dist/gesture-_SRHIvBm.js.map +1 -0
- package/dist/grid/grid-item.d.ts +22 -0
- package/dist/grid/grid.d.ts +42 -0
- package/dist/grid/index.d.ts +2 -0
- package/dist/grid/index.js +73 -0
- package/dist/grid/index.js.map +1 -0
- package/dist/icon/icon.d.ts +37 -1
- package/dist/icon/identity.d.ts +3 -0
- package/dist/icon/index.js +2 -20
- package/dist/icon-Cgdbnk1u.js +77 -0
- package/dist/icon-Cgdbnk1u.js.map +1 -0
- package/dist/image/image-load.d.ts +24 -0
- package/dist/image/image.d.ts +45 -8
- package/dist/image/index.d.ts +1 -0
- package/dist/image/index.js +116 -14
- package/dist/image/index.js.map +1 -1
- package/dist/image-preview/image-preview.d.ts +124 -0
- package/dist/image-preview/index.d.ts +1 -0
- package/dist/image-preview/index.js +450 -0
- package/dist/image-preview/index.js.map +1 -0
- package/dist/index-bar/index-bar.d.ts +121 -0
- package/dist/index-bar/index.d.ts +1 -0
- package/dist/index-bar/index.js +386 -0
- package/dist/index-bar/index.js.map +1 -0
- package/dist/index.d.ts +115 -10
- package/dist/index.js +151 -11
- package/dist/index.js.map +1 -0
- package/dist/infinite-scroll/index.d.ts +1 -0
- package/dist/infinite-scroll/index.js +248 -0
- package/dist/infinite-scroll/index.js.map +1 -0
- package/dist/infinite-scroll/infinite-scroll.d.ts +95 -0
- package/dist/input/index.js +181 -22
- package/dist/input/index.js.map +1 -1
- package/dist/input/input.d.ts +44 -1
- package/dist/layer-IpFrl5--.js +414 -0
- package/dist/layer-IpFrl5--.js.map +1 -0
- package/dist/layout-BRSqi4AQ.js +43 -0
- package/dist/layout-BRSqi4AQ.js.map +1 -0
- package/dist/layout.d.ts +13 -0
- package/dist/list/index.d.ts +2 -0
- package/dist/list/index.js +2 -0
- package/dist/list/list.d.ts +30 -0
- package/dist/list-6-iz-Irh.js +28 -0
- package/dist/list-6-iz-Irh.js.map +1 -0
- package/dist/loading/index.js +45 -2
- package/dist/loading/index.js.map +1 -1
- package/dist/loading/loading.d.ts +45 -2
- package/dist/modal-dialog-machine-CF9_z3Dm.js +487 -0
- package/dist/modal-dialog-machine-CF9_z3Dm.js.map +1 -0
- package/dist/modal-dialog-machine.d.ts +21 -0
- package/dist/modal-dismissable-lifetime.d.ts +21 -0
- package/dist/modal-registry.d.ts +24 -0
- package/dist/modal-render-hydration.d.ts +35 -0
- package/dist/modal-render-runtime.d.ts +19 -0
- package/dist/modal-render-scope.d.ts +63 -0
- package/dist/nav-bar/index.d.ts +1 -0
- package/dist/nav-bar/index.js +115 -0
- package/dist/nav-bar/index.js.map +1 -0
- package/dist/nav-bar/nav-bar.d.ts +76 -0
- package/dist/notice-bar/index.d.ts +2 -0
- package/dist/notice-bar/index.js +2 -0
- package/dist/notice-bar/notice-bar.d.ts +103 -0
- package/dist/notice-bar-DMpwLvRb.js +231 -0
- package/dist/notice-bar-DMpwLvRb.js.map +1 -0
- package/dist/notify/index.d.ts +1 -0
- package/dist/notify/index.js +251 -0
- package/dist/notify/index.js.map +1 -0
- package/dist/notify/notify.d.ts +123 -0
- package/dist/number-keyboard/index.d.ts +1 -0
- package/dist/number-keyboard/index.js +333 -0
- package/dist/number-keyboard/index.js.map +1 -0
- package/dist/number-keyboard/number-keyboard.d.ts +141 -0
- package/dist/overlay-panel/index.d.ts +2 -0
- package/dist/overlay-panel/index.js +2 -0
- package/dist/overlay-panel/overlay-panel.d.ts +20 -0
- package/dist/overlay-panel-Z_qdKeBj.js +26 -0
- package/dist/overlay-panel-Z_qdKeBj.js.map +1 -0
- package/dist/page-indicator/index.d.ts +1 -0
- package/dist/page-indicator/index.js +138 -0
- package/dist/page-indicator/index.js.map +1 -0
- package/dist/page-indicator/page-indicator.d.ts +93 -0
- package/dist/pagination/index.d.ts +1 -0
- package/dist/pagination/index.js +198 -0
- package/dist/pagination/index.js.map +1 -0
- package/dist/pagination/pagination.d.ts +125 -0
- package/dist/password-input/index.d.ts +1 -0
- package/dist/password-input/index.js +317 -0
- package/dist/password-input/index.js.map +1 -0
- package/dist/password-input/password-input.d.ts +144 -0
- package/dist/picker/index.d.ts +8 -0
- package/dist/picker/index.js +2 -0
- package/dist/picker/picker-machine.d.ts +80 -0
- package/dist/picker/picker.d.ts +121 -0
- package/dist/picker/platform.d.ts +84 -0
- package/dist/picker/selection-connect.d.ts +90 -0
- package/dist/picker/selection-model.d.ts +211 -0
- package/dist/picker-BykFntQN.js +1675 -0
- package/dist/picker-BykFntQN.js.map +1 -0
- package/dist/popover/index.d.ts +3 -0
- package/dist/popover/index.js +253 -0
- package/dist/popover/index.js.map +1 -0
- package/dist/popover/layer.d.ts +44 -0
- package/dist/popover/popover.d.ts +104 -0
- package/dist/popover/positioning.d.ts +132 -0
- package/dist/popup/index.d.ts +2 -0
- package/dist/popup/index.js +2 -0
- package/dist/popup/popup.d.ts +60 -0
- package/dist/popup-z5d8IYCt.js +576 -0
- package/dist/popup-z5d8IYCt.js.map +1 -0
- package/dist/portal-BHCNTWhg.js +78 -0
- package/dist/portal-BHCNTWhg.js.map +1 -0
- package/dist/portal.d.ts +61 -0
- package/dist/price/format.d.ts +19 -0
- package/dist/price/index.d.ts +1 -0
- package/dist/price/index.js +154 -0
- package/dist/price/index.js.map +1 -0
- package/dist/price/price.d.ts +88 -0
- package/dist/progress/index.d.ts +1 -0
- package/dist/progress/index.js +2 -0
- package/dist/progress/progress.d.ts +32 -0
- package/dist/progress-f3iYEfdA.js +37 -0
- package/dist/progress-f3iYEfdA.js.map +1 -0
- package/dist/pull-refresh/index.d.ts +1 -0
- package/dist/pull-refresh/index.js +414 -0
- package/dist/pull-refresh/index.js.map +1 -0
- package/dist/pull-refresh/pull-refresh.d.ts +118 -0
- package/dist/radio-group/index.d.ts +3 -0
- package/dist/radio-group/index.js +2 -0
- package/dist/radio-group/radio-group.d.ts +78 -0
- package/dist/radio-group-BOIMuqnS.js +230 -0
- package/dist/radio-group-BOIMuqnS.js.map +1 -0
- package/dist/rate/index.d.ts +1 -0
- package/dist/rate/index.js +2 -0
- package/dist/rate/rate-form.d.ts +28 -0
- package/dist/rate/rate.d.ts +144 -0
- package/dist/rate-5XsU2QkY.js +631 -0
- package/dist/rate-5XsU2QkY.js.map +1 -0
- package/dist/reorder/index.d.ts +1 -0
- package/dist/reorder/index.js +720 -0
- package/dist/reorder/index.js.map +1 -0
- package/dist/reorder/reorder.d.ts +190 -0
- package/dist/result/index.d.ts +1 -0
- package/dist/result/index.js +123 -0
- package/dist/result/index.js.map +1 -0
- package/dist/result/result.d.ts +88 -0
- package/dist/safe-area/index.d.ts +1 -0
- package/dist/safe-area/index.js +42 -0
- package/dist/safe-area/index.js.map +1 -0
- package/dist/safe-area/safe-area.d.ts +28 -0
- package/dist/search-bar/index.js +4 -2
- package/dist/search-bar/index.js.map +1 -1
- package/dist/search-bar/search-bar.d.ts +6 -0
- package/dist/segmented/index.d.ts +2 -0
- package/dist/segmented/index.js +2 -0
- package/dist/segmented/segmented.d.ts +127 -0
- package/dist/segmented-BaU38_L4.js +367 -0
- package/dist/segmented-BaU38_L4.js.map +1 -0
- package/dist/selection-form-BOM_odUk.js +88 -0
- package/dist/selection-form-BOM_odUk.js.map +1 -0
- package/dist/selection-form.d.ts +27 -0
- package/dist/selection-ivXqO1eu.js +55 -0
- package/dist/selection-ivXqO1eu.js.map +1 -0
- package/dist/selection.d.ts +29 -0
- package/dist/selector/choice-group.d.ts +114 -0
- package/dist/selector/index.d.ts +2 -0
- package/dist/selector/index.js +2 -0
- package/dist/selector/selector.d.ts +90 -0
- package/dist/selector-BU2MMJ4N.js +93 -0
- package/dist/selector-BU2MMJ4N.js.map +1 -0
- package/dist/share-sheet/index.d.ts +1 -0
- package/dist/share-sheet/index.js +138 -0
- package/dist/share-sheet/index.js.map +1 -0
- package/dist/share-sheet/share-sheet.d.ts +139 -0
- package/dist/side-nav/index.d.ts +1 -0
- package/dist/side-nav/index.js +99 -0
- package/dist/side-nav/index.js.map +1 -0
- package/dist/side-nav/side-nav.d.ts +94 -0
- package/dist/skeleton/index.js +51 -2
- package/dist/skeleton/index.js.map +1 -1
- package/dist/skeleton/skeleton.d.ts +34 -3
- package/dist/slider/index.d.ts +1 -0
- package/dist/slider/index.js +482 -0
- package/dist/slider/index.js.map +1 -0
- package/dist/slider/slider.d.ts +174 -0
- package/dist/space/index.d.ts +1 -0
- package/dist/space/index.js +52 -0
- package/dist/space/index.js.map +1 -0
- package/dist/space/space.d.ts +46 -0
- package/dist/statistic/index.d.ts +1 -0
- package/dist/statistic/index.js +152 -0
- package/dist/statistic/index.js.map +1 -0
- package/dist/statistic/statistic.d.ts +101 -0
- package/dist/stepper/index.d.ts +1 -0
- package/dist/stepper/index.js +172 -0
- package/dist/stepper/index.js.map +1 -0
- package/dist/stepper/stepper.d.ts +161 -0
- package/dist/steps/index.d.ts +1 -0
- package/dist/steps/index.js +72 -0
- package/dist/steps/index.js.map +1 -0
- package/dist/steps/steps.d.ts +67 -0
- package/dist/sticky/index.d.ts +1 -0
- package/dist/sticky/index.js +145 -0
- package/dist/sticky/index.js.map +1 -0
- package/dist/sticky/sticky.d.ts +70 -0
- package/dist/swipe-action/index.d.ts +1 -0
- package/dist/swipe-action/index.js +417 -0
- package/dist/swipe-action/index.js.map +1 -0
- package/dist/swipe-action/swipe-action.d.ts +148 -0
- package/dist/swiper/gesture.d.ts +32 -0
- package/dist/swiper/index.d.ts +1 -0
- package/dist/swiper/index.js +2 -0
- package/dist/swiper/swiper.d.ts +177 -0
- package/dist/swiper-BKivDkHp.js +550 -0
- package/dist/swiper-BKivDkHp.js.map +1 -0
- package/dist/switch/index.d.ts +1 -0
- package/dist/switch/index.js +168 -0
- package/dist/switch/index.js.map +1 -0
- package/dist/switch/switch.d.ts +142 -0
- package/dist/tabbar/index.d.ts +1 -0
- package/dist/tabbar/index.js +95 -0
- package/dist/tabbar/index.js.map +1 -0
- package/dist/tabbar/tabbar.d.ts +119 -0
- package/dist/tabs/index.js +22 -1
- package/dist/tabs/index.js.map +1 -1
- package/dist/tabs/tabs.d.ts +12 -8
- package/dist/tag/index.js +123 -2
- package/dist/tag/index.js.map +1 -1
- package/dist/tag/tag.d.ts +67 -1
- package/dist/textarea/index.d.ts +2 -0
- package/dist/textarea/index.js +2 -242
- package/dist/textarea/platform.d.ts +22 -0
- package/dist/textarea/textarea.d.ts +169 -46
- package/dist/textarea-qbnruDUG.js +775 -0
- package/dist/textarea-qbnruDUG.js.map +1 -0
- package/dist/time-picker/index.d.ts +1 -0
- package/dist/time-picker/index.js +228 -0
- package/dist/time-picker/index.js.map +1 -0
- package/dist/time-picker/time-picker.d.ts +83 -0
- package/dist/timeline/index.d.ts +1 -0
- package/dist/timeline/index.js +131 -0
- package/dist/timeline/index.js.map +1 -0
- package/dist/timeline/timeline.d.ts +79 -0
- package/dist/toast/index.js +47 -4
- package/dist/toast/index.js.map +1 -1
- package/dist/toast/toast.d.ts +26 -3
- package/dist/top-bar/index.js +16 -2
- package/dist/top-bar/index.js.map +1 -1
- package/dist/top-bar/top-bar.d.ts +13 -2
- package/dist/tree-select/index.d.ts +1 -0
- package/dist/tree-select/index.js +512 -0
- package/dist/tree-select/index.js.map +1 -0
- package/dist/tree-select/tree-select.d.ts +215 -0
- package/dist/typography/index.d.ts +1 -0
- package/dist/typography/index.js +82 -0
- package/dist/typography/index.js.map +1 -0
- package/dist/typography/typography.d.ts +54 -0
- package/dist/upload/index.d.ts +1 -0
- package/dist/upload/index.js +458 -0
- package/dist/upload/index.js.map +1 -0
- package/dist/upload/upload.d.ts +172 -0
- package/dist/virtual-list/index.d.ts +1 -0
- package/dist/virtual-list/index.js +445 -0
- package/dist/virtual-list/index.js.map +1 -0
- package/dist/virtual-list/virtual-list.d.ts +160 -0
- package/dist/visual-manifest.d.ts +27 -0
- package/dist/watermark/index.d.ts +1 -0
- package/dist/watermark/index.js +260 -0
- package/dist/watermark/index.js.map +1 -0
- package/dist/watermark/watermark.d.ts +106 -0
- package/package.json +417 -44
- package/dist/empty/index.js.map +0 -1
- package/dist/icon/index.js.map +0 -1
- package/dist/textarea/index.js.map +0 -1
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
import { createMachine } from "@zag-js/core";
|
|
2
|
+
//#region src/switch/switch.ts
|
|
3
|
+
/**
|
|
4
|
+
* Switch 的跨框架行为契约。
|
|
5
|
+
*
|
|
6
|
+
* Core Zag bindable owns controlled/uncontrolled state, requests and click cancellation.
|
|
7
|
+
* Browser button semantics supply keyboard/default form actions; adapters only project getters.
|
|
8
|
+
*/
|
|
9
|
+
/** Switch 各渲染部位全集(data-part 取值)。 */
|
|
10
|
+
const SWITCH_PARTS = ["root", "thumb"];
|
|
11
|
+
const SWITCH_TYPES = [
|
|
12
|
+
"button",
|
|
13
|
+
"submit",
|
|
14
|
+
"reset"
|
|
15
|
+
];
|
|
16
|
+
/** 将公开输入归一化为唯一的跨框架状态。 */
|
|
17
|
+
function resolveSwitchState(props = {}) {
|
|
18
|
+
const normalized = createSwitchProps(props);
|
|
19
|
+
return {
|
|
20
|
+
checked: normalized.checked ?? normalized.defaultChecked ?? false,
|
|
21
|
+
disabled: normalized.disabled ?? false,
|
|
22
|
+
readOnly: normalized.readOnly ?? false,
|
|
23
|
+
type: normalized.type ?? "button"
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
function getSwitchRootProps(state, options = {}) {
|
|
27
|
+
const standards = {};
|
|
28
|
+
for (const key of [
|
|
29
|
+
"name",
|
|
30
|
+
"value",
|
|
31
|
+
"form",
|
|
32
|
+
"title",
|
|
33
|
+
"lang",
|
|
34
|
+
"dir",
|
|
35
|
+
"hidden"
|
|
36
|
+
]) if (options[key] !== void 0) standards[key] = options[key];
|
|
37
|
+
return {
|
|
38
|
+
type: state.type,
|
|
39
|
+
role: "switch",
|
|
40
|
+
disabled: state.disabled,
|
|
41
|
+
"aria-checked": state.checked ? "true" : "false",
|
|
42
|
+
"data-scope": "switch",
|
|
43
|
+
"data-part": "root",
|
|
44
|
+
"data-checked": state.checked ? "true" : "false",
|
|
45
|
+
...state.disabled ? { "data-disabled": "true" } : {},
|
|
46
|
+
...state.readOnly ? {
|
|
47
|
+
"aria-readonly": "true",
|
|
48
|
+
"data-readonly": "true"
|
|
49
|
+
} : {},
|
|
50
|
+
...options.accessibleLabel === void 0 ? {} : { "aria-label": options.accessibleLabel },
|
|
51
|
+
...options.labelledBy === void 0 ? {} : { "aria-labelledby": options.labelledBy },
|
|
52
|
+
...options.describedBy === void 0 ? {} : { "aria-describedby": options.describedBy },
|
|
53
|
+
...standards
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
/** Keep undefined checked uncontrolled, rather than filling it with a default. */
|
|
57
|
+
function createSwitchProps(props = {}) {
|
|
58
|
+
return {
|
|
59
|
+
...props,
|
|
60
|
+
checked: typeof props.checked === "boolean" ? props.checked : void 0,
|
|
61
|
+
defaultChecked: typeof props.defaultChecked === "boolean" ? props.defaultChecked : false,
|
|
62
|
+
disabled: props.disabled === true,
|
|
63
|
+
readOnly: props.readOnly === true,
|
|
64
|
+
type: SWITCH_TYPES.includes(props.type) ? props.type : "button"
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
const cancelled = (event) => !!(event?.defaultPrevented || event?.nativeEvent?.defaultPrevented);
|
|
68
|
+
function request(params, checked) {
|
|
69
|
+
const generation = params.refs.get("generation");
|
|
70
|
+
const apply = () => {
|
|
71
|
+
if (params.refs.get("active") && params.refs.get("generation") === generation && !params.prop("disabled") && !params.prop("readOnly") && !cancelled(params.event.activation)) params.context.set("checked", checked());
|
|
72
|
+
};
|
|
73
|
+
if (params.event.activation) queueMicrotask(apply);
|
|
74
|
+
else apply();
|
|
75
|
+
}
|
|
76
|
+
/** Shared request processing; final event cancellation includes later bubble listeners. */
|
|
77
|
+
const switchMachine = createMachine({
|
|
78
|
+
props: ({ props }) => ({
|
|
79
|
+
...createSwitchProps(props),
|
|
80
|
+
initialSnapshot: props.initialSnapshot
|
|
81
|
+
}),
|
|
82
|
+
initialState: () => "ready",
|
|
83
|
+
states: { ready: {} },
|
|
84
|
+
context: ({ prop, bindable }) => {
|
|
85
|
+
const internalChecked = bindable(() => ({ defaultValue: typeof prop("initialSnapshot")?.internalChecked === "boolean" ? prop("initialSnapshot").internalChecked : prop("defaultChecked") ?? false }));
|
|
86
|
+
return {
|
|
87
|
+
checked: bindable(() => ({
|
|
88
|
+
defaultValue: internalChecked.get(),
|
|
89
|
+
value: prop("checked") ?? internalChecked.get(),
|
|
90
|
+
onChange(value) {
|
|
91
|
+
if (prop("checked") === void 0) internalChecked.set(value);
|
|
92
|
+
prop("onToggle")?.(value);
|
|
93
|
+
}
|
|
94
|
+
})),
|
|
95
|
+
internalChecked
|
|
96
|
+
};
|
|
97
|
+
},
|
|
98
|
+
refs: () => ({
|
|
99
|
+
active: false,
|
|
100
|
+
generation: 0
|
|
101
|
+
}),
|
|
102
|
+
effects: ["lifecycle"],
|
|
103
|
+
on: {
|
|
104
|
+
"CHECKED.TOGGLE": { actions: ["toggle"] },
|
|
105
|
+
"CHECKED.SET": { actions: ["setChecked"] }
|
|
106
|
+
},
|
|
107
|
+
implementations: {
|
|
108
|
+
effects: { lifecycle({ refs }) {
|
|
109
|
+
refs.set("active", true);
|
|
110
|
+
refs.set("generation", refs.get("generation") + 1);
|
|
111
|
+
return () => {
|
|
112
|
+
refs.set("active", false);
|
|
113
|
+
refs.set("generation", refs.get("generation") + 1);
|
|
114
|
+
};
|
|
115
|
+
} },
|
|
116
|
+
actions: {
|
|
117
|
+
toggle(params) {
|
|
118
|
+
request(params, () => !params.context.get("checked"));
|
|
119
|
+
},
|
|
120
|
+
setChecked(params) {
|
|
121
|
+
const event = params.event;
|
|
122
|
+
if (event.type === "CHECKED.SET" && typeof event.checked === "boolean") request(params, () => event.checked);
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
});
|
|
127
|
+
function connectSwitch(service, normalize, options = {}) {
|
|
128
|
+
const state = resolveSwitchState({
|
|
129
|
+
checked: service.context.get("checked"),
|
|
130
|
+
disabled: service.prop("disabled"),
|
|
131
|
+
readOnly: service.prop("readOnly"),
|
|
132
|
+
type: service.prop("type")
|
|
133
|
+
});
|
|
134
|
+
return {
|
|
135
|
+
checked: state.checked,
|
|
136
|
+
toggle: () => service.send({ type: "CHECKED.TOGGLE" }),
|
|
137
|
+
setChecked: (checked) => service.send({
|
|
138
|
+
type: "CHECKED.SET",
|
|
139
|
+
checked
|
|
140
|
+
}),
|
|
141
|
+
getSnapshot: () => Object.freeze({ internalChecked: service.context.get("internalChecked") }),
|
|
142
|
+
getThumbProps: () => normalize.element({ ...getSwitchThumbProps() }),
|
|
143
|
+
getRootProps: (root) => normalize.button({
|
|
144
|
+
...getSwitchRootProps(state, root ?? options.root),
|
|
145
|
+
onClick(event) {
|
|
146
|
+
if (service.prop("disabled")) return;
|
|
147
|
+
const callbacks = typeof options.onClick === "function" ? [options.onClick] : options.onClick ?? [];
|
|
148
|
+
for (const callback of callbacks) callback(event);
|
|
149
|
+
if (!cancelled(event)) service.send({
|
|
150
|
+
type: "CHECKED.TOGGLE",
|
|
151
|
+
activation: event
|
|
152
|
+
});
|
|
153
|
+
}
|
|
154
|
+
})
|
|
155
|
+
};
|
|
156
|
+
}
|
|
157
|
+
/** 生成旋钮属性。 */
|
|
158
|
+
function getSwitchThumbProps() {
|
|
159
|
+
return {
|
|
160
|
+
"data-scope": "switch",
|
|
161
|
+
"data-part": "thumb",
|
|
162
|
+
"aria-hidden": "true"
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
//#endregion
|
|
166
|
+
export { SWITCH_PARTS, SWITCH_TYPES, connectSwitch, createSwitchProps, getSwitchRootProps, getSwitchThumbProps, resolveSwitchState, switchMachine };
|
|
167
|
+
|
|
168
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../src/switch/switch.ts"],"sourcesContent":["/**\n * Switch 的跨框架行为契约。\n *\n * Core Zag bindable owns controlled/uncontrolled state, requests and click cancellation.\n * Browser button semantics supply keyboard/default form actions; adapters only project getters.\n */\nimport { createMachine, type Machine, type Params, type Service } from \"@zag-js/core\";\nimport type { NormalizeProps, PropTypes } from \"@zag-js/types\";\n\n/** Switch 各渲染部位全集(data-part 取值)。 */\nexport const SWITCH_PARTS = [\"root\", \"thumb\"] as const;\nexport const SWITCH_TYPES = [\"button\", \"submit\", \"reset\"] as const;\nexport type SwitchButtonType=(typeof SWITCH_TYPES)[number];\n\nexport type SwitchPart = (typeof SWITCH_PARTS)[number];\n\n/**\n * QwSwitchProps — 双栈共享的行为契约(全字段可选)。\n * checked 未传时走非受控模式,由Core bindable管理内部状态。\n */\nexport interface QwSwitchProps {\n /** 受控值。未传时走非受控模式。 */\n checked?: boolean;\n /** 非受控初始值,默认 false。仅在 checked 未传时生效。 */\n defaultChecked?: boolean;\n /** 状态变化回调,参数为新的 checked 值。 */\n onToggle?: (checked: boolean) => void;\n /** 禁用状态。 */\n disabled?: boolean;\n /** Prevent switch requests while keeping native focus and explicit submit/reset behavior. */\n readOnly?:boolean;\n /** 原生 button 类型,默认 `button`。 */\n type?: SwitchButtonType;\n}\n\n/** 适配器唯一可消费的归一化结果。 */\nexport interface ResolvedSwitchState {\n checked: boolean;\n disabled: boolean;\n readOnly:boolean;\n type: \"button\" | \"submit\" | \"reset\";\n}\n\n/** Core 生成、由适配器最后覆盖到根元素的属性。 */\nexport interface SwitchRootProps {\n type: \"button\" | \"submit\" | \"reset\";\n role: \"switch\";\n disabled: boolean;\n \"aria-checked\": \"true\" | \"false\";\n \"data-scope\": \"switch\";\n \"data-part\": \"root\";\n \"data-checked\": \"true\" | \"false\";\n \"data-disabled\"?: \"true\";\n}\n\n/** 旋钮属性(纯视觉元素)。 */\nexport interface SwitchThumbProps {\n \"data-scope\": \"switch\";\n \"data-part\": \"thumb\";\n \"aria-hidden\": \"true\";\n}\n\n/** 将公开输入归一化为唯一的跨框架状态。 */\nexport function resolveSwitchState(props: QwSwitchProps = {}): ResolvedSwitchState {\n const normalized=createSwitchProps(props);\n return {\n checked: normalized.checked ?? normalized.defaultChecked ?? false,\n disabled: normalized.disabled ?? false,\n readOnly:normalized.readOnly ?? false,\n type: normalized.type ?? \"button\",\n };\n}\n\n/** 将归一化结果转成 root 属性。 */\nexport interface SwitchRootOptions {accessibleLabel?:string;labelledBy?:string;describedBy?:string;name?:string;value?:string;form?:string;title?:string;lang?:string;dir?:string;hidden?:boolean}\nexport function getSwitchRootProps(state: ResolvedSwitchState,options:SwitchRootOptions={}): SwitchRootProps & {\"aria-readonly\"?:\"true\";\"data-readonly\"?:\"true\";\"aria-label\"?:string;\"aria-labelledby\"?:string;\"aria-describedby\"?:string;name?:string;value?:string;form?:string;title?:string;lang?:string;dir?:string;hidden?:boolean} {\n const standards:Record<string,string|boolean>={};\n for(const key of [\"name\",\"value\",\"form\",\"title\",\"lang\",\"dir\",\"hidden\"] as const)if(options[key]!==undefined)standards[key]=options[key]!;\n return {\n type: state.type,\n role: \"switch\",\n disabled: state.disabled,\n \"aria-checked\": state.checked ? \"true\" : \"false\",\n \"data-scope\": \"switch\",\n \"data-part\": \"root\",\n \"data-checked\": state.checked ? \"true\" : \"false\",\n ...(state.disabled ? { \"data-disabled\": \"true\" as const } : {}),\n ...(state.readOnly?{\"aria-readonly\":\"true\" as const,\"data-readonly\":\"true\" as const}:{}),\n ...(options.accessibleLabel===undefined?{}:{\"aria-label\":options.accessibleLabel}),\n ...(options.labelledBy===undefined?{}:{\"aria-labelledby\":options.labelledBy}),\n ...(options.describedBy===undefined?{}:{\"aria-describedby\":options.describedBy}),...standards,\n };\n}\n\n/** Common cancellation contract; framework/native events are transported without copying state rules. */\nexport interface SwitchActivationEvent {readonly defaultPrevented:boolean;readonly nativeEvent?:{readonly defaultPrevented:boolean};preventDefault?:()=>void}\nexport type SwitchClickHandler=(event:SwitchActivationEvent)=>void;\nexport interface SwitchConnectOptions {root?:SwitchRootOptions;onClick?:SwitchClickHandler|readonly SwitchClickHandler[]}\n/** Independent uncontrolled memory transported by adapter lifecycle snapshots. */\nexport interface SwitchStateSnapshot {readonly internalChecked:boolean}\n/** Keep undefined checked uncontrolled, rather than filling it with a default. */\nexport function createSwitchProps(props:QwSwitchProps={}):QwSwitchProps {\n return {...props,checked:typeof props.checked===\"boolean\"?props.checked:undefined,defaultChecked:typeof props.defaultChecked===\"boolean\"?props.defaultChecked:false,\n disabled:props.disabled===true,readOnly:props.readOnly===true,type:SWITCH_TYPES.includes(props.type!)?props.type!:\"button\"};\n}\nexport interface QwSwitchSchema {\n props:QwSwitchProps & {initialSnapshot?:SwitchStateSnapshot};context:{checked:boolean;internalChecked:boolean};state:\"ready\";action:\"toggle\"|\"setChecked\";\n refs:{active:boolean;generation:number};effect:\"lifecycle\";\n event:{type:\"CHECKED.TOGGLE\";activation?:SwitchActivationEvent}|{type:\"CHECKED.SET\";checked:boolean;activation?:SwitchActivationEvent};\n}\nexport type QwSwitchMachine=Machine<QwSwitchSchema>;\nexport type QwSwitchService=Service<QwSwitchSchema>;\nconst cancelled=(event:SwitchActivationEvent|undefined)=>!!(event?.defaultPrevented || event?.nativeEvent?.defaultPrevented);\nfunction request(params:Params<QwSwitchSchema>,checked:()=>boolean):void {\n const generation=params.refs.get(\"generation\");\n const apply=()=>{if(params.refs.get(\"active\") && params.refs.get(\"generation\")===generation && !params.prop(\"disabled\") && !params.prop(\"readOnly\") && !cancelled(params.event.activation))params.context.set(\"checked\",checked());};\n // Framework services can send synchronously. Wait for complete click propagation in Core,\n // while the immediate send still establishes the native updateComplete barrier.\n if(params.event.activation)queueMicrotask(apply);else apply();\n}\n/** Shared request processing; final event cancellation includes later bubble listeners. */\nexport const switchMachine:QwSwitchMachine=createMachine<QwSwitchSchema>({\n props:({props})=>({...createSwitchProps(props),initialSnapshot:props.initialSnapshot}),initialState:()=>\"ready\",states:{ready:{}},\n context:({prop,bindable})=>{\n // Preserve the existing adapters' independent uncontrolled memory, even when first mounted controlled.\n const internalChecked=bindable<boolean>(()=>({defaultValue:typeof prop(\"initialSnapshot\")?.internalChecked===\"boolean\"?prop(\"initialSnapshot\")!.internalChecked:prop(\"defaultChecked\")??false}));\n const checked=bindable<boolean>(()=>({defaultValue:internalChecked.get(),value:prop(\"checked\")??internalChecked.get(),onChange(value){if(prop(\"checked\")===undefined)internalChecked.set(value);prop(\"onToggle\")?.(value);}}));\n return {checked,internalChecked};\n },\n refs:()=>({active:false,generation:0}),effects:[\"lifecycle\"],\n on:{\"CHECKED.TOGGLE\":{actions:[\"toggle\"]},\"CHECKED.SET\":{actions:[\"setChecked\"]}},\n implementations:{effects:{lifecycle({refs}){refs.set(\"active\",true);refs.set(\"generation\",refs.get(\"generation\")+1);return()=>{refs.set(\"active\",false);refs.set(\"generation\",refs.get(\"generation\")+1);};}},actions:{\n toggle(params){request(params,()=>!params.context.get(\"checked\"));},\n setChecked(params){const event=params.event;if(event.type===\"CHECKED.SET\" && typeof event.checked===\"boolean\")request(params,()=>event.checked);},\n }},\n});\nexport interface QwSwitchApi<T extends PropTypes=PropTypes>{checked:boolean;toggle():void;setChecked(checked:boolean):void;getSnapshot():SwitchStateSnapshot;getRootProps(root?:SwitchRootOptions):T[\"button\"];getThumbProps():T[\"element\"]}\nexport function connectSwitch<T extends PropTypes>(service:QwSwitchService,normalize:NormalizeProps<T>,options:SwitchConnectOptions={}):QwSwitchApi<T> {\n const state=resolveSwitchState({checked:service.context.get(\"checked\"),disabled:service.prop(\"disabled\"),readOnly:service.prop(\"readOnly\"),type:service.prop(\"type\")});\n return {checked:state.checked,toggle:()=>service.send({type:\"CHECKED.TOGGLE\"}),setChecked:checked=>service.send({type:\"CHECKED.SET\",checked}),\n getSnapshot:()=>Object.freeze({internalChecked:service.context.get(\"internalChecked\")}),\n getThumbProps:()=>normalize.element({...getSwitchThumbProps()}),\n getRootProps:root=>normalize.button({...getSwitchRootProps(state,root??options.root),onClick(event:SwitchActivationEvent){\n if(service.prop(\"disabled\"))return;\n const callbacks=typeof options.onClick===\"function\"?[options.onClick]:options.onClick??[];\n for(const callback of callbacks)callback(event);\n if(!cancelled(event))service.send({type:\"CHECKED.TOGGLE\",activation:event});\n }}),\n };\n}\n\n/** 生成旋钮属性。 */\nexport function getSwitchThumbProps(): SwitchThumbProps {\n return {\n \"data-scope\": \"switch\",\n \"data-part\": \"thumb\",\n \"aria-hidden\": \"true\",\n };\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Switch 的跨框架行为契约。
|
|
3
|
+
*
|
|
4
|
+
* Core Zag bindable owns controlled/uncontrolled state, requests and click cancellation.
|
|
5
|
+
* Browser button semantics supply keyboard/default form actions; adapters only project getters.
|
|
6
|
+
*/
|
|
7
|
+
import { type Machine, type Service } from "@zag-js/core";
|
|
8
|
+
import type { NormalizeProps, PropTypes } from "@zag-js/types";
|
|
9
|
+
/** Switch 各渲染部位全集(data-part 取值)。 */
|
|
10
|
+
export declare const SWITCH_PARTS: readonly ["root", "thumb"];
|
|
11
|
+
export declare const SWITCH_TYPES: readonly ["button", "submit", "reset"];
|
|
12
|
+
export type SwitchButtonType = (typeof SWITCH_TYPES)[number];
|
|
13
|
+
export type SwitchPart = (typeof SWITCH_PARTS)[number];
|
|
14
|
+
/**
|
|
15
|
+
* QwSwitchProps — 双栈共享的行为契约(全字段可选)。
|
|
16
|
+
* checked 未传时走非受控模式,由Core bindable管理内部状态。
|
|
17
|
+
*/
|
|
18
|
+
export interface QwSwitchProps {
|
|
19
|
+
/** 受控值。未传时走非受控模式。 */
|
|
20
|
+
checked?: boolean;
|
|
21
|
+
/** 非受控初始值,默认 false。仅在 checked 未传时生效。 */
|
|
22
|
+
defaultChecked?: boolean;
|
|
23
|
+
/** 状态变化回调,参数为新的 checked 值。 */
|
|
24
|
+
onToggle?: (checked: boolean) => void;
|
|
25
|
+
/** 禁用状态。 */
|
|
26
|
+
disabled?: boolean;
|
|
27
|
+
/** Prevent switch requests while keeping native focus and explicit submit/reset behavior. */
|
|
28
|
+
readOnly?: boolean;
|
|
29
|
+
/** 原生 button 类型,默认 `button`。 */
|
|
30
|
+
type?: SwitchButtonType;
|
|
31
|
+
}
|
|
32
|
+
/** 适配器唯一可消费的归一化结果。 */
|
|
33
|
+
export interface ResolvedSwitchState {
|
|
34
|
+
checked: boolean;
|
|
35
|
+
disabled: boolean;
|
|
36
|
+
readOnly: boolean;
|
|
37
|
+
type: "button" | "submit" | "reset";
|
|
38
|
+
}
|
|
39
|
+
/** Core 生成、由适配器最后覆盖到根元素的属性。 */
|
|
40
|
+
export interface SwitchRootProps {
|
|
41
|
+
type: "button" | "submit" | "reset";
|
|
42
|
+
role: "switch";
|
|
43
|
+
disabled: boolean;
|
|
44
|
+
"aria-checked": "true" | "false";
|
|
45
|
+
"data-scope": "switch";
|
|
46
|
+
"data-part": "root";
|
|
47
|
+
"data-checked": "true" | "false";
|
|
48
|
+
"data-disabled"?: "true";
|
|
49
|
+
}
|
|
50
|
+
/** 旋钮属性(纯视觉元素)。 */
|
|
51
|
+
export interface SwitchThumbProps {
|
|
52
|
+
"data-scope": "switch";
|
|
53
|
+
"data-part": "thumb";
|
|
54
|
+
"aria-hidden": "true";
|
|
55
|
+
}
|
|
56
|
+
/** 将公开输入归一化为唯一的跨框架状态。 */
|
|
57
|
+
export declare function resolveSwitchState(props?: QwSwitchProps): ResolvedSwitchState;
|
|
58
|
+
/** 将归一化结果转成 root 属性。 */
|
|
59
|
+
export interface SwitchRootOptions {
|
|
60
|
+
accessibleLabel?: string;
|
|
61
|
+
labelledBy?: string;
|
|
62
|
+
describedBy?: string;
|
|
63
|
+
name?: string;
|
|
64
|
+
value?: string;
|
|
65
|
+
form?: string;
|
|
66
|
+
title?: string;
|
|
67
|
+
lang?: string;
|
|
68
|
+
dir?: string;
|
|
69
|
+
hidden?: boolean;
|
|
70
|
+
}
|
|
71
|
+
export declare function getSwitchRootProps(state: ResolvedSwitchState, options?: SwitchRootOptions): SwitchRootProps & {
|
|
72
|
+
"aria-readonly"?: "true";
|
|
73
|
+
"data-readonly"?: "true";
|
|
74
|
+
"aria-label"?: string;
|
|
75
|
+
"aria-labelledby"?: string;
|
|
76
|
+
"aria-describedby"?: string;
|
|
77
|
+
name?: string;
|
|
78
|
+
value?: string;
|
|
79
|
+
form?: string;
|
|
80
|
+
title?: string;
|
|
81
|
+
lang?: string;
|
|
82
|
+
dir?: string;
|
|
83
|
+
hidden?: boolean;
|
|
84
|
+
};
|
|
85
|
+
/** Common cancellation contract; framework/native events are transported without copying state rules. */
|
|
86
|
+
export interface SwitchActivationEvent {
|
|
87
|
+
readonly defaultPrevented: boolean;
|
|
88
|
+
readonly nativeEvent?: {
|
|
89
|
+
readonly defaultPrevented: boolean;
|
|
90
|
+
};
|
|
91
|
+
preventDefault?: () => void;
|
|
92
|
+
}
|
|
93
|
+
export type SwitchClickHandler = (event: SwitchActivationEvent) => void;
|
|
94
|
+
export interface SwitchConnectOptions {
|
|
95
|
+
root?: SwitchRootOptions;
|
|
96
|
+
onClick?: SwitchClickHandler | readonly SwitchClickHandler[];
|
|
97
|
+
}
|
|
98
|
+
/** Independent uncontrolled memory transported by adapter lifecycle snapshots. */
|
|
99
|
+
export interface SwitchStateSnapshot {
|
|
100
|
+
readonly internalChecked: boolean;
|
|
101
|
+
}
|
|
102
|
+
/** Keep undefined checked uncontrolled, rather than filling it with a default. */
|
|
103
|
+
export declare function createSwitchProps(props?: QwSwitchProps): QwSwitchProps;
|
|
104
|
+
export interface QwSwitchSchema {
|
|
105
|
+
props: QwSwitchProps & {
|
|
106
|
+
initialSnapshot?: SwitchStateSnapshot;
|
|
107
|
+
};
|
|
108
|
+
context: {
|
|
109
|
+
checked: boolean;
|
|
110
|
+
internalChecked: boolean;
|
|
111
|
+
};
|
|
112
|
+
state: "ready";
|
|
113
|
+
action: "toggle" | "setChecked";
|
|
114
|
+
refs: {
|
|
115
|
+
active: boolean;
|
|
116
|
+
generation: number;
|
|
117
|
+
};
|
|
118
|
+
effect: "lifecycle";
|
|
119
|
+
event: {
|
|
120
|
+
type: "CHECKED.TOGGLE";
|
|
121
|
+
activation?: SwitchActivationEvent;
|
|
122
|
+
} | {
|
|
123
|
+
type: "CHECKED.SET";
|
|
124
|
+
checked: boolean;
|
|
125
|
+
activation?: SwitchActivationEvent;
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
export type QwSwitchMachine = Machine<QwSwitchSchema>;
|
|
129
|
+
export type QwSwitchService = Service<QwSwitchSchema>;
|
|
130
|
+
/** Shared request processing; final event cancellation includes later bubble listeners. */
|
|
131
|
+
export declare const switchMachine: QwSwitchMachine;
|
|
132
|
+
export interface QwSwitchApi<T extends PropTypes = PropTypes> {
|
|
133
|
+
checked: boolean;
|
|
134
|
+
toggle(): void;
|
|
135
|
+
setChecked(checked: boolean): void;
|
|
136
|
+
getSnapshot(): SwitchStateSnapshot;
|
|
137
|
+
getRootProps(root?: SwitchRootOptions): T["button"];
|
|
138
|
+
getThumbProps(): T["element"];
|
|
139
|
+
}
|
|
140
|
+
export declare function connectSwitch<T extends PropTypes>(service: QwSwitchService, normalize: NormalizeProps<T>, options?: SwitchConnectOptions): QwSwitchApi<T>;
|
|
141
|
+
/** 生成旋钮属性。 */
|
|
142
|
+
export declare function getSwitchThumbProps(): SwitchThumbProps;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./tabbar.js";
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
//#region src/tabbar/tabbar.ts
|
|
2
|
+
/**
|
|
3
|
+
* TabBar 的跨框架行为契约。
|
|
4
|
+
*
|
|
5
|
+
* TabBar 是无状态的 Prototype A 底部操作栏:白底容器 + 顶部 1px 分割线 +
|
|
6
|
+
* 1–N 个等宽 L 号按钮(组合已交付的 Button)。这里仅归一化公开 props 与
|
|
7
|
+
* item → Button 的档位映射,React/Vue 适配器不得复制可见性、默认档位或
|
|
8
|
+
* 映射规则。
|
|
9
|
+
*/
|
|
10
|
+
const TABBAR_ITEM_VARIANTS = ["primary", "secondary"];
|
|
11
|
+
const TABBAR_ITEM_TONES = ["brand", "neutral"];
|
|
12
|
+
const TABBAR_PARTS = ["root"];
|
|
13
|
+
/** 将公开输入归一化为唯一的跨框架状态;items 缺省/空 → 不可见。 */
|
|
14
|
+
function resolveTabBarState(props = {}) {
|
|
15
|
+
const items = (props.items ?? []).map((item) => ({
|
|
16
|
+
text: item.text,
|
|
17
|
+
variant: item.variant ?? "primary",
|
|
18
|
+
tone: item.tone ?? "brand",
|
|
19
|
+
disabled: item.disabled ?? false,
|
|
20
|
+
loading: item.loading ?? false,
|
|
21
|
+
...item.onClick ? { onClick: item.onClick } : {}
|
|
22
|
+
}));
|
|
23
|
+
return {
|
|
24
|
+
visible: items.length > 0,
|
|
25
|
+
count: items.length,
|
|
26
|
+
items
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
/** 将归一化结果转成 root 属性。 */
|
|
30
|
+
function getTabBarRootProps(state) {
|
|
31
|
+
return {
|
|
32
|
+
"data-scope": "tabbar",
|
|
33
|
+
"data-part": "root",
|
|
34
|
+
"data-count": String(state.count)
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
/** 将单个操作项映射为 Button props(档位收口,适配器不得覆盖)。 */
|
|
38
|
+
function getTabBarItemButtonProps(item) {
|
|
39
|
+
return {
|
|
40
|
+
variant: item.variant === "primary" ? "solid" : "soft",
|
|
41
|
+
tone: item.tone,
|
|
42
|
+
size: "l",
|
|
43
|
+
disabled: item.disabled,
|
|
44
|
+
loading: item.loading
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
function resolveTabBarNavigation(props) {
|
|
48
|
+
return {
|
|
49
|
+
navigation: props.mode === "navigation",
|
|
50
|
+
tag: props.mode === "navigation" ? "nav" : "div",
|
|
51
|
+
items: props.mode === "navigation" ? [...props.navigationItems ?? []] : []
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
function getTabBarNavigationRootProps(props) {
|
|
55
|
+
return {
|
|
56
|
+
"data-scope": "tabbar",
|
|
57
|
+
"data-part": "root",
|
|
58
|
+
"data-mode": "navigation",
|
|
59
|
+
"aria-label": props.label ?? "Page navigation"
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
function getTabBarNavigationItemTag(item) {
|
|
63
|
+
return item.href ? "a" : "button";
|
|
64
|
+
}
|
|
65
|
+
function getTabBarNavigationItemProps(props, item) {
|
|
66
|
+
return {
|
|
67
|
+
"data-scope": "tabbar",
|
|
68
|
+
"data-part": "navigation-item",
|
|
69
|
+
"data-value": item.id,
|
|
70
|
+
"data-active": props.value === item.id ? "true" : "false",
|
|
71
|
+
...props.value === item.id ? { "aria-current": "page" } : {},
|
|
72
|
+
...item.href ? item.disabled ? {
|
|
73
|
+
role: "link",
|
|
74
|
+
"aria-disabled": true,
|
|
75
|
+
tabIndex: -1
|
|
76
|
+
} : { href: item.href } : {
|
|
77
|
+
type: "button",
|
|
78
|
+
disabled: item.disabled ?? false
|
|
79
|
+
},
|
|
80
|
+
onClick(event) {
|
|
81
|
+
if (props.mode !== "navigation" || item.disabled) {
|
|
82
|
+
event.preventDefault();
|
|
83
|
+
return;
|
|
84
|
+
}
|
|
85
|
+
props.onValueChange?.({
|
|
86
|
+
value: item.id,
|
|
87
|
+
previousValue: props.value
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
//#endregion
|
|
93
|
+
export { TABBAR_ITEM_TONES, TABBAR_ITEM_VARIANTS, TABBAR_PARTS, getTabBarItemButtonProps, getTabBarNavigationItemProps, getTabBarNavigationItemTag, getTabBarNavigationRootProps, getTabBarRootProps, resolveTabBarNavigation, resolveTabBarState };
|
|
94
|
+
|
|
95
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../src/tabbar/tabbar.ts"],"sourcesContent":["/**\n * TabBar 的跨框架行为契约。\n *\n * TabBar 是无状态的 Prototype A 底部操作栏:白底容器 + 顶部 1px 分割线 +\n * 1–N 个等宽 L 号按钮(组合已交付的 Button)。这里仅归一化公开 props 与\n * item → Button 的档位映射,React/Vue 适配器不得复制可见性、默认档位或\n * 映射规则。\n */\n\nexport const TABBAR_ITEM_VARIANTS = [\"primary\", \"secondary\"] as const;\nexport const TABBAR_ITEM_TONES = [\"brand\", \"neutral\"] as const;\nexport const TABBAR_PARTS = [\"root\"] as const;\n\nexport type TabBarItemVariant = (typeof TABBAR_ITEM_VARIANTS)[number];\nexport type TabBarItemTone = (typeof TABBAR_ITEM_TONES)[number];\nexport type TabBarPart = (typeof TABBAR_PARTS)[number];\n\n/** 单个操作项声明;双栈共享,框架特有的事件通道不进入 Core。 */\nexport interface QwTabBarItemProps {\n /** 按钮文案,同时作为可访问名。 */\n text: string;\n /** 视觉档位,默认 `primary`。primary→Button solid;secondary→Button soft。 */\n variant?: TabBarItemVariant;\n /** 语气,默认 `brand`。 */\n tone?: TabBarItemTone;\n /** 原生禁用状态。 */\n disabled?: boolean;\n /** 忙碌态,沿用 Button loading 契约。 */\n loading?: boolean;\n /** 点击(含键盘激活)回调。 */\n onClick?: () => void;\n}\n\n/** 双栈共享的标量 props。 */\nexport interface QwTabBarProps {\n /** Beta: opt-in page navigation; the default remains the legacy action bar. */\n mode?: \"actions\" | \"navigation\";\n navigationItems?: readonly TabBarNavigationItem[];\n /** Controlled active page id; requesting a value never changes it automatically. */\n value?: string;\n /** Navigation landmark accessible name. */\n label?: string;\n onValueChange?: (details: TabBarValueChangeDetails) => void;\n /** 操作项列表;缺省或空数组时组件不渲染。 */\n items?: readonly QwTabBarItemProps[];\n}\n\n/** 逐项归一化结果。 */\nexport interface ResolvedTabBarItemState {\n text: string;\n variant: TabBarItemVariant;\n tone: TabBarItemTone;\n disabled: boolean;\n loading: boolean;\n onClick?: () => void;\n}\n\n/** 适配器唯一可消费的归一化结果。 */\nexport interface ResolvedTabBarState {\n visible: boolean;\n count: number;\n items: ResolvedTabBarItemState[];\n}\n\n/** Core 生成、由适配器摊到根元素的属性。 */\nexport interface TabBarRootProps {\n \"data-scope\": \"tabbar\";\n \"data-part\": \"root\";\n \"data-count\": string;\n}\n\n/** item → Button 的档位映射结果(size 固定 l)。 */\nexport interface TabBarItemButtonProps {\n variant: \"solid\" | \"soft\";\n tone: \"brand\" | \"neutral\";\n size: \"l\";\n disabled: boolean;\n loading: boolean;\n}\n\n/** 将公开输入归一化为唯一的跨框架状态;items 缺省/空 → 不可见。 */\nexport function resolveTabBarState(props: QwTabBarProps = {}): ResolvedTabBarState {\n const items = (props.items ?? []).map((item) => ({\n text: item.text,\n variant: item.variant ?? \"primary\",\n tone: item.tone ?? \"brand\",\n disabled: item.disabled ?? false,\n loading: item.loading ?? false,\n ...(item.onClick ? { onClick: item.onClick } : {}),\n }));\n return {\n visible: items.length > 0,\n count: items.length,\n items,\n };\n}\n\n/** 将归一化结果转成 root 属性。 */\nexport function getTabBarRootProps(state: ResolvedTabBarState): TabBarRootProps {\n return {\n \"data-scope\": \"tabbar\",\n \"data-part\": \"root\",\n \"data-count\": String(state.count),\n };\n}\n\n/** 将单个操作项映射为 Button props(档位收口,适配器不得覆盖)。 */\nexport function getTabBarItemButtonProps(item: ResolvedTabBarItemState): TabBarItemButtonProps {\n return {\n variant: item.variant === \"primary\" ? \"solid\" : \"soft\",\n tone: item.tone,\n size: \"l\",\n disabled: item.disabled,\n loading: item.loading,\n };\n}\n\n/** Beta page navigation item. icon is a decorative text glyph, not an icon asset name. */\nexport interface TabBarNavigationItem { id: string; text: string; icon?: string; iconSrc?: string; href?: string; disabled?: boolean }\nexport interface TabBarValueChangeDetails { value: string; previousValue: string | undefined }\nexport interface TabBarNavigationItemProps {\n \"data-scope\": \"tabbar\";\n \"data-part\": \"navigation-item\";\n \"data-value\": string;\n \"data-active\": \"true\" | \"false\";\n \"aria-current\"?: \"page\";\n \"aria-disabled\"?: true;\n disabled?: boolean;\n href?: string;\n role?: \"link\";\n tabIndex?: number;\n type?: \"button\";\n onClick: (event: { preventDefault(): void }) => void;\n}\nexport function resolveTabBarNavigation(props: QwTabBarProps) {\n return {\n navigation: props.mode === \"navigation\",\n tag: props.mode === \"navigation\" ? \"nav\" as const : \"div\" as const,\n items: props.mode === \"navigation\" ? [...(props.navigationItems ?? [])] : [],\n };\n}\nexport function getTabBarNavigationRootProps(props: QwTabBarProps) {\n return { \"data-scope\": \"tabbar\", \"data-part\": \"root\", \"data-mode\": \"navigation\", \"aria-label\": props.label ?? \"Page navigation\" } as const;\n}\nexport function getTabBarNavigationItemTag(item: TabBarNavigationItem): \"a\" | \"button\" { return item.href ? \"a\" : \"button\"; }\nexport function getTabBarNavigationItemProps(props: QwTabBarProps, item: TabBarNavigationItem): TabBarNavigationItemProps {\n return {\n \"data-scope\": \"tabbar\", \"data-part\": \"navigation-item\", \"data-value\": item.id, \"data-active\": props.value === item.id ? \"true\" : \"false\",\n ...(props.value === item.id ? { \"aria-current\": \"page\" as const } : {}),\n ...(item.href ? item.disabled ? { role: \"link\" as const, \"aria-disabled\": true as const, tabIndex: -1 } : { href: item.href }\n : { type: \"button\" as const, disabled: item.disabled ?? false }),\n onClick(event) {\n if (props.mode !== \"navigation\" || item.disabled) { event.preventDefault(); return; }\n props.onValueChange?.({ value: item.id, previousValue: props.value });\n },\n };\n}\n"],"mappings":";;;;;;;;;AASA,MAAa,uBAAuB,CAAC,WAAW,WAAW;AAC3D,MAAa,oBAAoB,CAAC,SAAS,SAAS;AACpD,MAAa,eAAe,CAAC,MAAM;;AAsEnC,SAAgB,mBAAmB,QAAuB,CAAC,GAAwB;CACjF,MAAM,SAAS,MAAM,SAAS,CAAC,EAAA,CAAG,KAAK,UAAU;EAC/C,MAAM,KAAK;EACX,SAAS,KAAK,WAAW;EACzB,MAAM,KAAK,QAAQ;EACnB,UAAU,KAAK,YAAY;EAC3B,SAAS,KAAK,WAAW;EACzB,GAAI,KAAK,UAAU,EAAE,SAAS,KAAK,QAAQ,IAAI,CAAC;CAClD,EAAE;CACF,OAAO;EACL,SAAS,MAAM,SAAS;EACxB,OAAO,MAAM;EACb;CACF;AACF;;AAGA,SAAgB,mBAAmB,OAA6C;CAC9E,OAAO;EACL,cAAc;EACd,aAAa;EACb,cAAc,OAAO,MAAM,KAAK;CAClC;AACF;;AAGA,SAAgB,yBAAyB,MAAsD;CAC7F,OAAO;EACL,SAAS,KAAK,YAAY,YAAY,UAAU;EAChD,MAAM,KAAK;EACX,MAAM;EACN,UAAU,KAAK;EACf,SAAS,KAAK;CAChB;AACF;AAmBA,SAAgB,wBAAwB,OAAsB;CAC5D,OAAO;EACL,YAAY,MAAM,SAAS;EAC3B,KAAK,MAAM,SAAS,eAAe,QAAiB;EACpD,OAAO,MAAM,SAAS,eAAe,CAAC,GAAI,MAAM,mBAAmB,CAAC,CAAE,IAAI,CAAC;CAC7E;AACF;AACA,SAAgB,6BAA6B,OAAsB;CACjE,OAAO;EAAE,cAAc;EAAU,aAAa;EAAQ,aAAa;EAAc,cAAc,MAAM,SAAS;CAAkB;AAClI;AACA,SAAgB,2BAA2B,MAA4C;CAAE,OAAO,KAAK,OAAO,MAAM;AAAU;AAC5H,SAAgB,6BAA6B,OAAsB,MAAuD;CACxH,OAAO;EACL,cAAc;EAAU,aAAa;EAAmB,cAAc,KAAK;EAAI,eAAe,MAAM,UAAU,KAAK,KAAK,SAAS;EACjI,GAAI,MAAM,UAAU,KAAK,KAAK,EAAE,gBAAgB,OAAgB,IAAI,CAAC;EACrE,GAAI,KAAK,OAAO,KAAK,WAAW;GAAE,MAAM;GAAiB,iBAAiB;GAAe,UAAU;EAAG,IAAI,EAAE,MAAM,KAAK,KAAK,IACxH;GAAE,MAAM;GAAmB,UAAU,KAAK,YAAY;EAAM;EAChE,QAAQ,OAAO;GACb,IAAI,MAAM,SAAS,gBAAgB,KAAK,UAAU;IAAE,MAAM,eAAe;IAAG;GAAQ;GACpF,MAAM,gBAAgB;IAAE,OAAO,KAAK;IAAI,eAAe,MAAM;GAAM,CAAC;EACtE;CACF;AACF"}
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* TabBar 的跨框架行为契约。
|
|
3
|
+
*
|
|
4
|
+
* TabBar 是无状态的 Prototype A 底部操作栏:白底容器 + 顶部 1px 分割线 +
|
|
5
|
+
* 1–N 个等宽 L 号按钮(组合已交付的 Button)。这里仅归一化公开 props 与
|
|
6
|
+
* item → Button 的档位映射,React/Vue 适配器不得复制可见性、默认档位或
|
|
7
|
+
* 映射规则。
|
|
8
|
+
*/
|
|
9
|
+
export declare const TABBAR_ITEM_VARIANTS: readonly ["primary", "secondary"];
|
|
10
|
+
export declare const TABBAR_ITEM_TONES: readonly ["brand", "neutral"];
|
|
11
|
+
export declare const TABBAR_PARTS: readonly ["root"];
|
|
12
|
+
export type TabBarItemVariant = (typeof TABBAR_ITEM_VARIANTS)[number];
|
|
13
|
+
export type TabBarItemTone = (typeof TABBAR_ITEM_TONES)[number];
|
|
14
|
+
export type TabBarPart = (typeof TABBAR_PARTS)[number];
|
|
15
|
+
/** 单个操作项声明;双栈共享,框架特有的事件通道不进入 Core。 */
|
|
16
|
+
export interface QwTabBarItemProps {
|
|
17
|
+
/** 按钮文案,同时作为可访问名。 */
|
|
18
|
+
text: string;
|
|
19
|
+
/** 视觉档位,默认 `primary`。primary→Button solid;secondary→Button soft。 */
|
|
20
|
+
variant?: TabBarItemVariant;
|
|
21
|
+
/** 语气,默认 `brand`。 */
|
|
22
|
+
tone?: TabBarItemTone;
|
|
23
|
+
/** 原生禁用状态。 */
|
|
24
|
+
disabled?: boolean;
|
|
25
|
+
/** 忙碌态,沿用 Button loading 契约。 */
|
|
26
|
+
loading?: boolean;
|
|
27
|
+
/** 点击(含键盘激活)回调。 */
|
|
28
|
+
onClick?: () => void;
|
|
29
|
+
}
|
|
30
|
+
/** 双栈共享的标量 props。 */
|
|
31
|
+
export interface QwTabBarProps {
|
|
32
|
+
/** Beta: opt-in page navigation; the default remains the legacy action bar. */
|
|
33
|
+
mode?: "actions" | "navigation";
|
|
34
|
+
navigationItems?: readonly TabBarNavigationItem[];
|
|
35
|
+
/** Controlled active page id; requesting a value never changes it automatically. */
|
|
36
|
+
value?: string;
|
|
37
|
+
/** Navigation landmark accessible name. */
|
|
38
|
+
label?: string;
|
|
39
|
+
onValueChange?: (details: TabBarValueChangeDetails) => void;
|
|
40
|
+
/** 操作项列表;缺省或空数组时组件不渲染。 */
|
|
41
|
+
items?: readonly QwTabBarItemProps[];
|
|
42
|
+
}
|
|
43
|
+
/** 逐项归一化结果。 */
|
|
44
|
+
export interface ResolvedTabBarItemState {
|
|
45
|
+
text: string;
|
|
46
|
+
variant: TabBarItemVariant;
|
|
47
|
+
tone: TabBarItemTone;
|
|
48
|
+
disabled: boolean;
|
|
49
|
+
loading: boolean;
|
|
50
|
+
onClick?: () => void;
|
|
51
|
+
}
|
|
52
|
+
/** 适配器唯一可消费的归一化结果。 */
|
|
53
|
+
export interface ResolvedTabBarState {
|
|
54
|
+
visible: boolean;
|
|
55
|
+
count: number;
|
|
56
|
+
items: ResolvedTabBarItemState[];
|
|
57
|
+
}
|
|
58
|
+
/** Core 生成、由适配器摊到根元素的属性。 */
|
|
59
|
+
export interface TabBarRootProps {
|
|
60
|
+
"data-scope": "tabbar";
|
|
61
|
+
"data-part": "root";
|
|
62
|
+
"data-count": string;
|
|
63
|
+
}
|
|
64
|
+
/** item → Button 的档位映射结果(size 固定 l)。 */
|
|
65
|
+
export interface TabBarItemButtonProps {
|
|
66
|
+
variant: "solid" | "soft";
|
|
67
|
+
tone: "brand" | "neutral";
|
|
68
|
+
size: "l";
|
|
69
|
+
disabled: boolean;
|
|
70
|
+
loading: boolean;
|
|
71
|
+
}
|
|
72
|
+
/** 将公开输入归一化为唯一的跨框架状态;items 缺省/空 → 不可见。 */
|
|
73
|
+
export declare function resolveTabBarState(props?: QwTabBarProps): ResolvedTabBarState;
|
|
74
|
+
/** 将归一化结果转成 root 属性。 */
|
|
75
|
+
export declare function getTabBarRootProps(state: ResolvedTabBarState): TabBarRootProps;
|
|
76
|
+
/** 将单个操作项映射为 Button props(档位收口,适配器不得覆盖)。 */
|
|
77
|
+
export declare function getTabBarItemButtonProps(item: ResolvedTabBarItemState): TabBarItemButtonProps;
|
|
78
|
+
/** Beta page navigation item. icon is a decorative text glyph, not an icon asset name. */
|
|
79
|
+
export interface TabBarNavigationItem {
|
|
80
|
+
id: string;
|
|
81
|
+
text: string;
|
|
82
|
+
icon?: string;
|
|
83
|
+
iconSrc?: string;
|
|
84
|
+
href?: string;
|
|
85
|
+
disabled?: boolean;
|
|
86
|
+
}
|
|
87
|
+
export interface TabBarValueChangeDetails {
|
|
88
|
+
value: string;
|
|
89
|
+
previousValue: string | undefined;
|
|
90
|
+
}
|
|
91
|
+
export interface TabBarNavigationItemProps {
|
|
92
|
+
"data-scope": "tabbar";
|
|
93
|
+
"data-part": "navigation-item";
|
|
94
|
+
"data-value": string;
|
|
95
|
+
"data-active": "true" | "false";
|
|
96
|
+
"aria-current"?: "page";
|
|
97
|
+
"aria-disabled"?: true;
|
|
98
|
+
disabled?: boolean;
|
|
99
|
+
href?: string;
|
|
100
|
+
role?: "link";
|
|
101
|
+
tabIndex?: number;
|
|
102
|
+
type?: "button";
|
|
103
|
+
onClick: (event: {
|
|
104
|
+
preventDefault(): void;
|
|
105
|
+
}) => void;
|
|
106
|
+
}
|
|
107
|
+
export declare function resolveTabBarNavigation(props: QwTabBarProps): {
|
|
108
|
+
navigation: boolean;
|
|
109
|
+
tag: "div" | "nav";
|
|
110
|
+
items: TabBarNavigationItem[];
|
|
111
|
+
};
|
|
112
|
+
export declare function getTabBarNavigationRootProps(props: QwTabBarProps): {
|
|
113
|
+
readonly "data-scope": "tabbar";
|
|
114
|
+
readonly "data-part": "root";
|
|
115
|
+
readonly "data-mode": "navigation";
|
|
116
|
+
readonly "aria-label": string;
|
|
117
|
+
};
|
|
118
|
+
export declare function getTabBarNavigationItemTag(item: TabBarNavigationItem): "a" | "button";
|
|
119
|
+
export declare function getTabBarNavigationItemProps(props: QwTabBarProps, item: TabBarNavigationItem): TabBarNavigationItemProps;
|
package/dist/tabs/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { connect, machine as tabsMachine } from "@zag-js/tabs";
|
|
1
|
+
import { connect as connect$1, machine as tabsMachine } from "@zag-js/tabs";
|
|
2
2
|
//#region src/tabs/tabs.ts
|
|
3
3
|
/**
|
|
4
4
|
* Tabs 契约 — 原型 B(有状态),core 包裹 zag.js tabs machine。
|
|
@@ -13,6 +13,27 @@ const TABS_LEVELS = ["primary", "secondary"];
|
|
|
13
13
|
const TABS_VARIANTS = ["text", "button"];
|
|
14
14
|
/** 字号全集:仅 primary 生效,"14" / "16"(默认)。 */
|
|
15
15
|
const TABS_SIZES = ["14", "16"];
|
|
16
|
+
/** Nonempty all-disabled lists retain native keyboard scrolling without activating a trigger. */
|
|
17
|
+
function connect(service, normalize) {
|
|
18
|
+
const api = connect$1(service, normalize);
|
|
19
|
+
return {
|
|
20
|
+
...api,
|
|
21
|
+
getListProps(items) {
|
|
22
|
+
if (!items?.length || !items.every((item) => item.disabled)) return api.getListProps();
|
|
23
|
+
return connect$1(service, {
|
|
24
|
+
...normalize,
|
|
25
|
+
element(raw) {
|
|
26
|
+
const props = {
|
|
27
|
+
...raw,
|
|
28
|
+
tabIndex: 0
|
|
29
|
+
};
|
|
30
|
+
delete props.onKeyDown;
|
|
31
|
+
return normalize.element(props);
|
|
32
|
+
}
|
|
33
|
+
}).getListProps();
|
|
34
|
+
}
|
|
35
|
+
};
|
|
36
|
+
}
|
|
16
37
|
/**
|
|
17
38
|
* 把 QwTabsProps 的行为 props 转成 zag tabs machine 的 props (默认值收口 + 命名 rebrand)。
|
|
18
39
|
* 视觉 props(level/variant/size)不出现在返回值中——它们是适配层 data-* 属性。
|
package/dist/tabs/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../../src/tabs/tabs.ts"],"sourcesContent":["import type
|
|
1
|
+
{"version":3,"file":"index.js","names":["zagConnect"],"sources":["../../src/tabs/tabs.ts"],"sourcesContent":["import { connect as zagConnect, type Api as ZagTabsApi, type Props as ZagTabsProps, type Service as ZagTabsService, type ValueChangeDetails } from \"@zag-js/tabs\";\nimport type { NormalizeProps, PropTypes } from \"@zag-js/types\";\n\n/**\n * Tabs 契约 — 原型 B(有状态),core 包裹 zag.js tabs machine。\n * 行为 props 进 createTabsProps → zag context;视觉 props(level/variant/size)\n * 不进 machine,由适配层挂 data-* 属性驱动 CSS。\n *\n * 枚举以运行时常量数组为唯一事实源(类型从常量推导),__test__ 直接锁死词表。\n */\n\n/** 导航层级全集:primary 一级导航(默认)/ secondary 二级导航。 */\nexport const TABS_LEVELS = [\"primary\", \"secondary\"] as const;\nexport type TabsLevel = (typeof TABS_LEVELS)[number];\n\n/** 视觉形态全集:text 纯文本(默认)/ button 按钮。button 仅 secondary 支持。 */\nexport const TABS_VARIANTS = [\"text\", \"button\"] as const;\nexport type TabsVariant = (typeof TABS_VARIANTS)[number];\n\n/** 字号全集:仅 primary 生效,\"14\" / \"16\"(默认)。 */\nexport const TABS_SIZES = [\"14\", \"16\"] as const;\nexport type TabsSize = (typeof TABS_SIZES)[number];\n\n/**\n * QwTabsProps — 双栈共享的行为 + 视觉契约。\n * 行为 props(进 createTabsProps → zag machine):\n * - loop(默认 true)→ zag loopFocus;\n * - value / defaultValue / activationMode 透传;\n * - onValueChange 适配 zag details。\n * 视觉 props(不进 machine,适配层挂 data-*):\n * - level / variant / size。\n */\nexport interface QwTabsProps {\n /** 唯一 id 前缀;不传由适配层生成 (SSR/CSR 一致)。 */\n id?: string;\n /** 受控当前项。 */\n value?: string | null;\n /** 非受控初值。 */\n defaultValue?: string | null;\n /** 激活模式,默认 automatic(聚焦即激活)。 */\n activationMode?: \"manual\" | \"automatic\";\n /** 方向键首尾循环,默认 true (zag 原名 loopFocus)。 */\n loop?: boolean;\n /** 选中项变化回调;zag 原生 onValueChange。 */\n onValueChange?: (e: { value: string }) => void;\n /** 导航层级,默认 primary。 */\n level?: TabsLevel;\n /** 视觉形态,默认 text。level=primary 时强制 text。 */\n variant?: TabsVariant;\n /** 字号,默认 \"16\"。仅 level=primary 生效。 */\n size?: TabsSize;\n}\n\n/** The Zag machine remains the sole selected-value/focus owner. */\nexport { machine as tabsMachine } from \"@zag-js/tabs\";\n\n/** Shared list-props transport; omitted item information keeps the original getter. */\nexport type QwTabsApi<T extends PropTypes = PropTypes> = Omit<ZagTabsApi<T>, \"getListProps\"> & {\n getListProps(items?: readonly { disabled?: boolean }[]): T[\"element\"];\n};\n\n/** Nonempty all-disabled lists retain native keyboard scrolling without activating a trigger. */\nexport function connect<T extends PropTypes>(service: ZagTabsService, normalize: NormalizeProps<T>): QwTabsApi<T> {\n const api = zagConnect(service, normalize);\n return {\n ...api,\n getListProps(items) {\n if (!items?.length || !items.every(item => item.disabled)) return api.getListProps();\n return zagConnect(service, {\n ...normalize,\n element(raw) {\n const props = { ...raw, tabIndex: 0 };\n delete props.onKeyDown;\n return normalize.element(props);\n },\n }).getListProps();\n },\n };\n}\n\n/**\n * 把 QwTabsProps 的行为 props 转成 zag tabs machine 的 props (默认值收口 + 命名 rebrand)。\n * 视觉 props(level/variant/size)不出现在返回值中——它们是适配层 data-* 属性。\n * 用法:`useMachine(tabsMachine, createTabsProps(props))`。\n */\nexport function createTabsProps(props: QwTabsProps = {}): Partial<ZagTabsProps> {\n const ctx: Partial<ZagTabsProps> = {\n id: props.id,\n value: props.value,\n defaultValue: props.defaultValue,\n activationMode: props.activationMode,\n loopFocus: props.loop !== false,\n };\n\n if (props.onValueChange) {\n const cb = props.onValueChange;\n ctx.onValueChange = (d: ValueChangeDetails) => cb({ value: d.value });\n }\n\n return ctx;\n}\n"],"mappings":";;;;;;;;;;AAYA,MAAa,cAAc,CAAC,WAAW,WAAW;;AAIlD,MAAa,gBAAgB,CAAC,QAAQ,QAAQ;;AAI9C,MAAa,aAAa,CAAC,MAAM,IAAI;;AA0CrC,SAAgB,QAA6B,SAAyB,WAA4C;CAChH,MAAM,MAAMA,UAAW,SAAS,SAAS;CACzC,OAAO;EACL,GAAG;EACH,aAAa,OAAO;GAClB,IAAI,CAAC,OAAO,UAAU,CAAC,MAAM,OAAM,SAAQ,KAAK,QAAQ,GAAG,OAAO,IAAI,aAAa;GACnF,OAAOA,UAAW,SAAS;IACzB,GAAG;IACH,QAAQ,KAAK;KACX,MAAM,QAAQ;MAAE,GAAG;MAAK,UAAU;KAAE;KACpC,OAAO,MAAM;KACb,OAAO,UAAU,QAAQ,KAAK;IAChC;GACF,CAAC,CAAC,CAAC,aAAa;EAClB;CACF;AACF;;;;;;AAOA,SAAgB,gBAAgB,QAAqB,CAAC,GAA0B;CAC9E,MAAM,MAA6B;EACjC,IAAI,MAAM;EACV,OAAO,MAAM;EACb,cAAc,MAAM;EACpB,gBAAgB,MAAM;EACtB,WAAW,MAAM,SAAS;CAC5B;CAEA,IAAI,MAAM,eAAe;EACvB,MAAM,KAAK,MAAM;EACjB,IAAI,iBAAiB,MAA0B,GAAG,EAAE,OAAO,EAAE,MAAM,CAAC;CACtE;CAEA,OAAO;AACT"}
|