@feugene/granularity 0.10.0 → 0.11.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 +44 -45
- package/dist/GrButtonGroup.css +1 -1
- package/dist/GrFormFile.css +1 -1
- package/dist/GrIcon.css +1 -1
- package/dist/GrLoading.css +1 -1
- package/dist/GrSkeleton.css +1 -1
- package/dist/GrToaster.css +1 -0
- package/dist/GrTree.css +1 -1
- package/dist/chunks/{adapter-BqqjEZGU.js.map → adapter-CAOxmn2G.js.map} +1 -1
- package/dist/chunks/arrow-up-C_G4jg8M.js.map +1 -0
- package/dist/chunks/{classTokens-BPeBXNzu.js.map → classTokens-BzazaERD.js.map} +1 -1
- package/dist/chunks/{config-A-iei0Ux.js → config-1uSYl98Y.js} +5 -5
- package/dist/chunks/{config-A-iei0Ux.js.map → config-1uSYl98Y.js.map} +1 -1
- package/dist/chunks/{config-DZrlovR42.js.map → config-8Pcutu1j2.js.map} +1 -1
- package/dist/chunks/{config-VJuoznpH.js.map → config-B0qIpo8m.js.map} +1 -1
- package/dist/chunks/{config-C8MM2Dg0.js → config-B7IIWGt_2.js} +3 -3
- package/dist/chunks/config-B7IIWGt_2.js.map +1 -0
- package/dist/chunks/{config-DbghHyY_.js.map → config-BEegFP74.js.map} +1 -1
- package/dist/chunks/{config-D_Pafsjq2.js → config-BIRO0vDJ2.js} +6 -6
- package/dist/chunks/{config-D_Pafsjq2.js.map → config-BIRO0vDJ2.js.map} +1 -1
- package/dist/chunks/{config-BeBsN0c12.js.map → config-BLHqZhy-2.js.map} +1 -1
- package/dist/chunks/{config-BV4vBzdm.js.map → config-BNu8lFQB.js.map} +1 -1
- package/dist/chunks/config-BOlr7qw7.js +106 -0
- package/dist/chunks/config-BOlr7qw7.js.map +1 -0
- package/dist/chunks/{config-DhQc1TRY.js.map → config-BUHuGBik.js.map} +1 -1
- package/dist/chunks/{config-CPSdAjUi.js.map → config-BWGGp7uV.js.map} +1 -1
- package/dist/chunks/config-BX1JTrkV2.js +14 -0
- package/dist/chunks/config-BX1JTrkV2.js.map +1 -0
- package/dist/chunks/{config-BduXEXjt.js.map → config-BXtAmU3s.js.map} +1 -1
- package/dist/chunks/{config-CzgNEHKi.js.map → config-Bah4oHwL.js.map} +1 -1
- package/dist/chunks/{config-C_egzT_K.js → config-C49QUoJL.js} +3 -3
- package/dist/chunks/{config-C_egzT_K.js.map → config-C49QUoJL.js.map} +1 -1
- package/dist/chunks/{config-3I3vqDW4.js → config-C4snOIXg.js} +1 -1
- package/dist/chunks/{config-3I3vqDW4.js.map → config-C4snOIXg.js.map} +1 -1
- package/dist/chunks/{config-DvDNney3.js → config-C7NpDrfO.js} +5 -5
- package/dist/chunks/{config-DvDNney3.js.map → config-C7NpDrfO.js.map} +1 -1
- package/dist/chunks/{config-lMDE_8A5.js.map → config-C86UzUYf.js.map} +1 -1
- package/dist/chunks/{config-BgBWt9-A.js.map → config-C9AcVDkv.js.map} +1 -1
- package/dist/chunks/{config-BuoIngj32.js.map → config-CGHLoBlH2.js.map} +1 -1
- package/dist/chunks/{config-ChQxl75m.js.map → config-CThzliFi.js.map} +1 -1
- package/dist/chunks/{config-DDwBSoc_.js.map → config-Cb2PAlSD.js.map} +1 -1
- package/dist/chunks/{config-XspHtPsU.js → config-ClhKPJvg.js} +5 -5
- package/dist/chunks/{config-XspHtPsU.js.map → config-ClhKPJvg.js.map} +1 -1
- package/dist/chunks/{config-58Mj2rGH.js → config-Cpi9Mh2J.js} +3 -3
- package/dist/chunks/{config-58Mj2rGH.js.map → config-Cpi9Mh2J.js.map} +1 -1
- package/dist/chunks/{config-nrOj9p6I.js → config-CrG1XiE7.js} +4 -4
- package/dist/chunks/{config-nrOj9p6I.js.map → config-CrG1XiE7.js.map} +1 -1
- package/dist/chunks/{config-DRpkoSvq.js → config-CziwTDDL.js} +3 -3
- package/dist/chunks/{config-DRpkoSvq.js.map → config-CziwTDDL.js.map} +1 -1
- package/dist/chunks/{config-C5-ujXCI.js.map → config-D7GZO-Dx.js.map} +1 -1
- package/dist/chunks/{config-CUwF4E4R.js.map → config-DBmdgoVf.js.map} +1 -1
- package/dist/chunks/{config-C9MblwGq.js.map → config-DICOd-2X.js.map} +1 -1
- package/dist/chunks/{config-C6zT56Jc2.js → config-DUcu1D68.js} +3 -3
- package/dist/chunks/config-DUcu1D68.js.map +1 -0
- package/dist/chunks/{config-8f8624RN.js → config-D_R56_gT.js} +5 -5
- package/dist/chunks/{config-8f8624RN.js.map → config-D_R56_gT.js.map} +1 -1
- package/dist/chunks/{config-RjfJFv1Y.js → config-DezDih8_.js} +4 -4
- package/dist/chunks/config-DezDih8_.js.map +1 -0
- package/dist/chunks/{config-B0uUCaJW.js → config-DnvPqu4g.js} +3 -3
- package/dist/chunks/{config-B0uUCaJW.js.map → config-DnvPqu4g.js.map} +1 -1
- package/dist/chunks/{config-BLa1TEGm2.js.map → config-DpqOnJiz2.js.map} +1 -1
- package/dist/chunks/{config-V3LF-b_F.js.map → config-Dxuwwepq.js.map} +1 -1
- package/dist/chunks/{config-Doa_gU40.js.map → config-HZto2PVy.js.map} +1 -1
- package/dist/chunks/{config-Dl5aZ5VR.js.map → config-JOtB4mzs.js.map} +1 -1
- package/dist/chunks/{config-CWTfyPNI.js.map → config-JpHA4Xx0.js.map} +1 -1
- package/dist/chunks/{config-DkeLkzxj2.js → config-LGrZIdaZ2.js} +1 -1
- package/dist/chunks/{config-DkeLkzxj2.js.map → config-LGrZIdaZ2.js.map} +1 -1
- package/dist/chunks/{config-B3dn-gdC.js.map → config-PFg39mYo.js.map} +1 -1
- package/dist/chunks/{config-CU_CBd0k.js → config-QYGvEBu5.js} +2 -2
- package/dist/chunks/{config-CU_CBd0k.js.map → config-QYGvEBu5.js.map} +1 -1
- package/dist/chunks/{config-Bh4NWWsQ.js.map → config-QaIc_gRa.js.map} +1 -1
- package/dist/chunks/{config-vcDVCYXo.js.map → config-U4m9PSql.js.map} +1 -1
- package/dist/chunks/{config-C_q_4FrU.js.map → config-ZiXWIRBX.js.map} +1 -1
- package/dist/chunks/{config-hSlCXHoG.js → config-eYLZYOUS2.js} +63 -63
- package/dist/chunks/config-eYLZYOUS2.js.map +1 -0
- package/dist/chunks/{config-DDUPnue12.js.map → config-ipvU0lzP2.js.map} +1 -1
- package/dist/chunks/{config-B61cX08u.js → config-jBp9wVv-.js} +4 -4
- package/dist/chunks/{config-B61cX08u.js.map → config-jBp9wVv-.js.map} +1 -1
- package/dist/chunks/{config-D5ek7VSi.js.map → config-xR4XVmcy.js.map} +1 -1
- package/dist/chunks/{dialogShared-BtXUk6Zc.js.map → dialogShared-CxW62PQE.js.map} +1 -1
- package/dist/chunks/en-BdtiS2d3.js +138 -0
- package/dist/chunks/en-BdtiS2d3.js.map +1 -0
- package/dist/chunks/es-BGRMZbe9.js +138 -0
- package/dist/chunks/es-BGRMZbe9.js.map +1 -0
- package/dist/chunks/{es-CISK11Nv.js → es-DBhctWg-.js} +3 -3
- package/dist/chunks/{es-CISK11Nv.js.map → es-DBhctWg-.js.map} +1 -1
- package/dist/chunks/{fileValidation-c_iBg74s.js → fileValidation-C3WFaWU2.js} +2 -1
- package/dist/chunks/{fileValidation-c_iBg74s.js.map → fileValidation-C3WFaWU2.js.map} +1 -1
- package/dist/chunks/{grBadgeStyles-Cq0hH2Ls.js → grBadgeStyles-DrycBuKT.js} +13 -13
- package/dist/chunks/grBadgeStyles-DrycBuKT.js.map +1 -0
- package/dist/chunks/grButtonStyles-C7Yga_Q1.js +191 -0
- package/dist/chunks/grButtonStyles-C7Yga_Q1.js.map +1 -0
- package/dist/chunks/{grDropdownStyles-Bqx9hOzU.js → grDropdownStyles-B_-DKytw.js} +2 -2
- package/dist/chunks/{grDropdownStyles-Bqx9hOzU.js.map → grDropdownStyles-B_-DKytw.js.map} +1 -1
- package/dist/chunks/{grLoadingStyles-DmI-SJ3i.js.map → grLoadingStyles-R5sreH__.js.map} +1 -1
- package/dist/chunks/{grModalStyles-FgaKqx50.js → grModalStyles-DWd3i05Q.js} +6 -6
- package/dist/chunks/{grModalStyles-FgaKqx50.js.map → grModalStyles-DWd3i05Q.js.map} +1 -1
- package/dist/chunks/{grSelectStyles-AjWWl007.js → grSelectStyles-CLK5hRd3.js} +3 -3
- package/dist/chunks/grSelectStyles-CLK5hRd3.js.map +1 -0
- package/dist/chunks/{grStyle-D-gPHdyW.js → grStyle-Blc9otAx.js} +6 -6
- package/dist/chunks/grStyle-Blc9otAx.js.map +1 -0
- package/dist/chunks/{granularityI18n-D_7jowK2.js → granularityI18n-DoV7Ca2m.js} +1 -1
- package/dist/chunks/{granularityI18n-D_7jowK2.js.map → granularityI18n-DoV7Ca2m.js.map} +1 -1
- package/dist/chunks/info-Be2OccTu.js.map +1 -0
- package/dist/chunks/loader-circle-CfVLz7lb.js.map +1 -0
- package/dist/chunks/ru-BFCnOiML.js +138 -0
- package/dist/chunks/ru-BFCnOiML.js.map +1 -0
- package/dist/chunks/{safelist-_UVzJrgE2.js → safelist-CkF4v7DC.js} +3 -3
- package/dist/chunks/safelist-CkF4v7DC.js.map +1 -0
- package/dist/chunks/{safelist-DccvJqCE.js → safelist-Do2RtzLB.js} +3 -3
- package/dist/chunks/{safelist-DccvJqCE.js.map → safelist-Do2RtzLB.js.map} +1 -1
- package/dist/chunks/shared-ChvcQgDl.js +168 -0
- package/dist/chunks/shared-ChvcQgDl.js.map +1 -0
- package/dist/chunks/{transition-mJ3PZCHH.js → transition-TLFw4KBn.js} +26 -12
- package/dist/chunks/{transition-mJ3PZCHH.js.map → transition-TLFw4KBn.js.map} +1 -1
- package/dist/chunks/useAddonMeasurement-DM0akF4C.js +65 -0
- package/dist/chunks/useAddonMeasurement-DM0akF4C.js.map +1 -0
- package/dist/chunks/useEscapeToClose-C2t_S1gh.js +27 -0
- package/dist/chunks/useEscapeToClose-C2t_S1gh.js.map +1 -0
- package/dist/chunks/{useFloating-CLtbU7eD.js → useFloating-DtM6TyE4.js} +19 -4
- package/dist/chunks/{useFloating-CLtbU7eD.js.map → useFloating-DtM6TyE4.js.map} +1 -1
- package/dist/chunks/x-2KXnqxiD.js.map +1 -0
- package/dist/chunks/x-circle-BCBURwyX.js.map +1 -0
- package/dist/components/GrAlert/chunks/{GrAlert-HyCjYJeL.js → GrAlert-DPJSU_fG.js} +40 -37
- package/dist/components/GrAlert/chunks/GrAlert-DPJSU_fG.js.map +1 -0
- package/dist/components/GrAlert/index.js +2 -2
- package/dist/components/GrAvatar/chunks/{GrAvatar-BjnPKNAL.js → GrAvatar-96CpTCq5.js} +2 -2
- package/dist/components/GrAvatar/chunks/{GrAvatar-BjnPKNAL.js.map → GrAvatar-96CpTCq5.js.map} +1 -1
- package/dist/components/GrAvatar/index.js +2 -2
- package/dist/components/GrBadge/chunks/{GrBadge-Cs_cVfuO.js → GrBadge-B77XlaqE.js} +3 -3
- package/dist/components/GrBadge/chunks/{GrBadge-Cs_cVfuO.js.map → GrBadge-B77XlaqE.js.map} +1 -1
- package/dist/components/GrBadge/index.js +2 -2
- package/dist/components/GrBadgeWrap/chunks/{GrBadgeWrap-BEnE9DyJ.js → GrBadgeWrap-CcktMOdg.js} +2 -2
- package/dist/components/GrBadgeWrap/chunks/{GrBadgeWrap-BEnE9DyJ.js.map → GrBadgeWrap-CcktMOdg.js.map} +1 -1
- package/dist/components/GrBadgeWrap/index.js +2 -2
- package/dist/components/GrBottomNav/chunks/{GrBottomNav-XPHwd7UQ.js.map → GrBottomNav-usuMgG8_.js.map} +1 -1
- package/dist/components/GrBottomNav/index.js +2 -2
- package/dist/components/GrButton/chunks/GrButton-BlffdeJr.js +124 -0
- package/dist/components/GrButton/chunks/GrButton-BlffdeJr.js.map +1 -0
- package/dist/components/GrButton/index.js +4 -4
- package/dist/components/GrButtonGroup/chunks/{GrButtonGroup-CPOH6V-P.js → GrButtonGroup-Bs9dEKfA.js} +1 -1
- package/dist/components/GrButtonGroup/chunks/GrButtonGroup-Bs9dEKfA.js.map +1 -0
- package/dist/components/GrButtonGroup/index.js +2 -2
- package/dist/components/GrCard/chunks/{GrCard-6yk1RRAQ.js → GrCard-DUNMkuHW.js} +3 -3
- package/dist/components/GrCard/chunks/GrCard-DUNMkuHW.js.map +1 -0
- package/dist/components/GrCard/index.js +2 -2
- package/dist/components/GrCheckbox/chunks/{GrCheckbox-Bt3d7ckE.js → GrCheckbox-DJhzZZdO.js} +66 -18
- package/dist/components/GrCheckbox/chunks/GrCheckbox-DJhzZZdO.js.map +1 -0
- package/dist/components/GrCheckbox/index.js +2 -2
- package/dist/components/GrCollapse/chunks/{GrCollapse-CU94BTAR.js → GrCollapse-CPPLh_xU.js} +12 -12
- package/dist/components/GrCollapse/chunks/{GrCollapse-CU94BTAR.js.map → GrCollapse-CPPLh_xU.js.map} +1 -1
- package/dist/components/GrCollapse/index.js +2 -2
- package/dist/components/GrConfirmDialog/chunks/{GrConfirmDialog-Bi2KLumL.js → GrConfirmDialog-BWYKCsHd.js} +20 -14
- package/dist/components/GrConfirmDialog/chunks/GrConfirmDialog-BWYKCsHd.js.map +1 -0
- package/dist/components/GrConfirmDialog/index.js +2 -2
- package/dist/components/GrDataTable/chunks/{GrDataTable-ClcYiyc8.js → GrDataTable-ptbARmJ3.js} +7 -7
- package/dist/components/GrDataTable/chunks/{GrDataTable-ClcYiyc8.js.map → GrDataTable-ptbARmJ3.js.map} +1 -1
- package/dist/components/GrDataTable/index.js +2 -2
- package/dist/components/GrDialog/chunks/{GrDialog-CxK4Lj4F.js → GrDialog-5DAS-1Lb.js} +14 -12
- package/dist/components/GrDialog/chunks/GrDialog-5DAS-1Lb.js.map +1 -0
- package/dist/components/GrDialog/index.js +3 -3
- package/dist/components/GrDialogService/chunks/GrDialogService-DY_fmaMu.js +425 -0
- package/dist/components/GrDialogService/chunks/GrDialogService-DY_fmaMu.js.map +1 -0
- package/dist/components/GrDialogService/index.js +3 -0
- package/dist/components/GrDrawer/chunks/{GrDrawer-BW3wtI7h.js → GrDrawer-D1kzsjXN.js} +19 -15
- package/dist/components/GrDrawer/chunks/GrDrawer-D1kzsjXN.js.map +1 -0
- package/dist/components/GrDrawer/index.js +2 -2
- package/dist/components/GrDropdown/chunks/{GrDropdown-BGKeEfZ1.js → GrDropdown-BXb5Cxxf.js} +9 -19
- package/dist/components/GrDropdown/chunks/GrDropdown-BXb5Cxxf.js.map +1 -0
- package/dist/components/GrDropdown/index.js +2 -2
- package/dist/components/GrDropdownMenu/chunks/{GrDropdownMenu-CJom_-c2.js → GrDropdownMenu-DFEJLPcV.js} +10 -10
- package/dist/components/GrDropdownMenu/chunks/{GrDropdownMenu-CJom_-c2.js.map → GrDropdownMenu-DFEJLPcV.js.map} +1 -1
- package/dist/components/GrDropdownMenu/index.js +2 -2
- package/dist/components/GrEmptyState/chunks/{GrEmptyState-yOuZW7-t.js → GrEmptyState-CA3BiTV7.js} +3 -3
- package/dist/components/GrEmptyState/chunks/{GrEmptyState-yOuZW7-t.js.map → GrEmptyState-CA3BiTV7.js.map} +1 -1
- package/dist/components/GrEmptyState/index.js +2 -2
- package/dist/components/GrFileUpload/chunks/{GrFileUpload-CBKK3dgC.js → GrFileUpload-DvWPpiJS.js} +26 -23
- package/dist/components/GrFileUpload/chunks/GrFileUpload-DvWPpiJS.js.map +1 -0
- package/dist/components/GrFileUpload/index.js +3 -3
- package/dist/components/GrFormField/chunks/{GrFormField-U7c_aDPJ.js → GrFormField-BujNQrw8.js} +1 -1
- package/dist/components/GrFormField/chunks/{GrFormField-U7c_aDPJ.js.map → GrFormField-BujNQrw8.js.map} +1 -1
- package/dist/components/GrFormField/index.js +2 -2
- package/dist/components/GrFormFile/chunks/{GrFormFile-CkR6cYqf.js → GrFormFile-CXcqqdvV.js} +38 -31
- package/dist/components/GrFormFile/chunks/GrFormFile-CXcqqdvV.js.map +1 -0
- package/dist/components/GrFormFile/index.js +2 -2
- package/dist/components/GrFormSection/chunks/{GrFormSection-dbyzqxYk.js → GrFormSection-Ce21jcgo.js} +1 -1
- package/dist/components/GrFormSection/chunks/{GrFormSection-dbyzqxYk.js.map → GrFormSection-Ce21jcgo.js.map} +1 -1
- package/dist/components/GrFormSection/index.js +2 -2
- package/dist/components/GrIcon/chunks/{GrIcon-BV7RBU_0.js → GrIcon-D9AWQLk2.js} +3 -3
- package/dist/components/GrIcon/chunks/{GrIcon-BV7RBU_0.js.map → GrIcon-D9AWQLk2.js.map} +1 -1
- package/dist/components/GrIcon/index.js +2 -2
- package/dist/components/GrImageViewer/chunks/{GrImageViewer-BG40DsHa.js → GrImageViewer-OCUIrNh2.js} +44 -33
- package/dist/components/GrImageViewer/chunks/GrImageViewer-OCUIrNh2.js.map +1 -0
- package/dist/components/GrImageViewer/index.js +2 -2
- package/dist/components/GrInput/chunks/{GrInput-gwFQ1sk4.js → GrInput-C8pOJgCi.js} +43 -66
- package/dist/components/GrInput/chunks/GrInput-C8pOJgCi.js.map +1 -0
- package/dist/components/GrInput/index.js +2 -2
- package/dist/components/GrInputTag/chunks/{GrInputTag-g-KdUI_Z.js → GrInputTag-zMgFqp2g.js} +27 -24
- package/dist/components/GrInputTag/chunks/GrInputTag-zMgFqp2g.js.map +1 -0
- package/dist/components/GrInputTag/index.js +2 -2
- package/dist/components/GrLink/chunks/{GrLink-KSTmk9Yq.js → GrLink-CYUe-Q8k.js} +14 -7
- package/dist/components/GrLink/chunks/GrLink-CYUe-Q8k.js.map +1 -0
- package/dist/components/GrLink/index.js +2 -2
- package/dist/components/GrList/chunks/{GrList-CUW2sRm_.js → GrList-Dx772Ns4.js} +1 -1
- package/dist/components/GrList/chunks/{GrList-CUW2sRm_.js.map → GrList-Dx772Ns4.js.map} +1 -1
- package/dist/components/GrList/index.js +2 -2
- package/dist/components/GrLoading/chunks/{GrLoading-mfyfghxs.js → GrLoading--X_7rdbb.js} +7 -7
- package/dist/components/GrLoading/chunks/{GrLoading-mfyfghxs.js.map → GrLoading--X_7rdbb.js.map} +1 -1
- package/dist/components/GrLoading/index.js +2 -2
- package/dist/components/GrModal/chunks/{GrModal-CSOL3fHQ.js → GrModal-BkjW9jZS.js} +7 -7
- package/dist/components/GrModal/chunks/{GrModal-CSOL3fHQ.js.map → GrModal-BkjW9jZS.js.map} +1 -1
- package/dist/components/GrModal/index.js +3 -3
- package/dist/components/GrNavbar/chunks/{GrNavbar-CHxwtFIR.js → GrNavbar-DW3MiIIf.js} +6 -6
- package/dist/components/GrNavbar/chunks/{GrNavbar-CHxwtFIR.js.map → GrNavbar-DW3MiIIf.js.map} +1 -1
- package/dist/components/GrNavbar/index.js +2 -2
- package/dist/components/GrNumberInput/chunks/{GrNumberInput-ClPBwkxx.js → GrNumberInput-CldPIWQx.js} +51 -61
- package/dist/components/GrNumberInput/chunks/GrNumberInput-CldPIWQx.js.map +1 -0
- package/dist/components/GrNumberInput/index.js +2 -2
- package/dist/components/GrPagination/chunks/{GrPagination-D2GS0ShQ.js → GrPagination-Bu9wv6it.js} +76 -25
- package/dist/components/GrPagination/chunks/GrPagination-Bu9wv6it.js.map +1 -0
- package/dist/components/GrPagination/index.js +2 -2
- package/dist/components/GrProgressBar/chunks/{GrProgressBar-BBSFpVEq.js → GrProgressBar-CC3z-Zqp.js} +3 -3
- package/dist/components/GrProgressBar/chunks/{GrProgressBar-BBSFpVEq.js.map → GrProgressBar-CC3z-Zqp.js.map} +1 -1
- package/dist/components/GrProgressBar/index.js +2 -2
- package/dist/components/GrPromptDialog/chunks/{GrPromptDialog-D_TFqKsF.js → GrPromptDialog-TmWXbpEP.js} +31 -23
- package/dist/components/GrPromptDialog/chunks/GrPromptDialog-TmWXbpEP.js.map +1 -0
- package/dist/components/GrPromptDialog/index.js +2 -2
- package/dist/components/GrRadio/chunks/{GrRadio-CSbTnrom.js → GrRadio-CPTixXaY.js} +6 -6
- package/dist/components/GrRadio/chunks/{GrRadio-CSbTnrom.js.map → GrRadio-CPTixXaY.js.map} +1 -1
- package/dist/components/GrRadio/index.js +2 -2
- package/dist/components/GrRadioGroup/chunks/{GrRadioGroup-DsrnTygR.js → GrRadioGroup-vKZCbkCp.js} +3 -3
- package/dist/components/GrRadioGroup/chunks/{GrRadioGroup-DsrnTygR.js.map → GrRadioGroup-vKZCbkCp.js.map} +1 -1
- package/dist/components/GrRadioGroup/index.js +2 -2
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-K1uZ1mYD.js → GrResponseErrorBanner-BWJNe2gr.js} +21 -18
- package/dist/components/GrResponseErrorBanner/chunks/GrResponseErrorBanner-BWJNe2gr.js.map +1 -0
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-bM8FC_Bw.js → GrResponseErrorBanner-Cdu9ekK9.js} +5 -5
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-bM8FC_Bw.js.map → GrResponseErrorBanner-Cdu9ekK9.js.map} +1 -1
- package/dist/components/GrResponseErrorBanner/index.js +2 -2
- package/dist/components/GrSegmented/chunks/{GrSegmented-DpZGs4VX.js → GrSegmented-C1y0UXpQ.js} +5 -5
- package/dist/components/GrSegmented/chunks/{GrSegmented-DpZGs4VX.js.map → GrSegmented-C1y0UXpQ.js.map} +1 -1
- package/dist/components/GrSegmented/index.js +2 -2
- package/dist/components/GrSelect/chunks/{GrSelect-DSz7jvUb.js → GrSelect-RShK21lK.js} +84 -64
- package/dist/components/GrSelect/chunks/GrSelect-RShK21lK.js.map +1 -0
- package/dist/components/GrSelect/index.js +2 -2
- package/dist/components/GrSidebar/chunks/GrSidebar-DkWozzwA.js +238 -0
- package/dist/components/GrSidebar/chunks/GrSidebar-DkWozzwA.js.map +1 -0
- package/dist/components/GrSidebar/index.js +3 -3
- package/dist/components/GrSkeleton/chunks/{GrSkeleton-B05K0QKh.js → GrSkeleton-DsN-_CDZ.js} +1 -1
- package/dist/components/GrSkeleton/chunks/{GrSkeleton-B05K0QKh.js.map → GrSkeleton-DsN-_CDZ.js.map} +1 -1
- package/dist/components/GrSkeleton/index.js +2 -2
- package/dist/components/GrSwitch/chunks/{GrSwitch-CSRtcN5-.js → GrSwitch-DAioyccZ.js} +10 -10
- package/dist/components/GrSwitch/chunks/{GrSwitch-CSRtcN5-.js.map → GrSwitch-DAioyccZ.js.map} +1 -1
- package/dist/components/GrSwitch/index.js +2 -2
- package/dist/components/GrTable/chunks/{GrTable-dTWUxzRm.js → GrTable-Db3hRnKA.js} +3 -3
- package/dist/components/GrTable/chunks/{GrTable-dTWUxzRm.js.map → GrTable-Db3hRnKA.js.map} +1 -1
- package/dist/components/GrTable/index.js +2 -2
- package/dist/components/GrTabs/chunks/{GrTabs-BfeVNMFJ.js → GrTabs-Z-FDJUr_.js} +3 -3
- package/dist/components/GrTabs/chunks/{GrTabs-BfeVNMFJ.js.map → GrTabs-Z-FDJUr_.js.map} +1 -1
- package/dist/components/GrTabs/index.js +2 -2
- package/dist/components/GrTextarea/chunks/{GrTextarea-CBBzpF2S.js → GrTextarea-D56YxhKq.js} +3 -3
- package/dist/components/GrTextarea/chunks/{GrTextarea-CBBzpF2S.js.map → GrTextarea-D56YxhKq.js.map} +1 -1
- package/dist/components/GrTextarea/index.js +2 -2
- package/dist/components/GrToaster/chunks/GrToaster-eI8YvnIo.js +189 -0
- package/dist/components/GrToaster/chunks/GrToaster-eI8YvnIo.js.map +1 -0
- package/dist/components/GrToaster/index.js +2 -2
- package/dist/components/GrTooltip/chunks/{GrTooltip-BC-40SA5.js → GrTooltip-BeyZ8ssR.js} +10 -10
- package/dist/components/GrTooltip/chunks/{GrTooltip-BC-40SA5.js.map → GrTooltip-BeyZ8ssR.js.map} +1 -1
- package/dist/components/GrTooltip/index.js +2 -2
- package/dist/components/GrTree/chunks/{GrTree-uZr5SyQI.js → GrTree-D3ODe2dB.js} +40 -35
- package/dist/components/GrTree/chunks/GrTree-D3ODe2dB.js.map +1 -0
- package/dist/components/GrTree/index.js +2 -2
- package/dist/components/GrTreeSelect/chunks/{GrTreeSelect-CytivcCa.js → GrTreeSelect-B2xBKs5Q.js} +16 -16
- package/dist/components/GrTreeSelect/chunks/{GrTreeSelect-CytivcCa.js.map → GrTreeSelect-B2xBKs5Q.js.map} +1 -1
- package/dist/components/GrTreeSelect/index.js +2 -2
- package/dist/composables/useTheme.js +48 -8
- package/dist/composables/useTheme.js.map +1 -1
- package/dist/composables/useToast.js +88 -26
- package/dist/composables/useToast.js.map +1 -1
- package/dist/directives/autofocus.js.map +1 -1
- package/dist/directives/autosize.js.map +1 -1
- package/dist/directives/clickOutside.js.map +1 -1
- package/dist/directives/dropzone.js +6 -5
- package/dist/directives/dropzone.js.map +1 -1
- package/dist/directives/hotkey.js +24 -7
- package/dist/directives/hotkey.js.map +1 -1
- package/dist/directives/loading.js +2 -2
- package/dist/directives/loading.js.map +1 -1
- package/dist/fileValidation/index.js +1 -1
- package/dist/granular-provider-node.js +7 -7
- package/dist/granular-provider-node.js.map +1 -1
- package/dist/granular-provider.js +1 -1
- package/dist/granular-provider.js.map +1 -1
- package/dist/i18n/all.js +1 -1
- package/dist/i18n/all.js.map +1 -1
- package/dist/i18n/index.js +2 -2
- package/dist/index.js +109 -534
- package/dist/index.js.map +1 -1
- package/dist/styles/base.css +32 -0
- package/dist/styles/index.css +15 -0
- package/dist/styles/preflight.css +29 -0
- package/dist/styles/themes/dark.css +107 -0
- package/dist/styles/themes/light.css +98 -0
- package/dist/styles/tokens.css +135 -0
- package/dist/types/src/components/GrButton/GrButton.vue.d.ts +25 -2
- package/dist/types/src/components/GrCheckbox/GrCheckbox.vue.d.ts +7 -2
- package/dist/types/src/components/GrConfirmDialog/GrConfirmDialog.vue.d.ts +8 -8
- package/dist/types/src/components/GrDataTable/GrDataTable.vue.d.ts +1 -1
- package/dist/types/src/components/GrDialog/GrDialog.vue.d.ts +2 -2
- package/dist/types/src/components/GrDialog/GrDialogHeader.vue.d.ts +2 -2
- package/dist/types/src/components/GrDrawer/GrDrawer.vue.d.ts +2 -2
- package/dist/types/src/components/GrFileUpload/GrFileUpload.vue.d.ts +4 -4
- package/dist/types/src/components/GrFormFile/GrFormFile.vue.d.ts +11 -11
- package/dist/types/src/components/GrImageViewer/GrImageViewer.vue.d.ts +18 -18
- package/dist/types/src/components/GrInput/GrInput.vue.d.ts +14 -0
- package/dist/types/src/components/GrInput/grInputStyles.d.ts +3 -3
- package/dist/types/src/components/GrInputTag/GrInputTag.vue.d.ts +2 -2
- package/dist/types/src/components/GrLink/GrLink.vue.d.ts +12 -6
- package/dist/types/src/components/GrLink/grLinkStyles.d.ts +31 -3
- package/dist/types/src/components/GrLink/index.d.ts +1 -1
- package/dist/types/src/components/GrLoading/GrLoading.vue.d.ts +1 -1
- package/dist/types/src/components/GrModal/grModalStyles.d.ts +1 -1
- package/dist/types/src/components/GrNumberInput/GrNumberInput.vue.d.ts +17 -4
- package/dist/types/src/components/GrPagination/GrPagination.vue.d.ts +13 -1
- package/dist/types/src/components/GrPromptDialog/GrPromptDialog.vue.d.ts +12 -12
- package/dist/types/src/components/GrSegmented/GrSegmented.vue.d.ts +1 -1
- package/dist/types/src/components/GrSegmented/grSegmentedStyles.d.ts +5 -5
- package/dist/types/src/components/GrSelect/GrSelect.vue.d.ts +1 -1
- package/dist/types/src/components/GrSelect/grSelectStyles.d.ts +2 -1
- package/dist/types/src/components/GrSidebar/GrSidebar.vue.d.ts +33 -10
- package/dist/types/src/components/GrSidebar/GrSidebarItem.vue.d.ts +64 -0
- package/dist/types/src/components/GrSidebar/index.d.ts +1 -0
- package/dist/types/src/components/GrSidebar/sidebarContext.d.ts +9 -0
- package/dist/types/src/components/GrSwitch/GrSwitch.vue.d.ts +1 -1
- package/dist/types/src/components/GrSwitch/grSwitchStyles.d.ts +2 -2
- package/dist/types/src/components/GrToaster/GrToaster.vue.d.ts +9 -4
- package/dist/types/src/components/GrTree/GrTree.vue.d.ts +1 -1
- package/dist/types/src/components/GrTreeSelect/GrTreeSelect.vue.d.ts +2 -2
- package/dist/types/src/components/GrTreeSelect/grTreeSelectStyles.d.ts +1 -1
- package/dist/types/src/components/GrTreeSelect/grTreeSelectTypes.d.ts +1 -1
- package/dist/types/src/composables/internal/useAddonMeasurement.d.ts +18 -0
- package/dist/types/src/composables/internal/useEscapeToClose.d.ts +11 -0
- package/dist/types/src/composables/useTheme.d.ts +5 -2
- package/dist/types/src/composables/useToast.d.ts +33 -1
- package/dist/types/src/directives/hotkey.d.ts +14 -0
- package/dist/types/src/granular-provider/shared.d.ts +1 -3
- package/dist/types/src/i18n/messages/en.d.ts +120 -0
- package/dist/types/src/i18n/messages/es.d.ts +120 -0
- package/dist/types/src/i18n/messages/ru.d.ts +120 -0
- package/dist/types/src/index.d.ts +2 -2
- package/dist/vue/index.js.map +1 -1
- package/dist/web-types.json +4673 -0
- package/package.json +26 -20
- package/dist/chunks/arrow-up-DZdIrpaF.js.map +0 -1
- package/dist/chunks/config-C6zT56Jc2.js.map +0 -1
- package/dist/chunks/config-C8MM2Dg0.js.map +0 -1
- package/dist/chunks/config-NkbzVFZo.js +0 -59
- package/dist/chunks/config-NkbzVFZo.js.map +0 -1
- package/dist/chunks/config-RjfJFv1Y.js.map +0 -1
- package/dist/chunks/config-hSlCXHoG.js.map +0 -1
- package/dist/chunks/en-B_fSdoTi.js +0 -72
- package/dist/chunks/en-B_fSdoTi.js.map +0 -1
- package/dist/chunks/es-DKP6fLir.js +0 -72
- package/dist/chunks/es-DKP6fLir.js.map +0 -1
- package/dist/chunks/grBadgeStyles-Cq0hH2Ls.js.map +0 -1
- package/dist/chunks/grButtonStyles-DKuXUemw.js +0 -191
- package/dist/chunks/grButtonStyles-DKuXUemw.js.map +0 -1
- package/dist/chunks/grSelectStyles-AjWWl007.js.map +0 -1
- package/dist/chunks/grStyle-D-gPHdyW.js.map +0 -1
- package/dist/chunks/info-C0bHmdZq.js.map +0 -1
- package/dist/chunks/loader-circle-BUntgosj.js.map +0 -1
- package/dist/chunks/ru-S6VlnurJ.js +0 -72
- package/dist/chunks/ru-S6VlnurJ.js.map +0 -1
- package/dist/chunks/safelist-_UVzJrgE2.js.map +0 -1
- package/dist/chunks/shared-DpjTvFno.js +0 -169
- package/dist/chunks/shared-DpjTvFno.js.map +0 -1
- package/dist/chunks/x-Pa6C2hwi.js.map +0 -1
- package/dist/chunks/x-circle-DQSlBLmX.js.map +0 -1
- package/dist/components/GrAlert/chunks/GrAlert-HyCjYJeL.js.map +0 -1
- package/dist/components/GrButton/chunks/GrButton-CPDKonoB.js +0 -83
- package/dist/components/GrButton/chunks/GrButton-CPDKonoB.js.map +0 -1
- package/dist/components/GrButtonGroup/chunks/GrButtonGroup-CPOH6V-P.js.map +0 -1
- package/dist/components/GrCard/chunks/GrCard-6yk1RRAQ.js.map +0 -1
- package/dist/components/GrCheckbox/chunks/GrCheckbox-Bt3d7ckE.js.map +0 -1
- package/dist/components/GrConfirmDialog/chunks/GrConfirmDialog-Bi2KLumL.js.map +0 -1
- package/dist/components/GrDialog/chunks/GrDialog-CxK4Lj4F.js.map +0 -1
- package/dist/components/GrDrawer/chunks/GrDrawer-BW3wtI7h.js.map +0 -1
- package/dist/components/GrDropdown/chunks/GrDropdown-BGKeEfZ1.js.map +0 -1
- package/dist/components/GrFileUpload/chunks/GrFileUpload-CBKK3dgC.js.map +0 -1
- package/dist/components/GrFormFile/chunks/GrFormFile-CkR6cYqf.js.map +0 -1
- package/dist/components/GrImageViewer/chunks/GrImageViewer-BG40DsHa.js.map +0 -1
- package/dist/components/GrInput/chunks/GrInput-gwFQ1sk4.js.map +0 -1
- package/dist/components/GrInputTag/chunks/GrInputTag-g-KdUI_Z.js.map +0 -1
- package/dist/components/GrLink/chunks/GrLink-KSTmk9Yq.js.map +0 -1
- package/dist/components/GrNumberInput/chunks/GrNumberInput-ClPBwkxx.js.map +0 -1
- package/dist/components/GrPagination/chunks/GrPagination-D2GS0ShQ.js.map +0 -1
- package/dist/components/GrPromptDialog/chunks/GrPromptDialog-D_TFqKsF.js.map +0 -1
- package/dist/components/GrResponseErrorBanner/chunks/GrResponseErrorBanner-K1uZ1mYD.js.map +0 -1
- package/dist/components/GrSelect/chunks/GrSelect-DSz7jvUb.js.map +0 -1
- package/dist/components/GrSidebar/chunks/GrSidebar-BW8LRMZ-.js +0 -44
- package/dist/components/GrSidebar/chunks/GrSidebar-BW8LRMZ-.js.map +0 -1
- package/dist/components/GrToaster/chunks/GrToaster-C6_iHk2J.js +0 -172
- package/dist/components/GrToaster/chunks/GrToaster-C6_iHk2J.js.map +0 -1
- package/dist/components/GrTree/chunks/GrTree-uZr5SyQI.js.map +0 -1
- /package/dist/chunks/{_plugin-vue_export-helper-DQR7Sy7Q.js → _plugin-vue_export-helper-BOaGB7Aw.js} +0 -0
- /package/dist/chunks/{adapter-BqqjEZGU.js → adapter-CAOxmn2G.js} +0 -0
- /package/dist/chunks/{arrow-up-DZdIrpaF.js → arrow-up-C_G4jg8M.js} +0 -0
- /package/dist/chunks/{classTokens-BPeBXNzu.js → classTokens-BzazaERD.js} +0 -0
- /package/dist/chunks/{config-DZrlovR42.js → config-8Pcutu1j2.js} +0 -0
- /package/dist/chunks/{config-VJuoznpH.js → config-B0qIpo8m.js} +0 -0
- /package/dist/chunks/{config-DbghHyY_.js → config-BEegFP74.js} +0 -0
- /package/dist/chunks/{config-BeBsN0c12.js → config-BLHqZhy-2.js} +0 -0
- /package/dist/chunks/{config-BV4vBzdm.js → config-BNu8lFQB.js} +0 -0
- /package/dist/chunks/{config-DhQc1TRY.js → config-BUHuGBik.js} +0 -0
- /package/dist/chunks/{config-CPSdAjUi.js → config-BWGGp7uV.js} +0 -0
- /package/dist/chunks/{config-BduXEXjt.js → config-BXtAmU3s.js} +0 -0
- /package/dist/chunks/{config-CzgNEHKi.js → config-Bah4oHwL.js} +0 -0
- /package/dist/chunks/{config-lMDE_8A5.js → config-C86UzUYf.js} +0 -0
- /package/dist/chunks/{config-BgBWt9-A.js → config-C9AcVDkv.js} +0 -0
- /package/dist/chunks/{config-BuoIngj32.js → config-CGHLoBlH2.js} +0 -0
- /package/dist/chunks/{config-ChQxl75m.js → config-CThzliFi.js} +0 -0
- /package/dist/chunks/{config-DDwBSoc_.js → config-Cb2PAlSD.js} +0 -0
- /package/dist/chunks/{config-C5-ujXCI.js → config-D7GZO-Dx.js} +0 -0
- /package/dist/chunks/{config-CUwF4E4R.js → config-DBmdgoVf.js} +0 -0
- /package/dist/chunks/{config-C9MblwGq.js → config-DICOd-2X.js} +0 -0
- /package/dist/chunks/{config-BLa1TEGm2.js → config-DpqOnJiz2.js} +0 -0
- /package/dist/chunks/{config-V3LF-b_F.js → config-Dxuwwepq.js} +0 -0
- /package/dist/chunks/{config-Doa_gU40.js → config-HZto2PVy.js} +0 -0
- /package/dist/chunks/{config-Dl5aZ5VR.js → config-JOtB4mzs.js} +0 -0
- /package/dist/chunks/{config-CWTfyPNI.js → config-JpHA4Xx0.js} +0 -0
- /package/dist/chunks/{config-B3dn-gdC.js → config-PFg39mYo.js} +0 -0
- /package/dist/chunks/{config-Bh4NWWsQ.js → config-QaIc_gRa.js} +0 -0
- /package/dist/chunks/{config-vcDVCYXo.js → config-U4m9PSql.js} +0 -0
- /package/dist/chunks/{config-C_q_4FrU.js → config-ZiXWIRBX.js} +0 -0
- /package/dist/chunks/{config-DDUPnue12.js → config-ipvU0lzP2.js} +0 -0
- /package/dist/chunks/{config-D5ek7VSi.js → config-xR4XVmcy.js} +0 -0
- /package/dist/chunks/{dialogShared-BtXUk6Zc.js → dialogShared-CxW62PQE.js} +0 -0
- /package/dist/chunks/{grLoadingStyles-DmI-SJ3i.js → grLoadingStyles-R5sreH__.js} +0 -0
- /package/dist/chunks/{info-C0bHmdZq.js → info-Be2OccTu.js} +0 -0
- /package/dist/chunks/{loader-circle-BUntgosj.js → loader-circle-CfVLz7lb.js} +0 -0
- /package/dist/chunks/{x-Pa6C2hwi.js → x-2KXnqxiD.js} +0 -0
- /package/dist/chunks/{x-circle-DQSlBLmX.js → x-circle-BCBURwyX.js} +0 -0
- /package/dist/components/GrBottomNav/chunks/{GrBottomNav-XPHwd7UQ.js → GrBottomNav-usuMgG8_.js} +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"GrFileUpload-DvWPpiJS.js","names":["$slots"],"sources":["../../../../src/components/GrFileUpload/uploadViaXhr.ts","../../../../src/components/GrFileUpload/uploadState.ts","../../../../src/components/GrFileUpload/GrFileUpload.vue","../../../../src/components/GrFileUpload/GrFileUpload.vue"],"sourcesContent":["/**\n * Загрузка файлов через `XMLHttpRequest` с поддержкой прогресса аплоада и\n * отмены по `AbortSignal`. Используется в `GrFileUpload` для ветки `action`,\n * а также может применяться пользователем напрямую в `request`-загрузчике.\n */\n\nexport type GrUploadExtraDataValue = string | Blob\n\nexport type GrUploadExtraData = Record<string, GrUploadExtraDataValue | GrUploadExtraDataValue[]>\n\nexport interface GrUploadProgressInfo {\n /** Процент `0..100`. Для запросов без `lengthComputable` значение `0` и `indeterminate = true`. */\n percent: number\n loaded: number\n total: number\n indeterminate: boolean\n}\n\nexport interface UploadViaXhrOptions {\n url: string\n files: File[]\n name: string\n headers?: Record<string, string>\n withCredentials?: boolean\n extraData?: GrUploadExtraData\n signal: AbortSignal\n onProgress?: (info: GrUploadProgressInfo) => void\n}\n\nexport class GrUploadAbortError extends Error {\n constructor(message = 'Upload aborted') {\n super(message)\n this.name = 'GrUploadAbortError'\n }\n}\n\nexport class GrUploadHttpError extends Error {\n status: number\n payload: unknown\n\n constructor(status: number, payload: unknown) {\n super(`Upload failed with status ${status}`)\n this.name = 'GrUploadHttpError'\n this.status = status\n this.payload = payload\n }\n}\n\nfunction appendExtraFormData(body: FormData, extraData: GrUploadExtraData | undefined) {\n if (!extraData) return\n\n for (const [key, value] of Object.entries(extraData)) {\n if (Array.isArray(value)) {\n for (const entry of value) body.append(key, entry)\n continue\n }\n\n body.append(key, value)\n }\n}\n\nfunction parseResponse(xhr: XMLHttpRequest): unknown {\n const contentType = xhr.getResponseHeader('content-type') ?? ''\n const raw = xhr.responseText\n\n if (contentType.includes('application/json')) {\n try {\n return JSON.parse(raw)\n } catch {\n return raw\n }\n }\n\n return raw\n}\n\nexport function uploadViaXhr(options: UploadViaXhrOptions): Promise<unknown> {\n const { url, files, name, headers, withCredentials, extraData, signal, onProgress } = options\n\n return new Promise<unknown>((resolve, reject) => {\n if (signal.aborted) {\n reject(new GrUploadAbortError())\n return\n }\n\n const body = new FormData()\n for (const file of files) body.append(name, file)\n appendExtraFormData(body, extraData)\n\n const xhr = new XMLHttpRequest()\n xhr.open('POST', url, true)\n xhr.withCredentials = !!withCredentials\n\n if (headers) {\n for (const [key, value] of Object.entries(headers))\n xhr.setRequestHeader(key, value)\n }\n\n const onAbort = () => {\n try {\n xhr.abort()\n } catch {\n /* ignore */\n }\n }\n\n signal.addEventListener('abort', onAbort)\n\n const cleanup = () => {\n signal.removeEventListener('abort', onAbort)\n }\n\n if (onProgress) {\n xhr.upload.addEventListener('progress', (event) => {\n const indeterminate = !event.lengthComputable\n const total = indeterminate ? 0 : event.total\n const loaded = indeterminate ? 0 : event.loaded\n const percent = indeterminate || total === 0 ? 0 : Math.min(100, (loaded / total) * 100)\n onProgress({ percent, loaded, total, indeterminate })\n })\n }\n\n xhr.addEventListener('load', () => {\n cleanup()\n const payload = parseResponse(xhr)\n const status = xhr.status\n\n if (status >= 200 && status < 300) {\n if (onProgress) onProgress({ percent: 100, loaded: 1, total: 1, indeterminate: false })\n resolve(payload)\n return\n }\n\n reject(new GrUploadHttpError(status, payload))\n })\n\n xhr.addEventListener('error', () => {\n cleanup()\n reject(new Error('Network error during upload'))\n })\n\n xhr.addEventListener('abort', () => {\n cleanup()\n reject(new GrUploadAbortError())\n })\n\n xhr.send(body)\n })\n}\n","/**\n * Состояние процесса загрузки в `GrFileUpload`.\n *\n * Используется как для внутреннего управления UI, так и пробрасывается наружу\n * через scoped-слоты (`progress`, `default`) и `defineExpose`.\n */\n\nexport type GrUploadPhase = 'idle' | 'uploading' | 'success' | 'error'\n\nexport interface GrUploadStateIdle {\n phase: 'idle'\n percent: 0\n indeterminate: false\n loaded: 0\n total: 0\n}\n\nexport interface GrUploadStateUploading {\n phase: 'uploading'\n percent: number\n indeterminate: boolean\n loaded: number\n total: number\n}\n\nexport interface GrUploadStateSuccess {\n phase: 'success'\n percent: 100\n indeterminate: false\n loaded: number\n total: number\n}\n\nexport interface GrUploadStateError {\n phase: 'error'\n percent: number\n indeterminate: false\n loaded: number\n total: number\n error: unknown\n}\n\nexport type GrUploadState =\n | GrUploadStateIdle\n | GrUploadStateUploading\n | GrUploadStateSuccess\n | GrUploadStateError\n\nexport const GR_UPLOAD_STATE_IDLE: GrUploadStateIdle = Object.freeze({\n phase: 'idle',\n percent: 0,\n indeterminate: false,\n loaded: 0,\n total: 0,\n})\n","<script setup lang=\"ts\">\nimport { Comment, computed, Fragment, nextTick, reactive, ref, Text, useSlots, type VNode } from 'vue'\n\nimport IconArrowUp from '~icons/lucide/arrow-up'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport GrProgressBar from '../GrProgressBar/GrProgressBar.vue'\nimport type { GrProgressBarTone } from '../GrProgressBar/grStyle'\nimport type { FileValidator, FileValidatorSource } from '../../fileValidation'\nimport type { GrUploadProgressInfo } from './uploadViaXhr'\nimport type { GrUploadState } from './uploadState'\n\nimport { FileValidationError, runFileValidators } from '../../fileValidation'\nimport { GrUploadAbortError, uploadViaXhr } from './uploadViaXhr'\nimport { GR_UPLOAD_STATE_IDLE } from './uploadState'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nexport type GrFileUploadExtraDataValue = string | Blob\n\nexport type GrFileUploadExtraData = Record<string, GrFileUploadExtraDataValue | GrFileUploadExtraDataValue[]>\n\nexport type GrFileUploadRequestCtx = {\n signal: AbortSignal\n extraData?: GrFileUploadExtraData\n /**\n * Колбэк прогресса аплоада. Пользовательский `request` (например, axios)\n * должен вызывать его из `onUploadProgress`, чтобы `GrFileUpload` отображал\n * прогресс через слот `progress` / дефолтный `GrProgressBar`.\n */\n onProgress?: (info: GrUploadProgressInfo) => void\n}\n\nexport type GrFileUploadRequest = (files: File[], ctx: GrFileUploadRequestCtx) => Promise<any>\n\n/**\n * Пропы `GrFileUpload`.\n *\n * Либо `action` (URL для POST multipart/form-data), либо `request` — кастомный\n * загрузчик (например, через axios). Если переданы оба — приоритет у `request`.\n *\n * `placeholder` — надпись в дефолтном UI-варианте (без слота default).\n */\nexport interface GrFileUploadProps {\n action?: string\n request?: GrFileUploadRequest\n name?: string\n multiple?: boolean\n limit?: number\n onExceed?: (files: File[], limit: number) => void\n beforeUpload?: (file: File) => boolean | Promise<unknown>\n validators?: FileValidator[]\n disabled?: boolean\n headers?: Record<string, string>\n withCredentials?: boolean\n showFileList?: boolean\n uploadExtraData?: (files: File[]) => GrFileUploadExtraData | undefined\n /** i18n: надпись-подсказка в дефолтном UI. */\n placeholder?: string\n /** Показывать дефолтный прогресс-бар (если не используется слот `progress`). */\n showProgress?: boolean\n /** Цветовой тон полосы прогресса в фазе `uploading`. */\n progressTone?: GrProgressBarTone\n /** aria-label для прогресс-бара. */\n progressLabel?: string\n /** Через сколько мс после `success` скрыть прогресс-бар. `0` — не скрывать. */\n hideProgressOnSuccess?: number\n}\n\nconst props = withDefaults(\n defineProps<GrFileUploadProps>(),\n {\n action: undefined,\n request: undefined,\n name: 'file',\n multiple: false,\n limit: undefined,\n onExceed: undefined,\n beforeUpload: undefined,\n validators: undefined,\n disabled: false,\n headers: undefined,\n withCredentials: false,\n showFileList: false,\n uploadExtraData: undefined,\n placeholder: undefined,\n showProgress: true,\n progressTone: 'primary',\n progressLabel: undefined,\n hideProgressOnSuccess: 800,\n },\n)\n\nconst emit = defineEmits<{\n (e: 'success', payload: any): void\n (e: 'error', error: unknown): void\n (e: 'progress', percent: number, info?: GrUploadProgressInfo): void\n (e: 'change', files: File[]): void\n (e: 'stateChange', state: GrUploadState): void\n}>()\n\nconst slots = useSlots()\n\nconst { t } = useGranularityTranslations()\nconst resolvedPlaceholder = computed(() => props.placeholder ?? t('gr.fileUpload.placeholder', 'Drag files here or click to select'))\nconst resolvedProgressLabel = computed(() => props.progressLabel ?? t('gr.fileUpload.progress', 'Upload progress'))\n\nfunction flattenSlotNodes(nodes: VNode[]): VNode[] {\n const out: VNode[] = []\n\n for (const node of nodes) {\n if (node.type === Fragment && Array.isArray(node.children)) {\n out.push(...flattenSlotNodes(node.children as VNode[]))\n continue\n }\n\n out.push(node)\n }\n\n return out\n}\n\nfunction isWhitespaceTextNode(node: VNode): boolean {\n if (node.type !== Text) return false\n return typeof node.children === 'string' && node.children.trim().length === 0\n}\n\nfunction slotIsTextOnly(nodes: VNode[]): boolean {\n const flat = flattenSlotNodes(nodes)\n const meaningful = flat.filter(node => node.type !== Comment && !isWhitespaceTextNode(node))\n\n if (meaningful.length === 0) return true\n\n for (const node of meaningful) {\n if (node.type !== Text) return false\n }\n\n return true\n}\n\nconst defaultSlotNodes = computed(() => {\n return slots.default ? flattenSlotNodes(slots.default({} as any)) : []\n})\n\nconst hasCustomUi = computed(() => {\n return !!slots.default && !slotIsTextOnly(defaultSlotNodes.value)\n})\n\nconst inputRef = ref<HTMLInputElement | null>(null)\nconst isOver = ref(false)\nlet overCounter = 0\n\nconst lastFiles = ref<File[]>([])\n\nconst state = reactive<GrUploadState>({ ...GR_UPLOAD_STATE_IDLE }) as GrUploadState\n\nlet activeController: AbortController | null = null\nlet hideSuccessTimer: ReturnType<typeof setTimeout> | null = null\n\nfunction clearHideSuccessTimer() {\n if (hideSuccessTimer !== null) {\n clearTimeout(hideSuccessTimer)\n hideSuccessTimer = null\n }\n}\n\nfunction assignState(next: GrUploadState) {\n // мутируем через Object.assign, чтобы сохранить reactive ссылку\n for (const key of Object.keys(state) as (keyof GrUploadState)[])\n delete (state as any)[key]\n Object.assign(state, next)\n emit('stateChange', state as GrUploadState)\n}\n\nfunction setStateIdle() {\n assignState({ ...GR_UPLOAD_STATE_IDLE })\n}\n\nfunction setStateUploading(info?: GrUploadProgressInfo) {\n assignState({\n phase: 'uploading',\n percent: info?.percent ?? 0,\n indeterminate: info?.indeterminate ?? true,\n loaded: info?.loaded ?? 0,\n total: info?.total ?? 0,\n })\n}\n\nfunction setStateSuccess(info: { loaded: number, total: number }) {\n assignState({\n phase: 'success',\n percent: 100,\n indeterminate: false,\n loaded: info.loaded,\n total: info.total,\n })\n}\n\nfunction setStateError(error: unknown) {\n const prev = state\n assignState({\n phase: 'error',\n percent: prev.phase === 'uploading' ? prev.percent : 0,\n indeterminate: false,\n loaded: prev.phase === 'uploading' ? prev.loaded : 0,\n total: prev.phase === 'uploading' ? prev.total : 0,\n error,\n })\n}\n\nfunction handleProgress(info: GrUploadProgressInfo) {\n if (state.phase !== 'uploading') return\n assignState({\n phase: 'uploading',\n percent: info.percent,\n indeterminate: info.indeterminate,\n loaded: info.loaded,\n total: info.total,\n })\n emit('progress', info.percent, info)\n}\n\nconst tabIndex = computed(() => (props.disabled ? -1 : 0))\n\nconst hiddenInputStyle = {\n position: 'fixed',\n top: '-9999px',\n left: '-9999px',\n width: '1px',\n height: '1px',\n opacity: '0',\n overflow: 'hidden',\n pointerEvents: 'none',\n} as const satisfies Record<string, string>\n\nfunction setOver(next: boolean) {\n if (isOver.value === next) return\n isOver.value = next\n}\n\nfunction openDialog() {\n if (props.disabled) return\n inputRef.value?.click()\n}\n\nfunction abort() {\n activeController?.abort()\n activeController = null\n}\n\nfunction normalizeLimit(limit: number | undefined): number | undefined {\n if (typeof limit !== 'number') return undefined\n if (!Number.isFinite(limit)) return undefined\n if (limit <= 0) return undefined\n return Math.floor(limit)\n}\n\n\nasync function uploadViaAction(files: File[], signal: AbortSignal, extraData: GrFileUploadExtraData | undefined) {\n if (!props.action) throw new Error('GrFileUpload: either `action` or `request` must be provided')\n\n return uploadViaXhr({\n url: props.action,\n files,\n name: props.name,\n headers: props.headers,\n withCredentials: props.withCredentials,\n extraData,\n signal,\n onProgress: handleProgress,\n })\n}\n\nasync function runBeforeUpload(files: File[]): Promise<'ok' | { aborted: true; reason: unknown }> {\n if (!props.beforeUpload) return 'ok'\n\n for (const file of files) {\n try {\n const result = props.beforeUpload(file)\n\n if (result === false) {\n return { aborted: true, reason: new Error('Upload aborted by beforeUpload') }\n }\n\n if (result && typeof (result as any).then === 'function')\n await result\n } catch (error) {\n return { aborted: true, reason: error }\n }\n }\n\n return 'ok'\n}\n\nasync function handleFiles(files: File[], source: FileValidatorSource = 'input') {\n if (props.disabled) return\n if (!files.length) return\n\n const normalizedLimit = normalizeLimit(props.limit)\n if (props.multiple && normalizedLimit && files.length > normalizedLimit) {\n props.onExceed?.(files, normalizedLimit)\n emit('error', new Error(`Too many files selected, limit=${normalizedLimit}`))\n return\n }\n\n const { files: valid, issues } = await runFileValidators(files, props.validators ?? [], {\n source,\n multiple: props.multiple,\n })\n\n if (issues.length > 0) {\n emit('error', new FileValidationError(issues, valid))\n return\n }\n\n if (!valid.length) return\n\n lastFiles.value = valid\n\n const before = await runBeforeUpload(valid)\n if (before !== 'ok') {\n emit('error', before.reason)\n return\n }\n\n let extraData: GrFileUploadExtraData | undefined\n try {\n extraData = props.uploadExtraData?.(valid)\n } catch (error) {\n emit('error', error)\n return\n }\n\n abort()\n clearHideSuccessTimer()\n\n const controller = new AbortController()\n activeController = controller\n\n setStateUploading()\n emit('progress', 0, { percent: 0, loaded: 0, total: 0, indeterminate: true })\n\n try {\n const payload = props.request\n ? await props.request(valid, { signal: controller.signal, extraData, onProgress: handleProgress })\n : await uploadViaAction(valid, controller.signal, extraData)\n\n const finalLoaded = state.phase === 'uploading' ? state.total || state.loaded : 0\n setStateSuccess({ loaded: finalLoaded, total: finalLoaded })\n emit('success', payload)\n emit('change', valid)\n emit('progress', 100, { percent: 100, loaded: finalLoaded, total: finalLoaded, indeterminate: false })\n\n if (props.hideProgressOnSuccess && props.hideProgressOnSuccess > 0) {\n hideSuccessTimer = setTimeout(() => {\n if (state.phase === 'success') setStateIdle()\n hideSuccessTimer = null\n }, props.hideProgressOnSuccess)\n }\n } catch (error) {\n if (error instanceof GrUploadAbortError) {\n setStateIdle()\n } else {\n setStateError(error)\n }\n emit('error', error)\n } finally {\n if (activeController === controller) activeController = null\n }\n}\n\nfunction onDragEnter(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter += 1\n setOver(true)\n}\n\nfunction onDragOver(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n if (event.dataTransfer) event.dataTransfer.dropEffect = 'copy'\n}\n\nfunction onDragLeave(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter = Math.max(0, overCounter - 1)\n if (overCounter === 0) setOver(false)\n}\n\nfunction onDrop(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter = 0\n setOver(false)\n\n const files = event.dataTransfer?.files ? Array.prototype.slice.call(event.dataTransfer.files) as File[] : []\n void handleFiles(files, 'drop')\n}\n\nasync function onInputChange(event: Event) {\n if (props.disabled) return\n\n const target = event.target as HTMLInputElement | null\n const files = target?.files ? Array.prototype.slice.call(target.files) as File[] : []\n\n if (target) target.value = ''\n\n await nextTick()\n await handleFiles(files, 'input')\n}\n\nfunction onKeydown(event: KeyboardEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n\n if (event.key === 'Enter' || event.key === ' ') {\n event.preventDefault()\n openDialog()\n }\n}\n\nfunction onRootClick() {\n if (hasCustomUi.value) return\n openDialog()\n}\n\nfunction onRootKeydown(event: KeyboardEvent) {\n if (hasCustomUi.value) return\n onKeydown(event)\n}\n\nconst effectiveProgressTone = computed<GrProgressBarTone>(() => {\n if (state.phase === 'error') return 'danger'\n if (state.phase === 'success') return 'success'\n return props.progressTone\n})\n\nconst progressVisible = computed(() => state.phase !== 'idle')\nconst progressPercent = computed(() => (state.phase === 'uploading' && state.indeterminate ? 0 : state.percent))\nconst progressText = computed(() => {\n if (state.phase === 'uploading' && state.indeterminate) return ''\n return `${Math.round(progressPercent.value)}%`\n})\n\ndefineExpose({\n uploadFiles: handleFiles,\n abort,\n openDialog,\n state,\n})\n</script>\n\n<template>\n <div\n data-gr-file-upload\n :role=\"hasCustomUi ? undefined : 'button'\"\n :tabindex=\"hasCustomUi ? undefined : tabIndex\"\n :aria-disabled=\"hasCustomUi ? undefined : disabled ? 'true' : 'false'\"\n :class=\"\n hasCustomUi\n ? 'inline-block'\n : [\n 'relative w-full rounded-[var(--gr-radius-lg)] border border-dashed border-[var(--brd)] bg-[var(--card)] px-5 py-6 outline-none transition',\n disabled\n ? 'opacity-60 cursor-not-allowed'\n : 'cursor-pointer hover:bg-[var(--muted)] focus-visible:ring-2 focus-visible:ring-[var(--ring)] focus-visible:ring-offset-2 focus-visible:ring-offset-[var(--bg)]',\n isOver && !disabled ? 'border-[var(--ring)] bg-[var(--muted)]' : '',\n ]\n \"\n @click=\"onRootClick\"\n @keydown=\"onRootKeydown\"\n @dragenter=\"onDragEnter\"\n @dragover=\"onDragOver\"\n @dragleave=\"onDragLeave\"\n @drop=\"onDrop\"\n >\n <input\n ref=\"inputRef\"\n data-gr-file-upload-input\n :style=\"hiddenInputStyle\"\n type=\"file\"\n tabindex=\"-1\"\n aria-hidden=\"true\"\n :name=\"name\"\n :multiple=\"multiple\"\n :disabled=\"disabled\"\n @change=\"onInputChange\"\n >\n\n <slot\n v-if=\"hasCustomUi\"\n :open-dialog=\"openDialog\"\n :abort=\"abort\"\n :disabled=\"disabled\"\n :files=\"lastFiles\"\n :is-over=\"isOver\"\n :state=\"state\"\n />\n\n <div v-else class=\"flex items-start gap-4\">\n <div\n data-gr-file-upload-icon\n class=\"h-12 w-12 shrink-0 rounded-[12px] bg-[var(--muted)] border border-[var(--brd)] flex items-center justify-center\"\n aria-hidden=\"true\"\n >\n <GrIcon class=\"h-6 w-6 text-[var(--muted-fg)]\">\n <IconArrowUp />\n </GrIcon>\n </div>\n\n <div class=\"min-w-0\">\n <div data-gr-file-upload-label class=\"text-[14px] font-700\">\n <slot name=\"label\">\n <slot>\n {{ resolvedPlaceholder }}\n </slot>\n </slot>\n </div>\n\n <div v-if=\"$slots.tip\" data-gr-file-upload-tip class=\"mt-1 text-[13px] text-[var(--muted-fg)]\">\n <slot name=\"tip\" />\n </div>\n <div v-else class=\"mt-1 text-[13px] text-[var(--muted-fg)]\" />\n\n <ul v-if=\"showFileList && lastFiles.length\" data-gr-file-upload-list class=\"mt-3 space-y-1\">\n <li\n v-for=\"file in lastFiles\"\n :key=\"file.name\"\n data-gr-file-upload-item\n class=\"text-[13px]\"\n >\n <span class=\"font-600\">{{ file.name }}</span>\n <span class=\"text-[var(--muted-fg)]\"> · {{ Math.ceil(file.size / 1024) }} KB</span>\n </li>\n </ul>\n\n <slot\n v-if=\"showProgress || $slots.progress\"\n name=\"progress\"\n :state=\"state\"\n :percent=\"state.percent\"\n :indeterminate=\"state.phase === 'uploading' && state.indeterminate\"\n :phase=\"state.phase\"\n :files=\"lastFiles\"\n :abort=\"abort\"\n >\n <div\n v-if=\"showProgress\"\n data-gr-file-upload-progress\n class=\"mt-3 transition-opacity duration-150\"\n :class=\"progressVisible ? 'opacity-100' : 'opacity-0 pointer-events-none'\"\n :aria-hidden=\"!progressVisible\"\n >\n <div class=\"flex items-center gap-2\">\n <GrProgressBar\n :value=\"progressPercent\"\n :tone=\"effectiveProgressTone\"\n :aria-label=\"resolvedProgressLabel\"\n />\n <span\n data-gr-file-upload-progress-text\n class=\"text-[12px] text-[var(--muted-fg)] tabular-nums min-w-[3ch] text-right\"\n >{{ progressText }}</span>\n </div>\n </div>\n </slot>\n </div>\n </div>\n </div>\n</template>","<script setup lang=\"ts\">\nimport { Comment, computed, Fragment, nextTick, reactive, ref, Text, useSlots, type VNode } from 'vue'\n\nimport IconArrowUp from '~icons/lucide/arrow-up'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport GrProgressBar from '../GrProgressBar/GrProgressBar.vue'\nimport type { GrProgressBarTone } from '../GrProgressBar/grStyle'\nimport type { FileValidator, FileValidatorSource } from '../../fileValidation'\nimport type { GrUploadProgressInfo } from './uploadViaXhr'\nimport type { GrUploadState } from './uploadState'\n\nimport { FileValidationError, runFileValidators } from '../../fileValidation'\nimport { GrUploadAbortError, uploadViaXhr } from './uploadViaXhr'\nimport { GR_UPLOAD_STATE_IDLE } from './uploadState'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nexport type GrFileUploadExtraDataValue = string | Blob\n\nexport type GrFileUploadExtraData = Record<string, GrFileUploadExtraDataValue | GrFileUploadExtraDataValue[]>\n\nexport type GrFileUploadRequestCtx = {\n signal: AbortSignal\n extraData?: GrFileUploadExtraData\n /**\n * Колбэк прогресса аплоада. Пользовательский `request` (например, axios)\n * должен вызывать его из `onUploadProgress`, чтобы `GrFileUpload` отображал\n * прогресс через слот `progress` / дефолтный `GrProgressBar`.\n */\n onProgress?: (info: GrUploadProgressInfo) => void\n}\n\nexport type GrFileUploadRequest = (files: File[], ctx: GrFileUploadRequestCtx) => Promise<any>\n\n/**\n * Пропы `GrFileUpload`.\n *\n * Либо `action` (URL для POST multipart/form-data), либо `request` — кастомный\n * загрузчик (например, через axios). Если переданы оба — приоритет у `request`.\n *\n * `placeholder` — надпись в дефолтном UI-варианте (без слота default).\n */\nexport interface GrFileUploadProps {\n action?: string\n request?: GrFileUploadRequest\n name?: string\n multiple?: boolean\n limit?: number\n onExceed?: (files: File[], limit: number) => void\n beforeUpload?: (file: File) => boolean | Promise<unknown>\n validators?: FileValidator[]\n disabled?: boolean\n headers?: Record<string, string>\n withCredentials?: boolean\n showFileList?: boolean\n uploadExtraData?: (files: File[]) => GrFileUploadExtraData | undefined\n /** i18n: надпись-подсказка в дефолтном UI. */\n placeholder?: string\n /** Показывать дефолтный прогресс-бар (если не используется слот `progress`). */\n showProgress?: boolean\n /** Цветовой тон полосы прогресса в фазе `uploading`. */\n progressTone?: GrProgressBarTone\n /** aria-label для прогресс-бара. */\n progressLabel?: string\n /** Через сколько мс после `success` скрыть прогресс-бар. `0` — не скрывать. */\n hideProgressOnSuccess?: number\n}\n\nconst props = withDefaults(\n defineProps<GrFileUploadProps>(),\n {\n action: undefined,\n request: undefined,\n name: 'file',\n multiple: false,\n limit: undefined,\n onExceed: undefined,\n beforeUpload: undefined,\n validators: undefined,\n disabled: false,\n headers: undefined,\n withCredentials: false,\n showFileList: false,\n uploadExtraData: undefined,\n placeholder: undefined,\n showProgress: true,\n progressTone: 'primary',\n progressLabel: undefined,\n hideProgressOnSuccess: 800,\n },\n)\n\nconst emit = defineEmits<{\n (e: 'success', payload: any): void\n (e: 'error', error: unknown): void\n (e: 'progress', percent: number, info?: GrUploadProgressInfo): void\n (e: 'change', files: File[]): void\n (e: 'stateChange', state: GrUploadState): void\n}>()\n\nconst slots = useSlots()\n\nconst { t } = useGranularityTranslations()\nconst resolvedPlaceholder = computed(() => props.placeholder ?? t('gr.fileUpload.placeholder', 'Drag files here or click to select'))\nconst resolvedProgressLabel = computed(() => props.progressLabel ?? t('gr.fileUpload.progress', 'Upload progress'))\n\nfunction flattenSlotNodes(nodes: VNode[]): VNode[] {\n const out: VNode[] = []\n\n for (const node of nodes) {\n if (node.type === Fragment && Array.isArray(node.children)) {\n out.push(...flattenSlotNodes(node.children as VNode[]))\n continue\n }\n\n out.push(node)\n }\n\n return out\n}\n\nfunction isWhitespaceTextNode(node: VNode): boolean {\n if (node.type !== Text) return false\n return typeof node.children === 'string' && node.children.trim().length === 0\n}\n\nfunction slotIsTextOnly(nodes: VNode[]): boolean {\n const flat = flattenSlotNodes(nodes)\n const meaningful = flat.filter(node => node.type !== Comment && !isWhitespaceTextNode(node))\n\n if (meaningful.length === 0) return true\n\n for (const node of meaningful) {\n if (node.type !== Text) return false\n }\n\n return true\n}\n\nconst defaultSlotNodes = computed(() => {\n return slots.default ? flattenSlotNodes(slots.default({} as any)) : []\n})\n\nconst hasCustomUi = computed(() => {\n return !!slots.default && !slotIsTextOnly(defaultSlotNodes.value)\n})\n\nconst inputRef = ref<HTMLInputElement | null>(null)\nconst isOver = ref(false)\nlet overCounter = 0\n\nconst lastFiles = ref<File[]>([])\n\nconst state = reactive<GrUploadState>({ ...GR_UPLOAD_STATE_IDLE }) as GrUploadState\n\nlet activeController: AbortController | null = null\nlet hideSuccessTimer: ReturnType<typeof setTimeout> | null = null\n\nfunction clearHideSuccessTimer() {\n if (hideSuccessTimer !== null) {\n clearTimeout(hideSuccessTimer)\n hideSuccessTimer = null\n }\n}\n\nfunction assignState(next: GrUploadState) {\n // мутируем через Object.assign, чтобы сохранить reactive ссылку\n for (const key of Object.keys(state) as (keyof GrUploadState)[])\n delete (state as any)[key]\n Object.assign(state, next)\n emit('stateChange', state as GrUploadState)\n}\n\nfunction setStateIdle() {\n assignState({ ...GR_UPLOAD_STATE_IDLE })\n}\n\nfunction setStateUploading(info?: GrUploadProgressInfo) {\n assignState({\n phase: 'uploading',\n percent: info?.percent ?? 0,\n indeterminate: info?.indeterminate ?? true,\n loaded: info?.loaded ?? 0,\n total: info?.total ?? 0,\n })\n}\n\nfunction setStateSuccess(info: { loaded: number, total: number }) {\n assignState({\n phase: 'success',\n percent: 100,\n indeterminate: false,\n loaded: info.loaded,\n total: info.total,\n })\n}\n\nfunction setStateError(error: unknown) {\n const prev = state\n assignState({\n phase: 'error',\n percent: prev.phase === 'uploading' ? prev.percent : 0,\n indeterminate: false,\n loaded: prev.phase === 'uploading' ? prev.loaded : 0,\n total: prev.phase === 'uploading' ? prev.total : 0,\n error,\n })\n}\n\nfunction handleProgress(info: GrUploadProgressInfo) {\n if (state.phase !== 'uploading') return\n assignState({\n phase: 'uploading',\n percent: info.percent,\n indeterminate: info.indeterminate,\n loaded: info.loaded,\n total: info.total,\n })\n emit('progress', info.percent, info)\n}\n\nconst tabIndex = computed(() => (props.disabled ? -1 : 0))\n\nconst hiddenInputStyle = {\n position: 'fixed',\n top: '-9999px',\n left: '-9999px',\n width: '1px',\n height: '1px',\n opacity: '0',\n overflow: 'hidden',\n pointerEvents: 'none',\n} as const satisfies Record<string, string>\n\nfunction setOver(next: boolean) {\n if (isOver.value === next) return\n isOver.value = next\n}\n\nfunction openDialog() {\n if (props.disabled) return\n inputRef.value?.click()\n}\n\nfunction abort() {\n activeController?.abort()\n activeController = null\n}\n\nfunction normalizeLimit(limit: number | undefined): number | undefined {\n if (typeof limit !== 'number') return undefined\n if (!Number.isFinite(limit)) return undefined\n if (limit <= 0) return undefined\n return Math.floor(limit)\n}\n\n\nasync function uploadViaAction(files: File[], signal: AbortSignal, extraData: GrFileUploadExtraData | undefined) {\n if (!props.action) throw new Error('GrFileUpload: either `action` or `request` must be provided')\n\n return uploadViaXhr({\n url: props.action,\n files,\n name: props.name,\n headers: props.headers,\n withCredentials: props.withCredentials,\n extraData,\n signal,\n onProgress: handleProgress,\n })\n}\n\nasync function runBeforeUpload(files: File[]): Promise<'ok' | { aborted: true; reason: unknown }> {\n if (!props.beforeUpload) return 'ok'\n\n for (const file of files) {\n try {\n const result = props.beforeUpload(file)\n\n if (result === false) {\n return { aborted: true, reason: new Error('Upload aborted by beforeUpload') }\n }\n\n if (result && typeof (result as any).then === 'function')\n await result\n } catch (error) {\n return { aborted: true, reason: error }\n }\n }\n\n return 'ok'\n}\n\nasync function handleFiles(files: File[], source: FileValidatorSource = 'input') {\n if (props.disabled) return\n if (!files.length) return\n\n const normalizedLimit = normalizeLimit(props.limit)\n if (props.multiple && normalizedLimit && files.length > normalizedLimit) {\n props.onExceed?.(files, normalizedLimit)\n emit('error', new Error(`Too many files selected, limit=${normalizedLimit}`))\n return\n }\n\n const { files: valid, issues } = await runFileValidators(files, props.validators ?? [], {\n source,\n multiple: props.multiple,\n })\n\n if (issues.length > 0) {\n emit('error', new FileValidationError(issues, valid))\n return\n }\n\n if (!valid.length) return\n\n lastFiles.value = valid\n\n const before = await runBeforeUpload(valid)\n if (before !== 'ok') {\n emit('error', before.reason)\n return\n }\n\n let extraData: GrFileUploadExtraData | undefined\n try {\n extraData = props.uploadExtraData?.(valid)\n } catch (error) {\n emit('error', error)\n return\n }\n\n abort()\n clearHideSuccessTimer()\n\n const controller = new AbortController()\n activeController = controller\n\n setStateUploading()\n emit('progress', 0, { percent: 0, loaded: 0, total: 0, indeterminate: true })\n\n try {\n const payload = props.request\n ? await props.request(valid, { signal: controller.signal, extraData, onProgress: handleProgress })\n : await uploadViaAction(valid, controller.signal, extraData)\n\n const finalLoaded = state.phase === 'uploading' ? state.total || state.loaded : 0\n setStateSuccess({ loaded: finalLoaded, total: finalLoaded })\n emit('success', payload)\n emit('change', valid)\n emit('progress', 100, { percent: 100, loaded: finalLoaded, total: finalLoaded, indeterminate: false })\n\n if (props.hideProgressOnSuccess && props.hideProgressOnSuccess > 0) {\n hideSuccessTimer = setTimeout(() => {\n if (state.phase === 'success') setStateIdle()\n hideSuccessTimer = null\n }, props.hideProgressOnSuccess)\n }\n } catch (error) {\n if (error instanceof GrUploadAbortError) {\n setStateIdle()\n } else {\n setStateError(error)\n }\n emit('error', error)\n } finally {\n if (activeController === controller) activeController = null\n }\n}\n\nfunction onDragEnter(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter += 1\n setOver(true)\n}\n\nfunction onDragOver(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n if (event.dataTransfer) event.dataTransfer.dropEffect = 'copy'\n}\n\nfunction onDragLeave(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter = Math.max(0, overCounter - 1)\n if (overCounter === 0) setOver(false)\n}\n\nfunction onDrop(event: DragEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n event.preventDefault()\n overCounter = 0\n setOver(false)\n\n const files = event.dataTransfer?.files ? Array.prototype.slice.call(event.dataTransfer.files) as File[] : []\n void handleFiles(files, 'drop')\n}\n\nasync function onInputChange(event: Event) {\n if (props.disabled) return\n\n const target = event.target as HTMLInputElement | null\n const files = target?.files ? Array.prototype.slice.call(target.files) as File[] : []\n\n if (target) target.value = ''\n\n await nextTick()\n await handleFiles(files, 'input')\n}\n\nfunction onKeydown(event: KeyboardEvent) {\n if (hasCustomUi.value) return\n if (props.disabled) return\n\n if (event.key === 'Enter' || event.key === ' ') {\n event.preventDefault()\n openDialog()\n }\n}\n\nfunction onRootClick() {\n if (hasCustomUi.value) return\n openDialog()\n}\n\nfunction onRootKeydown(event: KeyboardEvent) {\n if (hasCustomUi.value) return\n onKeydown(event)\n}\n\nconst effectiveProgressTone = computed<GrProgressBarTone>(() => {\n if (state.phase === 'error') return 'danger'\n if (state.phase === 'success') return 'success'\n return props.progressTone\n})\n\nconst progressVisible = computed(() => state.phase !== 'idle')\nconst progressPercent = computed(() => (state.phase === 'uploading' && state.indeterminate ? 0 : state.percent))\nconst progressText = computed(() => {\n if (state.phase === 'uploading' && state.indeterminate) return ''\n return `${Math.round(progressPercent.value)}%`\n})\n\ndefineExpose({\n uploadFiles: handleFiles,\n abort,\n openDialog,\n state,\n})\n</script>\n\n<template>\n <div\n data-gr-file-upload\n :role=\"hasCustomUi ? undefined : 'button'\"\n :tabindex=\"hasCustomUi ? undefined : tabIndex\"\n :aria-disabled=\"hasCustomUi ? undefined : disabled ? 'true' : 'false'\"\n :class=\"\n hasCustomUi\n ? 'inline-block'\n : [\n 'relative w-full rounded-[var(--gr-radius-lg)] border border-dashed border-[var(--brd)] bg-[var(--card)] px-5 py-6 outline-none transition',\n disabled\n ? 'opacity-60 cursor-not-allowed'\n : 'cursor-pointer hover:bg-[var(--muted)] focus-visible:ring-2 focus-visible:ring-[var(--ring)] focus-visible:ring-offset-2 focus-visible:ring-offset-[var(--bg)]',\n isOver && !disabled ? 'border-[var(--ring)] bg-[var(--muted)]' : '',\n ]\n \"\n @click=\"onRootClick\"\n @keydown=\"onRootKeydown\"\n @dragenter=\"onDragEnter\"\n @dragover=\"onDragOver\"\n @dragleave=\"onDragLeave\"\n @drop=\"onDrop\"\n >\n <input\n ref=\"inputRef\"\n data-gr-file-upload-input\n :style=\"hiddenInputStyle\"\n type=\"file\"\n tabindex=\"-1\"\n aria-hidden=\"true\"\n :name=\"name\"\n :multiple=\"multiple\"\n :disabled=\"disabled\"\n @change=\"onInputChange\"\n >\n\n <slot\n v-if=\"hasCustomUi\"\n :open-dialog=\"openDialog\"\n :abort=\"abort\"\n :disabled=\"disabled\"\n :files=\"lastFiles\"\n :is-over=\"isOver\"\n :state=\"state\"\n />\n\n <div v-else class=\"flex items-start gap-4\">\n <div\n data-gr-file-upload-icon\n class=\"h-12 w-12 shrink-0 rounded-[12px] bg-[var(--muted)] border border-[var(--brd)] flex items-center justify-center\"\n aria-hidden=\"true\"\n >\n <GrIcon class=\"h-6 w-6 text-[var(--muted-fg)]\">\n <IconArrowUp />\n </GrIcon>\n </div>\n\n <div class=\"min-w-0\">\n <div data-gr-file-upload-label class=\"text-[14px] font-700\">\n <slot name=\"label\">\n <slot>\n {{ resolvedPlaceholder }}\n </slot>\n </slot>\n </div>\n\n <div v-if=\"$slots.tip\" data-gr-file-upload-tip class=\"mt-1 text-[13px] text-[var(--muted-fg)]\">\n <slot name=\"tip\" />\n </div>\n <div v-else class=\"mt-1 text-[13px] text-[var(--muted-fg)]\" />\n\n <ul v-if=\"showFileList && lastFiles.length\" data-gr-file-upload-list class=\"mt-3 space-y-1\">\n <li\n v-for=\"file in lastFiles\"\n :key=\"file.name\"\n data-gr-file-upload-item\n class=\"text-[13px]\"\n >\n <span class=\"font-600\">{{ file.name }}</span>\n <span class=\"text-[var(--muted-fg)]\"> · {{ Math.ceil(file.size / 1024) }} KB</span>\n </li>\n </ul>\n\n <slot\n v-if=\"showProgress || $slots.progress\"\n name=\"progress\"\n :state=\"state\"\n :percent=\"state.percent\"\n :indeterminate=\"state.phase === 'uploading' && state.indeterminate\"\n :phase=\"state.phase\"\n :files=\"lastFiles\"\n :abort=\"abort\"\n >\n <div\n v-if=\"showProgress\"\n data-gr-file-upload-progress\n class=\"mt-3 transition-opacity duration-150\"\n :class=\"progressVisible ? 'opacity-100' : 'opacity-0 pointer-events-none'\"\n :aria-hidden=\"!progressVisible\"\n >\n <div class=\"flex items-center gap-2\">\n <GrProgressBar\n :value=\"progressPercent\"\n :tone=\"effectiveProgressTone\"\n :aria-label=\"resolvedProgressLabel\"\n />\n <span\n data-gr-file-upload-progress-text\n class=\"text-[12px] text-[var(--muted-fg)] tabular-nums min-w-[3ch] text-right\"\n >{{ progressText }}</span>\n </div>\n </div>\n </slot>\n </div>\n </div>\n </div>\n</template>"],"mappings":"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"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { a as allowedExtensionsValidator, c as normalizeFiles, i as allowedMimeTypesValidator, l as runFileValidators, n as maxSizeMbValidator, o as acceptValidator, r as maxFileSizeBytesValidator, s as matchAccept, t as maxTotalSizeBytesValidator, u as FileValidationError } from "../../chunks/fileValidation-
|
|
2
|
-
import { i as GrUploadHttpError, n as GR_UPLOAD_STATE_IDLE, r as GrUploadAbortError, t as GrFileUpload_default } from "./chunks/GrFileUpload-
|
|
3
|
-
import { t as grFileUploadConfig } from "../../chunks/config-
|
|
1
|
+
import { a as allowedExtensionsValidator, c as normalizeFiles, i as allowedMimeTypesValidator, l as runFileValidators, n as maxSizeMbValidator, o as acceptValidator, r as maxFileSizeBytesValidator, s as matchAccept, t as maxTotalSizeBytesValidator, u as FileValidationError } from "../../chunks/fileValidation-C3WFaWU2.js";
|
|
2
|
+
import { i as GrUploadHttpError, n as GR_UPLOAD_STATE_IDLE, r as GrUploadAbortError, t as GrFileUpload_default } from "./chunks/GrFileUpload-DvWPpiJS.js";
|
|
3
|
+
import { t as grFileUploadConfig } from "../../chunks/config-BWGGp7uV.js";
|
|
4
4
|
export { FileValidationError, GR_UPLOAD_STATE_IDLE, GrFileUpload_default as GrFileUpload, GrFileUpload_default as default, GrUploadAbortError, GrUploadHttpError, acceptValidator, allowedExtensionsValidator, allowedMimeTypesValidator, grFileUploadConfig, matchAccept, maxFileSizeBytesValidator, maxSizeMbValidator, maxTotalSizeBytesValidator, normalizeFiles, runFileValidators };
|
package/dist/components/GrFormField/chunks/{GrFormField-U7c_aDPJ.js → GrFormField-BujNQrw8.js}
RENAMED
|
@@ -4,7 +4,7 @@ var _hoisted_1 = { class: "flex flex-col gap-2" };
|
|
|
4
4
|
var _hoisted_2 = ["for"];
|
|
5
5
|
var _hoisted_3 = {
|
|
6
6
|
key: 1,
|
|
7
|
-
class: "text-sm text-[var(--
|
|
7
|
+
class: "text-sm text-[var(--gr-danger)]"
|
|
8
8
|
};
|
|
9
9
|
//#endregion
|
|
10
10
|
//#region src/components/GrFormField/GrFormField.vue
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GrFormField-
|
|
1
|
+
{"version":3,"file":"GrFormField-BujNQrw8.js","names":[],"sources":["../../../../src/components/GrFormField/GrFormField.vue","../../../../src/components/GrFormField/GrFormField.vue"],"sourcesContent":["<script setup lang=\"ts\">\ntype LabelClass = string | string[] | Record<string, boolean>\n\nconst props = withDefaults(\n defineProps<{\n label?: string\n forId?: string\n error?: string\n labelClass?: LabelClass\n }>(),\n {\n label: undefined,\n forId: undefined,\n error: undefined,\n labelClass: undefined,\n },\n)\n</script>\n\n<template>\n <div class=\"flex flex-col gap-2\">\n <label\n v-if=\"props.label\"\n :for=\"props.forId\"\n class=\"text-sm text-[var(--muted-fg)]\"\n :class=\"props.labelClass\"\n >\n {{ props.label }}\n </label>\n <slot />\n <div v-if=\"props.error\" class=\"text-sm text-[var(--gr-danger)]\">\n {{ props.error }}\n </div>\n </div>\n</template>\n","<script setup lang=\"ts\">\ntype LabelClass = string | string[] | Record<string, boolean>\n\nconst props = withDefaults(\n defineProps<{\n label?: string\n forId?: string\n error?: string\n labelClass?: LabelClass\n }>(),\n {\n label: undefined,\n forId: undefined,\n error: undefined,\n labelClass: undefined,\n },\n)\n</script>\n\n<template>\n <div class=\"flex flex-col gap-2\">\n <label\n v-if=\"props.label\"\n :for=\"props.forId\"\n class=\"text-sm text-[var(--muted-fg)]\"\n :class=\"props.labelClass\"\n >\n {{ props.label }}\n </label>\n <slot />\n <div v-if=\"props.error\" class=\"text-sm text-[var(--gr-danger)]\">\n {{ props.error }}\n </div>\n </div>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;;EAGA,MAAM,QAAQ;;uBAiBZ,mBAaM,OAbN,YAaM;IAXI,MAAM,SAAA,UAAA,GADd,mBAOQ,SAAA;;KALL,KAAK,MAAM;KACZ,OAAK,eAAA,CAAC,kCACE,MAAM,UAAU,CAAA;uBAErB,MAAM,KAAK,GAAA,IAAA,UAAA,KAAA,mBAAA,IAAA,IAAA;IAEhB,WAAQ,KAAA,QAAA,SAAA;IACG,MAAM,SAAA,UAAA,GAAjB,mBAEM,OAFN,YAEM,gBADD,MAAM,KAAK,GAAA,CAAA,KAAA,mBAAA,IAAA,IAAA"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as GrFormField_default } from "./chunks/GrFormField-
|
|
2
|
-
import { t as grFormFieldConfig } from "../../chunks/config-
|
|
1
|
+
import { t as GrFormField_default } from "./chunks/GrFormField-BujNQrw8.js";
|
|
2
|
+
import { t as grFormFieldConfig } from "../../chunks/config-PFg39mYo.js";
|
|
3
3
|
export { GrFormField_default as GrFormField, GrFormField_default as default, grFormFieldConfig };
|
|
@@ -1,8 +1,9 @@
|
|
|
1
|
-
import { t as x_default } from "../../../chunks/x-
|
|
2
|
-
import { t as
|
|
3
|
-
import { t as
|
|
4
|
-
import { t as
|
|
5
|
-
import {
|
|
1
|
+
import { t as x_default } from "../../../chunks/x-2KXnqxiD.js";
|
|
2
|
+
import { t as useGranularityTranslations } from "../../../chunks/granularityI18n-DoV7Ca2m.js";
|
|
3
|
+
import { t as _plugin_vue_export_helper_default } from "../../../chunks/_plugin-vue_export-helper-BOaGB7Aw.js";
|
|
4
|
+
import { t as GrButton_default } from "../../GrButton/chunks/GrButton-BlffdeJr.js";
|
|
5
|
+
import { t as GrIcon_default } from "../../GrIcon/chunks/GrIcon-D9AWQLk2.js";
|
|
6
|
+
import { l as runFileValidators, o as acceptValidator, u as FileValidationError } from "../../../chunks/fileValidation-C3WFaWU2.js";
|
|
6
7
|
import { vDropzone } from "../../../directives/dropzone.js";
|
|
7
8
|
import { Fragment, computed, createBlock, createCommentVNode, createElementBlock, createElementVNode, createVNode, defineComponent, markRaw, nextTick, normalizeClass, openBlock, ref, renderList, renderSlot, toDisplayString, unref, watch, withCtx, withDirectives, withModifiers } from "vue";
|
|
8
9
|
import '../../../GrFormFile.css';//#region ~icons/lucide/upload
|
|
@@ -41,7 +42,7 @@ var _hoisted_7 = ["title"];
|
|
|
41
42
|
var _hoisted_8 = {
|
|
42
43
|
key: 3,
|
|
43
44
|
class: "text-sm text-[var(--muted-fg)]",
|
|
44
|
-
"data-
|
|
45
|
+
"data-gr-form-file-placeholder": ""
|
|
45
46
|
};
|
|
46
47
|
var _hoisted_9 = {
|
|
47
48
|
key: 0,
|
|
@@ -51,12 +52,12 @@ var _hoisted_10 = ["title"];
|
|
|
51
52
|
var _hoisted_11 = ["disabled", "onClick"];
|
|
52
53
|
var _hoisted_12 = {
|
|
53
54
|
key: 0,
|
|
54
|
-
class: "text-sm text-[var(--
|
|
55
|
-
"data-
|
|
55
|
+
class: "text-sm text-[var(--gr-danger)]",
|
|
56
|
+
"data-gr-form-file-errors": ""
|
|
56
57
|
};
|
|
57
58
|
//#endregion
|
|
58
59
|
//#region src/components/GrFormFile/GrFormFile.vue
|
|
59
|
-
var GrFormFile_default =
|
|
60
|
+
var GrFormFile_default = /*#__PURE__*/ _plugin_vue_export_helper_default(/* @__PURE__ */ defineComponent({
|
|
60
61
|
name: "GrFormFile",
|
|
61
62
|
__name: "GrFormFile",
|
|
62
63
|
props: {
|
|
@@ -71,11 +72,11 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
71
72
|
},
|
|
72
73
|
accept: { default: void 0 },
|
|
73
74
|
validators: { default: void 0 },
|
|
74
|
-
uploadText: { default:
|
|
75
|
-
changeText: { default:
|
|
76
|
-
removeText: { default:
|
|
77
|
-
clearAllText: { default:
|
|
78
|
-
placeholder: { default:
|
|
75
|
+
uploadText: { default: void 0 },
|
|
76
|
+
changeText: { default: void 0 },
|
|
77
|
+
removeText: { default: void 0 },
|
|
78
|
+
clearAllText: { default: void 0 },
|
|
79
|
+
placeholder: { default: void 0 },
|
|
79
80
|
validate: {
|
|
80
81
|
type: Function,
|
|
81
82
|
default: void 0
|
|
@@ -91,6 +92,12 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
91
92
|
setup(__props, { emit: __emit }) {
|
|
92
93
|
const props = __props;
|
|
93
94
|
const emit = __emit;
|
|
95
|
+
const { t } = useGranularityTranslations();
|
|
96
|
+
const resolvedUploadText = computed(() => props.uploadText ?? t("gr.formFile.upload", "Upload file"));
|
|
97
|
+
const resolvedChangeText = computed(() => props.changeText ?? t("gr.formFile.change", "Change file"));
|
|
98
|
+
const resolvedRemoveText = computed(() => props.removeText ?? t("gr.formFile.remove", "Remove"));
|
|
99
|
+
const resolvedClearAllText = computed(() => props.clearAllText ?? t("gr.formFile.clearAll", "Clear all"));
|
|
100
|
+
const resolvedPlaceholder = computed(() => props.placeholder ?? t("gr.formFile.placeholder", "No files selected"));
|
|
94
101
|
const inputRef = ref(null);
|
|
95
102
|
const localErrors = ref([]);
|
|
96
103
|
const files = computed(() => {
|
|
@@ -197,7 +204,7 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
197
204
|
if (error instanceof FileValidationError) setErrors(error.issues);
|
|
198
205
|
else setErrors([{
|
|
199
206
|
code: "accept",
|
|
200
|
-
message: "Failed to validate dropped files"
|
|
207
|
+
message: t("gr.formFile.validateError", "Failed to validate dropped files")
|
|
201
208
|
}]);
|
|
202
209
|
}
|
|
203
210
|
};
|
|
@@ -208,12 +215,12 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
208
215
|
});
|
|
209
216
|
return (_ctx, _cache) => {
|
|
210
217
|
return withDirectives((openBlock(), createElementBlock("div", {
|
|
211
|
-
"data-
|
|
212
|
-
class: normalizeClass(["rounded-[var(--
|
|
218
|
+
"data-gr-form-file": "",
|
|
219
|
+
class: normalizeClass(["rounded-[var(--gr-radius-md)]", __props.disabled ? "opacity-60 cursor-not-allowed" : ""])
|
|
213
220
|
}, [createElementVNode("input", {
|
|
214
221
|
ref_key: "inputRef",
|
|
215
222
|
ref: inputRef,
|
|
216
|
-
"data-
|
|
223
|
+
"data-gr-form-file-input": "",
|
|
217
224
|
type: "file",
|
|
218
225
|
tabindex: "-1",
|
|
219
226
|
"aria-hidden": "true",
|
|
@@ -227,7 +234,7 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
227
234
|
createVNode(GrButton_default, {
|
|
228
235
|
variant: "secondary",
|
|
229
236
|
size: "sm",
|
|
230
|
-
"data-
|
|
237
|
+
"data-gr-form-file-upload-btn": "",
|
|
231
238
|
disabled: __props.disabled,
|
|
232
239
|
onClick: withModifiers(openDialog, ["prevent"])
|
|
233
240
|
}, {
|
|
@@ -237,14 +244,14 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
237
244
|
}, {
|
|
238
245
|
default: withCtx(() => [createVNode(unref(upload_default))]),
|
|
239
246
|
_: 1
|
|
240
|
-
}), createElementVNode("span", _hoisted_4, toDisplayString(hasFiles.value ?
|
|
247
|
+
}), createElementVNode("span", _hoisted_4, toDisplayString(hasFiles.value ? resolvedChangeText.value : resolvedUploadText.value), 1)]),
|
|
241
248
|
_: 1
|
|
242
249
|
}, 8, ["disabled"]),
|
|
243
250
|
hasFiles.value && !__props.multiple ? (openBlock(), createBlock(GrButton_default, {
|
|
244
251
|
key: 0,
|
|
245
252
|
variant: "secondary",
|
|
246
253
|
size: "sm",
|
|
247
|
-
"data-
|
|
254
|
+
"data-gr-form-file-clear-btn": "",
|
|
248
255
|
disabled: __props.disabled,
|
|
249
256
|
onClick: withModifiers(clearAll, ["prevent"])
|
|
250
257
|
}, {
|
|
@@ -254,14 +261,14 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
254
261
|
}, {
|
|
255
262
|
default: withCtx(() => [createVNode(unref(x_default))]),
|
|
256
263
|
_: 1
|
|
257
|
-
}), createElementVNode("span", _hoisted_5, toDisplayString(
|
|
264
|
+
}), createElementVNode("span", _hoisted_5, toDisplayString(resolvedRemoveText.value), 1)]),
|
|
258
265
|
_: 1
|
|
259
266
|
}, 8, ["disabled"])) : createCommentVNode("", true),
|
|
260
267
|
__props.multiple && hasFiles.value ? (openBlock(), createBlock(GrButton_default, {
|
|
261
268
|
key: 1,
|
|
262
269
|
variant: "secondary",
|
|
263
270
|
size: "sm",
|
|
264
|
-
"data-
|
|
271
|
+
"data-gr-form-file-clear-all-btn": "",
|
|
265
272
|
disabled: __props.disabled,
|
|
266
273
|
onClick: withModifiers(clearAll, ["prevent"])
|
|
267
274
|
}, {
|
|
@@ -271,30 +278,30 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
271
278
|
}, {
|
|
272
279
|
default: withCtx(() => [createVNode(unref(x_default))]),
|
|
273
280
|
_: 1
|
|
274
|
-
}), createElementVNode("span", _hoisted_6, toDisplayString(
|
|
281
|
+
}), createElementVNode("span", _hoisted_6, toDisplayString(resolvedClearAllText.value), 1)]),
|
|
275
282
|
_: 1
|
|
276
283
|
}, 8, ["disabled"])) : createCommentVNode("", true),
|
|
277
284
|
!__props.multiple && hasFiles.value ? (openBlock(), createElementBlock("span", {
|
|
278
285
|
key: 2,
|
|
279
286
|
class: "text-sm text-[var(--muted-fg)] truncate max-w-[240px]",
|
|
280
|
-
"data-
|
|
287
|
+
"data-gr-form-file-single-name": "",
|
|
281
288
|
title: files.value[0]?.name
|
|
282
289
|
}, toDisplayString(files.value[0]?.name), 9, _hoisted_7)) : createCommentVNode("", true),
|
|
283
|
-
!hasFiles.value ? (openBlock(), createElementBlock("span", _hoisted_8, toDisplayString(
|
|
290
|
+
!hasFiles.value ? (openBlock(), createElementBlock("span", _hoisted_8, toDisplayString(resolvedPlaceholder.value), 1)) : createCommentVNode("", true)
|
|
284
291
|
]),
|
|
285
292
|
__props.multiple && hasFiles.value ? (openBlock(), createElementBlock("div", _hoisted_9, [(openBlock(true), createElementBlock(Fragment, null, renderList(files.value, (file, index) => {
|
|
286
293
|
return openBlock(), createElementBlock("div", {
|
|
287
294
|
key: `${file.name}-${file.size}-${index}`,
|
|
288
295
|
class: "flex items-center gap-2",
|
|
289
|
-
"data-
|
|
296
|
+
"data-gr-form-file-item": ""
|
|
290
297
|
}, [createElementVNode("span", {
|
|
291
298
|
class: "text-sm text-[var(--muted-fg)] truncate max-w-[240px]",
|
|
292
299
|
title: file.name,
|
|
293
|
-
"data-
|
|
300
|
+
"data-gr-form-file-item-name": ""
|
|
294
301
|
}, toDisplayString(file.name), 9, _hoisted_10), createElementVNode("button", {
|
|
295
302
|
type: "button",
|
|
296
303
|
class: "text-xs text-[var(--muted-fg)] hover:text-[var(--fg)]",
|
|
297
|
-
"data-
|
|
304
|
+
"data-gr-form-file-item-remove": "",
|
|
298
305
|
disabled: __props.disabled,
|
|
299
306
|
onClick: withModifiers(($event) => removeAt(index), ["prevent"])
|
|
300
307
|
}, toDisplayString(__props.removeText), 9, _hoisted_11)]);
|
|
@@ -302,12 +309,12 @@ var GrFormFile_default = /* @__PURE__ */ _plugin_vue_export_helper_default(/* @_
|
|
|
302
309
|
renderSlot(_ctx.$slots, "errors", { errors: localErrors.value }, () => [localErrors.value.length ? (openBlock(), createElementBlock("div", _hoisted_12, [(openBlock(true), createElementBlock(Fragment, null, renderList(localErrors.value, (e, i) => {
|
|
303
310
|
return openBlock(), createElementBlock("div", {
|
|
304
311
|
key: i,
|
|
305
|
-
"data-
|
|
312
|
+
"data-gr-form-file-error": ""
|
|
306
313
|
}, toDisplayString(issueMessage(e)), 1);
|
|
307
314
|
}), 128))])) : createCommentVNode("", true)], true)
|
|
308
315
|
])], 2)), [[unref(vDropzone), dropzone.value]]);
|
|
309
316
|
};
|
|
310
317
|
}
|
|
311
|
-
}), [["__scopeId", "data-v-
|
|
318
|
+
}), [["__scopeId", "data-v-ff219d2a"]]);
|
|
312
319
|
//#endregion
|
|
313
320
|
export { GrFormFile_default as t };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"GrFormFile-CXcqqdvV.js","names":[],"sources":["../../../../src/components/GrFormFile/GrFormFile.vue","../../../../src/components/GrFormFile/GrFormFile.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { computed, nextTick, ref, watch } from 'vue'\n\nimport IconUpload from '~icons/lucide/upload'\nimport IconX from '~icons/lucide/x'\n\nimport GrButton from '../GrButton/GrButton.vue'\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport { vDropzone } from '../../directives'\nimport { acceptValidator, FileValidationError, runFileValidators } from '../../fileValidation'\nimport type { FileValidationIssue, FileValidator } from '../../fileValidation'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\ndefineOptions({\n name: 'GrFormFile',\n})\n\nexport type GrFormFileError = FileValidationIssue\n\n/**\n * Пропы `GrFormFile` — форма-поле для выбора файлов с встроенной валидацией,\n * drag&drop (через `v-dropzone`) и списком выбранных файлов.\n *\n * Все `*Text`/`placeholder` — i18n-friendly, принимают готовые строки локали.\n */\nexport interface GrFormFileProps {\n modelValue: File | File[] | null\n multiple?: boolean\n disabled?: boolean\n /** W3C `accept` для `<input type=\"file\">` + sugar к `acceptValidator(...)`. */\n accept?: string\n validators?: FileValidator[]\n uploadText?: string\n changeText?: string\n removeText?: string\n clearAllText?: string\n placeholder?: string\n /** Дополнительная (кастомная) валидация на стороне потребителя. */\n validate?: (files: File[]) => GrFormFileError[] | Promise<GrFormFileError[]>\n}\n\nconst props = withDefaults(\n defineProps<GrFormFileProps>(),\n {\n multiple: false,\n disabled: false,\n accept: undefined,\n uploadText: undefined,\n changeText: undefined,\n removeText: undefined,\n clearAllText: undefined,\n placeholder: undefined,\n validators: undefined,\n validate: undefined,\n },\n)\n\nconst emit = defineEmits<{\n (e: 'update:modelValue', value: File | File[] | null): void\n (e: 'change', value: File | File[] | null): void\n (e: 'clear'): void\n (e: 'validation', errors: GrFormFileError[]): void\n (e: 'update:errors', errors: GrFormFileError[]): void\n}>()\n\nconst { t } = useGranularityTranslations()\nconst resolvedUploadText = computed(() => props.uploadText ?? t('gr.formFile.upload', 'Upload file'))\nconst resolvedChangeText = computed(() => props.changeText ?? t('gr.formFile.change', 'Change file'))\nconst resolvedRemoveText = computed(() => props.removeText ?? t('gr.formFile.remove', 'Remove'))\nconst resolvedClearAllText = computed(() => props.clearAllText ?? t('gr.formFile.clearAll', 'Clear all'))\nconst resolvedPlaceholder = computed(() => props.placeholder ?? t('gr.formFile.placeholder', 'No files selected'))\n\nconst inputRef = ref<HTMLInputElement | null>(null)\nconst localErrors = ref<GrFormFileError[]>([])\n\nconst files = computed<File[]>(() => {\n if (props.multiple) {\n return Array.isArray(props.modelValue) ? props.modelValue : []\n }\n\n return props.modelValue instanceof File ? [props.modelValue] : []\n})\n\nconst hasFiles = computed(() => files.value.length > 0)\n\nfunction clearInputValue() {\n if (!inputRef.value) return\n inputRef.value.value = ''\n}\n\nfunction setErrors(next: GrFormFileError[]) {\n localErrors.value = next\n emit('validation', next)\n emit('update:errors', next)\n}\n\nfunction clearErrors() {\n if (localErrors.value.length === 0) return\n setErrors([])\n}\n\nfunction openDialog() {\n if (props.disabled) return\n inputRef.value?.click()\n}\n\nfunction emitModel(nextFiles: File[]) {\n const value: File | File[] | null = props.multiple\n ? nextFiles\n : (nextFiles[0] ?? null)\n\n emit('update:modelValue', value)\n emit('change', value)\n}\n\nasync function applyFiles(nextFiles: File[]) {\n const isPromiseLike = (value: unknown): value is PromiseLike<any> => {\n return !!value && typeof (value as any).then === 'function'\n }\n\n const customValidator: FileValidator | undefined = props.validate\n ? async ({ files }) => (await props.validate?.(files)) ?? []\n : undefined\n\n const validators: FileValidator[] = [\n acceptValidator(props.accept),\n ...(props.validators ?? []),\n ...(customValidator ? [customValidator] : []),\n ]\n\n const res = runFileValidators(nextFiles, validators, {\n source: 'input',\n multiple: props.multiple,\n })\n\n const { files: picked, issues } = isPromiseLike(res) ? await res : res\n\n if (issues.length > 0) {\n setErrors(issues)\n clearInputValue()\n await nextTick()\n return\n }\n\n clearErrors()\n emitModel(picked)\n clearInputValue()\n await nextTick()\n}\n\nasync function onInputChange(event: Event) {\n if (props.disabled) return\n\n const target = event.target as HTMLInputElement | null\n const nextFiles = target?.files ? Array.prototype.slice.call(target.files) as File[] : []\n\n // Reset value so selecting the same file twice triggers change.\n if (target) target.value = ''\n await nextTick()\n\n await applyFiles(nextFiles)\n}\n\nfunction clearAll() {\n if (props.disabled) return\n clearErrors()\n clearInputValue()\n emit('clear')\n\n emit('update:modelValue', props.multiple ? [] : null)\n emit('change', props.multiple ? [] : null)\n}\n\nfunction removeAt(index: number) {\n if (props.disabled) return\n if (!props.multiple) {\n clearAll()\n return\n }\n\n const next = files.value.slice()\n next.splice(index, 1)\n\n emit('update:modelValue', next)\n emit('change', next)\n}\n\nfunction issueMessage(issue: GrFormFileError): string {\n if (issue.fileName) return `${issue.fileName}: ${issue.message}`\n return issue.message\n}\n\nconst dropzone = computed(() => {\n const customValidator: FileValidator | undefined = props.validate\n ? async ({ files }) => (await props.validate?.(files)) ?? []\n : undefined\n\n const validators: FileValidator[] = [\n acceptValidator(props.accept),\n ...(props.validators ?? []),\n ...(customValidator ? [customValidator] : []),\n ]\n\n return {\n enabled: !props.disabled,\n multiple: props.multiple,\n validators,\n onFiles: async (dropped: File[]) => {\n // `v-dropzone` уже выполнил валидаторы и нормализацию по `multiple`.\n clearErrors()\n emitModel(dropped)\n clearInputValue()\n await nextTick()\n },\n onError: (error: unknown) => {\n if (error instanceof FileValidationError) {\n setErrors(error.issues)\n }\n else {\n setErrors([\n {\n code: 'accept',\n message: t('gr.formFile.validateError', 'Failed to validate dropped files'),\n },\n ])\n }\n },\n }\n})\n\nwatch(\n () => props.modelValue,\n (value) => {\n if (!inputRef.value) return\n\n if (!value || (Array.isArray(value) && value.length === 0)) {\n // Позволяет выбрать тот же файл снова после внешнего сброса.\n inputRef.value.value = ''\n }\n },\n)\n</script>\n\n<template>\n <div\n v-dropzone=\"dropzone\"\n data-gr-form-file\n class=\"rounded-[var(--gr-radius-md)]\"\n :class=\"disabled ? 'opacity-60 cursor-not-allowed' : ''\"\n >\n <input\n ref=\"inputRef\"\n data-gr-form-file-input\n type=\"file\"\n tabindex=\"-1\"\n aria-hidden=\"true\"\n class=\"absolute opacity-0 w-px h-px pointer-events-none\"\n :multiple=\"multiple\"\n :accept=\"accept\"\n :disabled=\"disabled\"\n @change=\"onInputChange\"\n >\n\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-wrap items-center gap-3\">\n <GrButton\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-upload-btn\n :disabled=\"disabled\"\n @click.prevent=\"openDialog\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconUpload />\n </GrIcon>\n <span class=\"ml-2\">{{ hasFiles ? resolvedChangeText : resolvedUploadText }}</span>\n </GrButton>\n\n <GrButton\n v-if=\"hasFiles && !multiple\"\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-clear-btn\n :disabled=\"disabled\"\n @click.prevent=\"clearAll\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconX />\n </GrIcon>\n <span class=\"ml-2\">{{ resolvedRemoveText }}</span>\n </GrButton>\n\n <GrButton\n v-if=\"multiple && hasFiles\"\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-clear-all-btn\n :disabled=\"disabled\"\n @click.prevent=\"clearAll\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconX />\n </GrIcon>\n <span class=\"ml-2\">{{ resolvedClearAllText }}</span>\n </GrButton>\n\n <span\n v-if=\"!multiple && hasFiles\"\n class=\"text-sm text-[var(--muted-fg)] truncate max-w-[240px]\"\n data-gr-form-file-single-name\n :title=\"files[0]?.name\"\n >\n {{ files[0]?.name }}\n </span>\n\n <span\n v-if=\"!hasFiles\"\n class=\"text-sm text-[var(--muted-fg)]\"\n data-gr-form-file-placeholder\n >\n {{ resolvedPlaceholder }}\n </span>\n </div>\n\n <div v-if=\"multiple && hasFiles\" class=\"flex flex-col gap-2\">\n <div\n v-for=\"(file, index) in files\"\n :key=\"`${file.name}-${file.size}-${index}`\"\n class=\"flex items-center gap-2\"\n data-gr-form-file-item\n >\n <span\n class=\"text-sm text-[var(--muted-fg)] truncate max-w-[240px]\"\n :title=\"file.name\"\n data-gr-form-file-item-name\n >\n {{ file.name }}\n </span>\n\n <button\n type=\"button\"\n class=\"text-xs text-[var(--muted-fg)] hover:text-[var(--fg)]\"\n data-gr-form-file-item-remove\n :disabled=\"disabled\"\n @click.prevent=\"removeAt(index)\"\n >\n {{ removeText }}\n </button>\n </div>\n </div>\n\n <slot name=\"errors\" :errors=\"localErrors\">\n <div v-if=\"localErrors.length\" class=\"text-sm text-[var(--gr-danger)]\" data-gr-form-file-errors>\n <div v-for=\"(e, i) in localErrors\" :key=\"i\" data-gr-form-file-error>\n {{ issueMessage(e) }}\n </div>\n </div>\n </slot>\n </div>\n </div>\n</template>\n\n<style scoped>\n[data-gr-form-file].gr-dropzone--over {\n outline: 2px solid var(--ring);\n outline-offset: 2px;\n}\n</style>\n","<script setup lang=\"ts\">\nimport { computed, nextTick, ref, watch } from 'vue'\n\nimport IconUpload from '~icons/lucide/upload'\nimport IconX from '~icons/lucide/x'\n\nimport GrButton from '../GrButton/GrButton.vue'\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport { vDropzone } from '../../directives'\nimport { acceptValidator, FileValidationError, runFileValidators } from '../../fileValidation'\nimport type { FileValidationIssue, FileValidator } from '../../fileValidation'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\ndefineOptions({\n name: 'GrFormFile',\n})\n\nexport type GrFormFileError = FileValidationIssue\n\n/**\n * Пропы `GrFormFile` — форма-поле для выбора файлов с встроенной валидацией,\n * drag&drop (через `v-dropzone`) и списком выбранных файлов.\n *\n * Все `*Text`/`placeholder` — i18n-friendly, принимают готовые строки локали.\n */\nexport interface GrFormFileProps {\n modelValue: File | File[] | null\n multiple?: boolean\n disabled?: boolean\n /** W3C `accept` для `<input type=\"file\">` + sugar к `acceptValidator(...)`. */\n accept?: string\n validators?: FileValidator[]\n uploadText?: string\n changeText?: string\n removeText?: string\n clearAllText?: string\n placeholder?: string\n /** Дополнительная (кастомная) валидация на стороне потребителя. */\n validate?: (files: File[]) => GrFormFileError[] | Promise<GrFormFileError[]>\n}\n\nconst props = withDefaults(\n defineProps<GrFormFileProps>(),\n {\n multiple: false,\n disabled: false,\n accept: undefined,\n uploadText: undefined,\n changeText: undefined,\n removeText: undefined,\n clearAllText: undefined,\n placeholder: undefined,\n validators: undefined,\n validate: undefined,\n },\n)\n\nconst emit = defineEmits<{\n (e: 'update:modelValue', value: File | File[] | null): void\n (e: 'change', value: File | File[] | null): void\n (e: 'clear'): void\n (e: 'validation', errors: GrFormFileError[]): void\n (e: 'update:errors', errors: GrFormFileError[]): void\n}>()\n\nconst { t } = useGranularityTranslations()\nconst resolvedUploadText = computed(() => props.uploadText ?? t('gr.formFile.upload', 'Upload file'))\nconst resolvedChangeText = computed(() => props.changeText ?? t('gr.formFile.change', 'Change file'))\nconst resolvedRemoveText = computed(() => props.removeText ?? t('gr.formFile.remove', 'Remove'))\nconst resolvedClearAllText = computed(() => props.clearAllText ?? t('gr.formFile.clearAll', 'Clear all'))\nconst resolvedPlaceholder = computed(() => props.placeholder ?? t('gr.formFile.placeholder', 'No files selected'))\n\nconst inputRef = ref<HTMLInputElement | null>(null)\nconst localErrors = ref<GrFormFileError[]>([])\n\nconst files = computed<File[]>(() => {\n if (props.multiple) {\n return Array.isArray(props.modelValue) ? props.modelValue : []\n }\n\n return props.modelValue instanceof File ? [props.modelValue] : []\n})\n\nconst hasFiles = computed(() => files.value.length > 0)\n\nfunction clearInputValue() {\n if (!inputRef.value) return\n inputRef.value.value = ''\n}\n\nfunction setErrors(next: GrFormFileError[]) {\n localErrors.value = next\n emit('validation', next)\n emit('update:errors', next)\n}\n\nfunction clearErrors() {\n if (localErrors.value.length === 0) return\n setErrors([])\n}\n\nfunction openDialog() {\n if (props.disabled) return\n inputRef.value?.click()\n}\n\nfunction emitModel(nextFiles: File[]) {\n const value: File | File[] | null = props.multiple\n ? nextFiles\n : (nextFiles[0] ?? null)\n\n emit('update:modelValue', value)\n emit('change', value)\n}\n\nasync function applyFiles(nextFiles: File[]) {\n const isPromiseLike = (value: unknown): value is PromiseLike<any> => {\n return !!value && typeof (value as any).then === 'function'\n }\n\n const customValidator: FileValidator | undefined = props.validate\n ? async ({ files }) => (await props.validate?.(files)) ?? []\n : undefined\n\n const validators: FileValidator[] = [\n acceptValidator(props.accept),\n ...(props.validators ?? []),\n ...(customValidator ? [customValidator] : []),\n ]\n\n const res = runFileValidators(nextFiles, validators, {\n source: 'input',\n multiple: props.multiple,\n })\n\n const { files: picked, issues } = isPromiseLike(res) ? await res : res\n\n if (issues.length > 0) {\n setErrors(issues)\n clearInputValue()\n await nextTick()\n return\n }\n\n clearErrors()\n emitModel(picked)\n clearInputValue()\n await nextTick()\n}\n\nasync function onInputChange(event: Event) {\n if (props.disabled) return\n\n const target = event.target as HTMLInputElement | null\n const nextFiles = target?.files ? Array.prototype.slice.call(target.files) as File[] : []\n\n // Reset value so selecting the same file twice triggers change.\n if (target) target.value = ''\n await nextTick()\n\n await applyFiles(nextFiles)\n}\n\nfunction clearAll() {\n if (props.disabled) return\n clearErrors()\n clearInputValue()\n emit('clear')\n\n emit('update:modelValue', props.multiple ? [] : null)\n emit('change', props.multiple ? [] : null)\n}\n\nfunction removeAt(index: number) {\n if (props.disabled) return\n if (!props.multiple) {\n clearAll()\n return\n }\n\n const next = files.value.slice()\n next.splice(index, 1)\n\n emit('update:modelValue', next)\n emit('change', next)\n}\n\nfunction issueMessage(issue: GrFormFileError): string {\n if (issue.fileName) return `${issue.fileName}: ${issue.message}`\n return issue.message\n}\n\nconst dropzone = computed(() => {\n const customValidator: FileValidator | undefined = props.validate\n ? async ({ files }) => (await props.validate?.(files)) ?? []\n : undefined\n\n const validators: FileValidator[] = [\n acceptValidator(props.accept),\n ...(props.validators ?? []),\n ...(customValidator ? [customValidator] : []),\n ]\n\n return {\n enabled: !props.disabled,\n multiple: props.multiple,\n validators,\n onFiles: async (dropped: File[]) => {\n // `v-dropzone` уже выполнил валидаторы и нормализацию по `multiple`.\n clearErrors()\n emitModel(dropped)\n clearInputValue()\n await nextTick()\n },\n onError: (error: unknown) => {\n if (error instanceof FileValidationError) {\n setErrors(error.issues)\n }\n else {\n setErrors([\n {\n code: 'accept',\n message: t('gr.formFile.validateError', 'Failed to validate dropped files'),\n },\n ])\n }\n },\n }\n})\n\nwatch(\n () => props.modelValue,\n (value) => {\n if (!inputRef.value) return\n\n if (!value || (Array.isArray(value) && value.length === 0)) {\n // Позволяет выбрать тот же файл снова после внешнего сброса.\n inputRef.value.value = ''\n }\n },\n)\n</script>\n\n<template>\n <div\n v-dropzone=\"dropzone\"\n data-gr-form-file\n class=\"rounded-[var(--gr-radius-md)]\"\n :class=\"disabled ? 'opacity-60 cursor-not-allowed' : ''\"\n >\n <input\n ref=\"inputRef\"\n data-gr-form-file-input\n type=\"file\"\n tabindex=\"-1\"\n aria-hidden=\"true\"\n class=\"absolute opacity-0 w-px h-px pointer-events-none\"\n :multiple=\"multiple\"\n :accept=\"accept\"\n :disabled=\"disabled\"\n @change=\"onInputChange\"\n >\n\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-wrap items-center gap-3\">\n <GrButton\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-upload-btn\n :disabled=\"disabled\"\n @click.prevent=\"openDialog\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconUpload />\n </GrIcon>\n <span class=\"ml-2\">{{ hasFiles ? resolvedChangeText : resolvedUploadText }}</span>\n </GrButton>\n\n <GrButton\n v-if=\"hasFiles && !multiple\"\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-clear-btn\n :disabled=\"disabled\"\n @click.prevent=\"clearAll\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconX />\n </GrIcon>\n <span class=\"ml-2\">{{ resolvedRemoveText }}</span>\n </GrButton>\n\n <GrButton\n v-if=\"multiple && hasFiles\"\n variant=\"secondary\"\n size=\"sm\"\n data-gr-form-file-clear-all-btn\n :disabled=\"disabled\"\n @click.prevent=\"clearAll\"\n >\n <GrIcon size=\"sm\" aria-hidden=\"true\">\n <IconX />\n </GrIcon>\n <span class=\"ml-2\">{{ resolvedClearAllText }}</span>\n </GrButton>\n\n <span\n v-if=\"!multiple && hasFiles\"\n class=\"text-sm text-[var(--muted-fg)] truncate max-w-[240px]\"\n data-gr-form-file-single-name\n :title=\"files[0]?.name\"\n >\n {{ files[0]?.name }}\n </span>\n\n <span\n v-if=\"!hasFiles\"\n class=\"text-sm text-[var(--muted-fg)]\"\n data-gr-form-file-placeholder\n >\n {{ resolvedPlaceholder }}\n </span>\n </div>\n\n <div v-if=\"multiple && hasFiles\" class=\"flex flex-col gap-2\">\n <div\n v-for=\"(file, index) in files\"\n :key=\"`${file.name}-${file.size}-${index}`\"\n class=\"flex items-center gap-2\"\n data-gr-form-file-item\n >\n <span\n class=\"text-sm text-[var(--muted-fg)] truncate max-w-[240px]\"\n :title=\"file.name\"\n data-gr-form-file-item-name\n >\n {{ file.name }}\n </span>\n\n <button\n type=\"button\"\n class=\"text-xs text-[var(--muted-fg)] hover:text-[var(--fg)]\"\n data-gr-form-file-item-remove\n :disabled=\"disabled\"\n @click.prevent=\"removeAt(index)\"\n >\n {{ removeText }}\n </button>\n </div>\n </div>\n\n <slot name=\"errors\" :errors=\"localErrors\">\n <div v-if=\"localErrors.length\" class=\"text-sm text-[var(--gr-danger)]\" data-gr-form-file-errors>\n <div v-for=\"(e, i) in localErrors\" :key=\"i\" data-gr-form-file-error>\n {{ issueMessage(e) }}\n </div>\n </div>\n </slot>\n </div>\n </div>\n</template>\n\n<style scoped>\n[data-gr-form-file].gr-dropzone--over {\n outline: 2px solid var(--ring);\n outline-offset: 2px;\n}\n</style>\n"],"mappings":"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"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as GrFormFile_default } from "./chunks/GrFormFile-
|
|
2
|
-
import { t as grFormFileConfig } from "../../chunks/config-
|
|
1
|
+
import { t as GrFormFile_default } from "./chunks/GrFormFile-CXcqqdvV.js";
|
|
2
|
+
import { t as grFormFileConfig } from "../../chunks/config-D7GZO-Dx.js";
|
|
3
3
|
export { GrFormFile_default as GrFormFile, GrFormFile_default as default, grFormFileConfig };
|
package/dist/components/GrFormSection/chunks/{GrFormSection-dbyzqxYk.js → GrFormSection-Ce21jcgo.js}
RENAMED
|
@@ -16,7 +16,7 @@ var GrFormSection_default = /* @__PURE__ */ defineComponent({
|
|
|
16
16
|
const descriptionId = useId();
|
|
17
17
|
return (_ctx, _cache) => {
|
|
18
18
|
return openBlock(), createElementBlock("section", {
|
|
19
|
-
"data-
|
|
19
|
+
"data-gr-form-section": "",
|
|
20
20
|
class: "grid gap-4",
|
|
21
21
|
"aria-labelledby": unref(titleId),
|
|
22
22
|
"aria-describedby": __props.description ? unref(descriptionId) : void 0
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GrFormSection-
|
|
1
|
+
{"version":3,"file":"GrFormSection-Ce21jcgo.js","names":[],"sources":["../../../../src/components/GrFormSection/GrFormSection.vue","../../../../src/components/GrFormSection/GrFormSection.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { useId } from 'vue'\n\n/**\n * GrFormSection — секция формы с заголовком, опциональным описанием и контентом.\n *\n * - `section` связан с заголовком через `aria-labelledby` и c описанием\n * (если есть) через `aria-describedby` — для a11y.\n */\nexport interface GrFormSectionProps {\n title: string\n description?: string\n}\n\nwithDefaults(defineProps<GrFormSectionProps>(), {\n description: undefined,\n})\n\nconst titleId = useId()\nconst descriptionId = useId()\n</script>\n\n<template>\n <section\n data-gr-form-section\n class=\"grid gap-4\"\n :aria-labelledby=\"titleId\"\n :aria-describedby=\"description ? descriptionId : undefined\"\n >\n <div>\n <div :id=\"titleId\" class=\"text-[14px] font-700\">\n {{ title }}\n </div>\n <div\n v-if=\"description\"\n :id=\"descriptionId\"\n class=\"mt-1 text-[13px] text-[var(--muted-fg)]\"\n >\n {{ description }}\n </div>\n </div>\n <slot />\n </section>\n</template>\n","<script setup lang=\"ts\">\nimport { useId } from 'vue'\n\n/**\n * GrFormSection — секция формы с заголовком, опциональным описанием и контентом.\n *\n * - `section` связан с заголовком через `aria-labelledby` и c описанием\n * (если есть) через `aria-describedby` — для a11y.\n */\nexport interface GrFormSectionProps {\n title: string\n description?: string\n}\n\nwithDefaults(defineProps<GrFormSectionProps>(), {\n description: undefined,\n})\n\nconst titleId = useId()\nconst descriptionId = useId()\n</script>\n\n<template>\n <section\n data-gr-form-section\n class=\"grid gap-4\"\n :aria-labelledby=\"titleId\"\n :aria-describedby=\"description ? descriptionId : undefined\"\n >\n <div>\n <div :id=\"titleId\" class=\"text-[14px] font-700\">\n {{ title }}\n </div>\n <div\n v-if=\"description\"\n :id=\"descriptionId\"\n class=\"mt-1 text-[13px] text-[var(--muted-fg)]\"\n >\n {{ description }}\n </div>\n </div>\n <slot />\n </section>\n</template>\n"],"mappings":";;;;;;;;;;;;;;EAkBA,MAAM,UAAU,MAAM;EACtB,MAAM,gBAAgB,MAAM;;uBAI1B,mBAmBU,WAAA;IAlBR,wBAAA;IACA,OAAM;IACL,mBAAiB,MAAA,OAAA;IACjB,oBAAkB,QAAA,cAAc,MAAA,aAAA,IAAgB,KAAA;OAEjD,mBAWM,OAAA,MAAA,CAVJ,mBAEM,OAAA;IAFA,IAAI,MAAA,OAAA;IAAS,OAAM;sBACpB,QAAA,KAAK,GAAA,GAAA,UAAA,GAGF,QAAA,eAAA,UAAA,GADR,mBAMM,OAAA;;IAJH,IAAI,MAAA,aAAA;IACL,OAAM;sBAEH,QAAA,WAAW,GAAA,GAAA,UAAA,KAAA,mBAAA,IAAA,IAAA,CAAA,CAAA,GAGlB,WAAQ,KAAA,QAAA,SAAA,CAAA,GAAA,GAAA,UAAA"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as GrFormSection_default } from "./chunks/GrFormSection-
|
|
2
|
-
import { t as grFormSectionConfig } from "../../chunks/config-
|
|
1
|
+
import { t as GrFormSection_default } from "./chunks/GrFormSection-Ce21jcgo.js";
|
|
2
|
+
import { t as grFormSectionConfig } from "../../chunks/config-B0qIpo8m.js";
|
|
3
3
|
export { GrFormSection_default as GrFormSection, GrFormSection_default as default, grFormSectionConfig };
|
|
@@ -17,12 +17,12 @@ var GrIcon_default = /* @__PURE__ */ defineComponent({
|
|
|
17
17
|
const props = __props;
|
|
18
18
|
const resolvedSize = computed(() => props.size ?? "md");
|
|
19
19
|
const iconStyle = computed(() => {
|
|
20
|
-
return { "--
|
|
20
|
+
return { "--gr-icon-size": `${resolveGrIconSizePx(resolvedSize.value)}px` };
|
|
21
21
|
});
|
|
22
22
|
return (_ctx, _cache) => {
|
|
23
23
|
return openBlock(), createElementBlock("span", {
|
|
24
|
-
"data-
|
|
25
|
-
class: "
|
|
24
|
+
"data-gr-icon": "",
|
|
25
|
+
class: "gr-icon inline-flex items-center justify-center align-middle",
|
|
26
26
|
style: normalizeStyle(iconStyle.value)
|
|
27
27
|
}, [renderSlot(_ctx.$slots, "default")], 4);
|
|
28
28
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GrIcon-
|
|
1
|
+
{"version":3,"file":"GrIcon-D9AWQLk2.js","names":[],"sources":["../../../../src/components/GrIcon/GrIcon.vue","../../../../src/components/GrIcon/GrIcon.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport {computed} from 'vue'\n\nexport type GrIconSize = 'sm' | 'md' | 'lg'\n\nconst GR_ICON_SIZE_MAP: Record<GrIconSize, number> = {\n sm: 16,\n md: 18,\n lg: 20,\n}\n\nfunction resolveGrIconSizePx(size: GrIconSize | number): number {\n if (typeof size === 'number') return size\n return GR_ICON_SIZE_MAP[size]\n}\n\nconst props = defineProps<{\n size?: GrIconSize | number\n}>()\n\nconst resolvedSize = computed(() => props.size ?? 'md')\n\nconst iconStyle = computed(() => {\n return {\n '--gr-icon-size': `${resolveGrIconSizePx(resolvedSize.value)}px`,\n } as Record<string, string>\n})\n</script>\n\n<template>\n <span\n data-gr-icon\n class=\"gr-icon inline-flex items-center justify-center align-middle\"\n :style=\"iconStyle\"\n >\n <slot />\n </span>\n</template>\n<style>\n/*\n * GrIcon.\n *\n * This must be global because icons are usually passed via slots (SVG),\n * and we want consistent sizing without relying on SFC scoped + :deep.\n */\n:where(.gr-icon) {\n --gr-icon-size: 18px;\n width: var(--gr-icon-size);\n min-width: var(--gr-icon-size);\n height: var(--gr-icon-size);\n line-height: 0;\n flex: none;\n}\n\n:where(.gr-icon svg) {\n width: 100%;\n height: 100%;\n display: block;\n}\n</style>","<script setup lang=\"ts\">\nimport {computed} from 'vue'\n\nexport type GrIconSize = 'sm' | 'md' | 'lg'\n\nconst GR_ICON_SIZE_MAP: Record<GrIconSize, number> = {\n sm: 16,\n md: 18,\n lg: 20,\n}\n\nfunction resolveGrIconSizePx(size: GrIconSize | number): number {\n if (typeof size === 'number') return size\n return GR_ICON_SIZE_MAP[size]\n}\n\nconst props = defineProps<{\n size?: GrIconSize | number\n}>()\n\nconst resolvedSize = computed(() => props.size ?? 'md')\n\nconst iconStyle = computed(() => {\n return {\n '--gr-icon-size': `${resolveGrIconSizePx(resolvedSize.value)}px`,\n } as Record<string, string>\n})\n</script>\n\n<template>\n <span\n data-gr-icon\n class=\"gr-icon inline-flex items-center justify-center align-middle\"\n :style=\"iconStyle\"\n >\n <slot />\n </span>\n</template>\n<style>\n/*\n * GrIcon.\n *\n * This must be global because icons are usually passed via slots (SVG),\n * and we want consistent sizing without relying on SFC scoped + :deep.\n */\n:where(.gr-icon) {\n --gr-icon-size: 18px;\n width: var(--gr-icon-size);\n min-width: var(--gr-icon-size);\n height: var(--gr-icon-size);\n line-height: 0;\n flex: none;\n}\n\n:where(.gr-icon svg) {\n width: 100%;\n height: 100%;\n display: block;\n}\n</style>"],"mappings":";;;;;;;EAKA,MAAM,mBAA+C;GACnD,IAAI;GACJ,IAAI;GACJ,IAAI;EACN;EAEA,SAAS,oBAAoB,MAAmC;GAC9D,IAAI,OAAO,SAAS,UAAU,OAAO;GACrC,OAAO,iBAAiB;EAC1B;EAEA,MAAM,QAAQ;EAId,MAAM,eAAe,eAAe,MAAM,QAAQ,IAAI;EAEtD,MAAM,YAAY,eAAe;GAC/B,OAAO,EACL,kBAAkB,GAAG,oBAAoB,aAAa,KAAK,EAAE,IAC/D;EACF,CAAC;;uBAIC,mBAMO,QAAA;IALH,gBAAA;IACA,OAAM;IACL,OAAK,eAAE,UAAA,KAAS;OAEnB,WAAQ,KAAA,QAAA,SAAA,CAAA,GAAA,CAAA"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as GrIcon_default } from "./chunks/GrIcon-
|
|
2
|
-
import { t as grIconConfig } from "../../chunks/config-
|
|
1
|
+
import { t as GrIcon_default } from "./chunks/GrIcon-D9AWQLk2.js";
|
|
2
|
+
import { t as grIconConfig } from "../../chunks/config-BEegFP74.js";
|
|
3
3
|
export { GrIcon_default as GrIcon, GrIcon_default as default, grIconConfig };
|