@qw-ui/core 0.3.0-next.40 → 0.3.0-next.43
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 +9 -0
- package/dist/badge/index.js +14 -1
- package/dist/badge/index.js.map +1 -1
- 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 +32 -3
- package/dist/dialog/index.js +58 -3
- 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 +107 -14
- package/dist/index.js +148 -14
- 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/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 +3 -1
- package/dist/search-bar/index.js.map +1 -1
- package/dist/search-bar/search-bar.d.ts +4 -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/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.js +62 -3
- package/dist/stepper/index.js.map +1 -1
- package/dist/stepper/stepper.d.ts +44 -4
- 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.js +135 -10
- package/dist/switch/index.js.map +1 -1
- package/dist/switch/switch.d.ts +93 -6
- package/dist/tabbar/index.js +46 -1
- package/dist/tabbar/index.js.map +1 -1
- package/dist/tabbar/tabbar.d.ts +50 -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 +165 -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 +6 -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 +399 -50
- 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,458 @@
|
|
|
1
|
+
import { createMachine } from "@zag-js/core";
|
|
2
|
+
import { visuallyHiddenStyle } from "@zag-js/dom-query";
|
|
3
|
+
//#region src/upload/upload.ts
|
|
4
|
+
/** Stable DOM parts shared by every adapter. */
|
|
5
|
+
const UPLOAD_PARTS = [
|
|
6
|
+
"root",
|
|
7
|
+
"input",
|
|
8
|
+
"trigger",
|
|
9
|
+
"list",
|
|
10
|
+
"item",
|
|
11
|
+
"preview",
|
|
12
|
+
"name",
|
|
13
|
+
"status",
|
|
14
|
+
"retry",
|
|
15
|
+
"cancel",
|
|
16
|
+
"remove",
|
|
17
|
+
"live"
|
|
18
|
+
];
|
|
19
|
+
const UPLOAD_STATUSES = [
|
|
20
|
+
"pending",
|
|
21
|
+
"uploading",
|
|
22
|
+
"done",
|
|
23
|
+
"error"
|
|
24
|
+
];
|
|
25
|
+
const text = (value, fallback) => typeof value === "string" && value.trim() ? value : fallback;
|
|
26
|
+
const limit = (value) => typeof value === "number" && Number.isFinite(value) && value > 0 ? value : Infinity;
|
|
27
|
+
function resolveUploadState(props = {}) {
|
|
28
|
+
return {
|
|
29
|
+
name: typeof props.name === "string" && props.name ? props.name : void 0,
|
|
30
|
+
accept: typeof props.accept === "string" ? props.accept.trim() : "",
|
|
31
|
+
multiple: !!props.multiple,
|
|
32
|
+
maxCount: Math.floor(limit(props.maxCount)),
|
|
33
|
+
maxSize: limit(props.maxSize),
|
|
34
|
+
preview: props.preview !== false,
|
|
35
|
+
disabled: !!props.disabled,
|
|
36
|
+
readOnly: !!props.readOnly,
|
|
37
|
+
triggerText: text(props.triggerText, "上传文件"),
|
|
38
|
+
removeLabel: text(props.removeLabel, "删除 {name}"),
|
|
39
|
+
retryText: text(props.retryText, "重试"),
|
|
40
|
+
cancelText: text(props.cancelText, "取消"),
|
|
41
|
+
errorText: text(props.errorText, "上传失败"),
|
|
42
|
+
cancelledText: text(props.cancelledText, "已取消")
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
/** Normalize caller items; unknown status becomes done, duplicate or empty ids are dropped. */
|
|
46
|
+
function normalizeUploadItems(items) {
|
|
47
|
+
if (!Array.isArray(items)) return [];
|
|
48
|
+
const seen = /* @__PURE__ */ new Set(), out = [];
|
|
49
|
+
for (const item of items) {
|
|
50
|
+
if (!item || typeof item.id !== "string" || !item.id || seen.has(item.id)) continue;
|
|
51
|
+
seen.add(item.id);
|
|
52
|
+
out.push({
|
|
53
|
+
...item,
|
|
54
|
+
name: typeof item.name === "string" ? item.name : "",
|
|
55
|
+
size: Number.isFinite(item.size) ? item.size : 0,
|
|
56
|
+
type: typeof item.type === "string" ? item.type : "",
|
|
57
|
+
status: UPLOAD_STATUSES.includes(item.status) ? item.status : "done"
|
|
58
|
+
});
|
|
59
|
+
}
|
|
60
|
+
return out;
|
|
61
|
+
}
|
|
62
|
+
/** Native accept semantics: case-insensitive extension, type/* prefix or exact MIME; empty accepts everything. */
|
|
63
|
+
function matchesUploadAccept(file, accept) {
|
|
64
|
+
const tokens = accept.split(",").map((token) => token.trim().toLowerCase()).filter(Boolean);
|
|
65
|
+
if (!tokens.length) return true;
|
|
66
|
+
const name = file.name.toLowerCase(), type = (file.type || "").toLowerCase();
|
|
67
|
+
return tokens.some((token) => token.startsWith(".") ? name.endsWith(token) : token.endsWith("/*") ? type.startsWith(token.slice(0, -1)) : type === token);
|
|
68
|
+
}
|
|
69
|
+
function createUploadProps(props = {}) {
|
|
70
|
+
if (props.id !== void 0 && (typeof props.id !== "string" || !props.id.trim())) throw new TypeError("Upload requires a nonempty instance id when provided");
|
|
71
|
+
if (props.upload !== void 0 && typeof props.upload !== "function") throw new TypeError("Upload upload must be a function returning a Promise");
|
|
72
|
+
return {
|
|
73
|
+
...props,
|
|
74
|
+
value: props.value === void 0 ? void 0 : normalizeUploadItems(props.value),
|
|
75
|
+
defaultValue: normalizeUploadItems(props.defaultValue)
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
const live = (prop) => resolveUploadState({
|
|
79
|
+
name: prop("name"),
|
|
80
|
+
accept: prop("accept"),
|
|
81
|
+
multiple: prop("multiple"),
|
|
82
|
+
maxCount: prop("maxCount"),
|
|
83
|
+
maxSize: prop("maxSize"),
|
|
84
|
+
preview: prop("preview"),
|
|
85
|
+
disabled: prop("disabled"),
|
|
86
|
+
readOnly: prop("readOnly"),
|
|
87
|
+
triggerText: prop("triggerText"),
|
|
88
|
+
removeLabel: prop("removeLabel"),
|
|
89
|
+
retryText: prop("retryText"),
|
|
90
|
+
cancelText: prop("cancelText"),
|
|
91
|
+
errorText: prop("errorText"),
|
|
92
|
+
cancelledText: prop("cancelledText")
|
|
93
|
+
});
|
|
94
|
+
const inputId = (scope) => `upload:${scope.id}:input`;
|
|
95
|
+
const patchItem = (items, id, patch) => items.map((item) => item.id === id ? {
|
|
96
|
+
...item,
|
|
97
|
+
...patch
|
|
98
|
+
} : item);
|
|
99
|
+
const messageOf = (error, fallback) => error instanceof Error && error.message ? error.message : typeof error === "string" && error ? error : fallback;
|
|
100
|
+
function revoke(refs, id) {
|
|
101
|
+
const url = refs.get("urls").get(id);
|
|
102
|
+
if (url !== void 0) {
|
|
103
|
+
refs.get("urls").delete(id);
|
|
104
|
+
try {
|
|
105
|
+
URL.revokeObjectURL(url);
|
|
106
|
+
} catch {}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
function abort(refs, id) {
|
|
110
|
+
const controller = refs.get("controllers").get(id);
|
|
111
|
+
refs.get("controllers").delete(id);
|
|
112
|
+
controller?.abort();
|
|
113
|
+
}
|
|
114
|
+
function start({ refs, prop, send }, id, file) {
|
|
115
|
+
const request = prop("upload");
|
|
116
|
+
if (!request) return;
|
|
117
|
+
const controller = new AbortController();
|
|
118
|
+
refs.get("controllers").set(id, controller);
|
|
119
|
+
const settle = (patch, final) => {
|
|
120
|
+
if (!controller.signal.aborted) send({
|
|
121
|
+
type: "SETTLE",
|
|
122
|
+
id,
|
|
123
|
+
controller,
|
|
124
|
+
patch,
|
|
125
|
+
final
|
|
126
|
+
});
|
|
127
|
+
};
|
|
128
|
+
const onProgress = (percent) => {
|
|
129
|
+
if (Number.isFinite(percent)) settle({ progress: Math.min(100, Math.max(0, Math.round(percent))) }, false);
|
|
130
|
+
};
|
|
131
|
+
let result;
|
|
132
|
+
try {
|
|
133
|
+
result = request(file, {
|
|
134
|
+
signal: controller.signal,
|
|
135
|
+
onProgress
|
|
136
|
+
});
|
|
137
|
+
} catch (error) {
|
|
138
|
+
result = Promise.reject(error);
|
|
139
|
+
}
|
|
140
|
+
Promise.resolve(result).then((value) => {
|
|
141
|
+
const url = value && typeof value === "object" && typeof value.url === "string" ? value.url : void 0;
|
|
142
|
+
settle({
|
|
143
|
+
status: "done",
|
|
144
|
+
error: void 0,
|
|
145
|
+
...url ? { url } : {}
|
|
146
|
+
}, true);
|
|
147
|
+
}, (error) => settle({
|
|
148
|
+
status: "error",
|
|
149
|
+
error: messageOf(error, live(prop).errorText)
|
|
150
|
+
}, true));
|
|
151
|
+
}
|
|
152
|
+
/** Mirror the listed Core-owned files into the native input so form submission matches the list. */
|
|
153
|
+
function mirror({ context, refs, scope }) {
|
|
154
|
+
const input = scope.getById(inputId(scope)), win = input?.ownerDocument.defaultView;
|
|
155
|
+
if (!input || !win || typeof win.DataTransfer !== "function") return;
|
|
156
|
+
try {
|
|
157
|
+
const transfer = new win.DataTransfer();
|
|
158
|
+
for (const item of context.get("value")) {
|
|
159
|
+
const file = refs.get("files").get(item.id);
|
|
160
|
+
if (file) transfer.items.add(file);
|
|
161
|
+
}
|
|
162
|
+
input.files = transfer.files;
|
|
163
|
+
} catch {}
|
|
164
|
+
}
|
|
165
|
+
const editable = (prop) => {
|
|
166
|
+
const state = live(prop);
|
|
167
|
+
return !state.disabled && !state.readOnly;
|
|
168
|
+
};
|
|
169
|
+
/** Core owns validation, the list, caller-upload lifecycle with AbortSignal, object-URL ownership and announcements. */
|
|
170
|
+
const uploadMachine = createMachine({
|
|
171
|
+
props: ({ props }) => createUploadProps(props),
|
|
172
|
+
initialState: () => "ready",
|
|
173
|
+
context: ({ bindable, prop }) => ({
|
|
174
|
+
value: bindable(() => ({
|
|
175
|
+
defaultValue: [...prop("defaultValue") ?? []],
|
|
176
|
+
value: prop("value"),
|
|
177
|
+
onChange(value) {
|
|
178
|
+
prop("onChange")?.({ value });
|
|
179
|
+
}
|
|
180
|
+
})),
|
|
181
|
+
announcement: bindable(() => ({ defaultValue: "" }))
|
|
182
|
+
}),
|
|
183
|
+
refs: () => ({
|
|
184
|
+
files: /* @__PURE__ */ new Map(),
|
|
185
|
+
controllers: /* @__PURE__ */ new Map(),
|
|
186
|
+
urls: /* @__PURE__ */ new Map(),
|
|
187
|
+
seq: 0,
|
|
188
|
+
active: false
|
|
189
|
+
}),
|
|
190
|
+
watch({ track, context, send }) {
|
|
191
|
+
track([() => context.get("value").map((item) => item.id).join("\n")], () => send({ type: "SYNC" }));
|
|
192
|
+
},
|
|
193
|
+
effects: ["lifecycle"],
|
|
194
|
+
on: {
|
|
195
|
+
FILES: { actions: ["add"] },
|
|
196
|
+
REMOVE: { actions: ["remove"] },
|
|
197
|
+
RETRY: { actions: ["retry"] },
|
|
198
|
+
CANCEL: { actions: ["cancel"] },
|
|
199
|
+
SETTLE: { actions: ["settle"] },
|
|
200
|
+
SYNC: { actions: ["sync"] }
|
|
201
|
+
},
|
|
202
|
+
states: { ready: {} },
|
|
203
|
+
implementations: {
|
|
204
|
+
actions: {
|
|
205
|
+
add(params) {
|
|
206
|
+
const { event, context, prop, refs, scope } = params;
|
|
207
|
+
if (event.type !== "FILES" || !editable(prop)) return;
|
|
208
|
+
const state = live(prop), current = context.get("value"), rejections = [], added = [];
|
|
209
|
+
const reserved = new Set(current.map((item) => item.id));
|
|
210
|
+
for (const file of state.multiple ? event.files : event.files.slice(0, 1)) if (!matchesUploadAccept(file, state.accept)) rejections.push({
|
|
211
|
+
file,
|
|
212
|
+
reason: "accept"
|
|
213
|
+
});
|
|
214
|
+
else if (file.size > state.maxSize) rejections.push({
|
|
215
|
+
file,
|
|
216
|
+
reason: "max-size"
|
|
217
|
+
});
|
|
218
|
+
else if (current.length + added.length >= state.maxCount) rejections.push({
|
|
219
|
+
file,
|
|
220
|
+
reason: "max-count"
|
|
221
|
+
});
|
|
222
|
+
else {
|
|
223
|
+
let seq = refs.get("seq"), id;
|
|
224
|
+
do
|
|
225
|
+
id = `${scope.id}-${++seq}`;
|
|
226
|
+
while (reserved.has(id) || refs.get("files").has(id) || refs.get("controllers").has(id) || refs.get("urls").has(id));
|
|
227
|
+
refs.set("seq", seq);
|
|
228
|
+
reserved.add(id);
|
|
229
|
+
added.push({
|
|
230
|
+
file,
|
|
231
|
+
item: {
|
|
232
|
+
id,
|
|
233
|
+
name: file.name,
|
|
234
|
+
size: file.size,
|
|
235
|
+
type: file.type,
|
|
236
|
+
status: prop("upload") ? "uploading" : "done"
|
|
237
|
+
}
|
|
238
|
+
});
|
|
239
|
+
}
|
|
240
|
+
for (const { item, file } of added) {
|
|
241
|
+
refs.get("files").set(item.id, file);
|
|
242
|
+
if (state.preview && file.type.startsWith("image/") && typeof URL.createObjectURL === "function") try {
|
|
243
|
+
refs.get("urls").set(item.id, URL.createObjectURL(file));
|
|
244
|
+
} catch {}
|
|
245
|
+
}
|
|
246
|
+
const parts = [added.length ? `已添加 ${added.length} 个文件` : "", rejections.length ? `${rejections.length} 个文件未添加` : ""].filter(Boolean);
|
|
247
|
+
if (parts.length) context.set("announcement", parts.join(","));
|
|
248
|
+
if (added.length) context.set("value", [...current, ...added.map(({ item }) => item)]);
|
|
249
|
+
if (rejections.length) prop("onReject")?.({ rejections });
|
|
250
|
+
mirror(params);
|
|
251
|
+
for (const { item, file } of added) start(params, item.id, file);
|
|
252
|
+
},
|
|
253
|
+
remove({ event, context, prop, refs }) {
|
|
254
|
+
if (event.type !== "REMOVE" || !editable(prop)) return;
|
|
255
|
+
const item = context.get("value").find((entry) => entry.id === event.id);
|
|
256
|
+
if (!item) return;
|
|
257
|
+
abort(refs, item.id);
|
|
258
|
+
revoke(refs, item.id);
|
|
259
|
+
refs.get("files").delete(item.id);
|
|
260
|
+
context.set("announcement", `已删除 ${item.name}`);
|
|
261
|
+
context.set("value", context.get("value").filter((entry) => entry.id !== item.id));
|
|
262
|
+
},
|
|
263
|
+
retry(params) {
|
|
264
|
+
const { event, context, prop, refs } = params;
|
|
265
|
+
if (event.type !== "RETRY" || !editable(prop) || !prop("upload")) return;
|
|
266
|
+
const item = context.get("value").find((entry) => entry.id === event.id), file = refs.get("files").get(event.id);
|
|
267
|
+
if (!item || item.status !== "error" || !file) return;
|
|
268
|
+
context.set("value", patchItem(context.get("value"), item.id, {
|
|
269
|
+
status: "uploading",
|
|
270
|
+
error: void 0,
|
|
271
|
+
progress: void 0
|
|
272
|
+
}));
|
|
273
|
+
start(params, item.id, file);
|
|
274
|
+
},
|
|
275
|
+
cancel({ event, context, prop, refs }) {
|
|
276
|
+
if (event.type !== "CANCEL" || live(prop).disabled) return;
|
|
277
|
+
const item = context.get("value").find((entry) => entry.id === event.id);
|
|
278
|
+
if (!item || !refs.get("controllers").has(item.id)) return;
|
|
279
|
+
abort(refs, item.id);
|
|
280
|
+
context.set("announcement", `${item.name} ${live(prop).cancelledText}`);
|
|
281
|
+
context.set("value", patchItem(context.get("value"), item.id, {
|
|
282
|
+
status: "error",
|
|
283
|
+
error: live(prop).cancelledText,
|
|
284
|
+
progress: void 0
|
|
285
|
+
}));
|
|
286
|
+
},
|
|
287
|
+
settle({ event, context, refs }) {
|
|
288
|
+
if (event.type !== "SETTLE" || !refs.get("active") || refs.get("controllers").get(event.id) !== event.controller) return;
|
|
289
|
+
if (event.final) refs.get("controllers").delete(event.id);
|
|
290
|
+
const item = context.get("value").find((entry) => entry.id === event.id);
|
|
291
|
+
if (!item) return;
|
|
292
|
+
if (event.final) context.set("announcement", event.patch.status === "done" ? `${item.name} 上传完成` : `${item.name} 上传失败`);
|
|
293
|
+
context.set("value", patchItem(context.get("value"), event.id, event.patch));
|
|
294
|
+
},
|
|
295
|
+
sync({ context, refs, scope }) {
|
|
296
|
+
const ids = new Set(context.get("value").map((item) => item.id));
|
|
297
|
+
for (const id of [...refs.get("files").keys()]) if (!ids.has(id)) {
|
|
298
|
+
abort(refs, id);
|
|
299
|
+
revoke(refs, id);
|
|
300
|
+
refs.get("files").delete(id);
|
|
301
|
+
}
|
|
302
|
+
for (const id of [...refs.get("urls").keys()]) if (!ids.has(id)) revoke(refs, id);
|
|
303
|
+
mirror({
|
|
304
|
+
context,
|
|
305
|
+
refs,
|
|
306
|
+
scope
|
|
307
|
+
});
|
|
308
|
+
}
|
|
309
|
+
},
|
|
310
|
+
effects: { lifecycle({ refs }) {
|
|
311
|
+
refs.set("active", true);
|
|
312
|
+
return () => {
|
|
313
|
+
refs.set("active", false);
|
|
314
|
+
for (const id of [...refs.get("controllers").keys()]) abort(refs, id);
|
|
315
|
+
for (const id of [...refs.get("urls").keys()]) revoke(refs, id);
|
|
316
|
+
refs.get("files").clear();
|
|
317
|
+
};
|
|
318
|
+
} }
|
|
319
|
+
}
|
|
320
|
+
});
|
|
321
|
+
function statusText(item, state) {
|
|
322
|
+
if (item.status === "uploading") return typeof item.progress === "number" ? `上传中 ${item.progress}%` : "上传中";
|
|
323
|
+
if (item.status === "pending") return "等待上传";
|
|
324
|
+
if (item.status === "error") return item.error || state.errorText;
|
|
325
|
+
return "";
|
|
326
|
+
}
|
|
327
|
+
function connectUpload(service, normalize) {
|
|
328
|
+
const state = live(service.prop), value = service.context.get("value"), { send, refs, scope } = service;
|
|
329
|
+
const editableNow = !state.disabled && !state.readOnly, canAdd = editableNow && value.length < state.maxCount;
|
|
330
|
+
const part = (name) => ({
|
|
331
|
+
"data-scope": "upload",
|
|
332
|
+
"data-part": name
|
|
333
|
+
});
|
|
334
|
+
const items = value.map((item) => ({
|
|
335
|
+
...item,
|
|
336
|
+
previewUrl: item.url ?? refs.get("urls").get(item.id),
|
|
337
|
+
statusText: statusText(item, state),
|
|
338
|
+
removeLabel: state.removeLabel.replaceAll("{name}", item.name)
|
|
339
|
+
}));
|
|
340
|
+
const addFiles = (files) => send({
|
|
341
|
+
type: "FILES",
|
|
342
|
+
files: [...files]
|
|
343
|
+
});
|
|
344
|
+
return {
|
|
345
|
+
items,
|
|
346
|
+
announcement: service.context.get("announcement"),
|
|
347
|
+
triggerText: state.triggerText,
|
|
348
|
+
retryText: state.retryText,
|
|
349
|
+
cancelText: state.cancelText,
|
|
350
|
+
canAdd,
|
|
351
|
+
addFiles,
|
|
352
|
+
remove: (id) => send({
|
|
353
|
+
type: "REMOVE",
|
|
354
|
+
id
|
|
355
|
+
}),
|
|
356
|
+
retry: (id) => send({
|
|
357
|
+
type: "RETRY",
|
|
358
|
+
id
|
|
359
|
+
}),
|
|
360
|
+
cancel: (id) => send({
|
|
361
|
+
type: "CANCEL",
|
|
362
|
+
id
|
|
363
|
+
}),
|
|
364
|
+
getRootProps: () => normalize.element({
|
|
365
|
+
...part("root"),
|
|
366
|
+
id: `upload:${scope.id}`,
|
|
367
|
+
"data-disabled": state.disabled || void 0,
|
|
368
|
+
"data-readonly": state.readOnly || void 0
|
|
369
|
+
}),
|
|
370
|
+
getInputProps: () => normalize.input({
|
|
371
|
+
...part("input"),
|
|
372
|
+
id: inputId(scope),
|
|
373
|
+
type: "file",
|
|
374
|
+
name: state.name,
|
|
375
|
+
accept: state.accept || void 0,
|
|
376
|
+
multiple: state.multiple || void 0,
|
|
377
|
+
disabled: !canAdd || void 0,
|
|
378
|
+
style: visuallyHiddenStyle,
|
|
379
|
+
onChange(event) {
|
|
380
|
+
const input = event.currentTarget, files = input?.files ? Array.from(input.files) : [];
|
|
381
|
+
if (input) input.value = "";
|
|
382
|
+
if (files.length) addFiles(files);
|
|
383
|
+
}
|
|
384
|
+
}),
|
|
385
|
+
getTriggerProps: () => normalize.label({
|
|
386
|
+
...part("trigger"),
|
|
387
|
+
htmlFor: inputId(scope),
|
|
388
|
+
"data-disabled": !canAdd || void 0
|
|
389
|
+
}),
|
|
390
|
+
getListProps: () => normalize.element({
|
|
391
|
+
...part("list"),
|
|
392
|
+
hidden: !items.length || void 0
|
|
393
|
+
}),
|
|
394
|
+
getItemProps: (item) => normalize.element({
|
|
395
|
+
...part("item"),
|
|
396
|
+
"data-status": item.status,
|
|
397
|
+
"aria-busy": item.status === "uploading" || void 0
|
|
398
|
+
}),
|
|
399
|
+
getPreviewProps: (item) => normalize.img({
|
|
400
|
+
...part("preview"),
|
|
401
|
+
src: item.previewUrl,
|
|
402
|
+
alt: "",
|
|
403
|
+
hidden: !item.previewUrl || void 0
|
|
404
|
+
}),
|
|
405
|
+
getNameProps: () => normalize.element({ ...part("name") }),
|
|
406
|
+
getStatusProps: (item) => normalize.element({
|
|
407
|
+
...part("status"),
|
|
408
|
+
"data-status": item.status,
|
|
409
|
+
hidden: !item.statusText || void 0
|
|
410
|
+
}),
|
|
411
|
+
getRetryProps: (item) => normalize.button({
|
|
412
|
+
...part("retry"),
|
|
413
|
+
type: "button",
|
|
414
|
+
hidden: !(editableNow && item.status === "error" && refs.get("files").has(item.id) && service.prop("upload")) || void 0,
|
|
415
|
+
"aria-label": `${state.retryText} ${item.name}`,
|
|
416
|
+
onClick(event) {
|
|
417
|
+
if (!event.defaultPrevented) send({
|
|
418
|
+
type: "RETRY",
|
|
419
|
+
id: item.id
|
|
420
|
+
});
|
|
421
|
+
}
|
|
422
|
+
}),
|
|
423
|
+
getCancelProps: (item) => normalize.button({
|
|
424
|
+
...part("cancel"),
|
|
425
|
+
type: "button",
|
|
426
|
+
hidden: !(!state.disabled && item.status === "uploading" && refs.get("controllers").has(item.id)) || void 0,
|
|
427
|
+
"aria-label": `${state.cancelText} ${item.name}`,
|
|
428
|
+
onClick(event) {
|
|
429
|
+
if (!event.defaultPrevented) send({
|
|
430
|
+
type: "CANCEL",
|
|
431
|
+
id: item.id
|
|
432
|
+
});
|
|
433
|
+
}
|
|
434
|
+
}),
|
|
435
|
+
getRemoveProps: (item) => normalize.button({
|
|
436
|
+
...part("remove"),
|
|
437
|
+
type: "button",
|
|
438
|
+
hidden: !editableNow || void 0,
|
|
439
|
+
"aria-label": item.removeLabel,
|
|
440
|
+
onClick(event) {
|
|
441
|
+
if (!event.defaultPrevented) send({
|
|
442
|
+
type: "REMOVE",
|
|
443
|
+
id: item.id
|
|
444
|
+
});
|
|
445
|
+
}
|
|
446
|
+
}),
|
|
447
|
+
getLiveProps: () => normalize.element({
|
|
448
|
+
...part("live"),
|
|
449
|
+
role: "status",
|
|
450
|
+
"aria-live": "polite",
|
|
451
|
+
style: visuallyHiddenStyle
|
|
452
|
+
})
|
|
453
|
+
};
|
|
454
|
+
}
|
|
455
|
+
//#endregion
|
|
456
|
+
export { UPLOAD_PARTS, UPLOAD_STATUSES, connectUpload, createUploadProps, matchesUploadAccept, normalizeUploadItems, resolveUploadState, uploadMachine };
|
|
457
|
+
|
|
458
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../src/upload/upload.ts"],"sourcesContent":["import { createMachine, type Machine, type Params as ZagParams, type Service } from \"@zag-js/core\";\nimport { visuallyHiddenStyle } from \"@zag-js/dom-query\";\nimport type { NormalizeProps, PropTypes } from \"@zag-js/types\";\n\n/** Stable DOM parts shared by every adapter. */\nexport const UPLOAD_PARTS = [\"root\", \"input\", \"trigger\", \"list\", \"item\", \"preview\", \"name\", \"status\", \"retry\", \"cancel\", \"remove\", \"live\"] as const;\nexport const UPLOAD_STATUSES = [\"pending\", \"uploading\", \"done\", \"error\"] as const;\nexport type UploadStatus = (typeof UPLOAD_STATUSES)[number];\n/** Serializable list entry. The File itself stays private to Core (used for retry and form sync). */\nexport interface UploadItem {\n id: string; name: string; size: number; type: string; status: UploadStatus;\n /** Remote or caller-provided URL; preferred over the Core-owned preview and never revoked by Core. */\n url?: string;\n error?: string;\n /** 0–100, only when the caller reports progress through onProgress. */\n progress?: number;\n}\nexport type UploadRejectReason = \"accept\" | \"max-size\" | \"max-count\";\nexport interface UploadRejection { file: File; reason: UploadRejectReason }\nexport interface UploadRejectDetails { rejections: UploadRejection[] }\nexport interface UploadChangeDetails { value: UploadItem[] }\nexport interface UploadResult { url?: string }\nexport interface UploadRequestContext {\n /** Aborted when the item is cancelled, removed, replaced out of the list or the component unmounts. */\n signal: AbortSignal;\n /** Optional real progress (0–100). Core never fabricates progress. */\n onProgress(percent: number): void;\n}\n/** Caller-injected transport: resolve (optionally with { url }) on success, reject or throw on failure. */\nexport type UploadRequest = (file: File, context: UploadRequestContext) => Promise<UploadResult | void> | UploadResult | void;\n\nexport interface QwUploadProps {\n id?: string;\n /** Native form field name on the file input. */\n name?: string;\n /** Native accept list: extensions (.png), wildcards (image/*) or exact MIME types. */\n accept?: string;\n multiple?: boolean;\n /** Maximum list length; invalid or ≤0 means unlimited. */\n maxCount?: number;\n /** Maximum file size in bytes; invalid or ≤0 means unlimited. */\n maxSize?: number;\n /** Controlled list; undefined lets Core own it (seeded by defaultValue). */\n value?: readonly UploadItem[];\n defaultValue?: readonly UploadItem[];\n onChange?: (details: UploadChangeDetails) => void;\n upload?: UploadRequest;\n onReject?: (details: UploadRejectDetails) => void;\n /** Create object-URL previews for image files; default true. */\n preview?: boolean;\n disabled?: boolean;\n readOnly?: boolean;\n triggerText?: string;\n /** Remove button name with {name}; default 删除 {name}. */\n removeLabel?: string;\n retryText?: string;\n cancelText?: string;\n errorText?: string;\n cancelledText?: string;\n}\nexport interface ResolvedUploadState {\n name: string | undefined; accept: string; multiple: boolean; maxCount: number; maxSize: number; preview: boolean; disabled: boolean; readOnly: boolean;\n triggerText: string; removeLabel: string; retryText: string; cancelText: string; errorText: string; cancelledText: string;\n}\nconst text = (value: string | undefined, fallback: string): string => typeof value === \"string\" && value.trim() ? value : fallback;\nconst limit = (value: number | undefined) => typeof value === \"number\" && Number.isFinite(value) && value > 0 ? value : Infinity;\nexport function resolveUploadState(props: QwUploadProps = {}): ResolvedUploadState {\n return {\n name: typeof props.name === \"string\" && props.name ? props.name : undefined, accept: typeof props.accept === \"string\" ? props.accept.trim() : \"\",\n multiple: !!props.multiple, maxCount: Math.floor(limit(props.maxCount)), maxSize: limit(props.maxSize), preview: props.preview !== false, disabled: !!props.disabled, readOnly: !!props.readOnly,\n triggerText: text(props.triggerText, \"上传文件\"), removeLabel: text(props.removeLabel, \"删除 {name}\"), retryText: text(props.retryText, \"重试\"),\n cancelText: text(props.cancelText, \"取消\"), errorText: text(props.errorText, \"上传失败\"), cancelledText: text(props.cancelledText, \"已取消\"),\n };\n}\n/** Normalize caller items; unknown status becomes done, duplicate or empty ids are dropped. */\nexport function normalizeUploadItems(items: readonly UploadItem[] | undefined): UploadItem[] {\n if (!Array.isArray(items)) return [];\n const seen = new Set<string>(), out: UploadItem[] = [];\n for (const item of items) {\n if (!item || typeof item.id !== \"string\" || !item.id || seen.has(item.id)) continue;\n seen.add(item.id);\n out.push({ ...item, name: typeof item.name === \"string\" ? item.name : \"\", size: Number.isFinite(item.size) ? item.size : 0, type: typeof item.type === \"string\" ? item.type : \"\",\n status: UPLOAD_STATUSES.includes(item.status) ? item.status : \"done\" });\n }\n return out;\n}\n/** Native accept semantics: case-insensitive extension, type/* prefix or exact MIME; empty accepts everything. */\nexport function matchesUploadAccept(file: { name: string; type: string }, accept: string): boolean {\n const tokens = accept.split(\",\").map((token) => token.trim().toLowerCase()).filter(Boolean);\n if (!tokens.length) return true;\n const name = file.name.toLowerCase(), type = (file.type || \"\").toLowerCase();\n return tokens.some((token) => token.startsWith(\".\") ? name.endsWith(token) : token.endsWith(\"/*\") ? type.startsWith(token.slice(0, -1)) : type === token);\n}\nexport function createUploadProps(props: QwUploadProps = {}): QwUploadProps {\n if (props.id !== undefined && (typeof props.id !== \"string\" || !props.id.trim())) throw new TypeError(\"Upload requires a nonempty instance id when provided\");\n if (props.upload !== undefined && typeof props.upload !== \"function\") throw new TypeError(\"Upload upload must be a function returning a Promise\");\n return { ...props, value: props.value === undefined ? undefined : normalizeUploadItems(props.value), defaultValue: normalizeUploadItems(props.defaultValue) };\n}\n\nexport interface QwUploadSchema {\n props: QwUploadProps;\n context: { value: UploadItem[]; announcement: string };\n refs: { files: Map<string, File>; controllers: Map<string, AbortController>; urls: Map<string, string>; seq: number; active: boolean };\n state: \"ready\";\n action: \"add\" | \"remove\" | \"retry\" | \"cancel\" | \"settle\" | \"sync\";\n effect: \"lifecycle\";\n event:\n | { type: \"FILES\"; files: readonly File[] }\n | { type: \"REMOVE\"; id: string }\n | { type: \"RETRY\"; id: string }\n | { type: \"CANCEL\"; id: string }\n | { type: \"SETTLE\"; id: string; controller: AbortController; patch: Partial<UploadItem>; final: boolean }\n | { type: \"SYNC\" };\n}\nexport type QwUploadMachine = Machine<QwUploadSchema>;\nexport type QwUploadService = Service<QwUploadSchema>;\ntype Params = ZagParams<QwUploadSchema>;\nconst live = (prop: QwUploadService[\"prop\"]) => resolveUploadState({\n name: prop(\"name\"), accept: prop(\"accept\"), multiple: prop(\"multiple\"), maxCount: prop(\"maxCount\"), maxSize: prop(\"maxSize\"), preview: prop(\"preview\"), disabled: prop(\"disabled\"), readOnly: prop(\"readOnly\"),\n triggerText: prop(\"triggerText\"), removeLabel: prop(\"removeLabel\"), retryText: prop(\"retryText\"), cancelText: prop(\"cancelText\"), errorText: prop(\"errorText\"), cancelledText: prop(\"cancelledText\"),\n});\nconst inputId = (scope: QwUploadService[\"scope\"]) => `upload:${scope.id}:input`;\nconst patchItem = (items: readonly UploadItem[], id: string, patch: Partial<UploadItem>) => items.map((item) => item.id === id ? { ...item, ...patch } : item);\nconst messageOf = (error: unknown, fallback: string) => error instanceof Error && error.message ? error.message : typeof error === \"string\" && error ? error : fallback;\nfunction revoke(refs: Params[\"refs\"], id: string) {\n const url = refs.get(\"urls\").get(id);\n if (url !== undefined) { refs.get(\"urls\").delete(id); try { URL.revokeObjectURL(url); } catch { /* environment without object URLs */ } }\n}\nfunction abort(refs: Params[\"refs\"], id: string) { const controller = refs.get(\"controllers\").get(id); refs.get(\"controllers\").delete(id); controller?.abort(); }\nfunction start({ refs, prop, send }: Params, id: string, file: File) {\n const request = prop(\"upload\");\n if (!request) return;\n const controller = new AbortController(); refs.get(\"controllers\").set(id, controller);\n const settle = (patch: Partial<UploadItem>, final: boolean) => { if (!controller.signal.aborted) send({ type: \"SETTLE\", id, controller, patch, final }); };\n const onProgress = (percent: number) => { if (Number.isFinite(percent)) settle({ progress: Math.min(100, Math.max(0, Math.round(percent))) }, false); };\n let result: unknown;\n try { result = request(file, { signal: controller.signal, onProgress }); } catch (error) { result = Promise.reject(error); }\n Promise.resolve(result).then(\n (value) => { const url = value && typeof value === \"object\" && typeof (value as UploadResult).url === \"string\" ? (value as UploadResult).url : undefined; settle({ status: \"done\", error: undefined, ...(url ? { url } : {}) }, true); },\n (error: unknown) => settle({ status: \"error\", error: messageOf(error, live(prop).errorText) }, true),\n );\n}\n/** Mirror the listed Core-owned files into the native input so form submission matches the list. */\nfunction mirror({ context, refs, scope }: Pick<Params, \"context\" | \"refs\" | \"scope\">) {\n const input = scope.getById<HTMLInputElement>(inputId(scope)), win = input?.ownerDocument.defaultView as (Window & typeof globalThis) | null | undefined;\n if (!input || !win || typeof win.DataTransfer !== \"function\") return;\n try {\n const transfer = new win.DataTransfer();\n for (const item of context.get(\"value\")) { const file = refs.get(\"files\").get(item.id); if (file) transfer.items.add(file); }\n input.files = transfer.files;\n } catch { /* DataTransfer construction unsupported: the native input keeps the last selection */ }\n}\nconst editable = (prop: QwUploadService[\"prop\"]) => { const state = live(prop); return !state.disabled && !state.readOnly; };\n\n/** Core owns validation, the list, caller-upload lifecycle with AbortSignal, object-URL ownership and announcements. */\nexport const uploadMachine: QwUploadMachine = createMachine<QwUploadSchema>({\n props: ({ props }) => createUploadProps(props), initialState: () => \"ready\",\n context: ({ bindable, prop }) => ({\n value: bindable<UploadItem[]>(() => ({ defaultValue: [...(prop(\"defaultValue\") ?? [])], value: prop(\"value\") as UploadItem[] | undefined, onChange(value) { prop(\"onChange\")?.({ value }); } })),\n announcement: bindable(() => ({ defaultValue: \"\" })),\n }),\n refs: () => ({ files: new Map(), controllers: new Map(), urls: new Map(), seq: 0, active: false }),\n watch({ track, context, send }) { track([() => context.get(\"value\").map((item) => item.id).join(\"\\n\")], () => send({ type: \"SYNC\" })); },\n effects: [\"lifecycle\"],\n on: { FILES: { actions: [\"add\"] }, REMOVE: { actions: [\"remove\"] }, RETRY: { actions: [\"retry\"] }, CANCEL: { actions: [\"cancel\"] }, SETTLE: { actions: [\"settle\"] }, SYNC: { actions: [\"sync\"] } },\n states: { ready: {} },\n implementations: {\n actions: {\n add(params) {\n const { event, context, prop, refs, scope } = params;\n if (event.type !== \"FILES\" || !editable(prop)) return;\n const state = live(prop), current = context.get(\"value\"), rejections: UploadRejection[] = [], added: Array<{ item: UploadItem; file: File }> = [];\n const reserved = new Set(current.map(item => item.id));\n for (const file of state.multiple ? event.files : event.files.slice(0, 1)) {\n if (!matchesUploadAccept(file, state.accept)) rejections.push({ file, reason: \"accept\" });\n else if (file.size > state.maxSize) rejections.push({ file, reason: \"max-size\" });\n else if (current.length + added.length >= state.maxCount) rejections.push({ file, reason: \"max-count\" });\n else {\n let seq = refs.get(\"seq\"), id: string;\n do { id = `${scope.id}-${++seq}`; }\n while (reserved.has(id) || refs.get(\"files\").has(id) || refs.get(\"controllers\").has(id) || refs.get(\"urls\").has(id));\n refs.set(\"seq\", seq); reserved.add(id);\n added.push({ file, item: { id, name: file.name, size: file.size, type: file.type, status: prop(\"upload\") ? \"uploading\" : \"done\" } });\n }\n }\n for (const { item, file } of added) {\n refs.get(\"files\").set(item.id, file);\n if (state.preview && file.type.startsWith(\"image/\") && typeof URL.createObjectURL === \"function\") {\n try { refs.get(\"urls\").set(item.id, URL.createObjectURL(file)); } catch { /* preview unavailable */ }\n }\n }\n const parts = [added.length ? `已添加 ${added.length} 个文件` : \"\", rejections.length ? `${rejections.length} 个文件未添加` : \"\"].filter(Boolean);\n if (parts.length) context.set(\"announcement\", parts.join(\",\"));\n if (added.length) context.set(\"value\", [...current, ...added.map(({ item }) => item)]);\n if (rejections.length) prop(\"onReject\")?.({ rejections });\n mirror(params);\n for (const { item, file } of added) start(params, item.id, file);\n },\n remove({ event, context, prop, refs }) {\n if (event.type !== \"REMOVE\" || !editable(prop)) return;\n const item = context.get(\"value\").find((entry) => entry.id === event.id);\n if (!item) return;\n abort(refs, item.id); revoke(refs, item.id); refs.get(\"files\").delete(item.id);\n context.set(\"announcement\", `已删除 ${item.name}`);\n context.set(\"value\", context.get(\"value\").filter((entry) => entry.id !== item.id));\n },\n retry(params) {\n const { event, context, prop, refs } = params;\n if (event.type !== \"RETRY\" || !editable(prop) || !prop(\"upload\")) return;\n const item = context.get(\"value\").find((entry) => entry.id === event.id), file = refs.get(\"files\").get(event.id);\n if (!item || item.status !== \"error\" || !file) return;\n context.set(\"value\", patchItem(context.get(\"value\"), item.id, { status: \"uploading\", error: undefined, progress: undefined }));\n start(params, item.id, file);\n },\n cancel({ event, context, prop, refs }) {\n if (event.type !== \"CANCEL\" || live(prop).disabled) return;\n const item = context.get(\"value\").find((entry) => entry.id === event.id);\n if (!item || !refs.get(\"controllers\").has(item.id)) return;\n abort(refs, item.id);\n context.set(\"announcement\", `${item.name} ${live(prop).cancelledText}`);\n context.set(\"value\", patchItem(context.get(\"value\"), item.id, { status: \"error\", error: live(prop).cancelledText, progress: undefined }));\n },\n settle({ event, context, refs }) {\n if (event.type !== \"SETTLE\" || !refs.get(\"active\") || refs.get(\"controllers\").get(event.id) !== event.controller) return;\n if (event.final) refs.get(\"controllers\").delete(event.id);\n const item = context.get(\"value\").find((entry) => entry.id === event.id);\n if (!item) return;\n if (event.final) context.set(\"announcement\", event.patch.status === \"done\" ? `${item.name} 上传完成` : `${item.name} 上传失败`);\n context.set(\"value\", patchItem(context.get(\"value\"), event.id, event.patch));\n },\n // The list may be replaced by the owner: release files, uploads and previews that are no longer listed, then mirror the files to the native input.\n sync({ context, refs, scope }) {\n const ids = new Set(context.get(\"value\").map((item) => item.id));\n for (const id of [...refs.get(\"files\").keys()]) if (!ids.has(id)) { abort(refs, id); revoke(refs, id); refs.get(\"files\").delete(id); }\n for (const id of [...refs.get(\"urls\").keys()]) if (!ids.has(id)) revoke(refs, id);\n mirror({ context, refs, scope });\n },\n },\n effects: {\n lifecycle({ refs }) {\n refs.set(\"active\", true);\n return () => {\n refs.set(\"active\", false);\n for (const id of [...refs.get(\"controllers\").keys()]) abort(refs, id);\n for (const id of [...refs.get(\"urls\").keys()]) revoke(refs, id);\n refs.get(\"files\").clear();\n };\n },\n },\n },\n});\n\nexport interface UploadViewItem extends UploadItem {\n /** item.url, else the Core-owned object URL for images, else undefined. */\n previewUrl: string | undefined;\n statusText: string;\n removeLabel: string;\n}\nexport interface UploadInputEvent { readonly currentTarget: unknown }\nexport interface QwUploadApi<T extends PropTypes = PropTypes> {\n items: UploadViewItem[]; announcement: string; triggerText: string; retryText: string; cancelText: string;\n /** False while disabled, read-only or at maxCount. */\n canAdd: boolean;\n addFiles(files: readonly File[]): void;\n remove(id: string): void;\n retry(id: string): void;\n cancel(id: string): void;\n getRootProps(): T[\"element\"];\n getInputProps(): T[\"input\"];\n getTriggerProps(): T[\"label\"];\n getListProps(): T[\"element\"];\n getItemProps(item: UploadViewItem): T[\"element\"];\n getPreviewProps(item: UploadViewItem): T[\"img\"];\n getNameProps(item: UploadViewItem): T[\"element\"];\n getStatusProps(item: UploadViewItem): T[\"element\"];\n getRetryProps(item: UploadViewItem): T[\"button\"];\n getCancelProps(item: UploadViewItem): T[\"button\"];\n getRemoveProps(item: UploadViewItem): T[\"button\"];\n getLiveProps(): T[\"element\"];\n}\nfunction statusText(item: UploadItem, state: ResolvedUploadState): string {\n if (item.status === \"uploading\") return typeof item.progress === \"number\" ? `上传中 ${item.progress}%` : \"上传中\";\n if (item.status === \"pending\") return \"等待上传\";\n if (item.status === \"error\") return item.error || state.errorText;\n return \"\";\n}\n\nexport function connectUpload<T extends PropTypes>(service: QwUploadService, normalize: NormalizeProps<T>): QwUploadApi<T> {\n const state = live(service.prop), value = service.context.get(\"value\"), { send, refs, scope } = service;\n const editableNow = !state.disabled && !state.readOnly, canAdd = editableNow && value.length < state.maxCount;\n const part = (name: string) => ({ \"data-scope\": \"upload\", \"data-part\": name });\n const items: UploadViewItem[] = value.map((item) => ({ ...item, previewUrl: item.url ?? refs.get(\"urls\").get(item.id), statusText: statusText(item, state), removeLabel: state.removeLabel.replaceAll(\"{name}\", item.name) }));\n const addFiles = (files: readonly File[]) => send({ type: \"FILES\", files: [...files] });\n return {\n items, announcement: service.context.get(\"announcement\"), triggerText: state.triggerText, retryText: state.retryText, cancelText: state.cancelText, canAdd, addFiles,\n remove: (id) => send({ type: \"REMOVE\", id }), retry: (id) => send({ type: \"RETRY\", id }), cancel: (id) => send({ type: \"CANCEL\", id }),\n getRootProps: () => normalize.element({ ...part(\"root\"), id: `upload:${scope.id}`, \"data-disabled\": state.disabled || undefined, \"data-readonly\": state.readOnly || undefined }),\n // Visually hidden but focusable: Tab reaches it and Enter/Space opens the native picker; the following label is its visible trigger.\n getInputProps: () => normalize.input({ ...part(\"input\"), id: inputId(scope), type: \"file\", name: state.name, accept: state.accept || undefined, multiple: state.multiple || undefined,\n disabled: !canAdd || undefined, style: visuallyHiddenStyle,\n onChange(event: UploadInputEvent) {\n const input = event.currentTarget as HTMLInputElement | null, files = input?.files ? Array.from(input.files) : [];\n // Clear first so choosing the same file again still fires change; Core then mirrors the kept list back.\n if (input) input.value = \"\";\n if (files.length) addFiles(files);\n } }),\n getTriggerProps: () => normalize.label({ ...part(\"trigger\"), htmlFor: inputId(scope), \"data-disabled\": !canAdd || undefined }),\n getListProps: () => normalize.element({ ...part(\"list\"), hidden: !items.length || undefined }),\n getItemProps: (item) => normalize.element({ ...part(\"item\"), \"data-status\": item.status, \"aria-busy\": item.status === \"uploading\" || undefined }),\n getPreviewProps: (item) => normalize.img({ ...part(\"preview\"), src: item.previewUrl, alt: \"\", hidden: !item.previewUrl || undefined }),\n getNameProps: () => normalize.element({ ...part(\"name\") }),\n getStatusProps: (item) => normalize.element({ ...part(\"status\"), \"data-status\": item.status, hidden: !item.statusText || undefined }),\n getRetryProps: (item) => normalize.button({ ...part(\"retry\"), type: \"button\", hidden: !(editableNow && item.status === \"error\" && refs.get(\"files\").has(item.id) && service.prop(\"upload\")) || undefined,\n \"aria-label\": `${state.retryText} ${item.name}`, onClick(event: { defaultPrevented: boolean }) { if (!event.defaultPrevented) send({ type: \"RETRY\", id: item.id }); } }),\n getCancelProps: (item) => normalize.button({ ...part(\"cancel\"), type: \"button\", hidden: !(!state.disabled && item.status === \"uploading\" && refs.get(\"controllers\").has(item.id)) || undefined,\n \"aria-label\": `${state.cancelText} ${item.name}`, onClick(event: { defaultPrevented: boolean }) { if (!event.defaultPrevented) send({ type: \"CANCEL\", id: item.id }); } }),\n getRemoveProps: (item) => normalize.button({ ...part(\"remove\"), type: \"button\", hidden: !editableNow || undefined, \"aria-label\": item.removeLabel,\n onClick(event: { defaultPrevented: boolean }) { if (!event.defaultPrevented) send({ type: \"REMOVE\", id: item.id }); } }),\n getLiveProps: () => normalize.element({ ...part(\"live\"), role: \"status\", \"aria-live\": \"polite\", style: visuallyHiddenStyle }),\n };\n}\n"],"mappings":"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"}
|