@feugene/granularity 0.19.0 → 0.20.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (835) hide show
  1. package/README.md +8 -0
  2. package/dist/chunks/config-8Pcutu1j.js.map +1 -0
  3. package/dist/chunks/{config-06SQjBx0.js → config-B4w5gBD0.js} +1 -8
  4. package/dist/chunks/{config-06SQjBx0.js.map → config-B4w5gBD0.js.map} +1 -1
  5. package/dist/chunks/config-BE6n20np.js.map +1 -0
  6. package/dist/chunks/{config-B-iNaGdw.js → config-BEVBsvni.js} +1 -3
  7. package/dist/chunks/{config-B-iNaGdw.js.map → config-BEVBsvni.js.map} +1 -1
  8. package/dist/chunks/config-BKvX0q10.js.map +1 -0
  9. package/dist/chunks/config-BTCOJO5z.js +37 -0
  10. package/dist/chunks/config-BTCOJO5z.js.map +1 -0
  11. package/dist/chunks/{config-Rw9OyW702.js → config-BfsBepkH2.js} +1 -5
  12. package/dist/chunks/{config-Rw9OyW702.js.map → config-BfsBepkH2.js.map} +1 -1
  13. package/dist/chunks/{config-DP7eseR1.js → config-Bsh948nP.js} +1 -8
  14. package/dist/chunks/{config-DP7eseR1.js.map → config-Bsh948nP.js.map} +1 -1
  15. package/dist/chunks/config-CDat1wXf.js.map +1 -0
  16. package/dist/chunks/config-COpuWGr_2.js.map +1 -0
  17. package/dist/chunks/config-CY0_6cMi.js.map +1 -0
  18. package/dist/chunks/config-D94Z9po5.js.map +1 -0
  19. package/dist/chunks/config-DAX8Deh12.js.map +1 -0
  20. package/dist/chunks/{config-_qPUfb6-2.js → config-DWN4x6_e.js} +1 -7
  21. package/dist/chunks/config-DWN4x6_e.js.map +1 -0
  22. package/dist/chunks/{config-DhHbU3zO.js → config-Dgj1Q6JY.js} +1 -12
  23. package/dist/chunks/{config-DhHbU3zO.js.map → config-Dgj1Q6JY.js.map} +1 -1
  24. package/dist/chunks/{config-D3_g2KIn.js → config-Dguto_6o.js} +1 -13
  25. package/dist/chunks/{config-D3_g2KIn.js.map → config-Dguto_6o.js.map} +1 -1
  26. package/dist/chunks/config-WTNhdh6T.js.map +1 -0
  27. package/dist/chunks/config-eXB87DOi2.js.map +1 -0
  28. package/dist/chunks/{config-DvQIb4kb.js → config-vSji8w90.js} +1 -14
  29. package/dist/chunks/{config-DvQIb4kb.js.map → config-vSji8w90.js.map} +1 -1
  30. package/dist/chunks/{context-BSYR7RZs.js → context-CTbuwcYs.js} +1 -20
  31. package/dist/chunks/{context-BSYR7RZs.js.map → context-CTbuwcYs.js.map} +1 -1
  32. package/dist/chunks/{config-BqFjr3tN.js → grRadioStyles-BTjGNhtU.js} +1 -36
  33. package/dist/chunks/grRadioStyles-BTjGNhtU.js.map +1 -0
  34. package/dist/chunks/{granular-provider-C6uAujdJ.js → granular-provider-CZYm70Pm.js} +19 -19
  35. package/dist/chunks/{granular-provider-C6uAujdJ.js.map → granular-provider-CZYm70Pm.js.map} +1 -1
  36. package/dist/chunks/{useModalOverlay-DrQVYwwA.js → useModalOverlay-Cv5hF63W.js} +2 -2
  37. package/dist/chunks/{useModalOverlay-DrQVYwwA.js.map → useModalOverlay-Cv5hF63W.js.map} +1 -1
  38. package/dist/chunks/{usePortalTarget-Cn-Wiz5d.js → usePortalTarget-C0p-mhaM.js} +1 -1
  39. package/dist/chunks/{usePortalTarget-Cn-Wiz5d.js.map → usePortalTarget-C0p-mhaM.js.map} +1 -1
  40. package/dist/chunks/{validation-5HhpanPP.js → validation-DauXRIkL.js} +1 -1
  41. package/dist/chunks/{validation-5HhpanPP.js.map → validation-DauXRIkL.js.map} +1 -1
  42. package/dist/components/GrAlert/chunks/{GrAlert-BC1lplbY.js → GrAlert-B21QGele.js} +2 -16
  43. package/dist/components/GrAlert/chunks/{GrAlert-BC1lplbY.js.map → GrAlert-B21QGele.js.map} +1 -1
  44. package/dist/components/GrAlert/index.js +2 -2
  45. package/dist/components/GrAutocomplete/chunks/{GrAutocomplete-gY4Xopza.js → GrAutocomplete-DsevPtiS.js} +3 -3
  46. package/dist/components/GrAutocomplete/chunks/{GrAutocomplete-gY4Xopza.js.map → GrAutocomplete-DsevPtiS.js.map} +1 -1
  47. package/dist/components/GrAutocomplete/index.js +1 -1
  48. package/dist/components/GrAvatar/chunks/{GrAvatar-CVUujLmn.js → GrAvatar-BbdKRX8i.js} +3 -3
  49. package/dist/components/GrAvatar/chunks/{GrAvatar-CVUujLmn.js.map → GrAvatar-BbdKRX8i.js.map} +1 -1
  50. package/dist/components/GrAvatar/index.js +3 -3
  51. package/dist/components/GrBadge/chunks/{GrBadge-B1tgqfGQ.js → GrBadge-u2ZdS7CN.js} +1 -1
  52. package/dist/components/GrBadge/chunks/{GrBadge-B1tgqfGQ.js.map → GrBadge-u2ZdS7CN.js.map} +1 -1
  53. package/dist/components/GrBadge/index.js +1 -1
  54. package/dist/components/GrBadgeWrap/chunks/{GrBadgeWrap-C-E9betg.js → GrBadgeWrap-DDoFQscR.js} +1 -1
  55. package/dist/components/GrBadgeWrap/chunks/{GrBadgeWrap-C-E9betg.js.map → GrBadgeWrap-DDoFQscR.js.map} +1 -1
  56. package/dist/components/GrBadgeWrap/index.js +3 -3
  57. package/dist/components/GrBottomNav/chunks/{GrBottomNav-9GH7Dd9E.js → GrBottomNav-JUu4ylYv.js} +2 -2
  58. package/dist/components/GrBottomNav/chunks/{GrBottomNav-9GH7Dd9E.js.map → GrBottomNav-JUu4ylYv.js.map} +1 -1
  59. package/dist/components/GrBottomNav/index.js +3 -3
  60. package/dist/components/GrBreadcrumbs/chunks/{GrBreadcrumbs-DS_-PBVt.js → GrBreadcrumbs-CQ44iU2o.js} +2 -2
  61. package/dist/components/GrBreadcrumbs/chunks/{GrBreadcrumbs-DS_-PBVt.js.map → GrBreadcrumbs-CQ44iU2o.js.map} +1 -1
  62. package/dist/components/GrBreadcrumbs/index.js +1 -1
  63. package/dist/components/GrButton/chunks/{GrButton-D0m_z0XW.js → GrButton-Bw2AH4uX.js} +1 -1
  64. package/dist/components/GrButton/chunks/{GrButton-D0m_z0XW.js.map → GrButton-Bw2AH4uX.js.map} +1 -1
  65. package/dist/components/GrButton/index.js +2 -3
  66. package/dist/components/GrCard/chunks/{GrCard-DOrGHf2x.js → GrCard-DfIZOP5N.js} +1 -1
  67. package/dist/components/GrCard/chunks/{GrCard-DOrGHf2x.js.map → GrCard-DfIZOP5N.js.map} +1 -1
  68. package/dist/components/GrCard/index.js +1 -1
  69. package/dist/components/GrCheckbox/chunks/{GrCheckbox-BLOp8452.js → GrCheckbox-CEcHIsXM.js} +1 -1
  70. package/dist/components/GrCheckbox/chunks/{GrCheckbox-BLOp8452.js.map → GrCheckbox-CEcHIsXM.js.map} +1 -1
  71. package/dist/components/GrCheckbox/index.js +2 -2
  72. package/dist/components/GrCheckboxGroup/chunks/{GrCheckboxGroup-CXTx2Z5H.js → GrCheckboxGroup-BOwrVcFr.js} +2 -2
  73. package/dist/components/GrCheckboxGroup/chunks/{GrCheckboxGroup-CXTx2Z5H.js.map → GrCheckboxGroup-BOwrVcFr.js.map} +1 -1
  74. package/dist/components/GrCheckboxGroup/index.js +1 -1
  75. package/dist/components/GrCollapse/chunks/{GrCollapse-Kk0DE8tb.js → GrCollapse-KFcrji1L.js} +4 -18
  76. package/dist/components/GrCollapse/chunks/{GrCollapse-Kk0DE8tb.js.map → GrCollapse-KFcrji1L.js.map} +1 -1
  77. package/dist/components/GrCollapse/index.js +2 -2
  78. package/dist/components/GrColorPicker/chunks/{GrColorPicker-CkBTzkqn.js → GrColorPicker-qQdoEPHF.js} +5 -5
  79. package/dist/components/GrColorPicker/chunks/{GrColorPicker-CkBTzkqn.js.map → GrColorPicker-qQdoEPHF.js.map} +1 -1
  80. package/dist/components/GrColorPicker/index.js +2 -2
  81. package/dist/components/GrCommandPalette/chunks/{GrCommandPalette-BugTlGdj.js → GrCommandPalette-BFcMf4Pn.js} +4 -4
  82. package/dist/components/GrCommandPalette/chunks/{GrCommandPalette-BugTlGdj.js.map → GrCommandPalette-BFcMf4Pn.js.map} +1 -1
  83. package/dist/components/GrCommandPalette/index.js +2 -2
  84. package/dist/components/GrConfigProvider/chunks/{GrConfigProvider-BA6JO7V6.js → GrConfigProvider-UP-EaoAf.js} +1 -1
  85. package/dist/components/GrConfigProvider/chunks/{GrConfigProvider-BA6JO7V6.js.map → GrConfigProvider-UP-EaoAf.js.map} +1 -1
  86. package/dist/components/GrConfigProvider/index.js +3 -3
  87. package/dist/components/GrConfirmDialog/chunks/{GrConfirmDialog-Ds5T0GiR.js → GrConfirmDialog-rRtMScJX.js} +4 -4
  88. package/dist/components/GrConfirmDialog/chunks/{GrConfirmDialog-Ds5T0GiR.js.map → GrConfirmDialog-rRtMScJX.js.map} +1 -1
  89. package/dist/components/GrConfirmDialog/index.js +1 -1
  90. package/dist/components/GrDataTable/chunks/{GrDataTable-CYe2A2WA.js → GrDataTable-CNvZg2HZ.js} +5 -5
  91. package/dist/components/GrDataTable/chunks/{GrDataTable-CYe2A2WA.js.map → GrDataTable-CNvZg2HZ.js.map} +1 -1
  92. package/dist/components/GrDataTable/index.js +2 -2
  93. package/dist/components/GrDialog/chunks/{GrDialog-C3tYaA8v.js → GrDialog-D0U5iRqV.js} +3 -3
  94. package/dist/components/GrDialog/chunks/{GrDialog-C3tYaA8v.js.map → GrDialog-D0U5iRqV.js.map} +1 -1
  95. package/dist/components/GrDialog/index.js +2 -3
  96. package/dist/components/GrDialogService/chunks/{GrDialogService-CTBiiJDI.js → GrDialogService-CrwA4aJq.js} +6 -6
  97. package/dist/components/GrDialogService/chunks/GrDialogService-CrwA4aJq.js.map +1 -0
  98. package/dist/components/GrDialogService/index.js +2 -2
  99. package/dist/components/GrDivider/chunks/{GrDivider-xxq1_fIl.js → GrDivider-CAhm9jbE.js} +2 -2
  100. package/dist/components/GrDivider/chunks/{GrDivider-xxq1_fIl.js.map → GrDivider-CAhm9jbE.js.map} +1 -1
  101. package/dist/components/GrDivider/index.js +2 -2
  102. package/dist/components/GrDrawer/chunks/{GrDrawer-BSSuiNHU.js → GrDrawer-C3zAg2tG.js} +5 -5
  103. package/dist/components/GrDrawer/chunks/{GrDrawer-BSSuiNHU.js.map → GrDrawer-C3zAg2tG.js.map} +1 -1
  104. package/dist/components/GrDrawer/index.js +2 -2
  105. package/dist/components/GrDropdown/chunks/{GrDropdown-Bh6UK2M5.js → GrDropdown-BSfFOcDx.js} +2 -2
  106. package/dist/components/GrDropdown/chunks/{GrDropdown-Bh6UK2M5.js.map → GrDropdown-BSfFOcDx.js.map} +1 -1
  107. package/dist/components/GrDropdown/index.js +1 -1
  108. package/dist/components/GrDropdownMenu/chunks/{GrDropdownMenu-LyfEFUbg.js → GrDropdownMenu-LOaFSCyd.js} +3 -3
  109. package/dist/components/GrDropdownMenu/chunks/{GrDropdownMenu-LyfEFUbg.js.map → GrDropdownMenu-LOaFSCyd.js.map} +1 -1
  110. package/dist/components/GrDropdownMenu/index.js +3 -3
  111. package/dist/components/GrEmptyState/chunks/{GrEmptyState-W7Irx3vc.js → GrEmptyState-CS9do8eM.js} +3 -3
  112. package/dist/components/GrEmptyState/chunks/{GrEmptyState-W7Irx3vc.js.map → GrEmptyState-CS9do8eM.js.map} +1 -1
  113. package/dist/components/GrEmptyState/index.js +3 -3
  114. package/dist/components/GrFileUpload/chunks/{GrFileUpload-DuDzC43S.js → GrFileUpload-D3-vC-ap.js} +4 -4
  115. package/dist/components/GrFileUpload/chunks/{GrFileUpload-DuDzC43S.js.map → GrFileUpload-D3-vC-ap.js.map} +1 -1
  116. package/dist/components/GrFileUpload/index.js +3 -3
  117. package/dist/components/GrForm/chunks/{GrForm-BCHCfIMv.js → GrForm-DdJw23Pz.js} +1 -1
  118. package/dist/components/GrForm/chunks/{GrForm-BCHCfIMv.js.map → GrForm-DdJw23Pz.js.map} +1 -1
  119. package/dist/components/GrForm/index.js +4 -4
  120. package/dist/components/GrFormField/chunks/{GrFormField-CL5rcgj6.js → GrFormField-kqfVY30N.js} +1 -1
  121. package/dist/components/GrFormField/chunks/{GrFormField-CL5rcgj6.js.map → GrFormField-kqfVY30N.js.map} +1 -1
  122. package/dist/components/GrFormField/index.js +3 -3
  123. package/dist/components/GrFormFile/chunks/{GrFormFile-BikSD7bg.js → GrFormFile-D722xHn8.js} +3 -3
  124. package/dist/components/GrFormFile/chunks/{GrFormFile-BikSD7bg.js.map → GrFormFile-D722xHn8.js.map} +1 -1
  125. package/dist/components/GrFormFile/index.js +1 -1
  126. package/dist/components/GrFormSection/chunks/{GrFormSection-BEh5n4jF.js → GrFormSection-CdGWvzXO.js} +2 -2
  127. package/dist/components/GrFormSection/chunks/{GrFormSection-BEh5n4jF.js.map → GrFormSection-CdGWvzXO.js.map} +1 -1
  128. package/dist/components/GrFormSection/index.js +3 -3
  129. package/dist/components/GrIcon/chunks/{GrIcon-BvA2ZGXP.js → GrIcon-bQwtZtYT.js} +1 -1
  130. package/dist/components/GrIcon/chunks/{GrIcon-BvA2ZGXP.js.map → GrIcon-bQwtZtYT.js.map} +1 -1
  131. package/dist/components/GrIcon/index.js +1 -1
  132. package/dist/components/GrImageViewer/chunks/{GrImageViewer-DfD4euH5.js → GrImageViewer-CMO10TS7.js} +2 -2
  133. package/dist/components/GrImageViewer/chunks/{GrImageViewer-DfD4euH5.js.map → GrImageViewer-CMO10TS7.js.map} +1 -1
  134. package/dist/components/GrImageViewer/index.js +1 -1
  135. package/dist/components/GrInput/chunks/{GrInput-2wd7Crs0.js → GrInput-Bb_pxqpT.js} +1 -1
  136. package/dist/components/GrInput/chunks/{GrInput-2wd7Crs0.js.map → GrInput-Bb_pxqpT.js.map} +1 -1
  137. package/dist/components/GrInput/index.js +1 -1
  138. package/dist/components/GrInputTag/chunks/{GrInputTag-CyV2eY7Z.js → GrInputTag-Dghhg03-.js} +3 -3
  139. package/dist/components/GrInputTag/chunks/{GrInputTag-CyV2eY7Z.js.map → GrInputTag-Dghhg03-.js.map} +1 -1
  140. package/dist/components/GrInputTag/index.js +1 -1
  141. package/dist/components/GrKbd/chunks/{GrKbd-DU2lBkRV.js → GrKbd-BXbhsH0M.js} +1 -1
  142. package/dist/components/GrKbd/chunks/{GrKbd-DU2lBkRV.js.map → GrKbd-BXbhsH0M.js.map} +1 -1
  143. package/dist/components/GrKbd/index.js +1 -1
  144. package/dist/components/GrLink/chunks/{GrLink-D-cgUMXW.js → GrLink-BQb7U4so.js} +2 -2
  145. package/dist/components/GrLink/chunks/{GrLink-D-cgUMXW.js.map → GrLink-BQb7U4so.js.map} +1 -1
  146. package/dist/components/GrLink/index.js +1 -1
  147. package/dist/components/GrList/chunks/{GrList-4YU1NZtM.js → GrList-CHibO0xA.js} +2 -2
  148. package/dist/components/GrList/chunks/{GrList-4YU1NZtM.js.map → GrList-CHibO0xA.js.map} +1 -1
  149. package/dist/components/GrList/index.js +1 -1
  150. package/dist/components/GrLoading/chunks/{GrLoading-CH95CFzS.js → GrLoading-C3DZSSuh.js} +1 -1
  151. package/dist/components/GrLoading/chunks/{GrLoading-CH95CFzS.js.map → GrLoading-C3DZSSuh.js.map} +1 -1
  152. package/dist/components/GrLoading/index.js +1 -1
  153. package/dist/components/GrModal/chunks/{GrModal-CbMMr6W1.js → GrModal-CPz7SWD_.js} +2 -2
  154. package/dist/components/GrModal/chunks/{GrModal-CbMMr6W1.js.map → GrModal-CPz7SWD_.js.map} +1 -1
  155. package/dist/components/GrModal/index.js +1 -1
  156. package/dist/components/GrNavbar/chunks/{GrNavbar-CF0KbM_6.js → GrNavbar-DWaaoV7n.js} +2 -2
  157. package/dist/components/GrNavbar/chunks/{GrNavbar-CF0KbM_6.js.map → GrNavbar-DWaaoV7n.js.map} +1 -1
  158. package/dist/components/GrNavbar/index.js +1 -1
  159. package/dist/components/GrNumberInput/chunks/{GrNumberInput-B5CHZDBj.js → GrNumberInput-BotnzW77.js} +2 -2
  160. package/dist/components/GrNumberInput/chunks/{GrNumberInput-B5CHZDBj.js.map → GrNumberInput-BotnzW77.js.map} +1 -1
  161. package/dist/components/GrNumberInput/index.js +1 -1
  162. package/dist/components/GrPagination/chunks/{GrPagination-BM4FrD6Q.js → GrPagination-GtGtSMJG.js} +3 -3
  163. package/dist/components/GrPagination/chunks/{GrPagination-BM4FrD6Q.js.map → GrPagination-GtGtSMJG.js.map} +1 -1
  164. package/dist/components/GrPagination/index.js +1 -1
  165. package/dist/components/GrPopover/chunks/{GrPopover-DMH4Jjst.js → GrPopover-b70bIlQ9.js} +2 -2
  166. package/dist/components/GrPopover/chunks/{GrPopover-DMH4Jjst.js.map → GrPopover-b70bIlQ9.js.map} +1 -1
  167. package/dist/components/GrPopover/index.js +1 -1
  168. package/dist/components/GrProgressBar/chunks/{GrProgressBar-xwbNM9QB.js → GrProgressBar-hszUOC8f.js} +1 -1
  169. package/dist/components/GrProgressBar/chunks/{GrProgressBar-xwbNM9QB.js.map → GrProgressBar-hszUOC8f.js.map} +1 -1
  170. package/dist/components/GrProgressBar/index.js +1 -1
  171. package/dist/components/GrProgressCircle/chunks/{GrProgressCircle-B8olXRo5.js → GrProgressCircle-BeUx1g1f.js} +3 -11
  172. package/dist/components/GrProgressCircle/chunks/{GrProgressCircle-B8olXRo5.js.map → GrProgressCircle-BeUx1g1f.js.map} +1 -1
  173. package/dist/components/GrProgressCircle/index.js +2 -2
  174. package/dist/components/GrPromptDialog/chunks/{GrPromptDialog-Pwr9NPxK.js → GrPromptDialog-CEI8bf-t.js} +8 -8
  175. package/dist/components/GrPromptDialog/chunks/{GrPromptDialog-Pwr9NPxK.js.map → GrPromptDialog-CEI8bf-t.js.map} +1 -1
  176. package/dist/components/GrPromptDialog/index.js +1 -1
  177. package/dist/components/GrRadio/chunks/{GrRadio-DWiRaMzt.js → GrRadio-BdhknbO8.js} +2 -2
  178. package/dist/components/GrRadio/chunks/{GrRadio-DWiRaMzt.js.map → GrRadio-BdhknbO8.js.map} +1 -1
  179. package/dist/components/GrRadio/index.js +3 -3
  180. package/dist/components/GrRadioGroup/chunks/{GrRadioGroup-DIuBw0wk.js → GrRadioGroup-BVmjKXcv.js} +2 -2
  181. package/dist/components/GrRadioGroup/chunks/GrRadioGroup-BVmjKXcv.js.map +1 -0
  182. package/dist/components/GrRadioGroup/index.js +1 -1
  183. package/dist/components/GrRating/chunks/{GrRating-DVFH3lYu.js → GrRating-BSEtaibx.js} +1 -1
  184. package/dist/components/GrRating/chunks/{GrRating-DVFH3lYu.js.map → GrRating-BSEtaibx.js.map} +1 -1
  185. package/dist/components/GrRating/index.js +1 -1
  186. package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-C7W9mgYN.js → GrResponseErrorBanner-CZONq8uT.js} +3 -3
  187. package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-C7W9mgYN.js.map → GrResponseErrorBanner-CZONq8uT.js.map} +1 -1
  188. package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-DhX4jjay.js → GrResponseErrorBanner-CgfAwlg3.js} +1 -1
  189. package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-DhX4jjay.js.map → GrResponseErrorBanner-CgfAwlg3.js.map} +1 -1
  190. package/dist/components/GrResponseErrorBanner/index.js +3 -3
  191. package/dist/components/GrSegmented/chunks/{GrSegmented-CQw3ijqa.js → GrSegmented-DP9WMAbm.js} +2 -2
  192. package/dist/components/GrSegmented/chunks/{GrSegmented-CQw3ijqa.js.map → GrSegmented-DP9WMAbm.js.map} +1 -1
  193. package/dist/components/GrSegmented/index.js +3 -3
  194. package/dist/components/GrSelect/chunks/{GrSelect-B-Voni7D.js → GrSelect-CaGuyvtb.js} +5 -7
  195. package/dist/components/GrSelect/chunks/GrSelect-CaGuyvtb.js.map +1 -0
  196. package/dist/components/GrSelect/index.js +1 -1
  197. package/dist/components/GrSelect/styles.css +1 -1
  198. package/dist/components/GrSidebar/chunks/{GrSidebar-i7AxjhY_.js → GrSidebar-DG_t4aPE.js} +3 -3
  199. package/dist/components/GrSidebar/chunks/{GrSidebar-i7AxjhY_.js.map → GrSidebar-DG_t4aPE.js.map} +1 -1
  200. package/dist/components/GrSidebar/index.js +3 -3
  201. package/dist/components/GrSkeleton/chunks/{GrSkeleton-DEvNE3bC.js → GrSkeleton-CgfXxPQ2.js} +1 -7
  202. package/dist/components/GrSkeleton/chunks/{GrSkeleton-DEvNE3bC.js.map → GrSkeleton-CgfXxPQ2.js.map} +1 -1
  203. package/dist/components/GrSkeleton/index.js +3 -3
  204. package/dist/components/GrSlider/chunks/{GrSlider-CyhVsNKn.js → GrSlider-s99yAyz6.js} +1 -1
  205. package/dist/components/GrSlider/chunks/{GrSlider-CyhVsNKn.js.map → GrSlider-s99yAyz6.js.map} +1 -1
  206. package/dist/components/GrSlider/index.js +1 -1
  207. package/dist/components/GrSortableList/chunks/{GrSortableList-XB7mXM1W.js → GrSortableList-DJFPdUVv.js} +2 -2
  208. package/dist/components/GrSortableList/chunks/{GrSortableList-XB7mXM1W.js.map → GrSortableList-DJFPdUVv.js.map} +1 -1
  209. package/dist/components/GrSortableList/index.js +2 -2
  210. package/dist/components/GrSplitter/chunks/{GrSplitter-BzxVQwbY.js → GrSplitter-B9_JrT7q.js} +3 -12
  211. package/dist/components/GrSplitter/chunks/{GrSplitter-BzxVQwbY.js.map → GrSplitter-B9_JrT7q.js.map} +1 -1
  212. package/dist/components/GrSplitter/index.js +3 -3
  213. package/dist/components/GrStatistic/chunks/{GrStatistic-DOsM6s5V.js → GrStatistic-C3VpykHo.js} +2 -2
  214. package/dist/components/GrStatistic/chunks/{GrStatistic-DOsM6s5V.js.map → GrStatistic-C3VpykHo.js.map} +1 -1
  215. package/dist/components/GrStatistic/index.js +1 -1
  216. package/dist/components/GrSwitch/chunks/{GrSwitch-DpyvVrZG.js → GrSwitch-x_vQQ6ao.js} +1 -1
  217. package/dist/components/GrSwitch/chunks/{GrSwitch-DpyvVrZG.js.map → GrSwitch-x_vQQ6ao.js.map} +1 -1
  218. package/dist/components/GrSwitch/index.js +1 -1
  219. package/dist/components/GrTabPanels/chunks/{GrTabPanels-BVe1CZdJ.js → GrTabPanels-AJt1w1XC.js} +1 -1
  220. package/dist/components/GrTabPanels/chunks/{GrTabPanels-BVe1CZdJ.js.map → GrTabPanels-AJt1w1XC.js.map} +1 -1
  221. package/dist/components/GrTabPanels/index.js +3 -3
  222. package/dist/components/GrTable/chunks/{GrTable-BfqgwETQ.js → GrTable-f3qCWa99.js} +2 -2
  223. package/dist/components/GrTable/chunks/{GrTable-BfqgwETQ.js.map → GrTable-f3qCWa99.js.map} +1 -1
  224. package/dist/components/GrTable/index.js +2 -2
  225. package/dist/components/GrTabs/chunks/{GrTabs-f3-oQenu.js → GrTabs-CBHZkOFY.js} +2 -2
  226. package/dist/components/GrTabs/chunks/{GrTabs-f3-oQenu.js.map → GrTabs-CBHZkOFY.js.map} +1 -1
  227. package/dist/components/GrTabs/index.js +3 -3
  228. package/dist/components/GrTextarea/chunks/{GrTextarea-DSvd1nSy.js → GrTextarea-CNnkcIG1.js} +1 -1
  229. package/dist/components/GrTextarea/chunks/{GrTextarea-DSvd1nSy.js.map → GrTextarea-CNnkcIG1.js.map} +1 -1
  230. package/dist/components/GrTextarea/index.js +1 -1
  231. package/dist/components/GrTimeline/chunks/{GrTimeline-B-h2Yanw.js → GrTimeline-DlTraRn5.js} +4 -15
  232. package/dist/components/GrTimeline/chunks/{GrTimeline-B-h2Yanw.js.map → GrTimeline-DlTraRn5.js.map} +1 -1
  233. package/dist/components/GrTimeline/index.js +3 -3
  234. package/dist/components/GrToaster/chunks/{GrToaster-Dqja0Lf9.js → GrToaster-Db2NgrXu.js} +4 -4
  235. package/dist/components/GrToaster/chunks/{GrToaster-Dqja0Lf9.js.map → GrToaster-Db2NgrXu.js.map} +1 -1
  236. package/dist/components/GrToaster/index.js +1 -1
  237. package/dist/components/GrTooltip/chunks/{GrTooltip-Cn08heWz.js → GrTooltip-B6AwE_UX.js} +3 -3
  238. package/dist/components/GrTooltip/chunks/{GrTooltip-Cn08heWz.js.map → GrTooltip-B6AwE_UX.js.map} +1 -1
  239. package/dist/components/GrTooltip/index.js +1 -1
  240. package/dist/components/GrTree/chunks/{GrTree-BR9a2pay.js → GrTree-BvOeQ3xJ.js} +1 -1
  241. package/dist/components/GrTree/chunks/{GrTree-BR9a2pay.js.map → GrTree-BvOeQ3xJ.js.map} +1 -1
  242. package/dist/components/GrTree/index.js +2 -2
  243. package/dist/components/GrTreeSelect/chunks/{GrTreeSelect--muUeB0v.js → GrTreeSelect-_LjTRR7X.js} +5 -9
  244. package/dist/components/GrTreeSelect/chunks/GrTreeSelect-_LjTRR7X.js.map +1 -0
  245. package/dist/components/GrTreeSelect/index.js +1 -1
  246. package/dist/composables/useGrComponentConfig.js +1 -1
  247. package/dist/composables/usePortalTarget.js +1 -1
  248. package/dist/directives/loading.js +1 -1
  249. package/dist/granular-provider-node.js +1 -1
  250. package/dist/granular-provider.js +1 -1
  251. package/dist/index.js +95 -96
  252. package/dist/testing.js +33 -2
  253. package/dist/testing.js.map +1 -1
  254. package/dist/types/{src/components → components}/GrAlert/index.d.ts +0 -1
  255. package/dist/types/{src/components → components}/GrAvatar/index.d.ts +0 -1
  256. package/dist/types/{src/components → components}/GrBadgeWrap/index.d.ts +1 -1
  257. package/dist/types/{src/components → components}/GrBottomNav/index.d.ts +0 -1
  258. package/dist/types/{src/components → components}/GrButton/index.d.ts +0 -1
  259. package/dist/types/{src/components → components}/GrCheckbox/index.d.ts +0 -1
  260. package/dist/types/{src/components → components}/GrCollapse/index.d.ts +0 -1
  261. package/dist/types/{src/components → components}/GrColorPicker/index.d.ts +1 -1
  262. package/dist/types/{src/components → components}/GrCommandPalette/index.d.ts +0 -1
  263. package/dist/types/{src/components → components}/GrConfigProvider/index.d.ts +1 -1
  264. package/dist/types/{src/components → components}/GrDataTable/index.d.ts +0 -1
  265. package/dist/types/{src/components → components}/GrDialog/index.d.ts +1 -1
  266. package/dist/types/{src/components → components}/GrDialogService/index.d.ts +1 -1
  267. package/dist/types/{src/components → components}/GrDropdownMenu/index.d.ts +0 -1
  268. package/dist/types/{src/components → components}/GrEmptyState/index.d.ts +0 -1
  269. package/dist/types/{src/components → components}/GrFileUpload/index.d.ts +2 -3
  270. package/dist/types/{src/components → components}/GrForm/index.d.ts +2 -2
  271. package/dist/types/{src/components → components}/GrFormField/index.d.ts +1 -1
  272. package/dist/types/{src/components → components}/GrFormSection/index.d.ts +0 -1
  273. package/dist/types/{src/components → components}/GrProgressCircle/index.d.ts +0 -1
  274. package/dist/types/{src/components → components}/GrRadio/index.d.ts +0 -1
  275. package/dist/types/{src/components → components}/GrResponseErrorBanner/index.d.ts +2 -3
  276. package/dist/types/{src/components → components}/GrSegmented/index.d.ts +1 -1
  277. package/dist/types/{src/components → components}/GrSelect/GrSelect.vue.d.ts +0 -6
  278. package/dist/types/{src/components → components}/GrSidebar/index.d.ts +0 -1
  279. package/dist/types/{src/components → components}/GrSkeleton/index.d.ts +1 -1
  280. package/dist/types/{src/components → components}/GrSplitter/index.d.ts +1 -1
  281. package/dist/types/{src/components → components}/GrTabPanels/index.d.ts +0 -1
  282. package/dist/types/{src/components → components}/GrTabs/index.d.ts +0 -1
  283. package/dist/types/{src/components → components}/GrTimeline/index.d.ts +0 -2
  284. package/dist/types/{src/components → components}/GrTreeSelect/GrTreeSelect.vue.d.ts +0 -6
  285. package/dist/types/{src/testing → testing}/index.d.ts +1 -0
  286. package/dist/types/testing/keyboard.d.ts +32 -0
  287. package/dist/web-types.json +1 -9
  288. package/package.json +109 -106
  289. package/dist/chunks/config-8Pcutu1j2.js.map +0 -1
  290. package/dist/chunks/config-BE6n20np2.js.map +0 -1
  291. package/dist/chunks/config-BKvX0q102.js.map +0 -1
  292. package/dist/chunks/config-BqFjr3tN.js.map +0 -1
  293. package/dist/chunks/config-CDat1wXf2.js.map +0 -1
  294. package/dist/chunks/config-COpuWGr_.js.map +0 -1
  295. package/dist/chunks/config-CY0_6cMi2.js.map +0 -1
  296. package/dist/chunks/config-D94Z9po52.js.map +0 -1
  297. package/dist/chunks/config-DAX8Deh1.js.map +0 -1
  298. package/dist/chunks/config-WTNhdh6T2.js.map +0 -1
  299. package/dist/chunks/config-_qPUfb6-2.js.map +0 -1
  300. package/dist/chunks/config-eXB87DOi.js.map +0 -1
  301. package/dist/components/GrDialogService/chunks/GrDialogService-CTBiiJDI.js.map +0 -1
  302. package/dist/components/GrRadioGroup/chunks/GrRadioGroup-DIuBw0wk.js.map +0 -1
  303. package/dist/components/GrSelect/chunks/GrSelect-B-Voni7D.js.map +0 -1
  304. package/dist/components/GrTreeSelect/chunks/GrTreeSelect--muUeB0v.js.map +0 -1
  305. /package/dist/chunks/{config-8Pcutu1j2.js → config-8Pcutu1j.js} +0 -0
  306. /package/dist/chunks/{config-BE6n20np2.js → config-BE6n20np.js} +0 -0
  307. /package/dist/chunks/{config-BKvX0q102.js → config-BKvX0q10.js} +0 -0
  308. /package/dist/chunks/{config-CDat1wXf2.js → config-CDat1wXf.js} +0 -0
  309. /package/dist/chunks/{config-COpuWGr_.js → config-COpuWGr_2.js} +0 -0
  310. /package/dist/chunks/{config-CY0_6cMi2.js → config-CY0_6cMi.js} +0 -0
  311. /package/dist/chunks/{config-D94Z9po52.js → config-D94Z9po5.js} +0 -0
  312. /package/dist/chunks/{config-DAX8Deh1.js → config-DAX8Deh12.js} +0 -0
  313. /package/dist/chunks/{config-WTNhdh6T2.js → config-WTNhdh6T.js} +0 -0
  314. /package/dist/chunks/{config-eXB87DOi.js → config-eXB87DOi2.js} +0 -0
  315. /package/dist/types/{src/components → components}/GrAlert/GrAlert.vue.d.ts +0 -0
  316. /package/dist/types/{src/components → components}/GrAlert/config.d.ts +0 -0
  317. /package/dist/types/{src/components → components}/GrAlert/defaults.d.ts +0 -0
  318. /package/dist/types/{src/components → components}/GrAlert/grAlertStyles.d.ts +0 -0
  319. /package/dist/types/{src/components → components}/GrAutocomplete/GrAutocomplete.vue.d.ts +0 -0
  320. /package/dist/types/{src/components → components}/GrAutocomplete/config.d.ts +0 -0
  321. /package/dist/types/{src/components → components}/GrAutocomplete/defaults.d.ts +0 -0
  322. /package/dist/types/{src/components → components}/GrAutocomplete/grAutocompleteStyles.d.ts +0 -0
  323. /package/dist/types/{src/components → components}/GrAutocomplete/index.d.ts +0 -0
  324. /package/dist/types/{src/components → components}/GrAutocomplete/safelist.d.ts +0 -0
  325. /package/dist/types/{src/components → components}/GrAvatar/GrAvatar.vue.d.ts +0 -0
  326. /package/dist/types/{src/components → components}/GrAvatar/GrAvatarGroup.vue.d.ts +0 -0
  327. /package/dist/types/{src/components → components}/GrAvatar/avatarContext.d.ts +0 -0
  328. /package/dist/types/{src/components → components}/GrAvatar/config.d.ts +0 -0
  329. /package/dist/types/{src/components → components}/GrAvatar/defaults.d.ts +0 -0
  330. /package/dist/types/{src/components → components}/GrAvatar/grAvatarStyles.d.ts +0 -0
  331. /package/dist/types/{src/components → components}/GrAvatar/safelist.d.ts +0 -0
  332. /package/dist/types/{src/components → components}/GrBadge/GrBadge.vue.d.ts +0 -0
  333. /package/dist/types/{src/components → components}/GrBadge/config.d.ts +0 -0
  334. /package/dist/types/{src/components → components}/GrBadge/defaults.d.ts +0 -0
  335. /package/dist/types/{src/components → components}/GrBadge/grBadgeStyles.d.ts +0 -0
  336. /package/dist/types/{src/components → components}/GrBadge/index.d.ts +0 -0
  337. /package/dist/types/{src/components → components}/GrBadge/safelist.d.ts +0 -0
  338. /package/dist/types/{src/components → components}/GrBadgeWrap/GrBadgeWrap.vue.d.ts +0 -0
  339. /package/dist/types/{src/components → components}/GrBadgeWrap/config.d.ts +0 -0
  340. /package/dist/types/{src/components → components}/GrBadgeWrap/grBadgeWrapStyles.d.ts +0 -0
  341. /package/dist/types/{src/components → components}/GrBadgeWrap/safelist.d.ts +0 -0
  342. /package/dist/types/{src/components → components}/GrBottomNav/GrBottomNav.vue.d.ts +0 -0
  343. /package/dist/types/{src/components → components}/GrBottomNav/config.d.ts +0 -0
  344. /package/dist/types/{src/components → components}/GrBottomNav/defaults.d.ts +0 -0
  345. /package/dist/types/{src/components → components}/GrBottomNav/grBottomNavStyles.d.ts +0 -0
  346. /package/dist/types/{src/components → components}/GrBottomNav/safelist.d.ts +0 -0
  347. /package/dist/types/{src/components → components}/GrBreadcrumbs/GrBreadcrumbs.vue.d.ts +0 -0
  348. /package/dist/types/{src/components → components}/GrBreadcrumbs/config.d.ts +0 -0
  349. /package/dist/types/{src/components → components}/GrBreadcrumbs/defaults.d.ts +0 -0
  350. /package/dist/types/{src/components → components}/GrBreadcrumbs/grBreadcrumbsStyles.d.ts +0 -0
  351. /package/dist/types/{src/components → components}/GrBreadcrumbs/index.d.ts +0 -0
  352. /package/dist/types/{src/components → components}/GrBreadcrumbs/safelist.d.ts +0 -0
  353. /package/dist/types/{src/components → components}/GrButton/GrButton.vue.d.ts +0 -0
  354. /package/dist/types/{src/components → components}/GrButton/config.d.ts +0 -0
  355. /package/dist/types/{src/components → components}/GrButton/defaults.d.ts +0 -0
  356. /package/dist/types/{src/components → components}/GrButton/grButtonStyles.d.ts +0 -0
  357. /package/dist/types/{src/components → components}/GrButton/safelist.d.ts +0 -0
  358. /package/dist/types/{src/components → components}/GrButtonGroup/GrButtonGroup.vue.d.ts +0 -0
  359. /package/dist/types/{src/components → components}/GrButtonGroup/config.d.ts +0 -0
  360. /package/dist/types/{src/components → components}/GrButtonGroup/context.d.ts +0 -0
  361. /package/dist/types/{src/components → components}/GrButtonGroup/index.d.ts +0 -0
  362. /package/dist/types/{src/components → components}/GrCard/GrCard.vue.d.ts +0 -0
  363. /package/dist/types/{src/components → components}/GrCard/config.d.ts +0 -0
  364. /package/dist/types/{src/components → components}/GrCard/defaults.d.ts +0 -0
  365. /package/dist/types/{src/components → components}/GrCard/grCardStyles.d.ts +0 -0
  366. /package/dist/types/{src/components → components}/GrCard/index.d.ts +0 -0
  367. /package/dist/types/{src/components → components}/GrCard/safelist.d.ts +0 -0
  368. /package/dist/types/{src/components → components}/GrCheckbox/GrCheckbox.vue.d.ts +0 -0
  369. /package/dist/types/{src/components → components}/GrCheckbox/config.d.ts +0 -0
  370. /package/dist/types/{src/components → components}/GrCheckbox/defaults.d.ts +0 -0
  371. /package/dist/types/{src/components → components}/GrCheckbox/grCheckboxGroupContext.d.ts +0 -0
  372. /package/dist/types/{src/components → components}/GrCheckbox/grCheckboxStyles.d.ts +0 -0
  373. /package/dist/types/{src/components → components}/GrCheckbox/safelist.d.ts +0 -0
  374. /package/dist/types/{src/components → components}/GrCheckboxGroup/GrCheckboxGroup.vue.d.ts +0 -0
  375. /package/dist/types/{src/components → components}/GrCheckboxGroup/config.d.ts +0 -0
  376. /package/dist/types/{src/components → components}/GrCheckboxGroup/defaults.d.ts +0 -0
  377. /package/dist/types/{src/components → components}/GrCheckboxGroup/index.d.ts +0 -0
  378. /package/dist/types/{src/components → components}/GrCollapse/GrCollapse.vue.d.ts +0 -0
  379. /package/dist/types/{src/components → components}/GrCollapse/GrCollapseItem.vue.d.ts +0 -0
  380. /package/dist/types/{src/components → components}/GrCollapse/config.d.ts +0 -0
  381. /package/dist/types/{src/components → components}/GrCollapse/defaults.d.ts +0 -0
  382. /package/dist/types/{src/components → components}/GrCollapse/grCollapseContext.d.ts +0 -0
  383. /package/dist/types/{src/components → components}/GrCollapse/grCollapseStyles.d.ts +0 -0
  384. /package/dist/types/{src/components → components}/GrCollapse/safelist.d.ts +0 -0
  385. /package/dist/types/{src/components → components}/GrColorPicker/GrColorPicker.vue.d.ts +0 -0
  386. /package/dist/types/{src/components → components}/GrColorPicker/color.d.ts +0 -0
  387. /package/dist/types/{src/components → components}/GrColorPicker/config.d.ts +0 -0
  388. /package/dist/types/{src/components → components}/GrColorPicker/defaults.d.ts +0 -0
  389. /package/dist/types/{src/components → components}/GrColorPicker/grColorPickerStyles.d.ts +0 -0
  390. /package/dist/types/{src/components → components}/GrColorPicker/safelist.d.ts +0 -0
  391. /package/dist/types/{src/components → components}/GrCommandPalette/GrCommandPalette.vue.d.ts +0 -0
  392. /package/dist/types/{src/components → components}/GrCommandPalette/config.d.ts +0 -0
  393. /package/dist/types/{src/components → components}/GrCommandPalette/defaults.d.ts +0 -0
  394. /package/dist/types/{src/components → components}/GrCommandPalette/filtering.d.ts +0 -0
  395. /package/dist/types/{src/components → components}/GrCommandPalette/grCommandPaletteStyles.d.ts +0 -0
  396. /package/dist/types/{src/components → components}/GrCommandPalette/safelist.d.ts +0 -0
  397. /package/dist/types/{src/components → components}/GrConfigProvider/GrConfigProvider.vue.d.ts +0 -0
  398. /package/dist/types/{src/components → components}/GrConfigProvider/config.d.ts +0 -0
  399. /package/dist/types/{src/components → components}/GrConfigProvider/context.d.ts +0 -0
  400. /package/dist/types/{src/components → components}/GrConfigProvider/zIndexScale.d.ts +0 -0
  401. /package/dist/types/{src/components → components}/GrConfirmDialog/GrConfirmDialog.vue.d.ts +0 -0
  402. /package/dist/types/{src/components → components}/GrConfirmDialog/config.d.ts +0 -0
  403. /package/dist/types/{src/components → components}/GrConfirmDialog/defaults.d.ts +0 -0
  404. /package/dist/types/{src/components → components}/GrConfirmDialog/index.d.ts +0 -0
  405. /package/dist/types/{src/components → components}/GrDataTable/GrDataTable.vue.d.ts +0 -0
  406. /package/dist/types/{src/components → components}/GrDataTable/config.d.ts +0 -0
  407. /package/dist/types/{src/components → components}/GrDataTable/defaults.d.ts +0 -0
  408. /package/dist/types/{src/components → components}/GrDataTable/grDataTableSort.d.ts +0 -0
  409. /package/dist/types/{src/components → components}/GrDataTable/grDataTableStyles.d.ts +0 -0
  410. /package/dist/types/{src/components → components}/GrDataTable/safelist.d.ts +0 -0
  411. /package/dist/types/{src/components → components}/GrDialog/GrDialog.vue.d.ts +0 -0
  412. /package/dist/types/{src/components → components}/GrDialog/GrDialogCloseButton.vue.d.ts +0 -0
  413. /package/dist/types/{src/components → components}/GrDialog/GrDialogFooter.vue.d.ts +0 -0
  414. /package/dist/types/{src/components → components}/GrDialog/GrDialogHeader.vue.d.ts +0 -0
  415. /package/dist/types/{src/components → components}/GrDialog/config.d.ts +0 -0
  416. /package/dist/types/{src/components → components}/GrDialog/defaults.d.ts +0 -0
  417. /package/dist/types/{src/components → components}/GrDialog/dialogShared.d.ts +0 -0
  418. /package/dist/types/{src/components → components}/GrDialog/safelist.d.ts +0 -0
  419. /package/dist/types/{src/components → components}/GrDialogService/GrDialogServiceHost.vue.d.ts +0 -0
  420. /package/dist/types/{src/components → components}/GrDialogService/GrDialogServiceItem.vue.d.ts +0 -0
  421. /package/dist/types/{src/components → components}/GrDialogService/config.d.ts +0 -0
  422. /package/dist/types/{src/components → components}/GrDialogService/store.d.ts +0 -0
  423. /package/dist/types/{src/components → components}/GrDialogService/types.d.ts +0 -0
  424. /package/dist/types/{src/components → components}/GrDialogService/useDialogService.d.ts +0 -0
  425. /package/dist/types/{src/components → components}/GrDivider/GrDivider.vue.d.ts +0 -0
  426. /package/dist/types/{src/components → components}/GrDivider/config.d.ts +0 -0
  427. /package/dist/types/{src/components → components}/GrDivider/defaults.d.ts +0 -0
  428. /package/dist/types/{src/components → components}/GrDivider/grDividerStyles.d.ts +0 -0
  429. /package/dist/types/{src/components → components}/GrDivider/index.d.ts +0 -0
  430. /package/dist/types/{src/components → components}/GrDivider/safelist.d.ts +0 -0
  431. /package/dist/types/{src/components → components}/GrDrawer/GrDrawer.vue.d.ts +0 -0
  432. /package/dist/types/{src/components → components}/GrDrawer/config.d.ts +0 -0
  433. /package/dist/types/{src/components → components}/GrDrawer/defaults.d.ts +0 -0
  434. /package/dist/types/{src/components → components}/GrDrawer/grDrawerStyles.d.ts +0 -0
  435. /package/dist/types/{src/components → components}/GrDrawer/index.d.ts +0 -0
  436. /package/dist/types/{src/components → components}/GrDrawer/safelist.d.ts +0 -0
  437. /package/dist/types/{src/components → components}/GrDropdown/GrDropdown.vue.d.ts +0 -0
  438. /package/dist/types/{src/components → components}/GrDropdown/config.d.ts +0 -0
  439. /package/dist/types/{src/components → components}/GrDropdown/grDropdownStyles.d.ts +0 -0
  440. /package/dist/types/{src/components → components}/GrDropdown/index.d.ts +0 -0
  441. /package/dist/types/{src/components → components}/GrDropdown/safelist.d.ts +0 -0
  442. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenu.vue.d.ts +0 -0
  443. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuColumn.vue.d.ts +0 -0
  444. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuColumns.vue.d.ts +0 -0
  445. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuDivider.vue.d.ts +0 -0
  446. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuGroup.vue.d.ts +0 -0
  447. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuHeader.vue.d.ts +0 -0
  448. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuItem.vue.d.ts +0 -0
  449. /package/dist/types/{src/components → components}/GrDropdownMenu/GrDropdownMenuList.vue.d.ts +0 -0
  450. /package/dist/types/{src/components → components}/GrDropdownMenu/config.d.ts +0 -0
  451. /package/dist/types/{src/components → components}/GrDropdownMenu/grDropdownMenuStyles.d.ts +0 -0
  452. /package/dist/types/{src/components → components}/GrDropdownMenu/menuModel.d.ts +0 -0
  453. /package/dist/types/{src/components → components}/GrDropdownMenu/safelist.d.ts +0 -0
  454. /package/dist/types/{src/components → components}/GrEmptyState/GrEmptyState.vue.d.ts +0 -0
  455. /package/dist/types/{src/components → components}/GrEmptyState/config.d.ts +0 -0
  456. /package/dist/types/{src/components → components}/GrEmptyState/defaults.d.ts +0 -0
  457. /package/dist/types/{src/components → components}/GrEmptyState/grEmptyStateStyles.d.ts +0 -0
  458. /package/dist/types/{src/components → components}/GrEmptyState/safelist.d.ts +0 -0
  459. /package/dist/types/{src/components → components}/GrFileUpload/FileValidationError.d.ts +0 -0
  460. /package/dist/types/{src/components → components}/GrFileUpload/GrFileUpload.vue.d.ts +0 -0
  461. /package/dist/types/{src/components → components}/GrFileUpload/acceptValidator.d.ts +0 -0
  462. /package/dist/types/{src/components → components}/GrFileUpload/config.d.ts +0 -0
  463. /package/dist/types/{src/components → components}/GrFileUpload/defaults.d.ts +0 -0
  464. /package/dist/types/{src/components → components}/GrFileUpload/fileEntry.d.ts +0 -0
  465. /package/dist/types/{src/components → components}/GrFileUpload/grFileUploadStyles.d.ts +0 -0
  466. /package/dist/types/{src/components → components}/GrFileUpload/matchAccept.d.ts +0 -0
  467. /package/dist/types/{src/components → components}/GrFileUpload/maxFileSize.d.ts +0 -0
  468. /package/dist/types/{src/components → components}/GrFileUpload/runFileValidators.d.ts +0 -0
  469. /package/dist/types/{src/components → components}/GrFileUpload/safelist.d.ts +0 -0
  470. /package/dist/types/{src/components → components}/GrFileUpload/types.d.ts +0 -0
  471. /package/dist/types/{src/components → components}/GrFileUpload/uploadState.d.ts +0 -0
  472. /package/dist/types/{src/components → components}/GrFileUpload/uploadViaXhr.d.ts +0 -0
  473. /package/dist/types/{src/components → components}/GrFileUpload/useDropZone.d.ts +0 -0
  474. /package/dist/types/{src/components → components}/GrFileUpload/usePerFileUpload.d.ts +0 -0
  475. /package/dist/types/{src/components → components}/GrFileUpload/useUploadState.d.ts +0 -0
  476. /package/dist/types/{src/components → components}/GrForm/GrForm.vue.d.ts +0 -0
  477. /package/dist/types/{src/components → components}/GrForm/config.d.ts +0 -0
  478. /package/dist/types/{src/components → components}/GrForm/context.d.ts +0 -0
  479. /package/dist/types/{src/components → components}/GrForm/fileRule.d.ts +0 -0
  480. /package/dist/types/{src/components → components}/GrForm/modelSnapshot.d.ts +0 -0
  481. /package/dist/types/{src/components → components}/GrForm/validation.d.ts +0 -0
  482. /package/dist/types/{src/components → components}/GrFormField/GrFormField.vue.d.ts +0 -0
  483. /package/dist/types/{src/components → components}/GrFormField/config.d.ts +0 -0
  484. /package/dist/types/{src/components → components}/GrFormField/context.d.ts +0 -0
  485. /package/dist/types/{src/components → components}/GrFormField/defaults.d.ts +0 -0
  486. /package/dist/types/{src/components → components}/GrFormField/grFormFieldStyles.d.ts +0 -0
  487. /package/dist/types/{src/components → components}/GrFormField/safelist.d.ts +0 -0
  488. /package/dist/types/{src/components → components}/GrFormFile/GrFormFile.vue.d.ts +0 -0
  489. /package/dist/types/{src/components → components}/GrFormFile/config.d.ts +0 -0
  490. /package/dist/types/{src/components → components}/GrFormFile/defaults.d.ts +0 -0
  491. /package/dist/types/{src/components → components}/GrFormFile/grFormFileStyles.d.ts +0 -0
  492. /package/dist/types/{src/components → components}/GrFormFile/index.d.ts +0 -0
  493. /package/dist/types/{src/components → components}/GrFormFile/safelist.d.ts +0 -0
  494. /package/dist/types/{src/components → components}/GrFormSection/GrFormSection.vue.d.ts +0 -0
  495. /package/dist/types/{src/components → components}/GrFormSection/config.d.ts +0 -0
  496. /package/dist/types/{src/components → components}/GrFormSection/defaults.d.ts +0 -0
  497. /package/dist/types/{src/components → components}/GrFormSection/grFormSectionStyles.d.ts +0 -0
  498. /package/dist/types/{src/components → components}/GrFormSection/safelist.d.ts +0 -0
  499. /package/dist/types/{src/components → components}/GrIcon/GrIcon.vue.d.ts +0 -0
  500. /package/dist/types/{src/components → components}/GrIcon/config.d.ts +0 -0
  501. /package/dist/types/{src/components → components}/GrIcon/defaults.d.ts +0 -0
  502. /package/dist/types/{src/components → components}/GrIcon/grIconStyles.d.ts +0 -0
  503. /package/dist/types/{src/components → components}/GrIcon/index.d.ts +0 -0
  504. /package/dist/types/{src/components → components}/GrIcon/safelist.d.ts +0 -0
  505. /package/dist/types/{src/components → components}/GrImageViewer/GrImageViewer.vue.d.ts +0 -0
  506. /package/dist/types/{src/components → components}/GrImageViewer/composables/usePointerGestures.d.ts +0 -0
  507. /package/dist/types/{src/components → components}/GrImageViewer/composables/useViewerKeyboard.d.ts +0 -0
  508. /package/dist/types/{src/components → components}/GrImageViewer/composables/useWheelGesture.d.ts +0 -0
  509. /package/dist/types/{src/components → components}/GrImageViewer/composables/useZoomPan.d.ts +0 -0
  510. /package/dist/types/{src/components → components}/GrImageViewer/config.d.ts +0 -0
  511. /package/dist/types/{src/components → components}/GrImageViewer/grImageViewerStyles.d.ts +0 -0
  512. /package/dist/types/{src/components → components}/GrImageViewer/index.d.ts +0 -0
  513. /package/dist/types/{src/components → components}/GrImageViewer/safelist.d.ts +0 -0
  514. /package/dist/types/{src/components → components}/GrInput/GrInput.vue.d.ts +0 -0
  515. /package/dist/types/{src/components → components}/GrInput/config.d.ts +0 -0
  516. /package/dist/types/{src/components → components}/GrInput/defaults.d.ts +0 -0
  517. /package/dist/types/{src/components → components}/GrInput/grInputStyles.d.ts +0 -0
  518. /package/dist/types/{src/components → components}/GrInput/index.d.ts +0 -0
  519. /package/dist/types/{src/components → components}/GrInput/safelist.d.ts +0 -0
  520. /package/dist/types/{src/components → components}/GrInputTag/GrInputTag.vue.d.ts +0 -0
  521. /package/dist/types/{src/components → components}/GrInputTag/config.d.ts +0 -0
  522. /package/dist/types/{src/components → components}/GrInputTag/defaults.d.ts +0 -0
  523. /package/dist/types/{src/components → components}/GrInputTag/grInputTagStyles.d.ts +0 -0
  524. /package/dist/types/{src/components → components}/GrInputTag/index.d.ts +0 -0
  525. /package/dist/types/{src/components → components}/GrInputTag/safelist.d.ts +0 -0
  526. /package/dist/types/{src/components → components}/GrKbd/GrKbd.vue.d.ts +0 -0
  527. /package/dist/types/{src/components → components}/GrKbd/config.d.ts +0 -0
  528. /package/dist/types/{src/components → components}/GrKbd/defaults.d.ts +0 -0
  529. /package/dist/types/{src/components → components}/GrKbd/grKbdStyles.d.ts +0 -0
  530. /package/dist/types/{src/components → components}/GrKbd/index.d.ts +0 -0
  531. /package/dist/types/{src/components → components}/GrKbd/safelist.d.ts +0 -0
  532. /package/dist/types/{src/components → components}/GrLink/GrLink.vue.d.ts +0 -0
  533. /package/dist/types/{src/components → components}/GrLink/config.d.ts +0 -0
  534. /package/dist/types/{src/components → components}/GrLink/defaults.d.ts +0 -0
  535. /package/dist/types/{src/components → components}/GrLink/grLinkStyles.d.ts +0 -0
  536. /package/dist/types/{src/components → components}/GrLink/index.d.ts +0 -0
  537. /package/dist/types/{src/components → components}/GrLink/safelist.d.ts +0 -0
  538. /package/dist/types/{src/components → components}/GrList/GrList.vue.d.ts +0 -0
  539. /package/dist/types/{src/components → components}/GrList/GrListItem.vue.d.ts +0 -0
  540. /package/dist/types/{src/components → components}/GrList/config.d.ts +0 -0
  541. /package/dist/types/{src/components → components}/GrList/grListStyles.d.ts +0 -0
  542. /package/dist/types/{src/components → components}/GrList/index.d.ts +0 -0
  543. /package/dist/types/{src/components → components}/GrList/safelist.d.ts +0 -0
  544. /package/dist/types/{src/components → components}/GrLoading/GrLoading.vue.d.ts +0 -0
  545. /package/dist/types/{src/components → components}/GrLoading/config.d.ts +0 -0
  546. /package/dist/types/{src/components → components}/GrLoading/grLoadingStyles.d.ts +0 -0
  547. /package/dist/types/{src/components → components}/GrLoading/index.d.ts +0 -0
  548. /package/dist/types/{src/components → components}/GrLoading/safelist.d.ts +0 -0
  549. /package/dist/types/{src/components → components}/GrModal/GrModal.vue.d.ts +0 -0
  550. /package/dist/types/{src/components → components}/GrModal/config.d.ts +0 -0
  551. /package/dist/types/{src/components → components}/GrModal/context.d.ts +0 -0
  552. /package/dist/types/{src/components → components}/GrModal/defaults.d.ts +0 -0
  553. /package/dist/types/{src/components → components}/GrModal/grModalStyles.d.ts +0 -0
  554. /package/dist/types/{src/components → components}/GrModal/index.d.ts +0 -0
  555. /package/dist/types/{src/components → components}/GrModal/safelist.d.ts +0 -0
  556. /package/dist/types/{src/components → components}/GrNavbar/GrNavbar.vue.d.ts +0 -0
  557. /package/dist/types/{src/components → components}/GrNavbar/config.d.ts +0 -0
  558. /package/dist/types/{src/components → components}/GrNavbar/grNavbarStyles.d.ts +0 -0
  559. /package/dist/types/{src/components → components}/GrNavbar/index.d.ts +0 -0
  560. /package/dist/types/{src/components → components}/GrNavbar/safelist.d.ts +0 -0
  561. /package/dist/types/{src/components → components}/GrNumberInput/GrNumberInput.vue.d.ts +0 -0
  562. /package/dist/types/{src/components → components}/GrNumberInput/config.d.ts +0 -0
  563. /package/dist/types/{src/components → components}/GrNumberInput/defaults.d.ts +0 -0
  564. /package/dist/types/{src/components → components}/GrNumberInput/grNumberInputStyles.d.ts +0 -0
  565. /package/dist/types/{src/components → components}/GrNumberInput/index.d.ts +0 -0
  566. /package/dist/types/{src/components → components}/GrNumberInput/numberInputMath.d.ts +0 -0
  567. /package/dist/types/{src/components → components}/GrNumberInput/safelist.d.ts +0 -0
  568. /package/dist/types/{src/components → components}/GrPagination/GrPagination.vue.d.ts +0 -0
  569. /package/dist/types/{src/components → components}/GrPagination/config.d.ts +0 -0
  570. /package/dist/types/{src/components → components}/GrPagination/defaults.d.ts +0 -0
  571. /package/dist/types/{src/components → components}/GrPagination/grPaginationStyles.d.ts +0 -0
  572. /package/dist/types/{src/components → components}/GrPagination/index.d.ts +0 -0
  573. /package/dist/types/{src/components → components}/GrPagination/safelist.d.ts +0 -0
  574. /package/dist/types/{src/components → components}/GrPopover/GrPopover.vue.d.ts +0 -0
  575. /package/dist/types/{src/components → components}/GrPopover/config.d.ts +0 -0
  576. /package/dist/types/{src/components → components}/GrPopover/defaults.d.ts +0 -0
  577. /package/dist/types/{src/components → components}/GrPopover/grPopoverStyles.d.ts +0 -0
  578. /package/dist/types/{src/components → components}/GrPopover/index.d.ts +0 -0
  579. /package/dist/types/{src/components → components}/GrPopover/safelist.d.ts +0 -0
  580. /package/dist/types/{src/components → components}/GrProgressBar/GrProgressBar.vue.d.ts +0 -0
  581. /package/dist/types/{src/components → components}/GrProgressBar/config.d.ts +0 -0
  582. /package/dist/types/{src/components → components}/GrProgressBar/defaults.d.ts +0 -0
  583. /package/dist/types/{src/components → components}/GrProgressBar/grStyle.d.ts +0 -0
  584. /package/dist/types/{src/components → components}/GrProgressBar/index.d.ts +0 -0
  585. /package/dist/types/{src/components → components}/GrProgressBar/safelist.d.ts +0 -0
  586. /package/dist/types/{src/components → components}/GrProgressCircle/GrProgressCircle.vue.d.ts +0 -0
  587. /package/dist/types/{src/components → components}/GrProgressCircle/config.d.ts +0 -0
  588. /package/dist/types/{src/components → components}/GrProgressCircle/defaults.d.ts +0 -0
  589. /package/dist/types/{src/components → components}/GrProgressCircle/geometry.d.ts +0 -0
  590. /package/dist/types/{src/components → components}/GrProgressCircle/grProgressCircleStyles.d.ts +0 -0
  591. /package/dist/types/{src/components → components}/GrProgressCircle/safelist.d.ts +0 -0
  592. /package/dist/types/{src/components → components}/GrPromptDialog/GrPromptDialog.vue.d.ts +0 -0
  593. /package/dist/types/{src/components → components}/GrPromptDialog/config.d.ts +0 -0
  594. /package/dist/types/{src/components → components}/GrPromptDialog/defaults.d.ts +0 -0
  595. /package/dist/types/{src/components → components}/GrPromptDialog/index.d.ts +0 -0
  596. /package/dist/types/{src/components → components}/GrRadio/GrRadio.vue.d.ts +0 -0
  597. /package/dist/types/{src/components → components}/GrRadio/config.d.ts +0 -0
  598. /package/dist/types/{src/components → components}/GrRadio/defaults.d.ts +0 -0
  599. /package/dist/types/{src/components → components}/GrRadio/grRadioGroupContext.d.ts +0 -0
  600. /package/dist/types/{src/components → components}/GrRadio/grRadioStyles.d.ts +0 -0
  601. /package/dist/types/{src/components → components}/GrRadio/safelist.d.ts +0 -0
  602. /package/dist/types/{src/components → components}/GrRadioGroup/GrRadioGroup.vue.d.ts +0 -0
  603. /package/dist/types/{src/components → components}/GrRadioGroup/config.d.ts +0 -0
  604. /package/dist/types/{src/components → components}/GrRadioGroup/defaults.d.ts +0 -0
  605. /package/dist/types/{src/components → components}/GrRadioGroup/index.d.ts +0 -0
  606. /package/dist/types/{src/components → components}/GrRating/GrRating.vue.d.ts +0 -0
  607. /package/dist/types/{src/components → components}/GrRating/config.d.ts +0 -0
  608. /package/dist/types/{src/components → components}/GrRating/defaults.d.ts +0 -0
  609. /package/dist/types/{src/components → components}/GrRating/grRatingStyles.d.ts +0 -0
  610. /package/dist/types/{src/components → components}/GrRating/index.d.ts +0 -0
  611. /package/dist/types/{src/components → components}/GrRating/safelist.d.ts +0 -0
  612. /package/dist/types/{src/components → components}/GrResponseErrorBanner/GrFormErrorBanner.vue.d.ts +0 -0
  613. /package/dist/types/{src/components → components}/GrResponseErrorBanner/GrResponseErrorBanner.vue.d.ts +0 -0
  614. /package/dist/types/{src/components → components}/GrResponseErrorBanner/GrUploadErrorBanner.vue.d.ts +0 -0
  615. /package/dist/types/{src/components → components}/GrResponseErrorBanner/config.d.ts +0 -0
  616. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/abortErrorParser.d.ts +0 -0
  617. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/createResponseErrorClassifier.d.ts +0 -0
  618. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/fileValidationParser.d.ts +0 -0
  619. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/httpStatusParser.d.ts +0 -0
  620. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/index.d.ts +0 -0
  621. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/jsonApiErrorParser.d.ts +0 -0
  622. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/laravelValidationParser.d.ts +0 -0
  623. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/networkErrorParser.d.ts +0 -0
  624. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/normalizeError.d.ts +0 -0
  625. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/plainMessageParser.d.ts +0 -0
  626. /package/dist/types/{src/components → components}/GrResponseErrorBanner/parsers/problemDetailsParser.d.ts +0 -0
  627. /package/dist/types/{src/components → components}/GrResponseErrorBanner/responseError.defaults.d.ts +0 -0
  628. /package/dist/types/{src/components → components}/GrResponseErrorBanner/responseError.types.d.ts +0 -0
  629. /package/dist/types/{src/components → components}/GrResponseErrorBanner/useResponseError.d.ts +0 -0
  630. /package/dist/types/{src/components → components}/GrSegmented/GrSegmented.vue.d.ts +0 -0
  631. /package/dist/types/{src/components → components}/GrSegmented/config.d.ts +0 -0
  632. /package/dist/types/{src/components → components}/GrSegmented/defaults.d.ts +0 -0
  633. /package/dist/types/{src/components → components}/GrSegmented/grSegmentedStyles.d.ts +0 -0
  634. /package/dist/types/{src/components → components}/GrSegmented/safelist.d.ts +0 -0
  635. /package/dist/types/{src/components → components}/GrSelect/composables/useSelectNavigation.d.ts +0 -0
  636. /package/dist/types/{src/components → components}/GrSelect/composables/useSelectPanelItems.d.ts +0 -0
  637. /package/dist/types/{src/components → components}/GrSelect/composables/useSelectValues.d.ts +0 -0
  638. /package/dist/types/{src/components → components}/GrSelect/composables/useSelectVirtualization.d.ts +0 -0
  639. /package/dist/types/{src/components → components}/GrSelect/config.d.ts +0 -0
  640. /package/dist/types/{src/components → components}/GrSelect/defaults.d.ts +0 -0
  641. /package/dist/types/{src/components → components}/GrSelect/grSelectStyles.d.ts +0 -0
  642. /package/dist/types/{src/components → components}/GrSelect/index.d.ts +0 -0
  643. /package/dist/types/{src/components → components}/GrSelect/safelist.d.ts +0 -0
  644. /package/dist/types/{src/components → components}/GrSelect/selectValue.d.ts +0 -0
  645. /package/dist/types/{src/components → components}/GrSidebar/GrSidebar.vue.d.ts +0 -0
  646. /package/dist/types/{src/components → components}/GrSidebar/GrSidebarGroup.vue.d.ts +0 -0
  647. /package/dist/types/{src/components → components}/GrSidebar/GrSidebarItem.vue.d.ts +0 -0
  648. /package/dist/types/{src/components → components}/GrSidebar/config.d.ts +0 -0
  649. /package/dist/types/{src/components → components}/GrSidebar/grSidebarStyles.d.ts +0 -0
  650. /package/dist/types/{src/components → components}/GrSidebar/safelist.d.ts +0 -0
  651. /package/dist/types/{src/components → components}/GrSidebar/sidebarContext.d.ts +0 -0
  652. /package/dist/types/{src/components → components}/GrSkeleton/GrSkeleton.vue.d.ts +0 -0
  653. /package/dist/types/{src/components → components}/GrSkeleton/config.d.ts +0 -0
  654. /package/dist/types/{src/components → components}/GrSkeleton/grSkeletonStyles.d.ts +0 -0
  655. /package/dist/types/{src/components → components}/GrSlider/GrSlider.vue.d.ts +0 -0
  656. /package/dist/types/{src/components → components}/GrSlider/config.d.ts +0 -0
  657. /package/dist/types/{src/components → components}/GrSlider/defaults.d.ts +0 -0
  658. /package/dist/types/{src/components → components}/GrSlider/grSliderStyles.d.ts +0 -0
  659. /package/dist/types/{src/components → components}/GrSlider/index.d.ts +0 -0
  660. /package/dist/types/{src/components → components}/GrSlider/safelist.d.ts +0 -0
  661. /package/dist/types/{src/components → components}/GrSortableList/GrSortableList.vue.d.ts +0 -0
  662. /package/dist/types/{src/components → components}/GrSortableList/config.d.ts +0 -0
  663. /package/dist/types/{src/components → components}/GrSortableList/grSortableListStyles.d.ts +0 -0
  664. /package/dist/types/{src/components → components}/GrSortableList/index.d.ts +0 -0
  665. /package/dist/types/{src/components → components}/GrSortableList/safelist.d.ts +0 -0
  666. /package/dist/types/{src/components → components}/GrSplitter/GrSplitter.vue.d.ts +0 -0
  667. /package/dist/types/{src/components → components}/GrSplitter/config.d.ts +0 -0
  668. /package/dist/types/{src/components → components}/GrSplitter/defaults.d.ts +0 -0
  669. /package/dist/types/{src/components → components}/GrSplitter/grSplitterStyles.d.ts +0 -0
  670. /package/dist/types/{src/components → components}/GrSplitter/safelist.d.ts +0 -0
  671. /package/dist/types/{src/components → components}/GrSplitter/splitterGeometry.d.ts +0 -0
  672. /package/dist/types/{src/components → components}/GrStatistic/GrStatistic.vue.d.ts +0 -0
  673. /package/dist/types/{src/components → components}/GrStatistic/config.d.ts +0 -0
  674. /package/dist/types/{src/components → components}/GrStatistic/countUp.d.ts +0 -0
  675. /package/dist/types/{src/components → components}/GrStatistic/defaults.d.ts +0 -0
  676. /package/dist/types/{src/components → components}/GrStatistic/formatStatisticValue.d.ts +0 -0
  677. /package/dist/types/{src/components → components}/GrStatistic/grStatisticStyles.d.ts +0 -0
  678. /package/dist/types/{src/components → components}/GrStatistic/index.d.ts +0 -0
  679. /package/dist/types/{src/components → components}/GrStatistic/safelist.d.ts +0 -0
  680. /package/dist/types/{src/components → components}/GrSwitch/GrSwitch.vue.d.ts +0 -0
  681. /package/dist/types/{src/components → components}/GrSwitch/config.d.ts +0 -0
  682. /package/dist/types/{src/components → components}/GrSwitch/defaults.d.ts +0 -0
  683. /package/dist/types/{src/components → components}/GrSwitch/grSwitchStyles.d.ts +0 -0
  684. /package/dist/types/{src/components → components}/GrSwitch/index.d.ts +0 -0
  685. /package/dist/types/{src/components → components}/GrSwitch/safelist.d.ts +0 -0
  686. /package/dist/types/{src/components → components}/GrTabPanels/GrTabPanel.vue.d.ts +0 -0
  687. /package/dist/types/{src/components → components}/GrTabPanels/GrTabPanels.vue.d.ts +0 -0
  688. /package/dist/types/{src/components → components}/GrTabPanels/config.d.ts +0 -0
  689. /package/dist/types/{src/components → components}/GrTabPanels/context.d.ts +0 -0
  690. /package/dist/types/{src/components → components}/GrTable/GrTable.vue.d.ts +0 -0
  691. /package/dist/types/{src/components → components}/GrTable/config.d.ts +0 -0
  692. /package/dist/types/{src/components → components}/GrTable/defaults.d.ts +0 -0
  693. /package/dist/types/{src/components → components}/GrTable/grTableStyles.d.ts +0 -0
  694. /package/dist/types/{src/components → components}/GrTable/index.d.ts +0 -0
  695. /package/dist/types/{src/components → components}/GrTable/safelist.d.ts +0 -0
  696. /package/dist/types/{src/components → components}/GrTabs/GrTabs.vue.d.ts +0 -0
  697. /package/dist/types/{src/components → components}/GrTabs/config.d.ts +0 -0
  698. /package/dist/types/{src/components → components}/GrTabs/defaults.d.ts +0 -0
  699. /package/dist/types/{src/components → components}/GrTabs/grTabsStyles.d.ts +0 -0
  700. /package/dist/types/{src/components → components}/GrTabs/safelist.d.ts +0 -0
  701. /package/dist/types/{src/components → components}/GrTextarea/GrTextarea.vue.d.ts +0 -0
  702. /package/dist/types/{src/components → components}/GrTextarea/config.d.ts +0 -0
  703. /package/dist/types/{src/components → components}/GrTextarea/defaults.d.ts +0 -0
  704. /package/dist/types/{src/components → components}/GrTextarea/grTextareaStyles.d.ts +0 -0
  705. /package/dist/types/{src/components → components}/GrTextarea/index.d.ts +0 -0
  706. /package/dist/types/{src/components → components}/GrTextarea/safelist.d.ts +0 -0
  707. /package/dist/types/{src/components → components}/GrTimeline/GrTimeline.vue.d.ts +0 -0
  708. /package/dist/types/{src/components → components}/GrTimeline/GrTimelineItem.vue.d.ts +0 -0
  709. /package/dist/types/{src/components → components}/GrTimeline/config.d.ts +0 -0
  710. /package/dist/types/{src/components → components}/GrTimeline/defaults.d.ts +0 -0
  711. /package/dist/types/{src/components → components}/GrTimeline/grTimelineContext.d.ts +0 -0
  712. /package/dist/types/{src/components → components}/GrTimeline/grTimelineStyles.d.ts +0 -0
  713. /package/dist/types/{src/components → components}/GrTimeline/safelist.d.ts +0 -0
  714. /package/dist/types/{src/components → components}/GrTimeline/timelineGroups.d.ts +0 -0
  715. /package/dist/types/{src/components → components}/GrToaster/GrToaster.vue.d.ts +0 -0
  716. /package/dist/types/{src/components → components}/GrToaster/config.d.ts +0 -0
  717. /package/dist/types/{src/components → components}/GrToaster/grToasterStyles.d.ts +0 -0
  718. /package/dist/types/{src/components → components}/GrToaster/index.d.ts +0 -0
  719. /package/dist/types/{src/components → components}/GrToaster/safelist.d.ts +0 -0
  720. /package/dist/types/{src/components → components}/GrTooltip/GrTooltip.vue.d.ts +0 -0
  721. /package/dist/types/{src/components → components}/GrTooltip/config.d.ts +0 -0
  722. /package/dist/types/{src/components → components}/GrTooltip/defaults.d.ts +0 -0
  723. /package/dist/types/{src/components → components}/GrTooltip/grTooltipStyles.d.ts +0 -0
  724. /package/dist/types/{src/components → components}/GrTooltip/index.d.ts +0 -0
  725. /package/dist/types/{src/components → components}/GrTooltip/safelist.d.ts +0 -0
  726. /package/dist/types/{src/components → components}/GrTree/GrTree.vue.d.ts +0 -0
  727. /package/dist/types/{src/components → components}/GrTree/config.d.ts +0 -0
  728. /package/dist/types/{src/components → components}/GrTree/defaults.d.ts +0 -0
  729. /package/dist/types/{src/components → components}/GrTree/grTreeChecking.d.ts +0 -0
  730. /package/dist/types/{src/components → components}/GrTree/grTreeDataAdapter.d.ts +0 -0
  731. /package/dist/types/{src/components → components}/GrTree/grTreeInteractionContext.d.ts +0 -0
  732. /package/dist/types/{src/components → components}/GrTree/grTreeProps.d.ts +0 -0
  733. /package/dist/types/{src/components → components}/GrTree/grTreeStore.d.ts +0 -0
  734. /package/dist/types/{src/components → components}/GrTree/grTreeStyles.d.ts +0 -0
  735. /package/dist/types/{src/components → components}/GrTree/grTreeTypes.d.ts +0 -0
  736. /package/dist/types/{src/components → components}/GrTree/index.d.ts +0 -0
  737. /package/dist/types/{src/components → components}/GrTree/safelist.d.ts +0 -0
  738. /package/dist/types/{src/components → components}/GrTreeSelect/config.d.ts +0 -0
  739. /package/dist/types/{src/components → components}/GrTreeSelect/defaults.d.ts +0 -0
  740. /package/dist/types/{src/components → components}/GrTreeSelect/grTreeSelectStyles.d.ts +0 -0
  741. /package/dist/types/{src/components → components}/GrTreeSelect/grTreeSelectTypes.d.ts +0 -0
  742. /package/dist/types/{src/components → components}/GrTreeSelect/index.d.ts +0 -0
  743. /package/dist/types/{src/components → components}/GrTreeSelect/safelist.d.ts +0 -0
  744. /package/dist/types/{src/components → components}/shared/classTokens.d.ts +0 -0
  745. /package/dist/types/{src/components → components}/shared/hotkey.d.ts +0 -0
  746. /package/dist/types/{src/components → components}/shared/hotkeyTokens.d.ts +0 -0
  747. /package/dist/types/{src/components → components}/shared/icon.d.ts +0 -0
  748. /package/dist/types/{src/components → components}/shared/instance.d.ts +0 -0
  749. /package/dist/types/{src/components → components}/shared/optionFilter.d.ts +0 -0
  750. /package/dist/types/{src/components → components}/shared/sizes.d.ts +0 -0
  751. /package/dist/types/{src/components → components}/shared/slotNodes.d.ts +0 -0
  752. /package/dist/types/{src/components → components}/shared/tones.d.ts +0 -0
  753. /package/dist/types/{src/composables → composables}/internal/dragSortGeometry.d.ts +0 -0
  754. /package/dist/types/{src/composables → composables}/internal/focusables.d.ts +0 -0
  755. /package/dist/types/{src/composables → composables}/internal/inert.d.ts +0 -0
  756. /package/dist/types/{src/composables → composables}/internal/overlayStack.d.ts +0 -0
  757. /package/dist/types/{src/composables → composables}/internal/portalRoot.d.ts +0 -0
  758. /package/dist/types/{src/composables → composables}/internal/useAddonMeasurement.d.ts +0 -0
  759. /package/dist/types/{src/composables → composables}/internal/useControlAddons.d.ts +0 -0
  760. /package/dist/types/{src/composables → composables}/internal/useControlledOpen.d.ts +0 -0
  761. /package/dist/types/{src/composables → composables}/internal/useFilePreviews.d.ts +0 -0
  762. /package/dist/types/{src/composables → composables}/internal/useFocusWithin.d.ts +0 -0
  763. /package/dist/types/{src/composables → composables}/internal/useInertOthers.d.ts +0 -0
  764. /package/dist/types/{src/composables → composables}/internal/useModalOverlay.d.ts +0 -0
  765. /package/dist/types/{src/composables → composables}/internal/useOverlayPresence.d.ts +0 -0
  766. /package/dist/types/{src/composables → composables}/internal/useScrollLock.d.ts +0 -0
  767. /package/dist/types/{src/composables → composables}/internal/useTeleportEnabled.d.ts +0 -0
  768. /package/dist/types/{src/composables → composables}/useAnnouncer.d.ts +0 -0
  769. /package/dist/types/{src/composables → composables}/useComboboxNavigation.d.ts +0 -0
  770. /package/dist/types/{src/composables → composables}/useDismissible.d.ts +0 -0
  771. /package/dist/types/{src/composables → composables}/useDragGesture.d.ts +0 -0
  772. /package/dist/types/{src/composables → composables}/useDragSort.d.ts +0 -0
  773. /package/dist/types/{src/composables → composables}/useFloating.d.ts +0 -0
  774. /package/dist/types/{src/composables → composables}/useFocusTrap.d.ts +0 -0
  775. /package/dist/types/{src/composables → composables}/useGrComponentConfig.d.ts +0 -0
  776. /package/dist/types/{src/composables → composables}/useGrFormControl.d.ts +0 -0
  777. /package/dist/types/{src/composables → composables}/useGranularityTranslations.d.ts +0 -0
  778. /package/dist/types/{src/composables → composables}/useOverlayLayer.d.ts +0 -0
  779. /package/dist/types/{src/composables → composables}/usePortalTarget.d.ts +0 -0
  780. /package/dist/types/{src/composables → composables}/useRovingFocus.d.ts +0 -0
  781. /package/dist/types/{src/composables → composables}/useTheme.d.ts +0 -0
  782. /package/dist/types/{src/composables → composables}/useToast.d.ts +0 -0
  783. /package/dist/types/{src/composables → composables}/useVirtualList.d.ts +0 -0
  784. /package/dist/types/{src/directives → directives}/autofocus.d.ts +0 -0
  785. /package/dist/types/{src/directives → directives}/autosize.d.ts +0 -0
  786. /package/dist/types/{src/directives → directives}/clickOutside.d.ts +0 -0
  787. /package/dist/types/{src/directives → directives}/dropzone.d.ts +0 -0
  788. /package/dist/types/{src/directives → directives}/globalDirectives.d.ts +0 -0
  789. /package/dist/types/{src/directives → directives}/hotkey.d.ts +0 -0
  790. /package/dist/types/{src/directives → directives}/index.d.ts +0 -0
  791. /package/dist/types/{src/directives → directives}/loading.d.ts +0 -0
  792. /package/dist/types/{src/fileValidation → fileValidation}/FileValidationError.d.ts +0 -0
  793. /package/dist/types/{src/fileValidation → fileValidation}/acceptValidator.d.ts +0 -0
  794. /package/dist/types/{src/fileValidation → fileValidation}/allowedExtensionsValidator.d.ts +0 -0
  795. /package/dist/types/{src/fileValidation → fileValidation}/allowedMimeTypesValidator.d.ts +0 -0
  796. /package/dist/types/{src/fileValidation → fileValidation}/i18n.d.ts +0 -0
  797. /package/dist/types/{src/fileValidation → fileValidation}/index.d.ts +0 -0
  798. /package/dist/types/{src/fileValidation → fileValidation}/matchAccept.d.ts +0 -0
  799. /package/dist/types/{src/fileValidation → fileValidation}/maxCountValidator.d.ts +0 -0
  800. /package/dist/types/{src/fileValidation → fileValidation}/maxFileSize.d.ts +0 -0
  801. /package/dist/types/{src/fileValidation → fileValidation}/maxTotalSizeBytesValidator.d.ts +0 -0
  802. /package/dist/types/{src/fileValidation → fileValidation}/runFileValidators.d.ts +0 -0
  803. /package/dist/types/{src/fileValidation → fileValidation}/types.d.ts +0 -0
  804. /package/dist/types/{src/granular-provider → granular-provider}/index.d.ts +0 -0
  805. /package/dist/types/{src/granular-provider → granular-provider}/node.d.ts +0 -0
  806. /package/dist/types/{src/granular-provider → granular-provider}/shared.d.ts +0 -0
  807. /package/dist/types/{src/i18n → i18n}/adapter.d.ts +0 -0
  808. /package/dist/types/{src/i18n → i18n}/all.d.ts +0 -0
  809. /package/dist/types/{src/i18n → i18n}/index.d.ts +0 -0
  810. /package/dist/types/{src/i18n → i18n}/messages/const.d.ts +0 -0
  811. /package/dist/types/{src/i18n → i18n}/messages/en.d.ts +0 -0
  812. /package/dist/types/{src/i18n → i18n}/messages/es.d.ts +0 -0
  813. /package/dist/types/{src/i18n → i18n}/messages/index.d.ts +0 -0
  814. /package/dist/types/{src/i18n → i18n}/messages/ru.d.ts +0 -0
  815. /package/dist/types/{src/index.d.ts → index.d.ts} +0 -0
  816. /package/dist/types/{src/internal → internal}/granularityFormat.d.ts +0 -0
  817. /package/dist/types/{src/internal → internal}/granularityI18n.d.ts +0 -0
  818. /package/dist/types/{src/internal → internal}/keyboard.d.ts +0 -0
  819. /package/dist/types/{src/testing → testing}/announcer.d.ts +0 -0
  820. /package/dist/types/{src/testing → testing}/context.d.ts +0 -0
  821. /package/dist/types/{src/testing → testing}/env.d.ts +0 -0
  822. /package/dist/types/{src/testing → testing}/geometry.d.ts +0 -0
  823. /package/dist/types/{src/testing → testing}/pointer.d.ts +0 -0
  824. /package/dist/types/{src/theme → theme}/apply.d.ts +0 -0
  825. /package/dist/types/{src/theme → theme}/color.d.ts +0 -0
  826. /package/dist/types/{src/theme → theme}/extendTheme.d.ts +0 -0
  827. /package/dist/types/{src/theme → theme}/index.d.ts +0 -0
  828. /package/dist/types/{src/theme → theme}/roles.d.ts +0 -0
  829. /package/dist/types/{src/theme → theme}/tone.d.ts +0 -0
  830. /package/dist/types/{src/theme → theme}/validate.d.ts +0 -0
  831. /package/dist/types/{src/tokens → tokens}/generated.d.ts +0 -0
  832. /package/dist/types/{src/tokens → tokens}/index.d.ts +0 -0
  833. /package/dist/types/{src/tokens → tokens}/types.d.ts +0 -0
  834. /package/dist/types/{src/vue → vue}/index.d.ts +0 -0
  835. /package/dist/types/{src/vue → vue}/plugin.d.ts +0 -0
@@ -1 +1 @@
1
- {"version":3,"file":"GrKbd-DU2lBkRV.js","names":[],"sources":["../../../../src/components/shared/hotkeyTokens.ts","../../../../src/components/shared/hotkey.ts","../../../../src/components/GrKbd/GrKbd.vue","../../../../src/components/GrKbd/GrKbd.vue"],"sourcesContent":["/**\n * Каталог клавиш, которые понимает `keys` у `GrKbd`.\n *\n * Таблица, а не цепочка `if`, по двум причинам: во-первых, список — часть\n * публичного контракта (потребителю нужно знать, что можно написать), и\n * витрина показывает именно его, а не свою копию; во-вторых, копия в демо или\n * в доке разошлась бы с форматтером молча.\n */\n\n/** Ключи читаемых имён — `gr.kbd.<name>`. */\nexport type GrKbdKeyName =\n | 'command' | 'option' | 'shift' | 'control' | 'enter' | 'escape' | 'tab'\n | 'backspace' | 'delete' | 'pageUp' | 'pageDown'\n | 'arrowUp' | 'arrowDown' | 'arrowLeft' | 'arrowRight'\n\n/** Одна клавиша в человекочитаемом виде. */\nexport interface HotkeyKeyView {\n /** Что видно на экране: символ (`⌘`) или слово (`Ctrl`). */\n label: string\n /**\n * Ключ читаемого имени (`gr.kbd.<name>`) для символьных клавиш. У `K` или\n * `Ctrl` его нет — они и так читаются вслух.\n */\n name?: GrKbdKeyName\n /** Символ (`⌘`, `↑`) или слово (`Ctrl`, `Esc`): от этого зависит склейка в одной плашке. */\n symbol?: boolean\n}\n\n/** Смысловая группа — ею витрина и дока раскладывают каталог. */\nexport type GrKbdTokenGroup = 'modifier' | 'editing' | 'navigation'\n\nexport interface GrKbdTokenSpec {\n /** Канонический токен: его пишут в `keys`. */\n token: string\n /** Что ещё принимается — синонимы и сам глиф. */\n aliases: readonly string[]\n group: GrKbdTokenGroup\n /** Вид на macOS и на остальных платформах. */\n apple: HotkeyKeyView\n other: HotkeyKeyView\n}\n\nfunction symbol(label: string, name: GrKbdKeyName): HotkeyKeyView {\n return { label, name, symbol: true }\n}\n\nfunction word(label: string, name?: GrKbdKeyName): HotkeyKeyView {\n return name ? { label, name } : { label }\n}\n\nexport const GR_KBD_TOKENS: readonly GrKbdTokenSpec[] = [\n // Модификаторы: на macOS символы, на остальных платформах слова.\n { token: 'mod', aliases: [], group: 'modifier', apple: symbol('⌘', 'command'), other: word('Ctrl') },\n { token: 'meta', aliases: ['cmd', 'command', '⌘'], group: 'modifier', apple: symbol('⌘', 'command'), other: word('Meta') },\n { token: 'ctrl', aliases: ['control', '⌃'], group: 'modifier', apple: symbol('⌃', 'control'), other: word('Ctrl') },\n { token: 'alt', aliases: ['option', '⌥'], group: 'modifier', apple: symbol('⌥', 'option'), other: word('Alt') },\n { token: 'shift', aliases: ['⇧'], group: 'modifier', apple: symbol('⇧', 'shift'), other: word('Shift') },\n\n { token: 'enter', aliases: ['return', '↵', '↩'], group: 'editing', apple: symbol('↩', 'enter'), other: word('Enter') },\n { token: 'esc', aliases: ['escape'], group: 'editing', apple: word('Esc', 'escape'), other: word('Esc', 'escape') },\n { token: 'tab', aliases: ['⇥'], group: 'editing', apple: symbol('⇥', 'tab'), other: word('Tab') },\n { token: 'space', aliases: [], group: 'editing', apple: word('Space'), other: word('Space') },\n { token: 'backspace', aliases: ['⌫'], group: 'editing', apple: symbol('⌫', 'backspace'), other: word('Backspace') },\n { token: 'delete', aliases: ['del', '⌦'], group: 'editing', apple: symbol('⌦', 'delete'), other: word('Del') },\n\n { token: 'up', aliases: ['arrowup', '↑'], group: 'navigation', apple: symbol('↑', 'arrowUp'), other: symbol('↑', 'arrowUp') },\n { token: 'down', aliases: ['arrowdown', '↓'], group: 'navigation', apple: symbol('↓', 'arrowDown'), other: symbol('↓', 'arrowDown') },\n { token: 'left', aliases: ['arrowleft', '←'], group: 'navigation', apple: symbol('←', 'arrowLeft'), other: symbol('←', 'arrowLeft') },\n { token: 'right', aliases: ['arrowright', '→'], group: 'navigation', apple: symbol('→', 'arrowRight'), other: symbol('→', 'arrowRight') },\n { token: 'home', aliases: [], group: 'navigation', apple: word('Home'), other: word('Home') },\n { token: 'end', aliases: [], group: 'navigation', apple: word('End'), other: word('End') },\n { token: 'pageup', aliases: ['pgup', '⇞'], group: 'navigation', apple: symbol('⇞', 'pageUp'), other: word('PgUp') },\n { token: 'pagedown', aliases: ['pgdn', 'pgdown', '⇟'], group: 'navigation', apple: symbol('⇟', 'pageDown'), other: word('PgDn') },\n]\n\nconst BY_ALIAS = new Map<string, GrKbdTokenSpec>()\nfor (const spec of GR_KBD_TOKENS) {\n BY_ALIAS.set(spec.token, spec)\n for (const alias of spec.aliases) BY_ALIAS.set(alias, spec)\n}\n\n/** Токен или его синоним — в описание клавиши. Регистр не важен, глиф тоже принимается. */\nexport function findKbdToken(token: string): GrKbdTokenSpec | undefined {\n const trimmed = token.trim()\n return BY_ALIAS.get(trimmed.toLowerCase()) ?? BY_ALIAS.get(trimmed)\n}\n","/**\n * Разбор, матчинг и человекочитаемое представление сочетаний клавиш.\n *\n * Общий модуль, а не часть `GrCommandPalette`: то же нужно `GrKbd`, а импорт из\n * чужой компонентной директории на сборке дал бы ребро `GrKbd →\n * GrCommandPalette` (хелпер уехал бы в чанк палитры) — `granular doctor` считает\n * такое незадекларированной зависимостью.\n *\n * Директива `v-hotkey` для палитры не годится: ей нужен смонтированный элемент,\n * а палитра в закрытом состоянии не рендерит ничего. Поэтому здесь — свой\n * матчер на `window`, с тем же синтаксисом комбинаций плюс токен `mod`.\n */\n\nimport { eventMatchesKey, isAppleDevice, isComposingEvent, shiftSatisfied } from '../../internal/keyboard'\n\nimport { findKbdToken, type HotkeyKeyView } from './hotkeyTokens'\n\nexport { isAppleDevice } from '../../internal/keyboard'\nexport { findKbdToken, GR_KBD_TOKENS } from './hotkeyTokens'\nexport type { GrKbdKeyName, GrKbdTokenGroup, GrKbdTokenSpec, HotkeyKeyView } from './hotkeyTokens'\n\nexport type ParsedCommandHotkey = {\n key: string\n ctrl: boolean\n meta: boolean\n alt: boolean\n shift: boolean\n /** `mod` — Cmd на macOS, Ctrl на остальных платформах. */\n mod: boolean\n}\n\nexport function parseCommandHotkey(combo: string): ParsedCommandHotkey | null {\n const parts = combo.split('+').map(p => p.trim()).filter(Boolean)\n const keyToken = parts.at(-1)\n if (!keyToken) return null\n\n const parsed: ParsedCommandHotkey = {\n key: keyToken.length === 1 ? keyToken.toLowerCase() : keyToken,\n ctrl: false,\n meta: false,\n alt: false,\n shift: false,\n mod: false,\n }\n\n for (const part of parts.slice(0, -1)) {\n const token = part.toLowerCase()\n if (token === 'mod') parsed.mod = true\n else if (token === 'ctrl' || token === 'control') parsed.ctrl = true\n else if (token === 'meta' || token === 'cmd' || token === 'command' || token === '⌘') parsed.meta = true\n else if (token === 'alt' || token === 'option') parsed.alt = true\n else if (token === 'shift') parsed.shift = true\n }\n\n return parsed\n}\n\nexport function matchesCommandHotkey(\n event: KeyboardEvent,\n hotkey: ParsedCommandHotkey,\n apple = isAppleDevice(),\n): boolean {\n // Клавиша во время IME-композиции принадлежит композиции, а не сочетанию.\n if (isComposingEvent(event)) return false\n\n const expectMeta = hotkey.meta || (hotkey.mod && apple)\n const expectCtrl = hotkey.ctrl || (hotkey.mod && !apple)\n\n if (event.metaKey !== expectMeta) return false\n if (event.ctrlKey !== expectCtrl) return false\n if (event.altKey !== hotkey.alt) return false\n if (!shiftSatisfied(event, hotkey.key, hotkey.shift)) return false\n\n // Комбинация с модификаторами матчится и по физическому коду: на нелатинской\n // раскладке `mod+K` приходит как `key: 'л'`, и без кода сочетание мертво.\n return eventMatchesKey(event, hotkey.key, {\n codeFallback: expectMeta || expectCtrl || hotkey.alt,\n })\n}\n\n/** Человекочитаемые клавиши для подсказки в поле ввода (`⌘` / `Ctrl`). */\nexport function formatCommandHotkey(hotkey: ParsedCommandHotkey, apple = isAppleDevice()): string[] {\n const keys: string[] = []\n if (hotkey.meta || (hotkey.mod && apple)) keys.push('⌘')\n if (hotkey.ctrl || (hotkey.mod && !apple)) keys.push('Ctrl')\n if (hotkey.alt) keys.push(apple ? '⌥' : 'Alt')\n if (hotkey.shift) keys.push(apple ? '⇧' : 'Shift')\n keys.push(hotkey.key.length === 1 ? hotkey.key.toUpperCase() : hotkey.key)\n return keys\n}\n\n/**\n * Токен → то, что видит пользователь. Каталог общий с витриной и докой\n * (`hotkeyTokens.ts`): цепочка `if` расходилась бы со списком, который читает\n * потребитель.\n */\nexport function formatHotkeyToken(token: string, apple: boolean): HotkeyKeyView {\n const spec = findKbdToken(token)\n if (spec) return apple ? spec.apple : spec.other\n\n // Не из каталога — печатная клавиша: одиночный символ заглавным, потому что\n // `k` и `K` на клавише выглядят одинаково.\n const t = token.trim()\n return { label: t.length === 1 ? t.toUpperCase() : t }\n}\n\nexport function formatHotkeyTokens(tokens: readonly string[], apple: boolean): HotkeyKeyView[] {\n return tokens.map(token => formatHotkeyToken(token, apple))\n}\n\n/** Комбинация строкой (`mod+shift+K`) — в набор токенов в порядке показа. */\nexport function splitHotkeyCombo(combo: string): string[] {\n return combo.split('+').map(part => part.trim()).filter(Boolean)\n}\n","<script setup lang=\"ts\">\nimport { computed, onMounted, ref } from 'vue'\n\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport type { GrComponentSize } from '../shared/sizes'\nimport { formatHotkeyTokens, isAppleDevice, splitHotkeyCombo } from '../shared/hotkey'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n grKbdComboClass,\n grKbdInnerKeyClass,\n grKbdKeyClass,\n separatorClass,\n sequenceSeparatorClass,\n type GrKbdVariant,\n} from './grKbdStyles'\n\nexport interface GrKbdProps {\n size?: GrKbdSize\n /**\n * `merged` (по умолчанию) — сочетание одной плашкой, как его пишут сами\n * системы: `⌘K` на macOS, `Ctrl+K` на прочих. `split` — по плашке на клавишу.\n * `sequence` — аккорд «G затем I»: клавиши нажимают одну за другой.\n */\n variant?: GrKbdVariant\n /**\n * Сочетание: строкой (`\"mod+shift+K\"`) или набором токенов\n * (`['mod', 'K']`). Токен `mod` — Cmd на macOS, Ctrl на остальных.\n */\n keys?: string | string[]\n /**\n * Разделитель между клавишами. Не задан — авто: в общей плашке символы\n * склеиваются (`⌘K`), а слова разделяются плюсом (`Ctrl+K`); у `split` это\n * плюс, у `sequence` — слово из локали. Пустая строка — только зазор.\n */\n separator?: string\n platform?: GrKbdPlatform\n}\n\n/**\n * GrKbd — GR-примитив для отображения клавиш и сочетаний (`<kbd>`).\n *\n * Одна клавиша — слотом: `<GrKbd>Esc</GrKbd>`.\n * Сочетание — пропом: `<GrKbd keys=\"mod+K\" />` (на macOS `⌘ K`, иначе `Ctrl K`).\n */\nexport type GrKbdSize = GrComponentSize\n\nexport type { GrKbdVariant } from './grKbdStyles'\n\n/** Откуда брать платформу для токена `mod`. */\nexport type GrKbdPlatform = 'auto' | 'apple' | 'other'\n\nconst props = withDefaults(\n defineProps<GrKbdProps>(),\n {\n size: undefined,\n variant: 'merged',\n keys: undefined,\n separator: undefined,\n platform: 'auto',\n },\n)\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrKbd' })\nconst { t } = useGranularityTranslations()\n\n/**\n * Платформа уточняется только после монтирования: `navigator` в теле `setup`\n * либо роняет серверный рендер, либо расходится с ним и ломает гидрацию.\n * До этого момента показываем не-Apple вариант — он же приходит с сервера.\n */\nconst detectedApple = ref(false)\n\nonMounted(() => {\n detectedApple.value = isAppleDevice()\n})\n\nconst isApple = computed(() => {\n if (props.platform === 'apple') return true\n if (props.platform === 'other') return false\n return detectedApple.value\n})\n\nconst tokens = computed(() => {\n if (props.keys === undefined) return []\n return Array.isArray(props.keys) ? props.keys : splitHotkeyCombo(props.keys)\n})\n\n// Сочетание рисуется вложенными `<kbd>` — приём из спецификации HTML, а не\n// обёртка-div: сочетание остаётся клавиатурным вводом целиком.\nconst keyViews = computed(() => formatHotkeyTokens(tokens.value, isApple.value))\nconst hasCombo = computed(() => keyViews.value.length > 0)\n\nconst keyClass = computed(() => grKbdKeyClass(resolvedSize.value))\nconst innerKeyClass = computed(() => grKbdInnerKeyClass(resolvedSize.value, props.variant))\nconst comboClass = computed(() => grKbdComboClass(resolvedSize.value, props.variant))\n\n/**\n * Разделитель перед клавишей `index`.\n *\n * Авто-правило одно: в общей плашке символы склеиваются, слова — нет. Внутри\n * одной платформы набор однороден (macOS даёт `⌘⌥⇧`, прочие — `Ctrl`, `Alt`),\n * поэтому «слева символ» и означает «пишем как система».\n */\nfunction separatorAt(index: number): string {\n if (index === 0) return ''\n if (props.separator !== undefined) return props.separator\n if (props.variant === 'sequence') return t('gr.kbd.then', 'then')\n if (props.variant === 'split') return '+'\n\n return keyViews.value[index - 1]?.symbol ? '' : '+'\n}\n\nconst NAME_FALLBACKS: Record<string, string> = {\n command: 'Command',\n option: 'Option',\n shift: 'Shift',\n control: 'Control',\n enter: 'Enter',\n escape: 'Escape',\n tab: 'Tab',\n backspace: 'Backspace',\n delete: 'Delete',\n pageUp: 'Page Up',\n pageDown: 'Page Down',\n arrowUp: 'Arrow Up',\n arrowDown: 'Arrow Down',\n arrowLeft: 'Arrow Left',\n arrowRight: 'Arrow Right',\n}\n\n/** Читаемое имя символьной клавиши: `⌘` без него диктор произносит как знак. */\nfunction readableName(name: string): string {\n return t(`gr.kbd.${name}`, NAME_FALLBACKS[name] ?? name)\n}\n</script>\n\n<template>\n <kbd\n v-if=\"hasCombo\"\n data-gr-kbd\n data-gr-kbd-combo\n :data-variant=\"variant\"\n :class=\"comboClass\"\n ><template\n v-for=\"(key, index) in keyViews\"\n :key=\"`${key.label}-${index}`\"\n ><span\n v-if=\"separatorAt(index)\"\n :class=\"variant === 'sequence' ? sequenceSeparatorClass : separatorClass\"\n aria-hidden=\"true\"\n >{{ separatorAt(index) }}</span><kbd\n data-gr-kbd-key\n :class=\"innerKeyClass\"\n ><span :aria-hidden=\"key.name ? 'true' : undefined\">{{ key.label }}</span><span\n v-if=\"key.name\"\n class=\"sr-only\"\n >{{ readableName(key.name) }}</span></kbd></template></kbd>\n\n <kbd\n v-else\n data-gr-kbd\n data-gr-kbd-key\n :class=\"keyClass\"\n ><slot /></kbd>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, onMounted, ref } from 'vue'\n\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport type { GrComponentSize } from '../shared/sizes'\nimport { formatHotkeyTokens, isAppleDevice, splitHotkeyCombo } from '../shared/hotkey'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n grKbdComboClass,\n grKbdInnerKeyClass,\n grKbdKeyClass,\n separatorClass,\n sequenceSeparatorClass,\n type GrKbdVariant,\n} from './grKbdStyles'\n\nexport interface GrKbdProps {\n size?: GrKbdSize\n /**\n * `merged` (по умолчанию) — сочетание одной плашкой, как его пишут сами\n * системы: `⌘K` на macOS, `Ctrl+K` на прочих. `split` — по плашке на клавишу.\n * `sequence` — аккорд «G затем I»: клавиши нажимают одну за другой.\n */\n variant?: GrKbdVariant\n /**\n * Сочетание: строкой (`\"mod+shift+K\"`) или набором токенов\n * (`['mod', 'K']`). Токен `mod` — Cmd на macOS, Ctrl на остальных.\n */\n keys?: string | string[]\n /**\n * Разделитель между клавишами. Не задан — авто: в общей плашке символы\n * склеиваются (`⌘K`), а слова разделяются плюсом (`Ctrl+K`); у `split` это\n * плюс, у `sequence` — слово из локали. Пустая строка — только зазор.\n */\n separator?: string\n platform?: GrKbdPlatform\n}\n\n/**\n * GrKbd — GR-примитив для отображения клавиш и сочетаний (`<kbd>`).\n *\n * Одна клавиша — слотом: `<GrKbd>Esc</GrKbd>`.\n * Сочетание — пропом: `<GrKbd keys=\"mod+K\" />` (на macOS `⌘ K`, иначе `Ctrl K`).\n */\nexport type GrKbdSize = GrComponentSize\n\nexport type { GrKbdVariant } from './grKbdStyles'\n\n/** Откуда брать платформу для токена `mod`. */\nexport type GrKbdPlatform = 'auto' | 'apple' | 'other'\n\nconst props = withDefaults(\n defineProps<GrKbdProps>(),\n {\n size: undefined,\n variant: 'merged',\n keys: undefined,\n separator: undefined,\n platform: 'auto',\n },\n)\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrKbd' })\nconst { t } = useGranularityTranslations()\n\n/**\n * Платформа уточняется только после монтирования: `navigator` в теле `setup`\n * либо роняет серверный рендер, либо расходится с ним и ломает гидрацию.\n * До этого момента показываем не-Apple вариант — он же приходит с сервера.\n */\nconst detectedApple = ref(false)\n\nonMounted(() => {\n detectedApple.value = isAppleDevice()\n})\n\nconst isApple = computed(() => {\n if (props.platform === 'apple') return true\n if (props.platform === 'other') return false\n return detectedApple.value\n})\n\nconst tokens = computed(() => {\n if (props.keys === undefined) return []\n return Array.isArray(props.keys) ? props.keys : splitHotkeyCombo(props.keys)\n})\n\n// Сочетание рисуется вложенными `<kbd>` — приём из спецификации HTML, а не\n// обёртка-div: сочетание остаётся клавиатурным вводом целиком.\nconst keyViews = computed(() => formatHotkeyTokens(tokens.value, isApple.value))\nconst hasCombo = computed(() => keyViews.value.length > 0)\n\nconst keyClass = computed(() => grKbdKeyClass(resolvedSize.value))\nconst innerKeyClass = computed(() => grKbdInnerKeyClass(resolvedSize.value, props.variant))\nconst comboClass = computed(() => grKbdComboClass(resolvedSize.value, props.variant))\n\n/**\n * Разделитель перед клавишей `index`.\n *\n * Авто-правило одно: в общей плашке символы склеиваются, слова — нет. Внутри\n * одной платформы набор однороден (macOS даёт `⌘⌥⇧`, прочие — `Ctrl`, `Alt`),\n * поэтому «слева символ» и означает «пишем как система».\n */\nfunction separatorAt(index: number): string {\n if (index === 0) return ''\n if (props.separator !== undefined) return props.separator\n if (props.variant === 'sequence') return t('gr.kbd.then', 'then')\n if (props.variant === 'split') return '+'\n\n return keyViews.value[index - 1]?.symbol ? '' : '+'\n}\n\nconst NAME_FALLBACKS: Record<string, string> = {\n command: 'Command',\n option: 'Option',\n shift: 'Shift',\n control: 'Control',\n enter: 'Enter',\n escape: 'Escape',\n tab: 'Tab',\n backspace: 'Backspace',\n delete: 'Delete',\n pageUp: 'Page Up',\n pageDown: 'Page Down',\n arrowUp: 'Arrow Up',\n arrowDown: 'Arrow Down',\n arrowLeft: 'Arrow Left',\n arrowRight: 'Arrow Right',\n}\n\n/** Читаемое имя символьной клавиши: `⌘` без него диктор произносит как знак. */\nfunction readableName(name: string): string {\n return t(`gr.kbd.${name}`, NAME_FALLBACKS[name] ?? name)\n}\n</script>\n\n<template>\n <kbd\n v-if=\"hasCombo\"\n data-gr-kbd\n data-gr-kbd-combo\n :data-variant=\"variant\"\n :class=\"comboClass\"\n ><template\n v-for=\"(key, index) in keyViews\"\n :key=\"`${key.label}-${index}`\"\n ><span\n v-if=\"separatorAt(index)\"\n :class=\"variant === 'sequence' ? sequenceSeparatorClass : separatorClass\"\n aria-hidden=\"true\"\n >{{ separatorAt(index) }}</span><kbd\n data-gr-kbd-key\n :class=\"innerKeyClass\"\n ><span :aria-hidden=\"key.name ? 'true' : undefined\">{{ key.label }}</span><span\n v-if=\"key.name\"\n class=\"sr-only\"\n >{{ readableName(key.name) }}</span></kbd></template></kbd>\n\n <kbd\n v-else\n data-gr-kbd\n data-gr-kbd-key\n :class=\"keyClass\"\n ><slot /></kbd>\n</template>\n"],"mappings":"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"}
1
+ {"version":3,"file":"GrKbd-BXbhsH0M.js","names":[],"sources":["../../../../src/components/shared/hotkeyTokens.ts","../../../../src/components/shared/hotkey.ts","../../../../src/components/GrKbd/GrKbd.vue","../../../../src/components/GrKbd/GrKbd.vue"],"sourcesContent":["/**\n * Каталог клавиш, которые понимает `keys` у `GrKbd`.\n *\n * Таблица, а не цепочка `if`, по двум причинам: во-первых, список — часть\n * публичного контракта (потребителю нужно знать, что можно написать), и\n * витрина показывает именно его, а не свою копию; во-вторых, копия в демо или\n * в доке разошлась бы с форматтером молча.\n */\n\n/** Ключи читаемых имён — `gr.kbd.<name>`. */\nexport type GrKbdKeyName =\n | 'command' | 'option' | 'shift' | 'control' | 'enter' | 'escape' | 'tab'\n | 'backspace' | 'delete' | 'pageUp' | 'pageDown'\n | 'arrowUp' | 'arrowDown' | 'arrowLeft' | 'arrowRight'\n\n/** Одна клавиша в человекочитаемом виде. */\nexport interface HotkeyKeyView {\n /** Что видно на экране: символ (`⌘`) или слово (`Ctrl`). */\n label: string\n /**\n * Ключ читаемого имени (`gr.kbd.<name>`) для символьных клавиш. У `K` или\n * `Ctrl` его нет — они и так читаются вслух.\n */\n name?: GrKbdKeyName\n /** Символ (`⌘`, `↑`) или слово (`Ctrl`, `Esc`): от этого зависит склейка в одной плашке. */\n symbol?: boolean\n}\n\n/** Смысловая группа — ею витрина и дока раскладывают каталог. */\nexport type GrKbdTokenGroup = 'modifier' | 'editing' | 'navigation'\n\nexport interface GrKbdTokenSpec {\n /** Канонический токен: его пишут в `keys`. */\n token: string\n /** Что ещё принимается — синонимы и сам глиф. */\n aliases: readonly string[]\n group: GrKbdTokenGroup\n /** Вид на macOS и на остальных платформах. */\n apple: HotkeyKeyView\n other: HotkeyKeyView\n}\n\nfunction symbol(label: string, name: GrKbdKeyName): HotkeyKeyView {\n return { label, name, symbol: true }\n}\n\nfunction word(label: string, name?: GrKbdKeyName): HotkeyKeyView {\n return name ? { label, name } : { label }\n}\n\nexport const GR_KBD_TOKENS: readonly GrKbdTokenSpec[] = [\n // Модификаторы: на macOS символы, на остальных платформах слова.\n { token: 'mod', aliases: [], group: 'modifier', apple: symbol('⌘', 'command'), other: word('Ctrl') },\n { token: 'meta', aliases: ['cmd', 'command', '⌘'], group: 'modifier', apple: symbol('⌘', 'command'), other: word('Meta') },\n { token: 'ctrl', aliases: ['control', '⌃'], group: 'modifier', apple: symbol('⌃', 'control'), other: word('Ctrl') },\n { token: 'alt', aliases: ['option', '⌥'], group: 'modifier', apple: symbol('⌥', 'option'), other: word('Alt') },\n { token: 'shift', aliases: ['⇧'], group: 'modifier', apple: symbol('⇧', 'shift'), other: word('Shift') },\n\n { token: 'enter', aliases: ['return', '↵', '↩'], group: 'editing', apple: symbol('↩', 'enter'), other: word('Enter') },\n { token: 'esc', aliases: ['escape'], group: 'editing', apple: word('Esc', 'escape'), other: word('Esc', 'escape') },\n { token: 'tab', aliases: ['⇥'], group: 'editing', apple: symbol('⇥', 'tab'), other: word('Tab') },\n { token: 'space', aliases: [], group: 'editing', apple: word('Space'), other: word('Space') },\n { token: 'backspace', aliases: ['⌫'], group: 'editing', apple: symbol('⌫', 'backspace'), other: word('Backspace') },\n { token: 'delete', aliases: ['del', '⌦'], group: 'editing', apple: symbol('⌦', 'delete'), other: word('Del') },\n\n { token: 'up', aliases: ['arrowup', '↑'], group: 'navigation', apple: symbol('↑', 'arrowUp'), other: symbol('↑', 'arrowUp') },\n { token: 'down', aliases: ['arrowdown', '↓'], group: 'navigation', apple: symbol('↓', 'arrowDown'), other: symbol('↓', 'arrowDown') },\n { token: 'left', aliases: ['arrowleft', '←'], group: 'navigation', apple: symbol('←', 'arrowLeft'), other: symbol('←', 'arrowLeft') },\n { token: 'right', aliases: ['arrowright', '→'], group: 'navigation', apple: symbol('→', 'arrowRight'), other: symbol('→', 'arrowRight') },\n { token: 'home', aliases: [], group: 'navigation', apple: word('Home'), other: word('Home') },\n { token: 'end', aliases: [], group: 'navigation', apple: word('End'), other: word('End') },\n { token: 'pageup', aliases: ['pgup', '⇞'], group: 'navigation', apple: symbol('⇞', 'pageUp'), other: word('PgUp') },\n { token: 'pagedown', aliases: ['pgdn', 'pgdown', '⇟'], group: 'navigation', apple: symbol('⇟', 'pageDown'), other: word('PgDn') },\n]\n\nconst BY_ALIAS = new Map<string, GrKbdTokenSpec>()\nfor (const spec of GR_KBD_TOKENS) {\n BY_ALIAS.set(spec.token, spec)\n for (const alias of spec.aliases) BY_ALIAS.set(alias, spec)\n}\n\n/** Токен или его синоним — в описание клавиши. Регистр не важен, глиф тоже принимается. */\nexport function findKbdToken(token: string): GrKbdTokenSpec | undefined {\n const trimmed = token.trim()\n return BY_ALIAS.get(trimmed.toLowerCase()) ?? BY_ALIAS.get(trimmed)\n}\n","/**\n * Разбор, матчинг и человекочитаемое представление сочетаний клавиш.\n *\n * Общий модуль, а не часть `GrCommandPalette`: то же нужно `GrKbd`, а импорт из\n * чужой компонентной директории на сборке дал бы ребро `GrKbd →\n * GrCommandPalette` (хелпер уехал бы в чанк палитры) — `granular doctor` считает\n * такое незадекларированной зависимостью.\n *\n * Директива `v-hotkey` для палитры не годится: ей нужен смонтированный элемент,\n * а палитра в закрытом состоянии не рендерит ничего. Поэтому здесь — свой\n * матчер на `window`, с тем же синтаксисом комбинаций плюс токен `mod`.\n */\n\nimport { eventMatchesKey, isAppleDevice, isComposingEvent, shiftSatisfied } from '../../internal/keyboard'\n\nimport { findKbdToken, type HotkeyKeyView } from './hotkeyTokens'\n\nexport { isAppleDevice } from '../../internal/keyboard'\nexport { findKbdToken, GR_KBD_TOKENS } from './hotkeyTokens'\nexport type { GrKbdKeyName, GrKbdTokenGroup, GrKbdTokenSpec, HotkeyKeyView } from './hotkeyTokens'\n\nexport type ParsedCommandHotkey = {\n key: string\n ctrl: boolean\n meta: boolean\n alt: boolean\n shift: boolean\n /** `mod` — Cmd на macOS, Ctrl на остальных платформах. */\n mod: boolean\n}\n\nexport function parseCommandHotkey(combo: string): ParsedCommandHotkey | null {\n const parts = combo.split('+').map(p => p.trim()).filter(Boolean)\n const keyToken = parts.at(-1)\n if (!keyToken) return null\n\n const parsed: ParsedCommandHotkey = {\n key: keyToken.length === 1 ? keyToken.toLowerCase() : keyToken,\n ctrl: false,\n meta: false,\n alt: false,\n shift: false,\n mod: false,\n }\n\n for (const part of parts.slice(0, -1)) {\n const token = part.toLowerCase()\n if (token === 'mod') parsed.mod = true\n else if (token === 'ctrl' || token === 'control') parsed.ctrl = true\n else if (token === 'meta' || token === 'cmd' || token === 'command' || token === '⌘') parsed.meta = true\n else if (token === 'alt' || token === 'option') parsed.alt = true\n else if (token === 'shift') parsed.shift = true\n }\n\n return parsed\n}\n\nexport function matchesCommandHotkey(\n event: KeyboardEvent,\n hotkey: ParsedCommandHotkey,\n apple = isAppleDevice(),\n): boolean {\n // Клавиша во время IME-композиции принадлежит композиции, а не сочетанию.\n if (isComposingEvent(event)) return false\n\n const expectMeta = hotkey.meta || (hotkey.mod && apple)\n const expectCtrl = hotkey.ctrl || (hotkey.mod && !apple)\n\n if (event.metaKey !== expectMeta) return false\n if (event.ctrlKey !== expectCtrl) return false\n if (event.altKey !== hotkey.alt) return false\n if (!shiftSatisfied(event, hotkey.key, hotkey.shift)) return false\n\n // Комбинация с модификаторами матчится и по физическому коду: на нелатинской\n // раскладке `mod+K` приходит как `key: 'л'`, и без кода сочетание мертво.\n return eventMatchesKey(event, hotkey.key, {\n codeFallback: expectMeta || expectCtrl || hotkey.alt,\n })\n}\n\n/** Человекочитаемые клавиши для подсказки в поле ввода (`⌘` / `Ctrl`). */\nexport function formatCommandHotkey(hotkey: ParsedCommandHotkey, apple = isAppleDevice()): string[] {\n const keys: string[] = []\n if (hotkey.meta || (hotkey.mod && apple)) keys.push('⌘')\n if (hotkey.ctrl || (hotkey.mod && !apple)) keys.push('Ctrl')\n if (hotkey.alt) keys.push(apple ? '⌥' : 'Alt')\n if (hotkey.shift) keys.push(apple ? '⇧' : 'Shift')\n keys.push(hotkey.key.length === 1 ? hotkey.key.toUpperCase() : hotkey.key)\n return keys\n}\n\n/**\n * Токен → то, что видит пользователь. Каталог общий с витриной и докой\n * (`hotkeyTokens.ts`): цепочка `if` расходилась бы со списком, который читает\n * потребитель.\n */\nexport function formatHotkeyToken(token: string, apple: boolean): HotkeyKeyView {\n const spec = findKbdToken(token)\n if (spec) return apple ? spec.apple : spec.other\n\n // Не из каталога — печатная клавиша: одиночный символ заглавным, потому что\n // `k` и `K` на клавише выглядят одинаково.\n const t = token.trim()\n return { label: t.length === 1 ? t.toUpperCase() : t }\n}\n\nexport function formatHotkeyTokens(tokens: readonly string[], apple: boolean): HotkeyKeyView[] {\n return tokens.map(token => formatHotkeyToken(token, apple))\n}\n\n/** Комбинация строкой (`mod+shift+K`) — в набор токенов в порядке показа. */\nexport function splitHotkeyCombo(combo: string): string[] {\n return combo.split('+').map(part => part.trim()).filter(Boolean)\n}\n","<script setup lang=\"ts\">\nimport { computed, onMounted, ref } from 'vue'\n\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport type { GrComponentSize } from '../shared/sizes'\nimport { formatHotkeyTokens, isAppleDevice, splitHotkeyCombo } from '../shared/hotkey'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n grKbdComboClass,\n grKbdInnerKeyClass,\n grKbdKeyClass,\n separatorClass,\n sequenceSeparatorClass,\n type GrKbdVariant,\n} from './grKbdStyles'\n\nexport interface GrKbdProps {\n size?: GrKbdSize\n /**\n * `merged` (по умолчанию) — сочетание одной плашкой, как его пишут сами\n * системы: `⌘K` на macOS, `Ctrl+K` на прочих. `split` — по плашке на клавишу.\n * `sequence` — аккорд «G затем I»: клавиши нажимают одну за другой.\n */\n variant?: GrKbdVariant\n /**\n * Сочетание: строкой (`\"mod+shift+K\"`) или набором токенов\n * (`['mod', 'K']`). Токен `mod` — Cmd на macOS, Ctrl на остальных.\n */\n keys?: string | string[]\n /**\n * Разделитель между клавишами. Не задан — авто: в общей плашке символы\n * склеиваются (`⌘K`), а слова разделяются плюсом (`Ctrl+K`); у `split` это\n * плюс, у `sequence` — слово из локали. Пустая строка — только зазор.\n */\n separator?: string\n platform?: GrKbdPlatform\n}\n\n/**\n * GrKbd — GR-примитив для отображения клавиш и сочетаний (`<kbd>`).\n *\n * Одна клавиша — слотом: `<GrKbd>Esc</GrKbd>`.\n * Сочетание — пропом: `<GrKbd keys=\"mod+K\" />` (на macOS `⌘ K`, иначе `Ctrl K`).\n */\nexport type GrKbdSize = GrComponentSize\n\nexport type { GrKbdVariant } from './grKbdStyles'\n\n/** Откуда брать платформу для токена `mod`. */\nexport type GrKbdPlatform = 'auto' | 'apple' | 'other'\n\nconst props = withDefaults(\n defineProps<GrKbdProps>(),\n {\n size: undefined,\n variant: 'merged',\n keys: undefined,\n separator: undefined,\n platform: 'auto',\n },\n)\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrKbd' })\nconst { t } = useGranularityTranslations()\n\n/**\n * Платформа уточняется только после монтирования: `navigator` в теле `setup`\n * либо роняет серверный рендер, либо расходится с ним и ломает гидрацию.\n * До этого момента показываем не-Apple вариант — он же приходит с сервера.\n */\nconst detectedApple = ref(false)\n\nonMounted(() => {\n detectedApple.value = isAppleDevice()\n})\n\nconst isApple = computed(() => {\n if (props.platform === 'apple') return true\n if (props.platform === 'other') return false\n return detectedApple.value\n})\n\nconst tokens = computed(() => {\n if (props.keys === undefined) return []\n return Array.isArray(props.keys) ? props.keys : splitHotkeyCombo(props.keys)\n})\n\n// Сочетание рисуется вложенными `<kbd>` — приём из спецификации HTML, а не\n// обёртка-div: сочетание остаётся клавиатурным вводом целиком.\nconst keyViews = computed(() => formatHotkeyTokens(tokens.value, isApple.value))\nconst hasCombo = computed(() => keyViews.value.length > 0)\n\nconst keyClass = computed(() => grKbdKeyClass(resolvedSize.value))\nconst innerKeyClass = computed(() => grKbdInnerKeyClass(resolvedSize.value, props.variant))\nconst comboClass = computed(() => grKbdComboClass(resolvedSize.value, props.variant))\n\n/**\n * Разделитель перед клавишей `index`.\n *\n * Авто-правило одно: в общей плашке символы склеиваются, слова — нет. Внутри\n * одной платформы набор однороден (macOS даёт `⌘⌥⇧`, прочие — `Ctrl`, `Alt`),\n * поэтому «слева символ» и означает «пишем как система».\n */\nfunction separatorAt(index: number): string {\n if (index === 0) return ''\n if (props.separator !== undefined) return props.separator\n if (props.variant === 'sequence') return t('gr.kbd.then', 'then')\n if (props.variant === 'split') return '+'\n\n return keyViews.value[index - 1]?.symbol ? '' : '+'\n}\n\nconst NAME_FALLBACKS: Record<string, string> = {\n command: 'Command',\n option: 'Option',\n shift: 'Shift',\n control: 'Control',\n enter: 'Enter',\n escape: 'Escape',\n tab: 'Tab',\n backspace: 'Backspace',\n delete: 'Delete',\n pageUp: 'Page Up',\n pageDown: 'Page Down',\n arrowUp: 'Arrow Up',\n arrowDown: 'Arrow Down',\n arrowLeft: 'Arrow Left',\n arrowRight: 'Arrow Right',\n}\n\n/** Читаемое имя символьной клавиши: `⌘` без него диктор произносит как знак. */\nfunction readableName(name: string): string {\n return t(`gr.kbd.${name}`, NAME_FALLBACKS[name] ?? name)\n}\n</script>\n\n<template>\n <kbd\n v-if=\"hasCombo\"\n data-gr-kbd\n data-gr-kbd-combo\n :data-variant=\"variant\"\n :class=\"comboClass\"\n ><template\n v-for=\"(key, index) in keyViews\"\n :key=\"`${key.label}-${index}`\"\n ><span\n v-if=\"separatorAt(index)\"\n :class=\"variant === 'sequence' ? sequenceSeparatorClass : separatorClass\"\n aria-hidden=\"true\"\n >{{ separatorAt(index) }}</span><kbd\n data-gr-kbd-key\n :class=\"innerKeyClass\"\n ><span :aria-hidden=\"key.name ? 'true' : undefined\">{{ key.label }}</span><span\n v-if=\"key.name\"\n class=\"sr-only\"\n >{{ readableName(key.name) }}</span></kbd></template></kbd>\n\n <kbd\n v-else\n data-gr-kbd\n data-gr-kbd-key\n :class=\"keyClass\"\n ><slot /></kbd>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, onMounted, ref } from 'vue'\n\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport type { GrComponentSize } from '../shared/sizes'\nimport { formatHotkeyTokens, isAppleDevice, splitHotkeyCombo } from '../shared/hotkey'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n grKbdComboClass,\n grKbdInnerKeyClass,\n grKbdKeyClass,\n separatorClass,\n sequenceSeparatorClass,\n type GrKbdVariant,\n} from './grKbdStyles'\n\nexport interface GrKbdProps {\n size?: GrKbdSize\n /**\n * `merged` (по умолчанию) — сочетание одной плашкой, как его пишут сами\n * системы: `⌘K` на macOS, `Ctrl+K` на прочих. `split` — по плашке на клавишу.\n * `sequence` — аккорд «G затем I»: клавиши нажимают одну за другой.\n */\n variant?: GrKbdVariant\n /**\n * Сочетание: строкой (`\"mod+shift+K\"`) или набором токенов\n * (`['mod', 'K']`). Токен `mod` — Cmd на macOS, Ctrl на остальных.\n */\n keys?: string | string[]\n /**\n * Разделитель между клавишами. Не задан — авто: в общей плашке символы\n * склеиваются (`⌘K`), а слова разделяются плюсом (`Ctrl+K`); у `split` это\n * плюс, у `sequence` — слово из локали. Пустая строка — только зазор.\n */\n separator?: string\n platform?: GrKbdPlatform\n}\n\n/**\n * GrKbd — GR-примитив для отображения клавиш и сочетаний (`<kbd>`).\n *\n * Одна клавиша — слотом: `<GrKbd>Esc</GrKbd>`.\n * Сочетание — пропом: `<GrKbd keys=\"mod+K\" />` (на macOS `⌘ K`, иначе `Ctrl K`).\n */\nexport type GrKbdSize = GrComponentSize\n\nexport type { GrKbdVariant } from './grKbdStyles'\n\n/** Откуда брать платформу для токена `mod`. */\nexport type GrKbdPlatform = 'auto' | 'apple' | 'other'\n\nconst props = withDefaults(\n defineProps<GrKbdProps>(),\n {\n size: undefined,\n variant: 'merged',\n keys: undefined,\n separator: undefined,\n platform: 'auto',\n },\n)\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrKbd' })\nconst { t } = useGranularityTranslations()\n\n/**\n * Платформа уточняется только после монтирования: `navigator` в теле `setup`\n * либо роняет серверный рендер, либо расходится с ним и ломает гидрацию.\n * До этого момента показываем не-Apple вариант — он же приходит с сервера.\n */\nconst detectedApple = ref(false)\n\nonMounted(() => {\n detectedApple.value = isAppleDevice()\n})\n\nconst isApple = computed(() => {\n if (props.platform === 'apple') return true\n if (props.platform === 'other') return false\n return detectedApple.value\n})\n\nconst tokens = computed(() => {\n if (props.keys === undefined) return []\n return Array.isArray(props.keys) ? props.keys : splitHotkeyCombo(props.keys)\n})\n\n// Сочетание рисуется вложенными `<kbd>` — приём из спецификации HTML, а не\n// обёртка-div: сочетание остаётся клавиатурным вводом целиком.\nconst keyViews = computed(() => formatHotkeyTokens(tokens.value, isApple.value))\nconst hasCombo = computed(() => keyViews.value.length > 0)\n\nconst keyClass = computed(() => grKbdKeyClass(resolvedSize.value))\nconst innerKeyClass = computed(() => grKbdInnerKeyClass(resolvedSize.value, props.variant))\nconst comboClass = computed(() => grKbdComboClass(resolvedSize.value, props.variant))\n\n/**\n * Разделитель перед клавишей `index`.\n *\n * Авто-правило одно: в общей плашке символы склеиваются, слова — нет. Внутри\n * одной платформы набор однороден (macOS даёт `⌘⌥⇧`, прочие — `Ctrl`, `Alt`),\n * поэтому «слева символ» и означает «пишем как система».\n */\nfunction separatorAt(index: number): string {\n if (index === 0) return ''\n if (props.separator !== undefined) return props.separator\n if (props.variant === 'sequence') return t('gr.kbd.then', 'then')\n if (props.variant === 'split') return '+'\n\n return keyViews.value[index - 1]?.symbol ? '' : '+'\n}\n\nconst NAME_FALLBACKS: Record<string, string> = {\n command: 'Command',\n option: 'Option',\n shift: 'Shift',\n control: 'Control',\n enter: 'Enter',\n escape: 'Escape',\n tab: 'Tab',\n backspace: 'Backspace',\n delete: 'Delete',\n pageUp: 'Page Up',\n pageDown: 'Page Down',\n arrowUp: 'Arrow Up',\n arrowDown: 'Arrow Down',\n arrowLeft: 'Arrow Left',\n arrowRight: 'Arrow Right',\n}\n\n/** Читаемое имя символьной клавиши: `⌘` без него диктор произносит как знак. */\nfunction readableName(name: string): string {\n return t(`gr.kbd.${name}`, NAME_FALLBACKS[name] ?? name)\n}\n</script>\n\n<template>\n <kbd\n v-if=\"hasCombo\"\n data-gr-kbd\n data-gr-kbd-combo\n :data-variant=\"variant\"\n :class=\"comboClass\"\n ><template\n v-for=\"(key, index) in keyViews\"\n :key=\"`${key.label}-${index}`\"\n ><span\n v-if=\"separatorAt(index)\"\n :class=\"variant === 'sequence' ? sequenceSeparatorClass : separatorClass\"\n aria-hidden=\"true\"\n >{{ separatorAt(index) }}</span><kbd\n data-gr-kbd-key\n :class=\"innerKeyClass\"\n ><span :aria-hidden=\"key.name ? 'true' : undefined\">{{ key.label }}</span><span\n v-if=\"key.name\"\n class=\"sr-only\"\n >{{ readableName(key.name) }}</span></kbd></template></kbd>\n\n <kbd\n v-else\n data-gr-kbd\n data-gr-kbd-key\n :class=\"keyClass\"\n ><slot /></kbd>\n</template>\n"],"mappings":"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"}
@@ -1,3 +1,3 @@
1
- import { a as GR_KBD_TOKENS, o as findKbdToken, t as GrKbd_default } from "./chunks/GrKbd-DU2lBkRV.js";
1
+ import { a as GR_KBD_TOKENS, o as findKbdToken, t as GrKbd_default } from "./chunks/GrKbd-BXbhsH0M.js";
2
2
  import { n as grKbdSafelist, t as grKbdConfig } from "../../chunks/config-DA6SnEoy.js";
3
3
  export { GR_KBD_TOKENS, GrKbd_default as GrKbd, GrKbd_default as default, findKbdToken, grKbdConfig, grKbdSafelist };
@@ -1,6 +1,6 @@
1
- import { o as useGrComponentSize } from "../../../chunks/context-BSYR7RZs.js";
1
+ import { a as useGrComponentSize } from "../../../chunks/context-CTbuwcYs.js";
2
2
  import { n as useGranularityTranslations } from "../../../chunks/granularityI18n-BC5zsj_d.js";
3
- import { t as GrIcon_default } from "../../GrIcon/chunks/GrIcon-BvA2ZGXP.js";
3
+ import { t as GrIcon_default } from "../../GrIcon/chunks/GrIcon-bQwtZtYT.js";
4
4
  import { a as grLinkClass, i as focusRingClass, o as grLinkColorStyle, t as baseRootClass } from "../../../chunks/grLinkStyles-BoL8QYcV.js";
5
5
  import { computed, createBlock, createCommentVNode, createElementBlock, createElementVNode, createVNode, defineComponent, markRaw, mergeProps, openBlock, renderSlot, resolveDynamicComponent, toDisplayString, unref, useAttrs, withCtx } from "vue";
6
6
  //#region ~icons/lucide/external-link
@@ -1 +1 @@
1
- {"version":3,"file":"GrLink-D-cgUMXW.js","names":[],"sources":["../../../../src/components/GrLink/GrLink.vue","../../../../src/components/GrLink/GrLink.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { useGrComponentSize } from '../GrConfigProvider/context'\n/**\n * GrLink — GR-примитив ссылки.\n *\n * Корневой тег зависит от пропов:\n * - кастомный компонент/тег из пропа `as` — когда `as` передан и не `disabled`\n * (например, `Link` от `@inertiajs/vue3` или `RouterLink` от Vue Router);\n * - `<a>` — когда задан `href` и не `disabled`;\n * - `<span>` — во всех остальных случаях (включая `disabled`, даже если задан\n * `href`/`as`).\n *\n * Это осознанное решение, чтобы отключённая ссылка не была кликабельной и\n * не участвовала в порядке табуляции. Учтите это в внешних CSS-селекторах.\n *\n * Проп `as` нужен для интеграции с роутерами (Inertia, Vue Router и пр.):\n * стили/поведение GR остаются едиными, а тег корня подменяется. Все\n * специфичные для роутера атрибуты (`method`, `replace`, `preserve-scroll` и т.п.)\n * проходят через fallthrough-attrs.\n */\nimport { computed, markRaw, useAttrs, type Component } from 'vue'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport IconExternal from '~icons/lucide/external-link'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n baseRootClass,\n focusRingClass,\n type GrLinkSize,\n type GrLinkTone,\n type GrLinkUnderline,\n type GrLinkVariant,\n grLinkClass,\n grLinkColorStyle,\n} from './grLinkStyles'\n\nexport interface GrLinkProps {\n /**\n * Кастомный корневой тег/компонент. Если передан и компонент не `disabled` —\n * рендерится через `<component :is=\"as\">`. Игнорируется при `disabled`.\n */\n as?: string | Component\n href?: string\n external?: boolean\n target?: string\n rel?: string\n disabled?: boolean\n ariaLabel?: string\n /** Семантический цвет ссылки из палитры `GrTone`. */\n tone?: GrLinkTone\n /** Уровень акцента: `default` (окрашен) или `muted` (приглушён, акцент на hover). */\n variant?: GrLinkVariant\n underline?: GrLinkUnderline\n size?: GrLinkSize\n /**\n * Иконка внешней ссылки. По умолчанию показывается у любой ссылки, которая\n * открывается в новой вкладке, — не только при `external`.\n */\n externalIcon?: boolean\n /** i18n: скрытая подсказка «откроется в новой вкладке». */\n newTabLabel?: string\n}\n\ndefineOptions({\n inheritAttrs: false,\n})\n\nconst props = withDefaults(defineProps<GrLinkProps>(), {\n as: undefined,\n href: undefined,\n external: false,\n target: undefined,\n rel: undefined,\n disabled: false,\n ariaLabel: undefined,\n tone: 'primary',\n variant: 'default',\n underline: 'auto',\n size: undefined,\n externalIcon: undefined,\n newTabLabel: undefined,\n})\n\nconst attrs = useAttrs()\n\n// Кастомный корень имеет приоритет над `<a>` — GR не пытается угадывать\n// «правильный» тег за пользователя, если он явно его указал.\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href))\n\nconst renderAs = computed<string | Component>(() => {\n if (!isInteractive.value) return 'span'\n if (props.as) {\n // Если `as` — объект-компонент, помечаем его как нереактивный, чтобы избежать\n // оверхеда от Vue-прокси и предупреждений в консоли. Строки (нативные теги)\n // оставляем как есть.\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n }\n return 'a'\n})\n\nconst resolvedTarget = computed(() => {\n if (props.target)\n return props.target\n\n if (props.external)\n return '_blank'\n\n return undefined\n})\n\nconst resolvedRel = computed(() => {\n if (props.rel)\n return props.rel\n\n // Авто-защита для любых ссылок, открывающихся в новой вкладке,\n // а не только когда выставлен `external`.\n if (resolvedTarget.value === '_blank')\n return 'noopener noreferrer'\n\n return undefined\n})\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrLink' })\n\nconst { t } = useGranularityTranslations()\n\n/**\n * Смена контекста должна быть объявлена (WCAG 3.2.5). Условие — ссылка реально\n * открывается в новой вкладке, а не наличие пропа `external`: `target=\"_blank\"`\n * снаружи даёт ровно тот же сюрприз (та же генерализация, что у `rel`).\n */\nconst opensInNewTab = computed(() => isInteractive.value && resolvedTarget.value === '_blank')\nconst newTabHint = computed(() => props.newTabLabel ?? t('gr.link.opensInNewTab', 'opens in a new tab'))\n\nconst showExternalIcon = computed(() => props.externalIcon ?? opensInNewTab.value)\n\n/**\n * `aria-label` перекрывает содержимое целиком — вместе со скрытой подсказкой.\n * Поэтому, если имя задано руками, подсказка дописывается к нему.\n */\nconst resolvedAriaLabel = computed(() => {\n if (!props.ariaLabel)\n return undefined\n\n return opensInNewTab.value ? `${props.ariaLabel}, ${newTabHint.value}` : props.ariaLabel\n})\n\nconst iconSize = computed(() => (resolvedSize.value === 'lg' ? 'sm' : 'xs'))\n\nconst rootClass = computed(() => {\n const variantClass = grLinkClass({\n size: resolvedSize.value,\n underline: props.underline,\n disabled: props.disabled,\n })\n\n // На disabled-ветке (`<span>`) focus-ring не нужен: элемент не фокусируется,\n // а если снаружи ему навесят `tabindex`, фокус-рамка на «отключённой» ссылке смотрелась бы странно.\n return props.disabled\n ? `${baseRootClass} ${variantClass}`\n : `${baseRootClass} ${focusRingClass} ${variantClass}`\n})\n\n// Цвет (tone × variant) прокидываем через CSS-переменные, чтобы не плодить классы.\nconst colorStyle = computed(() => grLinkColorStyle({\n tone: props.tone,\n variant: props.variant,\n disabled: props.disabled,\n}))\n</script>\n\n<template>\n <component\n :is=\"renderAs\"\n v-bind=\"attrs\"\n :href=\"isInteractive ? href : undefined\"\n :target=\"isInteractive ? resolvedTarget : undefined\"\n :rel=\"isInteractive ? resolvedRel : undefined\"\n :aria-label=\"resolvedAriaLabel\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n :class=\"rootClass\"\n :style=\"colorStyle\"\n >\n <slot />\n\n <GrIcon v-if=\"showExternalIcon\" :size=\"iconSize\">\n <IconExternal />\n </GrIcon>\n\n <!-- Подсказка не дублируется, когда её уже вобрал `aria-label`. -->\n <span v-if=\"opensInNewTab && !ariaLabel\" class=\"sr-only\">({{ newTabHint }})</span>\n </component>\n</template>\n","<script setup lang=\"ts\">\nimport { useGrComponentSize } from '../GrConfigProvider/context'\n/**\n * GrLink — GR-примитив ссылки.\n *\n * Корневой тег зависит от пропов:\n * - кастомный компонент/тег из пропа `as` — когда `as` передан и не `disabled`\n * (например, `Link` от `@inertiajs/vue3` или `RouterLink` от Vue Router);\n * - `<a>` — когда задан `href` и не `disabled`;\n * - `<span>` — во всех остальных случаях (включая `disabled`, даже если задан\n * `href`/`as`).\n *\n * Это осознанное решение, чтобы отключённая ссылка не была кликабельной и\n * не участвовала в порядке табуляции. Учтите это в внешних CSS-селекторах.\n *\n * Проп `as` нужен для интеграции с роутерами (Inertia, Vue Router и пр.):\n * стили/поведение GR остаются едиными, а тег корня подменяется. Все\n * специфичные для роутера атрибуты (`method`, `replace`, `preserve-scroll` и т.п.)\n * проходят через fallthrough-attrs.\n */\nimport { computed, markRaw, useAttrs, type Component } from 'vue'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport IconExternal from '~icons/lucide/external-link'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n baseRootClass,\n focusRingClass,\n type GrLinkSize,\n type GrLinkTone,\n type GrLinkUnderline,\n type GrLinkVariant,\n grLinkClass,\n grLinkColorStyle,\n} from './grLinkStyles'\n\nexport interface GrLinkProps {\n /**\n * Кастомный корневой тег/компонент. Если передан и компонент не `disabled` —\n * рендерится через `<component :is=\"as\">`. Игнорируется при `disabled`.\n */\n as?: string | Component\n href?: string\n external?: boolean\n target?: string\n rel?: string\n disabled?: boolean\n ariaLabel?: string\n /** Семантический цвет ссылки из палитры `GrTone`. */\n tone?: GrLinkTone\n /** Уровень акцента: `default` (окрашен) или `muted` (приглушён, акцент на hover). */\n variant?: GrLinkVariant\n underline?: GrLinkUnderline\n size?: GrLinkSize\n /**\n * Иконка внешней ссылки. По умолчанию показывается у любой ссылки, которая\n * открывается в новой вкладке, — не только при `external`.\n */\n externalIcon?: boolean\n /** i18n: скрытая подсказка «откроется в новой вкладке». */\n newTabLabel?: string\n}\n\ndefineOptions({\n inheritAttrs: false,\n})\n\nconst props = withDefaults(defineProps<GrLinkProps>(), {\n as: undefined,\n href: undefined,\n external: false,\n target: undefined,\n rel: undefined,\n disabled: false,\n ariaLabel: undefined,\n tone: 'primary',\n variant: 'default',\n underline: 'auto',\n size: undefined,\n externalIcon: undefined,\n newTabLabel: undefined,\n})\n\nconst attrs = useAttrs()\n\n// Кастомный корень имеет приоритет над `<a>` — GR не пытается угадывать\n// «правильный» тег за пользователя, если он явно его указал.\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href))\n\nconst renderAs = computed<string | Component>(() => {\n if (!isInteractive.value) return 'span'\n if (props.as) {\n // Если `as` — объект-компонент, помечаем его как нереактивный, чтобы избежать\n // оверхеда от Vue-прокси и предупреждений в консоли. Строки (нативные теги)\n // оставляем как есть.\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n }\n return 'a'\n})\n\nconst resolvedTarget = computed(() => {\n if (props.target)\n return props.target\n\n if (props.external)\n return '_blank'\n\n return undefined\n})\n\nconst resolvedRel = computed(() => {\n if (props.rel)\n return props.rel\n\n // Авто-защита для любых ссылок, открывающихся в новой вкладке,\n // а не только когда выставлен `external`.\n if (resolvedTarget.value === '_blank')\n return 'noopener noreferrer'\n\n return undefined\n})\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrLink' })\n\nconst { t } = useGranularityTranslations()\n\n/**\n * Смена контекста должна быть объявлена (WCAG 3.2.5). Условие — ссылка реально\n * открывается в новой вкладке, а не наличие пропа `external`: `target=\"_blank\"`\n * снаружи даёт ровно тот же сюрприз (та же генерализация, что у `rel`).\n */\nconst opensInNewTab = computed(() => isInteractive.value && resolvedTarget.value === '_blank')\nconst newTabHint = computed(() => props.newTabLabel ?? t('gr.link.opensInNewTab', 'opens in a new tab'))\n\nconst showExternalIcon = computed(() => props.externalIcon ?? opensInNewTab.value)\n\n/**\n * `aria-label` перекрывает содержимое целиком — вместе со скрытой подсказкой.\n * Поэтому, если имя задано руками, подсказка дописывается к нему.\n */\nconst resolvedAriaLabel = computed(() => {\n if (!props.ariaLabel)\n return undefined\n\n return opensInNewTab.value ? `${props.ariaLabel}, ${newTabHint.value}` : props.ariaLabel\n})\n\nconst iconSize = computed(() => (resolvedSize.value === 'lg' ? 'sm' : 'xs'))\n\nconst rootClass = computed(() => {\n const variantClass = grLinkClass({\n size: resolvedSize.value,\n underline: props.underline,\n disabled: props.disabled,\n })\n\n // На disabled-ветке (`<span>`) focus-ring не нужен: элемент не фокусируется,\n // а если снаружи ему навесят `tabindex`, фокус-рамка на «отключённой» ссылке смотрелась бы странно.\n return props.disabled\n ? `${baseRootClass} ${variantClass}`\n : `${baseRootClass} ${focusRingClass} ${variantClass}`\n})\n\n// Цвет (tone × variant) прокидываем через CSS-переменные, чтобы не плодить классы.\nconst colorStyle = computed(() => grLinkColorStyle({\n tone: props.tone,\n variant: props.variant,\n disabled: props.disabled,\n}))\n</script>\n\n<template>\n <component\n :is=\"renderAs\"\n v-bind=\"attrs\"\n :href=\"isInteractive ? href : undefined\"\n :target=\"isInteractive ? resolvedTarget : undefined\"\n :rel=\"isInteractive ? resolvedRel : undefined\"\n :aria-label=\"resolvedAriaLabel\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n :class=\"rootClass\"\n :style=\"colorStyle\"\n >\n <slot />\n\n <GrIcon v-if=\"showExternalIcon\" :size=\"iconSize\">\n <IconExternal />\n </GrIcon>\n\n <!-- Подсказка не дублируется, когда её уже вобрал `aria-label`. -->\n <span v-if=\"opensInNewTab && !ariaLabel\" class=\"sr-only\">({{ newTabHint }})</span>\n </component>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAoEA,MAAM,QAAQ;EAgBd,MAAM,QAAQ,SAAS;EAIvB,MAAM,gBAAgB,eAAe,CAAC,MAAM,aAAa,CAAC,CAAC,MAAM,MAAM,CAAC,CAAC,MAAM,KAAK;EAEpF,MAAM,WAAW,eAAmC;GAClD,IAAI,CAAC,cAAc,OAAO,OAAO;GACjC,IAAI,MAAM,IAIR,OAAO,OAAO,MAAM,OAAO,WAAW,MAAM,KAAK,QAAQ,MAAM,EAAE;GAEnE,OAAO;EACT,CAAC;EAED,MAAM,iBAAiB,eAAe;GACpC,IAAI,MAAM,QACR,OAAO,MAAM;GAEf,IAAI,MAAM,UACR,OAAO;EAGX,CAAC;EAED,MAAM,cAAc,eAAe;GACjC,IAAI,MAAM,KACR,OAAO,MAAM;GAIf,IAAI,eAAe,UAAU,UAC3B,OAAO;EAGX,CAAC;EAED,MAAM,eAAe,yBAAyB,MAAM,MAAM,EAAE,WAAW,SAAS,CAAC;EAEjF,MAAM,EAAE,MAAM,2BAA2B;;;;;;EAOzC,MAAM,gBAAgB,eAAe,cAAc,SAAS,eAAe,UAAU,QAAQ;EAC7F,MAAM,aAAa,eAAe,MAAM,eAAe,EAAE,yBAAyB,oBAAoB,CAAC;EAEvG,MAAM,mBAAmB,eAAe,MAAM,gBAAgB,cAAc,KAAK;;;;;EAMjF,MAAM,oBAAoB,eAAe;GACvC,IAAI,CAAC,MAAM,WACT,OAAO,KAAA;GAET,OAAO,cAAc,QAAQ,GAAG,MAAM,UAAU,IAAI,WAAW,UAAU,MAAM;EACjF,CAAC;EAED,MAAM,WAAW,eAAgB,aAAa,UAAU,OAAO,OAAO,IAAK;EAE3E,MAAM,YAAY,eAAe;GAC/B,MAAM,eAAe,YAAY;IAC/B,MAAM,aAAa;IACnB,WAAW,MAAM;IACjB,UAAU,MAAM;GAClB,CAAC;GAID,OAAO,MAAM,WACT,GAAG,cAAc,GAAG,iBACpB,GAAG,cAAc,GAAG,eAAe,GAAG;EAC5C,CAAC;EAGD,MAAM,aAAa,eAAe,iBAAiB;GACjD,MAAM,MAAM;GACZ,SAAS,MAAM;GACf,UAAU,MAAM;EAClB,CAAC,CAAC;;uBAIA,YAmBY,wBAlBL,SAAA,KAAQ,GADf,WAEU,MAiBE,KAAA,GAjBG;IACZ,MAAM,cAAA,QAAgB,QAAA,OAAO,KAAA;IAC7B,QAAQ,cAAA,QAAgB,eAAA,QAAiB,KAAA;IACzC,KAAK,cAAA,QAAgB,YAAA,QAAc,KAAA;IACnC,cAAY,kBAAA;IACZ,iBAAe,QAAA,WAAQ,SAAY,KAAA;IACnC,OAAO,UAAA;IACP,OAAO,WAAA;;2BAEA;KAAR,WAAQ,KAAA,QAAA,SAAA;KAEM,iBAAA,SAAA,UAAA,GAAd,YAES,gBAAA;;MAFwB,MAAM,SAAA;;6BACrB,CAAhB,YAAgB,MAAA,qBAAA,CAAA,CAAA,CAAA;;;KAIN,cAAA,SAAa,CAAK,QAAA,aAAA,UAAA,GAA9B,mBAAkF,QAAlF,YAAyD,MAAC,gBAAG,WAAA,KAAU,IAAG,KAAC,CAAA,KAAA,mBAAA,IAAA,IAAA"}
1
+ {"version":3,"file":"GrLink-BQb7U4so.js","names":[],"sources":["../../../../src/components/GrLink/GrLink.vue","../../../../src/components/GrLink/GrLink.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { useGrComponentSize } from '../GrConfigProvider/context'\n/**\n * GrLink — GR-примитив ссылки.\n *\n * Корневой тег зависит от пропов:\n * - кастомный компонент/тег из пропа `as` — когда `as` передан и не `disabled`\n * (например, `Link` от `@inertiajs/vue3` или `RouterLink` от Vue Router);\n * - `<a>` — когда задан `href` и не `disabled`;\n * - `<span>` — во всех остальных случаях (включая `disabled`, даже если задан\n * `href`/`as`).\n *\n * Это осознанное решение, чтобы отключённая ссылка не была кликабельной и\n * не участвовала в порядке табуляции. Учтите это в внешних CSS-селекторах.\n *\n * Проп `as` нужен для интеграции с роутерами (Inertia, Vue Router и пр.):\n * стили/поведение GR остаются едиными, а тег корня подменяется. Все\n * специфичные для роутера атрибуты (`method`, `replace`, `preserve-scroll` и т.п.)\n * проходят через fallthrough-attrs.\n */\nimport { computed, markRaw, useAttrs, type Component } from 'vue'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport IconExternal from '~icons/lucide/external-link'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n baseRootClass,\n focusRingClass,\n type GrLinkSize,\n type GrLinkTone,\n type GrLinkUnderline,\n type GrLinkVariant,\n grLinkClass,\n grLinkColorStyle,\n} from './grLinkStyles'\n\nexport interface GrLinkProps {\n /**\n * Кастомный корневой тег/компонент. Если передан и компонент не `disabled` —\n * рендерится через `<component :is=\"as\">`. Игнорируется при `disabled`.\n */\n as?: string | Component\n href?: string\n external?: boolean\n target?: string\n rel?: string\n disabled?: boolean\n ariaLabel?: string\n /** Семантический цвет ссылки из палитры `GrTone`. */\n tone?: GrLinkTone\n /** Уровень акцента: `default` (окрашен) или `muted` (приглушён, акцент на hover). */\n variant?: GrLinkVariant\n underline?: GrLinkUnderline\n size?: GrLinkSize\n /**\n * Иконка внешней ссылки. По умолчанию показывается у любой ссылки, которая\n * открывается в новой вкладке, — не только при `external`.\n */\n externalIcon?: boolean\n /** i18n: скрытая подсказка «откроется в новой вкладке». */\n newTabLabel?: string\n}\n\ndefineOptions({\n inheritAttrs: false,\n})\n\nconst props = withDefaults(defineProps<GrLinkProps>(), {\n as: undefined,\n href: undefined,\n external: false,\n target: undefined,\n rel: undefined,\n disabled: false,\n ariaLabel: undefined,\n tone: 'primary',\n variant: 'default',\n underline: 'auto',\n size: undefined,\n externalIcon: undefined,\n newTabLabel: undefined,\n})\n\nconst attrs = useAttrs()\n\n// Кастомный корень имеет приоритет над `<a>` — GR не пытается угадывать\n// «правильный» тег за пользователя, если он явно его указал.\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href))\n\nconst renderAs = computed<string | Component>(() => {\n if (!isInteractive.value) return 'span'\n if (props.as) {\n // Если `as` — объект-компонент, помечаем его как нереактивный, чтобы избежать\n // оверхеда от Vue-прокси и предупреждений в консоли. Строки (нативные теги)\n // оставляем как есть.\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n }\n return 'a'\n})\n\nconst resolvedTarget = computed(() => {\n if (props.target)\n return props.target\n\n if (props.external)\n return '_blank'\n\n return undefined\n})\n\nconst resolvedRel = computed(() => {\n if (props.rel)\n return props.rel\n\n // Авто-защита для любых ссылок, открывающихся в новой вкладке,\n // а не только когда выставлен `external`.\n if (resolvedTarget.value === '_blank')\n return 'noopener noreferrer'\n\n return undefined\n})\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrLink' })\n\nconst { t } = useGranularityTranslations()\n\n/**\n * Смена контекста должна быть объявлена (WCAG 3.2.5). Условие — ссылка реально\n * открывается в новой вкладке, а не наличие пропа `external`: `target=\"_blank\"`\n * снаружи даёт ровно тот же сюрприз (та же генерализация, что у `rel`).\n */\nconst opensInNewTab = computed(() => isInteractive.value && resolvedTarget.value === '_blank')\nconst newTabHint = computed(() => props.newTabLabel ?? t('gr.link.opensInNewTab', 'opens in a new tab'))\n\nconst showExternalIcon = computed(() => props.externalIcon ?? opensInNewTab.value)\n\n/**\n * `aria-label` перекрывает содержимое целиком — вместе со скрытой подсказкой.\n * Поэтому, если имя задано руками, подсказка дописывается к нему.\n */\nconst resolvedAriaLabel = computed(() => {\n if (!props.ariaLabel)\n return undefined\n\n return opensInNewTab.value ? `${props.ariaLabel}, ${newTabHint.value}` : props.ariaLabel\n})\n\nconst iconSize = computed(() => (resolvedSize.value === 'lg' ? 'sm' : 'xs'))\n\nconst rootClass = computed(() => {\n const variantClass = grLinkClass({\n size: resolvedSize.value,\n underline: props.underline,\n disabled: props.disabled,\n })\n\n // На disabled-ветке (`<span>`) focus-ring не нужен: элемент не фокусируется,\n // а если снаружи ему навесят `tabindex`, фокус-рамка на «отключённой» ссылке смотрелась бы странно.\n return props.disabled\n ? `${baseRootClass} ${variantClass}`\n : `${baseRootClass} ${focusRingClass} ${variantClass}`\n})\n\n// Цвет (tone × variant) прокидываем через CSS-переменные, чтобы не плодить классы.\nconst colorStyle = computed(() => grLinkColorStyle({\n tone: props.tone,\n variant: props.variant,\n disabled: props.disabled,\n}))\n</script>\n\n<template>\n <component\n :is=\"renderAs\"\n v-bind=\"attrs\"\n :href=\"isInteractive ? href : undefined\"\n :target=\"isInteractive ? resolvedTarget : undefined\"\n :rel=\"isInteractive ? resolvedRel : undefined\"\n :aria-label=\"resolvedAriaLabel\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n :class=\"rootClass\"\n :style=\"colorStyle\"\n >\n <slot />\n\n <GrIcon v-if=\"showExternalIcon\" :size=\"iconSize\">\n <IconExternal />\n </GrIcon>\n\n <!-- Подсказка не дублируется, когда её уже вобрал `aria-label`. -->\n <span v-if=\"opensInNewTab && !ariaLabel\" class=\"sr-only\">({{ newTabHint }})</span>\n </component>\n</template>\n","<script setup lang=\"ts\">\nimport { useGrComponentSize } from '../GrConfigProvider/context'\n/**\n * GrLink — GR-примитив ссылки.\n *\n * Корневой тег зависит от пропов:\n * - кастомный компонент/тег из пропа `as` — когда `as` передан и не `disabled`\n * (например, `Link` от `@inertiajs/vue3` или `RouterLink` от Vue Router);\n * - `<a>` — когда задан `href` и не `disabled`;\n * - `<span>` — во всех остальных случаях (включая `disabled`, даже если задан\n * `href`/`as`).\n *\n * Это осознанное решение, чтобы отключённая ссылка не была кликабельной и\n * не участвовала в порядке табуляции. Учтите это в внешних CSS-селекторах.\n *\n * Проп `as` нужен для интеграции с роутерами (Inertia, Vue Router и пр.):\n * стили/поведение GR остаются едиными, а тег корня подменяется. Все\n * специфичные для роутера атрибуты (`method`, `replace`, `preserve-scroll` и т.п.)\n * проходят через fallthrough-attrs.\n */\nimport { computed, markRaw, useAttrs, type Component } from 'vue'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport IconExternal from '~icons/lucide/external-link'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\n\nimport {\n baseRootClass,\n focusRingClass,\n type GrLinkSize,\n type GrLinkTone,\n type GrLinkUnderline,\n type GrLinkVariant,\n grLinkClass,\n grLinkColorStyle,\n} from './grLinkStyles'\n\nexport interface GrLinkProps {\n /**\n * Кастомный корневой тег/компонент. Если передан и компонент не `disabled` —\n * рендерится через `<component :is=\"as\">`. Игнорируется при `disabled`.\n */\n as?: string | Component\n href?: string\n external?: boolean\n target?: string\n rel?: string\n disabled?: boolean\n ariaLabel?: string\n /** Семантический цвет ссылки из палитры `GrTone`. */\n tone?: GrLinkTone\n /** Уровень акцента: `default` (окрашен) или `muted` (приглушён, акцент на hover). */\n variant?: GrLinkVariant\n underline?: GrLinkUnderline\n size?: GrLinkSize\n /**\n * Иконка внешней ссылки. По умолчанию показывается у любой ссылки, которая\n * открывается в новой вкладке, — не только при `external`.\n */\n externalIcon?: boolean\n /** i18n: скрытая подсказка «откроется в новой вкладке». */\n newTabLabel?: string\n}\n\ndefineOptions({\n inheritAttrs: false,\n})\n\nconst props = withDefaults(defineProps<GrLinkProps>(), {\n as: undefined,\n href: undefined,\n external: false,\n target: undefined,\n rel: undefined,\n disabled: false,\n ariaLabel: undefined,\n tone: 'primary',\n variant: 'default',\n underline: 'auto',\n size: undefined,\n externalIcon: undefined,\n newTabLabel: undefined,\n})\n\nconst attrs = useAttrs()\n\n// Кастомный корень имеет приоритет над `<a>` — GR не пытается угадывать\n// «правильный» тег за пользователя, если он явно его указал.\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href))\n\nconst renderAs = computed<string | Component>(() => {\n if (!isInteractive.value) return 'span'\n if (props.as) {\n // Если `as` — объект-компонент, помечаем его как нереактивный, чтобы избежать\n // оверхеда от Vue-прокси и предупреждений в консоли. Строки (нативные теги)\n // оставляем как есть.\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n }\n return 'a'\n})\n\nconst resolvedTarget = computed(() => {\n if (props.target)\n return props.target\n\n if (props.external)\n return '_blank'\n\n return undefined\n})\n\nconst resolvedRel = computed(() => {\n if (props.rel)\n return props.rel\n\n // Авто-защита для любых ссылок, открывающихся в новой вкладке,\n // а не только когда выставлен `external`.\n if (resolvedTarget.value === '_blank')\n return 'noopener noreferrer'\n\n return undefined\n})\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrLink' })\n\nconst { t } = useGranularityTranslations()\n\n/**\n * Смена контекста должна быть объявлена (WCAG 3.2.5). Условие — ссылка реально\n * открывается в новой вкладке, а не наличие пропа `external`: `target=\"_blank\"`\n * снаружи даёт ровно тот же сюрприз (та же генерализация, что у `rel`).\n */\nconst opensInNewTab = computed(() => isInteractive.value && resolvedTarget.value === '_blank')\nconst newTabHint = computed(() => props.newTabLabel ?? t('gr.link.opensInNewTab', 'opens in a new tab'))\n\nconst showExternalIcon = computed(() => props.externalIcon ?? opensInNewTab.value)\n\n/**\n * `aria-label` перекрывает содержимое целиком — вместе со скрытой подсказкой.\n * Поэтому, если имя задано руками, подсказка дописывается к нему.\n */\nconst resolvedAriaLabel = computed(() => {\n if (!props.ariaLabel)\n return undefined\n\n return opensInNewTab.value ? `${props.ariaLabel}, ${newTabHint.value}` : props.ariaLabel\n})\n\nconst iconSize = computed(() => (resolvedSize.value === 'lg' ? 'sm' : 'xs'))\n\nconst rootClass = computed(() => {\n const variantClass = grLinkClass({\n size: resolvedSize.value,\n underline: props.underline,\n disabled: props.disabled,\n })\n\n // На disabled-ветке (`<span>`) focus-ring не нужен: элемент не фокусируется,\n // а если снаружи ему навесят `tabindex`, фокус-рамка на «отключённой» ссылке смотрелась бы странно.\n return props.disabled\n ? `${baseRootClass} ${variantClass}`\n : `${baseRootClass} ${focusRingClass} ${variantClass}`\n})\n\n// Цвет (tone × variant) прокидываем через CSS-переменные, чтобы не плодить классы.\nconst colorStyle = computed(() => grLinkColorStyle({\n tone: props.tone,\n variant: props.variant,\n disabled: props.disabled,\n}))\n</script>\n\n<template>\n <component\n :is=\"renderAs\"\n v-bind=\"attrs\"\n :href=\"isInteractive ? href : undefined\"\n :target=\"isInteractive ? resolvedTarget : undefined\"\n :rel=\"isInteractive ? resolvedRel : undefined\"\n :aria-label=\"resolvedAriaLabel\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n :class=\"rootClass\"\n :style=\"colorStyle\"\n >\n <slot />\n\n <GrIcon v-if=\"showExternalIcon\" :size=\"iconSize\">\n <IconExternal />\n </GrIcon>\n\n <!-- Подсказка не дублируется, когда её уже вобрал `aria-label`. -->\n <span v-if=\"opensInNewTab && !ariaLabel\" class=\"sr-only\">({{ newTabHint }})</span>\n </component>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAoEA,MAAM,QAAQ;EAgBd,MAAM,QAAQ,SAAS;EAIvB,MAAM,gBAAgB,eAAe,CAAC,MAAM,aAAa,CAAC,CAAC,MAAM,MAAM,CAAC,CAAC,MAAM,KAAK;EAEpF,MAAM,WAAW,eAAmC;GAClD,IAAI,CAAC,cAAc,OAAO,OAAO;GACjC,IAAI,MAAM,IAIR,OAAO,OAAO,MAAM,OAAO,WAAW,MAAM,KAAK,QAAQ,MAAM,EAAE;GAEnE,OAAO;EACT,CAAC;EAED,MAAM,iBAAiB,eAAe;GACpC,IAAI,MAAM,QACR,OAAO,MAAM;GAEf,IAAI,MAAM,UACR,OAAO;EAGX,CAAC;EAED,MAAM,cAAc,eAAe;GACjC,IAAI,MAAM,KACR,OAAO,MAAM;GAIf,IAAI,eAAe,UAAU,UAC3B,OAAO;EAGX,CAAC;EAED,MAAM,eAAe,yBAAyB,MAAM,MAAM,EAAE,WAAW,SAAS,CAAC;EAEjF,MAAM,EAAE,MAAM,2BAA2B;;;;;;EAOzC,MAAM,gBAAgB,eAAe,cAAc,SAAS,eAAe,UAAU,QAAQ;EAC7F,MAAM,aAAa,eAAe,MAAM,eAAe,EAAE,yBAAyB,oBAAoB,CAAC;EAEvG,MAAM,mBAAmB,eAAe,MAAM,gBAAgB,cAAc,KAAK;;;;;EAMjF,MAAM,oBAAoB,eAAe;GACvC,IAAI,CAAC,MAAM,WACT,OAAO,KAAA;GAET,OAAO,cAAc,QAAQ,GAAG,MAAM,UAAU,IAAI,WAAW,UAAU,MAAM;EACjF,CAAC;EAED,MAAM,WAAW,eAAgB,aAAa,UAAU,OAAO,OAAO,IAAK;EAE3E,MAAM,YAAY,eAAe;GAC/B,MAAM,eAAe,YAAY;IAC/B,MAAM,aAAa;IACnB,WAAW,MAAM;IACjB,UAAU,MAAM;GAClB,CAAC;GAID,OAAO,MAAM,WACT,GAAG,cAAc,GAAG,iBACpB,GAAG,cAAc,GAAG,eAAe,GAAG;EAC5C,CAAC;EAGD,MAAM,aAAa,eAAe,iBAAiB;GACjD,MAAM,MAAM;GACZ,SAAS,MAAM;GACf,UAAU,MAAM;EAClB,CAAC,CAAC;;uBAIA,YAmBY,wBAlBL,SAAA,KAAQ,GADf,WAEU,MAiBE,KAAA,GAjBG;IACZ,MAAM,cAAA,QAAgB,QAAA,OAAO,KAAA;IAC7B,QAAQ,cAAA,QAAgB,eAAA,QAAiB,KAAA;IACzC,KAAK,cAAA,QAAgB,YAAA,QAAc,KAAA;IACnC,cAAY,kBAAA;IACZ,iBAAe,QAAA,WAAQ,SAAY,KAAA;IACnC,OAAO,UAAA;IACP,OAAO,WAAA;;2BAEA;KAAR,WAAQ,KAAA,QAAA,SAAA;KAEM,iBAAA,SAAA,UAAA,GAAd,YAES,gBAAA;;MAFwB,MAAM,SAAA;;6BACrB,CAAhB,YAAgB,MAAA,qBAAA,CAAA,CAAA,CAAA;;;KAIN,cAAA,SAAa,CAAK,QAAA,aAAA,UAAA,GAA9B,mBAAkF,QAAlF,YAAyD,MAAC,gBAAG,WAAA,KAAU,IAAG,KAAC,CAAA,KAAA,mBAAA,IAAA,IAAA"}
@@ -1,3 +1,3 @@
1
- import { t as GrLink_default } from "./chunks/GrLink-D-cgUMXW.js";
1
+ import { t as GrLink_default } from "./chunks/GrLink-BQb7U4so.js";
2
2
  import { n as grLinkSafelist, t as grLinkConfig } from "../../chunks/config-Cl4ST6Qd.js";
3
3
  export { GrLink_default as GrLink, GrLink_default as default, grLinkConfig, grLinkSafelist };
@@ -1,8 +1,8 @@
1
1
  import { n as useGranularityTranslations } from "../../../chunks/granularityI18n-BC5zsj_d.js";
2
2
  import { useVirtualList } from "../../../composables/useVirtualList.js";
3
3
  import { t as _plugin_vue_export_helper_default } from "../../../chunks/_plugin-vue_export-helper-BOaGB7Aw.js";
4
- import { t as GrSkeleton_default } from "../../GrSkeleton/chunks/GrSkeleton-DEvNE3bC.js";
5
- import { t as GrCard_default } from "../../GrCard/chunks/GrCard-DOrGHf2x.js";
4
+ import { t as GrSkeleton_default } from "../../GrSkeleton/chunks/GrSkeleton-CgfXxPQ2.js";
5
+ import { t as GrCard_default } from "../../GrCard/chunks/GrCard-DfIZOP5N.js";
6
6
  import { n as hasMeaningfulSlotContent } from "../../../chunks/slotNodes-DxNXpC7v.js";
7
7
  import { a as grListItemPaddingClass, c as itemHoverClass, d as itemTitleClass, f as loadingRowClass, i as emptyClass, l as itemInteractiveClass, o as itemDescriptionClass, r as dividedClass, s as itemDisabledClass, u as itemLayoutClass } from "../../../chunks/config-BsuDM3Hb.js";
8
8
  import { Fragment, computed, createBlock, createCommentVNode, createElementBlock, createElementVNode, createTextVNode, createVNode, defineComponent, markRaw, normalizeClass, normalizeStyle, onMounted, onUpdated, openBlock, ref, renderList, renderSlot, resolveDynamicComponent, toDisplayString, unref, useSlots, withCtx } from "vue";
@@ -1 +1 @@
1
- {"version":3,"file":"GrList-4YU1NZtM.js","names":["$slots"],"sources":["../../../../src/components/GrList/GrList.vue","../../../../src/components/GrList/GrList.vue","../../../../src/components/GrList/GrListItem.vue","../../../../src/components/GrList/GrListItem.vue"],"sourcesContent":["<script setup lang=\"ts\" generic=\"T = unknown\">\nimport { computed, onMounted, onUpdated, ref, useSlots, watch } from 'vue'\n\nimport GrCard from '../GrCard'\nimport type { GrCardVariant } from '../GrCard/grCardStyles'\nimport GrSkeleton from '../GrSkeleton/GrSkeleton.vue'\nimport { hasMeaningfulSlotContent } from '../shared/slotNodes'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { useVirtualList, type GrVirtualAlign } from '../../composables/useVirtualList'\n\nimport { dividedClass, emptyClass, loadingRowClass } from './grListStyles'\n\nexport interface GrListProps<TItem = unknown> {\n /**\n * Поверхность списка — вариант карточки под ним. `ghost` убирает рамку и\n * тень: список внутри уже существующей карточки не должен давать вторую.\n */\n variant?: GrCardVariant\n /** Показывать ли горизонтальные разделители между элементами (по умолчанию — да). */\n divided?: boolean\n /** Идёт загрузка: вместо пунктов — строки-скелетоны, контейнер помечен `aria-busy`. */\n loading?: boolean\n /** Сколько строк-заглушек показать при `loading`. */\n loadingRows?: number\n /**\n * Список пуст. По умолчанию определяется сам — по содержимому слота; проп\n * нужен там, где потребитель знает лучше (например, слот заполнен\n * заголовками групп, а данных в них нет).\n */\n empty?: boolean\n /** Текст пустого состояния. Слот `#empty` сильнее. */\n emptyText?: string\n /**\n * Данные списка. С ними пункты рисует слот `#item`, а не слот по умолчанию, —\n * и только так список знает размер набора, то есть может его виртуализировать.\n */\n items?: TItem[]\n /** Ключ пункта для `v-for`: имя поля или функция. Без него — индекс. */\n itemKey?: string | ((item: TItem, index: number) => string | number)\n /** Высота видимой части: контейнер становится скроллером. Число — пиксели. */\n maxHeight?: number | string\n /** Держать в DOM только окно вокруг вьюпорта. Требует `items` и `maxHeight`. */\n virtual?: boolean\n /** Оценка высоты пункта до замера. Уточняется по факту при первом рендере. */\n estimatedItemSize?: number\n}\n\nconst props = withDefaults(defineProps<GrListProps<T>>(), {\n // Дефолт живёт в `GrCard` (и его резолвере `GrConfigProvider`), поэтому здесь\n // остаётся `undefined` — иначе список перебивал бы настройку карточки.\n variant: undefined,\n divided: true,\n loading: false,\n loadingRows: 3,\n empty: undefined,\n emptyText: undefined,\n items: undefined,\n itemKey: undefined,\n maxHeight: undefined,\n virtual: false,\n // Строка обычной плотности с заголовком и описанием.\n estimatedItemSize: 56,\n})\n\nconst slots = useSlots()\nconst { t } = useGranularityTranslations()\n\nconst listEl = ref<HTMLElement | null>(null)\n\nconst resolvedEmptyText = computed(() => props.emptyText ?? t('gr.list.empty', 'Nothing here yet'))\n\nconst dataMode = computed(() => props.items !== undefined)\n\n// Пустоту видно по слоту: `v-for` по пустому массиву оставляет фрагмент без\n// узлов, `v-if` — комментарий, и ни то ни другое пунктом списка не является.\nconst isEmpty = computed(() => {\n if (props.empty !== undefined)\n return props.empty\n\n if (dataMode.value)\n return props.items!.length === 0\n\n return !hasMeaningfulSlotContent(slots.default?.() ?? [])\n})\n\nconst showItems = computed(() => !props.loading && !isEmpty.value)\n\n// Разделители нужны только между пунктами: в пустой и загрузочной ветках они\n// оставили бы висящую линию.\nconst listClass = computed(() => (props.divided && showItems.value ? dividedClass : undefined))\n\nconst loadingRowCount = computed(() => Math.max(1, Math.trunc(props.loadingRows)))\n\nconst virtualEnabled = computed(() => props.virtual && dataMode.value && props.maxHeight !== undefined)\n\nconst virtualizer = useVirtualList({\n container: listEl,\n count: () => (virtualEnabled.value && showItems.value ? props.items!.length : 0),\n // Замена массива сбрасывает замеры; append в тот же массив их сохраняет.\n source: () => props.items,\n itemSize: () => props.estimatedItemSize,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof props.maxHeight === 'number' ? props.maxHeight : undefined),\n})\n\n/** Окно к отрисовке: при выключенной виртуализации — весь набор. */\nconst renderedItems = computed(() => {\n const items = props.items ?? []\n if (!virtualEnabled.value) return items.map((item, index) => ({ item, index }))\n\n const { start, end } = virtualizer.range.value\n return items.slice(start, end).map((item, offset) => ({ item, index: start + offset }))\n})\n\nfunction keyOf(item: T, index: number): string | number {\n const key = props.itemKey\n if (typeof key === 'function') return key(item, index)\n if (typeof key === 'string') return (item as Record<string, unknown>)[key] as string | number\n\n return index\n}\n\n/**\n * ARIA-набор для пункта.\n *\n * Только в виртуальном режиме: в DOM тогда неполный набор, и без этих атрибутов\n * диктор объявил бы «7 из 20» на списке в пять тысяч. Когда набор в DOM целиком,\n * его размер и позицию браузер считает сам, а руками проставленные атрибуты\n * начинают расходиться с разметкой при любой фильтрации.\n */\nfunction ariaOf(index: number): Record<string, number> {\n if (!virtualEnabled.value) return {}\n\n return { 'aria-setsize': props.items!.length, 'aria-posinset': index + 1 }\n}\n\nconst maxHeightStyle = computed(() => {\n const value = props.maxHeight\n if (value == null) return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst listStyle = computed(() => {\n if (props.maxHeight === undefined) return undefined\n\n const scroller = { overflowY: 'auto' as const, maxHeight: maxHeightStyle.value }\n if (!virtualEnabled.value) return scroller\n\n return { ...scroller, ...virtualizer.spacerStyle.value }\n})\n\n/**\n * Замер отрисованных пунктов.\n *\n * Идёт по детям контейнера, а не по `ref` на элементе: пункт рисует слот\n * потребителя, привязать к нему `ref` неоткуда. В виртуальном режиме прямые\n * дети контейнера — ровно окно (распорки живут псевдоэлементами и детьми не\n * считаются), поэтому сопоставление по позиции однозначно.\n */\nfunction measureRendered(): void {\n if (!virtualEnabled.value) return\n // В состояниях loading/empty дети контейнера — скелетоны и заглушки: их\n // высоты записались бы в замеры под индексами будущих строк данных.\n if (!showItems.value) return\n\n const container = listEl.value\n if (!container) return\n\n const { start } = virtualizer.range.value\n const children = container.children\n for (let offset = 0; offset < children.length; offset++) {\n virtualizer.measure(start + offset, children[offset])\n }\n}\n\nonMounted(measureRendered)\nonUpdated(measureRendered)\n\nfunction scrollToIndex(index: number, align?: GrVirtualAlign): void {\n virtualizer.scrollToIndex(index, align)\n}\n\ndefineExpose({ scrollToIndex })\n\nif (import.meta.env?.DEV) {\n watch(\n () => [props.virtual, dataMode.value, props.maxHeight] as const,\n ([virtual, hasItems, maxHeight]) => {\n if (!virtual) return\n\n if (!hasItems) {\n console.warn(\n '[granularity] GrList: `virtual` требует `items` — пункты из слота по умолчанию '\n + 'список не считает и резать окно ему не из чего.',\n )\n }\n else if (maxHeight === undefined) {\n console.warn(\n '[granularity] GrList: `virtual` требует `maxHeight` — без ограничения высоты '\n + 'вьюпорта нет, и в окно попадает весь набор.',\n )\n }\n },\n { immediate: true },\n )\n\n watch(\n () => [dataMode.value, Boolean(slots.item)] as const,\n ([hasItems, hasSlot]) => {\n if (hasItems && !hasSlot) {\n console.warn(\n '[granularity] GrList: с `items` пункты рисует слот `#item` — без него список пуст.',\n )\n }\n },\n { immediate: true },\n )\n\n onMounted(() => {\n if (!virtualEnabled.value) return\n\n const first = listEl.value?.firstElementChild\n if (first && !first.hasAttribute('aria-posinset')) {\n console.warn(\n '[granularity] GrList: при `virtual` пункты обязаны нести `aria-setsize`/`aria-posinset` — '\n + 'пробросьте `aria` из слота `#item`: <GrListItem v-bind=\"aria\" … />. Иначе диктор '\n + 'посчитает набор по отрисованному окну.',\n )\n }\n })\n}\n</script>\n\n<template>\n <GrCard :variant=\"variant\">\n <div\n ref=\"listEl\"\n data-gr-list\n role=\"list\"\n :class=\"listClass\"\n :style=\"listStyle\"\n :tabindex=\"maxHeight === undefined ? undefined : 0\"\n :data-gr-virtual=\"virtualEnabled ? '' : undefined\"\n :aria-busy=\"loading ? 'true' : undefined\"\n >\n <template v-if=\"loading\">\n <slot name=\"loading\">\n <div\n v-for=\"row in loadingRowCount\"\n :key=\"row\"\n data-gr-list-loading-row\n :class=\"loadingRowClass\"\n >\n <GrSkeleton />\n </div>\n </slot>\n </template>\n\n <div\n v-else-if=\"isEmpty\"\n data-gr-list-empty\n :class=\"emptyClass\"\n >\n <slot name=\"empty\">\n {{ resolvedEmptyText }}\n </slot>\n </div>\n\n <template v-else-if=\"dataMode\">\n <template\n v-for=\"entry in renderedItems\"\n :key=\"keyOf(entry.item, entry.index)\"\n >\n <slot\n name=\"item\"\n :item=\"entry.item\"\n :index=\"entry.index\"\n :aria=\"ariaOf(entry.index)\"\n />\n </template>\n </template>\n\n <slot v-else />\n </div>\n </GrCard>\n</template>\n\n<style scoped>\n/* Срезанное сверху и снизу держат псевдоэлементы контейнера: их не за что\n размонтировать, в дереве доступности их нет, а высота приезжает переменными\n в том же патче, что и пункты. Почему не отступы контейнера и не поля крайних\n пунктов — `docs/virtual-list.md`. */\n[data-gr-virtual]::before,\n[data-gr-virtual]::after {\n content: '';\n display: block;\n flex: none;\n}\n\n[data-gr-virtual]::before {\n height: var(--gr-virtual-before, 0px);\n}\n\n[data-gr-virtual]::after {\n height: var(--gr-virtual-after, 0px);\n}\n</style>\n","<script setup lang=\"ts\" generic=\"T = unknown\">\nimport { computed, onMounted, onUpdated, ref, useSlots, watch } from 'vue'\n\nimport GrCard from '../GrCard'\nimport type { GrCardVariant } from '../GrCard/grCardStyles'\nimport GrSkeleton from '../GrSkeleton/GrSkeleton.vue'\nimport { hasMeaningfulSlotContent } from '../shared/slotNodes'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { useVirtualList, type GrVirtualAlign } from '../../composables/useVirtualList'\n\nimport { dividedClass, emptyClass, loadingRowClass } from './grListStyles'\n\nexport interface GrListProps<TItem = unknown> {\n /**\n * Поверхность списка — вариант карточки под ним. `ghost` убирает рамку и\n * тень: список внутри уже существующей карточки не должен давать вторую.\n */\n variant?: GrCardVariant\n /** Показывать ли горизонтальные разделители между элементами (по умолчанию — да). */\n divided?: boolean\n /** Идёт загрузка: вместо пунктов — строки-скелетоны, контейнер помечен `aria-busy`. */\n loading?: boolean\n /** Сколько строк-заглушек показать при `loading`. */\n loadingRows?: number\n /**\n * Список пуст. По умолчанию определяется сам — по содержимому слота; проп\n * нужен там, где потребитель знает лучше (например, слот заполнен\n * заголовками групп, а данных в них нет).\n */\n empty?: boolean\n /** Текст пустого состояния. Слот `#empty` сильнее. */\n emptyText?: string\n /**\n * Данные списка. С ними пункты рисует слот `#item`, а не слот по умолчанию, —\n * и только так список знает размер набора, то есть может его виртуализировать.\n */\n items?: TItem[]\n /** Ключ пункта для `v-for`: имя поля или функция. Без него — индекс. */\n itemKey?: string | ((item: TItem, index: number) => string | number)\n /** Высота видимой части: контейнер становится скроллером. Число — пиксели. */\n maxHeight?: number | string\n /** Держать в DOM только окно вокруг вьюпорта. Требует `items` и `maxHeight`. */\n virtual?: boolean\n /** Оценка высоты пункта до замера. Уточняется по факту при первом рендере. */\n estimatedItemSize?: number\n}\n\nconst props = withDefaults(defineProps<GrListProps<T>>(), {\n // Дефолт живёт в `GrCard` (и его резолвере `GrConfigProvider`), поэтому здесь\n // остаётся `undefined` — иначе список перебивал бы настройку карточки.\n variant: undefined,\n divided: true,\n loading: false,\n loadingRows: 3,\n empty: undefined,\n emptyText: undefined,\n items: undefined,\n itemKey: undefined,\n maxHeight: undefined,\n virtual: false,\n // Строка обычной плотности с заголовком и описанием.\n estimatedItemSize: 56,\n})\n\nconst slots = useSlots()\nconst { t } = useGranularityTranslations()\n\nconst listEl = ref<HTMLElement | null>(null)\n\nconst resolvedEmptyText = computed(() => props.emptyText ?? t('gr.list.empty', 'Nothing here yet'))\n\nconst dataMode = computed(() => props.items !== undefined)\n\n// Пустоту видно по слоту: `v-for` по пустому массиву оставляет фрагмент без\n// узлов, `v-if` — комментарий, и ни то ни другое пунктом списка не является.\nconst isEmpty = computed(() => {\n if (props.empty !== undefined)\n return props.empty\n\n if (dataMode.value)\n return props.items!.length === 0\n\n return !hasMeaningfulSlotContent(slots.default?.() ?? [])\n})\n\nconst showItems = computed(() => !props.loading && !isEmpty.value)\n\n// Разделители нужны только между пунктами: в пустой и загрузочной ветках они\n// оставили бы висящую линию.\nconst listClass = computed(() => (props.divided && showItems.value ? dividedClass : undefined))\n\nconst loadingRowCount = computed(() => Math.max(1, Math.trunc(props.loadingRows)))\n\nconst virtualEnabled = computed(() => props.virtual && dataMode.value && props.maxHeight !== undefined)\n\nconst virtualizer = useVirtualList({\n container: listEl,\n count: () => (virtualEnabled.value && showItems.value ? props.items!.length : 0),\n // Замена массива сбрасывает замеры; append в тот же массив их сохраняет.\n source: () => props.items,\n itemSize: () => props.estimatedItemSize,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof props.maxHeight === 'number' ? props.maxHeight : undefined),\n})\n\n/** Окно к отрисовке: при выключенной виртуализации — весь набор. */\nconst renderedItems = computed(() => {\n const items = props.items ?? []\n if (!virtualEnabled.value) return items.map((item, index) => ({ item, index }))\n\n const { start, end } = virtualizer.range.value\n return items.slice(start, end).map((item, offset) => ({ item, index: start + offset }))\n})\n\nfunction keyOf(item: T, index: number): string | number {\n const key = props.itemKey\n if (typeof key === 'function') return key(item, index)\n if (typeof key === 'string') return (item as Record<string, unknown>)[key] as string | number\n\n return index\n}\n\n/**\n * ARIA-набор для пункта.\n *\n * Только в виртуальном режиме: в DOM тогда неполный набор, и без этих атрибутов\n * диктор объявил бы «7 из 20» на списке в пять тысяч. Когда набор в DOM целиком,\n * его размер и позицию браузер считает сам, а руками проставленные атрибуты\n * начинают расходиться с разметкой при любой фильтрации.\n */\nfunction ariaOf(index: number): Record<string, number> {\n if (!virtualEnabled.value) return {}\n\n return { 'aria-setsize': props.items!.length, 'aria-posinset': index + 1 }\n}\n\nconst maxHeightStyle = computed(() => {\n const value = props.maxHeight\n if (value == null) return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst listStyle = computed(() => {\n if (props.maxHeight === undefined) return undefined\n\n const scroller = { overflowY: 'auto' as const, maxHeight: maxHeightStyle.value }\n if (!virtualEnabled.value) return scroller\n\n return { ...scroller, ...virtualizer.spacerStyle.value }\n})\n\n/**\n * Замер отрисованных пунктов.\n *\n * Идёт по детям контейнера, а не по `ref` на элементе: пункт рисует слот\n * потребителя, привязать к нему `ref` неоткуда. В виртуальном режиме прямые\n * дети контейнера — ровно окно (распорки живут псевдоэлементами и детьми не\n * считаются), поэтому сопоставление по позиции однозначно.\n */\nfunction measureRendered(): void {\n if (!virtualEnabled.value) return\n // В состояниях loading/empty дети контейнера — скелетоны и заглушки: их\n // высоты записались бы в замеры под индексами будущих строк данных.\n if (!showItems.value) return\n\n const container = listEl.value\n if (!container) return\n\n const { start } = virtualizer.range.value\n const children = container.children\n for (let offset = 0; offset < children.length; offset++) {\n virtualizer.measure(start + offset, children[offset])\n }\n}\n\nonMounted(measureRendered)\nonUpdated(measureRendered)\n\nfunction scrollToIndex(index: number, align?: GrVirtualAlign): void {\n virtualizer.scrollToIndex(index, align)\n}\n\ndefineExpose({ scrollToIndex })\n\nif (import.meta.env?.DEV) {\n watch(\n () => [props.virtual, dataMode.value, props.maxHeight] as const,\n ([virtual, hasItems, maxHeight]) => {\n if (!virtual) return\n\n if (!hasItems) {\n console.warn(\n '[granularity] GrList: `virtual` требует `items` — пункты из слота по умолчанию '\n + 'список не считает и резать окно ему не из чего.',\n )\n }\n else if (maxHeight === undefined) {\n console.warn(\n '[granularity] GrList: `virtual` требует `maxHeight` — без ограничения высоты '\n + 'вьюпорта нет, и в окно попадает весь набор.',\n )\n }\n },\n { immediate: true },\n )\n\n watch(\n () => [dataMode.value, Boolean(slots.item)] as const,\n ([hasItems, hasSlot]) => {\n if (hasItems && !hasSlot) {\n console.warn(\n '[granularity] GrList: с `items` пункты рисует слот `#item` — без него список пуст.',\n )\n }\n },\n { immediate: true },\n )\n\n onMounted(() => {\n if (!virtualEnabled.value) return\n\n const first = listEl.value?.firstElementChild\n if (first && !first.hasAttribute('aria-posinset')) {\n console.warn(\n '[granularity] GrList: при `virtual` пункты обязаны нести `aria-setsize`/`aria-posinset` — '\n + 'пробросьте `aria` из слота `#item`: <GrListItem v-bind=\"aria\" … />. Иначе диктор '\n + 'посчитает набор по отрисованному окну.',\n )\n }\n })\n}\n</script>\n\n<template>\n <GrCard :variant=\"variant\">\n <div\n ref=\"listEl\"\n data-gr-list\n role=\"list\"\n :class=\"listClass\"\n :style=\"listStyle\"\n :tabindex=\"maxHeight === undefined ? undefined : 0\"\n :data-gr-virtual=\"virtualEnabled ? '' : undefined\"\n :aria-busy=\"loading ? 'true' : undefined\"\n >\n <template v-if=\"loading\">\n <slot name=\"loading\">\n <div\n v-for=\"row in loadingRowCount\"\n :key=\"row\"\n data-gr-list-loading-row\n :class=\"loadingRowClass\"\n >\n <GrSkeleton />\n </div>\n </slot>\n </template>\n\n <div\n v-else-if=\"isEmpty\"\n data-gr-list-empty\n :class=\"emptyClass\"\n >\n <slot name=\"empty\">\n {{ resolvedEmptyText }}\n </slot>\n </div>\n\n <template v-else-if=\"dataMode\">\n <template\n v-for=\"entry in renderedItems\"\n :key=\"keyOf(entry.item, entry.index)\"\n >\n <slot\n name=\"item\"\n :item=\"entry.item\"\n :index=\"entry.index\"\n :aria=\"ariaOf(entry.index)\"\n />\n </template>\n </template>\n\n <slot v-else />\n </div>\n </GrCard>\n</template>\n\n<style scoped>\n/* Срезанное сверху и снизу держат псевдоэлементы контейнера: их не за что\n размонтировать, в дереве доступности их нет, а высота приезжает переменными\n в том же патче, что и пункты. Почему не отступы контейнера и не поля крайних\n пунктов — `docs/virtual-list.md`. */\n[data-gr-virtual]::before,\n[data-gr-virtual]::after {\n content: '';\n display: block;\n flex: none;\n}\n\n[data-gr-virtual]::before {\n height: var(--gr-virtual-before, 0px);\n}\n\n[data-gr-virtual]::after {\n height: var(--gr-virtual-after, 0px);\n}\n</style>\n","<script setup lang=\"ts\">\nimport { computed, markRaw, useSlots, watch, type Component } from 'vue'\n\nimport {\n grListItemPaddingClass,\n itemDescriptionClass,\n itemDisabledClass,\n itemHoverClass,\n itemInteractiveClass,\n itemLayoutClass,\n itemTitleClass,\n type GrListItemDensity,\n} from './grListStyles'\n\nexport type { GrListItemDensity } from './grListStyles'\n\nexport interface GrListItemProps {\n /** Заголовок строки. Если передан слот `#title`, проп игнорируется. */\n title?: string\n /** Описание под заголовком. Если передан слот `#description`, проп игнорируется. */\n description?: string\n /** Плотность вертикальных отступов: `regular` — 12px, `compact` — 8px. */\n density?: GrListItemDensity\n /** Ссылка: строка становится `<a>`. */\n href?: string\n /** Свой корневой тег строки (`RouterLink`, `Link` от Inertia). Сильнее `href`. */\n as?: string | Component\n /** Кликабельная строка без ссылки — `<button>` с событием `click`. */\n clickable?: boolean\n /** Подсветка при наведении без интерактивности. */\n hoverable?: boolean\n disabled?: boolean\n}\n\nexport interface GrListItemEmits {\n (e: 'click', event: MouseEvent): void\n}\n\nconst props = withDefaults(defineProps<GrListItemProps>(), {\n title: undefined,\n description: undefined,\n density: 'regular',\n href: undefined,\n as: undefined,\n clickable: false,\n hoverable: false,\n disabled: false,\n})\n\nconst emit = defineEmits<GrListItemEmits>()\n\nconst slots = useSlots()\n\nconst hasTitle = computed(() => !!slots.title || !!props.title)\nconst hasDescription = computed(() => !!slots.description || !!props.description)\n\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href || props.clickable))\n\n/**\n * `role=\"listitem\"` остаётся на обёртке, а строка целиком — вложенный элемент:\n * `<a role=\"listitem\">` потерял бы роль ссылки, а интерактив снаружи разорвал бы\n * связку `list` → `listitem`. Обычная строка идёт по той же схеме, чтобы\n * разметка содержимого была написана один раз, а не по копии на ветку.\n */\nconst rowTag = computed<string | Component>(() => {\n if (!isInteractive.value)\n return 'div'\n\n if (props.as)\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n\n return props.href ? 'a' : 'button'\n})\n\nconst rowClass = computed(() => [\n itemLayoutClass,\n grListItemPaddingClass(props.density),\n isInteractive.value ? `${itemInteractiveClass} ${itemHoverClass}` : '',\n !isInteractive.value && props.hoverable && !props.disabled ? itemHoverClass : '',\n props.disabled ? itemDisabledClass : '',\n].filter(Boolean).join(' '))\n\nfunction onClick(event: MouseEvent): void {\n // `disabled` сюда попадает вместе с обычной строкой: и то и другое —\n // не-интерактив, а кликов не эмитит ни один.\n if (!isInteractive.value)\n return\n\n emit('click', event)\n}\n\n/** Теги, попадающие в таб-порядок сами. `<a>` — только со ссылкой. */\nfunction isFocusableTag(tag: string): boolean {\n return tag === 'button' || (tag === 'a' && !!props.href)\n}\n\nif (import.meta.env?.DEV) {\n watch(\n () => [isInteractive.value, props.as] as const,\n ([interactive, as]) => {\n // Компонент из `as` (`RouterLink`, Inertia `Link`) рендерит `<a>`, но узнать\n // это до рендера нельзя — предупреждаем только по явно названному тегу.\n if (!interactive || typeof as !== 'string' || isFocusableTag(as)) return\n\n console.warn(\n `[granularity] GrListItem: as=\"${as}\" не попадает в таб-порядок — строка кликается `\n + 'мышью, но не с клавиатуры. Возьмите тег, умеющий фокус (`button`, `a` со ссылкой), '\n + 'или компонент роутера.',\n )\n },\n { immediate: true },\n )\n}\n</script>\n\n<template>\n <div\n data-gr-list-item\n role=\"listitem\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n >\n <component\n :is=\"rowTag\"\n :data-gr-list-item-action=\"isInteractive ? '' : undefined\"\n :type=\"rowTag === 'button' ? 'button' : undefined\"\n :href=\"isInteractive ? href : undefined\"\n :class=\"rowClass\"\n @click=\"onClick\"\n >\n <div v-if=\"$slots.prefix\" class=\"shrink-0\">\n <slot name=\"prefix\" />\n </div>\n <div class=\"min-w-0 flex-1\">\n <div v-if=\"hasTitle\" :class=\"itemTitleClass\">\n <slot name=\"title\">\n{{ title }}\n</slot>\n </div>\n <div\n v-if=\"hasDescription\"\n :class=\"itemDescriptionClass\"\n >\n <slot name=\"description\">\n{{ description }}\n</slot>\n </div>\n </div>\n <div v-if=\"$slots.default\" class=\"shrink-0\">\n <slot />\n </div>\n </component>\n </div>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, markRaw, useSlots, watch, type Component } from 'vue'\n\nimport {\n grListItemPaddingClass,\n itemDescriptionClass,\n itemDisabledClass,\n itemHoverClass,\n itemInteractiveClass,\n itemLayoutClass,\n itemTitleClass,\n type GrListItemDensity,\n} from './grListStyles'\n\nexport type { GrListItemDensity } from './grListStyles'\n\nexport interface GrListItemProps {\n /** Заголовок строки. Если передан слот `#title`, проп игнорируется. */\n title?: string\n /** Описание под заголовком. Если передан слот `#description`, проп игнорируется. */\n description?: string\n /** Плотность вертикальных отступов: `regular` — 12px, `compact` — 8px. */\n density?: GrListItemDensity\n /** Ссылка: строка становится `<a>`. */\n href?: string\n /** Свой корневой тег строки (`RouterLink`, `Link` от Inertia). Сильнее `href`. */\n as?: string | Component\n /** Кликабельная строка без ссылки — `<button>` с событием `click`. */\n clickable?: boolean\n /** Подсветка при наведении без интерактивности. */\n hoverable?: boolean\n disabled?: boolean\n}\n\nexport interface GrListItemEmits {\n (e: 'click', event: MouseEvent): void\n}\n\nconst props = withDefaults(defineProps<GrListItemProps>(), {\n title: undefined,\n description: undefined,\n density: 'regular',\n href: undefined,\n as: undefined,\n clickable: false,\n hoverable: false,\n disabled: false,\n})\n\nconst emit = defineEmits<GrListItemEmits>()\n\nconst slots = useSlots()\n\nconst hasTitle = computed(() => !!slots.title || !!props.title)\nconst hasDescription = computed(() => !!slots.description || !!props.description)\n\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href || props.clickable))\n\n/**\n * `role=\"listitem\"` остаётся на обёртке, а строка целиком — вложенный элемент:\n * `<a role=\"listitem\">` потерял бы роль ссылки, а интерактив снаружи разорвал бы\n * связку `list` → `listitem`. Обычная строка идёт по той же схеме, чтобы\n * разметка содержимого была написана один раз, а не по копии на ветку.\n */\nconst rowTag = computed<string | Component>(() => {\n if (!isInteractive.value)\n return 'div'\n\n if (props.as)\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n\n return props.href ? 'a' : 'button'\n})\n\nconst rowClass = computed(() => [\n itemLayoutClass,\n grListItemPaddingClass(props.density),\n isInteractive.value ? `${itemInteractiveClass} ${itemHoverClass}` : '',\n !isInteractive.value && props.hoverable && !props.disabled ? itemHoverClass : '',\n props.disabled ? itemDisabledClass : '',\n].filter(Boolean).join(' '))\n\nfunction onClick(event: MouseEvent): void {\n // `disabled` сюда попадает вместе с обычной строкой: и то и другое —\n // не-интерактив, а кликов не эмитит ни один.\n if (!isInteractive.value)\n return\n\n emit('click', event)\n}\n\n/** Теги, попадающие в таб-порядок сами. `<a>` — только со ссылкой. */\nfunction isFocusableTag(tag: string): boolean {\n return tag === 'button' || (tag === 'a' && !!props.href)\n}\n\nif (import.meta.env?.DEV) {\n watch(\n () => [isInteractive.value, props.as] as const,\n ([interactive, as]) => {\n // Компонент из `as` (`RouterLink`, Inertia `Link`) рендерит `<a>`, но узнать\n // это до рендера нельзя — предупреждаем только по явно названному тегу.\n if (!interactive || typeof as !== 'string' || isFocusableTag(as)) return\n\n console.warn(\n `[granularity] GrListItem: as=\"${as}\" не попадает в таб-порядок — строка кликается `\n + 'мышью, но не с клавиатуры. Возьмите тег, умеющий фокус (`button`, `a` со ссылкой), '\n + 'или компонент роутера.',\n )\n },\n { immediate: true },\n )\n}\n</script>\n\n<template>\n <div\n data-gr-list-item\n role=\"listitem\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n >\n <component\n :is=\"rowTag\"\n :data-gr-list-item-action=\"isInteractive ? '' : undefined\"\n :type=\"rowTag === 'button' ? 'button' : undefined\"\n :href=\"isInteractive ? href : undefined\"\n :class=\"rowClass\"\n @click=\"onClick\"\n >\n <div v-if=\"$slots.prefix\" class=\"shrink-0\">\n <slot name=\"prefix\" />\n </div>\n <div class=\"min-w-0 flex-1\">\n <div v-if=\"hasTitle\" :class=\"itemTitleClass\">\n <slot name=\"title\">\n{{ title }}\n</slot>\n </div>\n <div\n v-if=\"hasDescription\"\n :class=\"itemDescriptionClass\"\n >\n <slot name=\"description\">\n{{ description }}\n</slot>\n </div>\n </div>\n <div v-if=\"$slots.default\" class=\"shrink-0\">\n <slot />\n </div>\n </component>\n </div>\n</template>\n"],"mappings":"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"}
1
+ {"version":3,"file":"GrList-CHibO0xA.js","names":["$slots"],"sources":["../../../../src/components/GrList/GrList.vue","../../../../src/components/GrList/GrList.vue","../../../../src/components/GrList/GrListItem.vue","../../../../src/components/GrList/GrListItem.vue"],"sourcesContent":["<script setup lang=\"ts\" generic=\"T = unknown\">\nimport { computed, onMounted, onUpdated, ref, useSlots, watch } from 'vue'\n\nimport GrCard from '../GrCard'\nimport type { GrCardVariant } from '../GrCard/grCardStyles'\nimport GrSkeleton from '../GrSkeleton/GrSkeleton.vue'\nimport { hasMeaningfulSlotContent } from '../shared/slotNodes'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { useVirtualList, type GrVirtualAlign } from '../../composables/useVirtualList'\n\nimport { dividedClass, emptyClass, loadingRowClass } from './grListStyles'\n\nexport interface GrListProps<TItem = unknown> {\n /**\n * Поверхность списка — вариант карточки под ним. `ghost` убирает рамку и\n * тень: список внутри уже существующей карточки не должен давать вторую.\n */\n variant?: GrCardVariant\n /** Показывать ли горизонтальные разделители между элементами (по умолчанию — да). */\n divided?: boolean\n /** Идёт загрузка: вместо пунктов — строки-скелетоны, контейнер помечен `aria-busy`. */\n loading?: boolean\n /** Сколько строк-заглушек показать при `loading`. */\n loadingRows?: number\n /**\n * Список пуст. По умолчанию определяется сам — по содержимому слота; проп\n * нужен там, где потребитель знает лучше (например, слот заполнен\n * заголовками групп, а данных в них нет).\n */\n empty?: boolean\n /** Текст пустого состояния. Слот `#empty` сильнее. */\n emptyText?: string\n /**\n * Данные списка. С ними пункты рисует слот `#item`, а не слот по умолчанию, —\n * и только так список знает размер набора, то есть может его виртуализировать.\n */\n items?: TItem[]\n /** Ключ пункта для `v-for`: имя поля или функция. Без него — индекс. */\n itemKey?: string | ((item: TItem, index: number) => string | number)\n /** Высота видимой части: контейнер становится скроллером. Число — пиксели. */\n maxHeight?: number | string\n /** Держать в DOM только окно вокруг вьюпорта. Требует `items` и `maxHeight`. */\n virtual?: boolean\n /** Оценка высоты пункта до замера. Уточняется по факту при первом рендере. */\n estimatedItemSize?: number\n}\n\nconst props = withDefaults(defineProps<GrListProps<T>>(), {\n // Дефолт живёт в `GrCard` (и его резолвере `GrConfigProvider`), поэтому здесь\n // остаётся `undefined` — иначе список перебивал бы настройку карточки.\n variant: undefined,\n divided: true,\n loading: false,\n loadingRows: 3,\n empty: undefined,\n emptyText: undefined,\n items: undefined,\n itemKey: undefined,\n maxHeight: undefined,\n virtual: false,\n // Строка обычной плотности с заголовком и описанием.\n estimatedItemSize: 56,\n})\n\nconst slots = useSlots()\nconst { t } = useGranularityTranslations()\n\nconst listEl = ref<HTMLElement | null>(null)\n\nconst resolvedEmptyText = computed(() => props.emptyText ?? t('gr.list.empty', 'Nothing here yet'))\n\nconst dataMode = computed(() => props.items !== undefined)\n\n// Пустоту видно по слоту: `v-for` по пустому массиву оставляет фрагмент без\n// узлов, `v-if` — комментарий, и ни то ни другое пунктом списка не является.\nconst isEmpty = computed(() => {\n if (props.empty !== undefined)\n return props.empty\n\n if (dataMode.value)\n return props.items!.length === 0\n\n return !hasMeaningfulSlotContent(slots.default?.() ?? [])\n})\n\nconst showItems = computed(() => !props.loading && !isEmpty.value)\n\n// Разделители нужны только между пунктами: в пустой и загрузочной ветках они\n// оставили бы висящую линию.\nconst listClass = computed(() => (props.divided && showItems.value ? dividedClass : undefined))\n\nconst loadingRowCount = computed(() => Math.max(1, Math.trunc(props.loadingRows)))\n\nconst virtualEnabled = computed(() => props.virtual && dataMode.value && props.maxHeight !== undefined)\n\nconst virtualizer = useVirtualList({\n container: listEl,\n count: () => (virtualEnabled.value && showItems.value ? props.items!.length : 0),\n // Замена массива сбрасывает замеры; append в тот же массив их сохраняет.\n source: () => props.items,\n itemSize: () => props.estimatedItemSize,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof props.maxHeight === 'number' ? props.maxHeight : undefined),\n})\n\n/** Окно к отрисовке: при выключенной виртуализации — весь набор. */\nconst renderedItems = computed(() => {\n const items = props.items ?? []\n if (!virtualEnabled.value) return items.map((item, index) => ({ item, index }))\n\n const { start, end } = virtualizer.range.value\n return items.slice(start, end).map((item, offset) => ({ item, index: start + offset }))\n})\n\nfunction keyOf(item: T, index: number): string | number {\n const key = props.itemKey\n if (typeof key === 'function') return key(item, index)\n if (typeof key === 'string') return (item as Record<string, unknown>)[key] as string | number\n\n return index\n}\n\n/**\n * ARIA-набор для пункта.\n *\n * Только в виртуальном режиме: в DOM тогда неполный набор, и без этих атрибутов\n * диктор объявил бы «7 из 20» на списке в пять тысяч. Когда набор в DOM целиком,\n * его размер и позицию браузер считает сам, а руками проставленные атрибуты\n * начинают расходиться с разметкой при любой фильтрации.\n */\nfunction ariaOf(index: number): Record<string, number> {\n if (!virtualEnabled.value) return {}\n\n return { 'aria-setsize': props.items!.length, 'aria-posinset': index + 1 }\n}\n\nconst maxHeightStyle = computed(() => {\n const value = props.maxHeight\n if (value == null) return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst listStyle = computed(() => {\n if (props.maxHeight === undefined) return undefined\n\n const scroller = { overflowY: 'auto' as const, maxHeight: maxHeightStyle.value }\n if (!virtualEnabled.value) return scroller\n\n return { ...scroller, ...virtualizer.spacerStyle.value }\n})\n\n/**\n * Замер отрисованных пунктов.\n *\n * Идёт по детям контейнера, а не по `ref` на элементе: пункт рисует слот\n * потребителя, привязать к нему `ref` неоткуда. В виртуальном режиме прямые\n * дети контейнера — ровно окно (распорки живут псевдоэлементами и детьми не\n * считаются), поэтому сопоставление по позиции однозначно.\n */\nfunction measureRendered(): void {\n if (!virtualEnabled.value) return\n // В состояниях loading/empty дети контейнера — скелетоны и заглушки: их\n // высоты записались бы в замеры под индексами будущих строк данных.\n if (!showItems.value) return\n\n const container = listEl.value\n if (!container) return\n\n const { start } = virtualizer.range.value\n const children = container.children\n for (let offset = 0; offset < children.length; offset++) {\n virtualizer.measure(start + offset, children[offset])\n }\n}\n\nonMounted(measureRendered)\nonUpdated(measureRendered)\n\nfunction scrollToIndex(index: number, align?: GrVirtualAlign): void {\n virtualizer.scrollToIndex(index, align)\n}\n\ndefineExpose({ scrollToIndex })\n\nif (import.meta.env?.DEV) {\n watch(\n () => [props.virtual, dataMode.value, props.maxHeight] as const,\n ([virtual, hasItems, maxHeight]) => {\n if (!virtual) return\n\n if (!hasItems) {\n console.warn(\n '[granularity] GrList: `virtual` требует `items` — пункты из слота по умолчанию '\n + 'список не считает и резать окно ему не из чего.',\n )\n }\n else if (maxHeight === undefined) {\n console.warn(\n '[granularity] GrList: `virtual` требует `maxHeight` — без ограничения высоты '\n + 'вьюпорта нет, и в окно попадает весь набор.',\n )\n }\n },\n { immediate: true },\n )\n\n watch(\n () => [dataMode.value, Boolean(slots.item)] as const,\n ([hasItems, hasSlot]) => {\n if (hasItems && !hasSlot) {\n console.warn(\n '[granularity] GrList: с `items` пункты рисует слот `#item` — без него список пуст.',\n )\n }\n },\n { immediate: true },\n )\n\n onMounted(() => {\n if (!virtualEnabled.value) return\n\n const first = listEl.value?.firstElementChild\n if (first && !first.hasAttribute('aria-posinset')) {\n console.warn(\n '[granularity] GrList: при `virtual` пункты обязаны нести `aria-setsize`/`aria-posinset` — '\n + 'пробросьте `aria` из слота `#item`: <GrListItem v-bind=\"aria\" … />. Иначе диктор '\n + 'посчитает набор по отрисованному окну.',\n )\n }\n })\n}\n</script>\n\n<template>\n <GrCard :variant=\"variant\">\n <div\n ref=\"listEl\"\n data-gr-list\n role=\"list\"\n :class=\"listClass\"\n :style=\"listStyle\"\n :tabindex=\"maxHeight === undefined ? undefined : 0\"\n :data-gr-virtual=\"virtualEnabled ? '' : undefined\"\n :aria-busy=\"loading ? 'true' : undefined\"\n >\n <template v-if=\"loading\">\n <slot name=\"loading\">\n <div\n v-for=\"row in loadingRowCount\"\n :key=\"row\"\n data-gr-list-loading-row\n :class=\"loadingRowClass\"\n >\n <GrSkeleton />\n </div>\n </slot>\n </template>\n\n <div\n v-else-if=\"isEmpty\"\n data-gr-list-empty\n :class=\"emptyClass\"\n >\n <slot name=\"empty\">\n {{ resolvedEmptyText }}\n </slot>\n </div>\n\n <template v-else-if=\"dataMode\">\n <template\n v-for=\"entry in renderedItems\"\n :key=\"keyOf(entry.item, entry.index)\"\n >\n <slot\n name=\"item\"\n :item=\"entry.item\"\n :index=\"entry.index\"\n :aria=\"ariaOf(entry.index)\"\n />\n </template>\n </template>\n\n <slot v-else />\n </div>\n </GrCard>\n</template>\n\n<style scoped>\n/* Срезанное сверху и снизу держат псевдоэлементы контейнера: их не за что\n размонтировать, в дереве доступности их нет, а высота приезжает переменными\n в том же патче, что и пункты. Почему не отступы контейнера и не поля крайних\n пунктов — `docs/virtual-list.md`. */\n[data-gr-virtual]::before,\n[data-gr-virtual]::after {\n content: '';\n display: block;\n flex: none;\n}\n\n[data-gr-virtual]::before {\n height: var(--gr-virtual-before, 0px);\n}\n\n[data-gr-virtual]::after {\n height: var(--gr-virtual-after, 0px);\n}\n</style>\n","<script setup lang=\"ts\" generic=\"T = unknown\">\nimport { computed, onMounted, onUpdated, ref, useSlots, watch } from 'vue'\n\nimport GrCard from '../GrCard'\nimport type { GrCardVariant } from '../GrCard/grCardStyles'\nimport GrSkeleton from '../GrSkeleton/GrSkeleton.vue'\nimport { hasMeaningfulSlotContent } from '../shared/slotNodes'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { useVirtualList, type GrVirtualAlign } from '../../composables/useVirtualList'\n\nimport { dividedClass, emptyClass, loadingRowClass } from './grListStyles'\n\nexport interface GrListProps<TItem = unknown> {\n /**\n * Поверхность списка — вариант карточки под ним. `ghost` убирает рамку и\n * тень: список внутри уже существующей карточки не должен давать вторую.\n */\n variant?: GrCardVariant\n /** Показывать ли горизонтальные разделители между элементами (по умолчанию — да). */\n divided?: boolean\n /** Идёт загрузка: вместо пунктов — строки-скелетоны, контейнер помечен `aria-busy`. */\n loading?: boolean\n /** Сколько строк-заглушек показать при `loading`. */\n loadingRows?: number\n /**\n * Список пуст. По умолчанию определяется сам — по содержимому слота; проп\n * нужен там, где потребитель знает лучше (например, слот заполнен\n * заголовками групп, а данных в них нет).\n */\n empty?: boolean\n /** Текст пустого состояния. Слот `#empty` сильнее. */\n emptyText?: string\n /**\n * Данные списка. С ними пункты рисует слот `#item`, а не слот по умолчанию, —\n * и только так список знает размер набора, то есть может его виртуализировать.\n */\n items?: TItem[]\n /** Ключ пункта для `v-for`: имя поля или функция. Без него — индекс. */\n itemKey?: string | ((item: TItem, index: number) => string | number)\n /** Высота видимой части: контейнер становится скроллером. Число — пиксели. */\n maxHeight?: number | string\n /** Держать в DOM только окно вокруг вьюпорта. Требует `items` и `maxHeight`. */\n virtual?: boolean\n /** Оценка высоты пункта до замера. Уточняется по факту при первом рендере. */\n estimatedItemSize?: number\n}\n\nconst props = withDefaults(defineProps<GrListProps<T>>(), {\n // Дефолт живёт в `GrCard` (и его резолвере `GrConfigProvider`), поэтому здесь\n // остаётся `undefined` — иначе список перебивал бы настройку карточки.\n variant: undefined,\n divided: true,\n loading: false,\n loadingRows: 3,\n empty: undefined,\n emptyText: undefined,\n items: undefined,\n itemKey: undefined,\n maxHeight: undefined,\n virtual: false,\n // Строка обычной плотности с заголовком и описанием.\n estimatedItemSize: 56,\n})\n\nconst slots = useSlots()\nconst { t } = useGranularityTranslations()\n\nconst listEl = ref<HTMLElement | null>(null)\n\nconst resolvedEmptyText = computed(() => props.emptyText ?? t('gr.list.empty', 'Nothing here yet'))\n\nconst dataMode = computed(() => props.items !== undefined)\n\n// Пустоту видно по слоту: `v-for` по пустому массиву оставляет фрагмент без\n// узлов, `v-if` — комментарий, и ни то ни другое пунктом списка не является.\nconst isEmpty = computed(() => {\n if (props.empty !== undefined)\n return props.empty\n\n if (dataMode.value)\n return props.items!.length === 0\n\n return !hasMeaningfulSlotContent(slots.default?.() ?? [])\n})\n\nconst showItems = computed(() => !props.loading && !isEmpty.value)\n\n// Разделители нужны только между пунктами: в пустой и загрузочной ветках они\n// оставили бы висящую линию.\nconst listClass = computed(() => (props.divided && showItems.value ? dividedClass : undefined))\n\nconst loadingRowCount = computed(() => Math.max(1, Math.trunc(props.loadingRows)))\n\nconst virtualEnabled = computed(() => props.virtual && dataMode.value && props.maxHeight !== undefined)\n\nconst virtualizer = useVirtualList({\n container: listEl,\n count: () => (virtualEnabled.value && showItems.value ? props.items!.length : 0),\n // Замена массива сбрасывает замеры; append в тот же массив их сохраняет.\n source: () => props.items,\n itemSize: () => props.estimatedItemSize,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof props.maxHeight === 'number' ? props.maxHeight : undefined),\n})\n\n/** Окно к отрисовке: при выключенной виртуализации — весь набор. */\nconst renderedItems = computed(() => {\n const items = props.items ?? []\n if (!virtualEnabled.value) return items.map((item, index) => ({ item, index }))\n\n const { start, end } = virtualizer.range.value\n return items.slice(start, end).map((item, offset) => ({ item, index: start + offset }))\n})\n\nfunction keyOf(item: T, index: number): string | number {\n const key = props.itemKey\n if (typeof key === 'function') return key(item, index)\n if (typeof key === 'string') return (item as Record<string, unknown>)[key] as string | number\n\n return index\n}\n\n/**\n * ARIA-набор для пункта.\n *\n * Только в виртуальном режиме: в DOM тогда неполный набор, и без этих атрибутов\n * диктор объявил бы «7 из 20» на списке в пять тысяч. Когда набор в DOM целиком,\n * его размер и позицию браузер считает сам, а руками проставленные атрибуты\n * начинают расходиться с разметкой при любой фильтрации.\n */\nfunction ariaOf(index: number): Record<string, number> {\n if (!virtualEnabled.value) return {}\n\n return { 'aria-setsize': props.items!.length, 'aria-posinset': index + 1 }\n}\n\nconst maxHeightStyle = computed(() => {\n const value = props.maxHeight\n if (value == null) return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst listStyle = computed(() => {\n if (props.maxHeight === undefined) return undefined\n\n const scroller = { overflowY: 'auto' as const, maxHeight: maxHeightStyle.value }\n if (!virtualEnabled.value) return scroller\n\n return { ...scroller, ...virtualizer.spacerStyle.value }\n})\n\n/**\n * Замер отрисованных пунктов.\n *\n * Идёт по детям контейнера, а не по `ref` на элементе: пункт рисует слот\n * потребителя, привязать к нему `ref` неоткуда. В виртуальном режиме прямые\n * дети контейнера — ровно окно (распорки живут псевдоэлементами и детьми не\n * считаются), поэтому сопоставление по позиции однозначно.\n */\nfunction measureRendered(): void {\n if (!virtualEnabled.value) return\n // В состояниях loading/empty дети контейнера — скелетоны и заглушки: их\n // высоты записались бы в замеры под индексами будущих строк данных.\n if (!showItems.value) return\n\n const container = listEl.value\n if (!container) return\n\n const { start } = virtualizer.range.value\n const children = container.children\n for (let offset = 0; offset < children.length; offset++) {\n virtualizer.measure(start + offset, children[offset])\n }\n}\n\nonMounted(measureRendered)\nonUpdated(measureRendered)\n\nfunction scrollToIndex(index: number, align?: GrVirtualAlign): void {\n virtualizer.scrollToIndex(index, align)\n}\n\ndefineExpose({ scrollToIndex })\n\nif (import.meta.env?.DEV) {\n watch(\n () => [props.virtual, dataMode.value, props.maxHeight] as const,\n ([virtual, hasItems, maxHeight]) => {\n if (!virtual) return\n\n if (!hasItems) {\n console.warn(\n '[granularity] GrList: `virtual` требует `items` — пункты из слота по умолчанию '\n + 'список не считает и резать окно ему не из чего.',\n )\n }\n else if (maxHeight === undefined) {\n console.warn(\n '[granularity] GrList: `virtual` требует `maxHeight` — без ограничения высоты '\n + 'вьюпорта нет, и в окно попадает весь набор.',\n )\n }\n },\n { immediate: true },\n )\n\n watch(\n () => [dataMode.value, Boolean(slots.item)] as const,\n ([hasItems, hasSlot]) => {\n if (hasItems && !hasSlot) {\n console.warn(\n '[granularity] GrList: с `items` пункты рисует слот `#item` — без него список пуст.',\n )\n }\n },\n { immediate: true },\n )\n\n onMounted(() => {\n if (!virtualEnabled.value) return\n\n const first = listEl.value?.firstElementChild\n if (first && !first.hasAttribute('aria-posinset')) {\n console.warn(\n '[granularity] GrList: при `virtual` пункты обязаны нести `aria-setsize`/`aria-posinset` — '\n + 'пробросьте `aria` из слота `#item`: <GrListItem v-bind=\"aria\" … />. Иначе диктор '\n + 'посчитает набор по отрисованному окну.',\n )\n }\n })\n}\n</script>\n\n<template>\n <GrCard :variant=\"variant\">\n <div\n ref=\"listEl\"\n data-gr-list\n role=\"list\"\n :class=\"listClass\"\n :style=\"listStyle\"\n :tabindex=\"maxHeight === undefined ? undefined : 0\"\n :data-gr-virtual=\"virtualEnabled ? '' : undefined\"\n :aria-busy=\"loading ? 'true' : undefined\"\n >\n <template v-if=\"loading\">\n <slot name=\"loading\">\n <div\n v-for=\"row in loadingRowCount\"\n :key=\"row\"\n data-gr-list-loading-row\n :class=\"loadingRowClass\"\n >\n <GrSkeleton />\n </div>\n </slot>\n </template>\n\n <div\n v-else-if=\"isEmpty\"\n data-gr-list-empty\n :class=\"emptyClass\"\n >\n <slot name=\"empty\">\n {{ resolvedEmptyText }}\n </slot>\n </div>\n\n <template v-else-if=\"dataMode\">\n <template\n v-for=\"entry in renderedItems\"\n :key=\"keyOf(entry.item, entry.index)\"\n >\n <slot\n name=\"item\"\n :item=\"entry.item\"\n :index=\"entry.index\"\n :aria=\"ariaOf(entry.index)\"\n />\n </template>\n </template>\n\n <slot v-else />\n </div>\n </GrCard>\n</template>\n\n<style scoped>\n/* Срезанное сверху и снизу держат псевдоэлементы контейнера: их не за что\n размонтировать, в дереве доступности их нет, а высота приезжает переменными\n в том же патче, что и пункты. Почему не отступы контейнера и не поля крайних\n пунктов — `docs/virtual-list.md`. */\n[data-gr-virtual]::before,\n[data-gr-virtual]::after {\n content: '';\n display: block;\n flex: none;\n}\n\n[data-gr-virtual]::before {\n height: var(--gr-virtual-before, 0px);\n}\n\n[data-gr-virtual]::after {\n height: var(--gr-virtual-after, 0px);\n}\n</style>\n","<script setup lang=\"ts\">\nimport { computed, markRaw, useSlots, watch, type Component } from 'vue'\n\nimport {\n grListItemPaddingClass,\n itemDescriptionClass,\n itemDisabledClass,\n itemHoverClass,\n itemInteractiveClass,\n itemLayoutClass,\n itemTitleClass,\n type GrListItemDensity,\n} from './grListStyles'\n\nexport type { GrListItemDensity } from './grListStyles'\n\nexport interface GrListItemProps {\n /** Заголовок строки. Если передан слот `#title`, проп игнорируется. */\n title?: string\n /** Описание под заголовком. Если передан слот `#description`, проп игнорируется. */\n description?: string\n /** Плотность вертикальных отступов: `regular` — 12px, `compact` — 8px. */\n density?: GrListItemDensity\n /** Ссылка: строка становится `<a>`. */\n href?: string\n /** Свой корневой тег строки (`RouterLink`, `Link` от Inertia). Сильнее `href`. */\n as?: string | Component\n /** Кликабельная строка без ссылки — `<button>` с событием `click`. */\n clickable?: boolean\n /** Подсветка при наведении без интерактивности. */\n hoverable?: boolean\n disabled?: boolean\n}\n\nexport interface GrListItemEmits {\n (e: 'click', event: MouseEvent): void\n}\n\nconst props = withDefaults(defineProps<GrListItemProps>(), {\n title: undefined,\n description: undefined,\n density: 'regular',\n href: undefined,\n as: undefined,\n clickable: false,\n hoverable: false,\n disabled: false,\n})\n\nconst emit = defineEmits<GrListItemEmits>()\n\nconst slots = useSlots()\n\nconst hasTitle = computed(() => !!slots.title || !!props.title)\nconst hasDescription = computed(() => !!slots.description || !!props.description)\n\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href || props.clickable))\n\n/**\n * `role=\"listitem\"` остаётся на обёртке, а строка целиком — вложенный элемент:\n * `<a role=\"listitem\">` потерял бы роль ссылки, а интерактив снаружи разорвал бы\n * связку `list` → `listitem`. Обычная строка идёт по той же схеме, чтобы\n * разметка содержимого была написана один раз, а не по копии на ветку.\n */\nconst rowTag = computed<string | Component>(() => {\n if (!isInteractive.value)\n return 'div'\n\n if (props.as)\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n\n return props.href ? 'a' : 'button'\n})\n\nconst rowClass = computed(() => [\n itemLayoutClass,\n grListItemPaddingClass(props.density),\n isInteractive.value ? `${itemInteractiveClass} ${itemHoverClass}` : '',\n !isInteractive.value && props.hoverable && !props.disabled ? itemHoverClass : '',\n props.disabled ? itemDisabledClass : '',\n].filter(Boolean).join(' '))\n\nfunction onClick(event: MouseEvent): void {\n // `disabled` сюда попадает вместе с обычной строкой: и то и другое —\n // не-интерактив, а кликов не эмитит ни один.\n if (!isInteractive.value)\n return\n\n emit('click', event)\n}\n\n/** Теги, попадающие в таб-порядок сами. `<a>` — только со ссылкой. */\nfunction isFocusableTag(tag: string): boolean {\n return tag === 'button' || (tag === 'a' && !!props.href)\n}\n\nif (import.meta.env?.DEV) {\n watch(\n () => [isInteractive.value, props.as] as const,\n ([interactive, as]) => {\n // Компонент из `as` (`RouterLink`, Inertia `Link`) рендерит `<a>`, но узнать\n // это до рендера нельзя — предупреждаем только по явно названному тегу.\n if (!interactive || typeof as !== 'string' || isFocusableTag(as)) return\n\n console.warn(\n `[granularity] GrListItem: as=\"${as}\" не попадает в таб-порядок — строка кликается `\n + 'мышью, но не с клавиатуры. Возьмите тег, умеющий фокус (`button`, `a` со ссылкой), '\n + 'или компонент роутера.',\n )\n },\n { immediate: true },\n )\n}\n</script>\n\n<template>\n <div\n data-gr-list-item\n role=\"listitem\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n >\n <component\n :is=\"rowTag\"\n :data-gr-list-item-action=\"isInteractive ? '' : undefined\"\n :type=\"rowTag === 'button' ? 'button' : undefined\"\n :href=\"isInteractive ? href : undefined\"\n :class=\"rowClass\"\n @click=\"onClick\"\n >\n <div v-if=\"$slots.prefix\" class=\"shrink-0\">\n <slot name=\"prefix\" />\n </div>\n <div class=\"min-w-0 flex-1\">\n <div v-if=\"hasTitle\" :class=\"itemTitleClass\">\n <slot name=\"title\">\n{{ title }}\n</slot>\n </div>\n <div\n v-if=\"hasDescription\"\n :class=\"itemDescriptionClass\"\n >\n <slot name=\"description\">\n{{ description }}\n</slot>\n </div>\n </div>\n <div v-if=\"$slots.default\" class=\"shrink-0\">\n <slot />\n </div>\n </component>\n </div>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, markRaw, useSlots, watch, type Component } from 'vue'\n\nimport {\n grListItemPaddingClass,\n itemDescriptionClass,\n itemDisabledClass,\n itemHoverClass,\n itemInteractiveClass,\n itemLayoutClass,\n itemTitleClass,\n type GrListItemDensity,\n} from './grListStyles'\n\nexport type { GrListItemDensity } from './grListStyles'\n\nexport interface GrListItemProps {\n /** Заголовок строки. Если передан слот `#title`, проп игнорируется. */\n title?: string\n /** Описание под заголовком. Если передан слот `#description`, проп игнорируется. */\n description?: string\n /** Плотность вертикальных отступов: `regular` — 12px, `compact` — 8px. */\n density?: GrListItemDensity\n /** Ссылка: строка становится `<a>`. */\n href?: string\n /** Свой корневой тег строки (`RouterLink`, `Link` от Inertia). Сильнее `href`. */\n as?: string | Component\n /** Кликабельная строка без ссылки — `<button>` с событием `click`. */\n clickable?: boolean\n /** Подсветка при наведении без интерактивности. */\n hoverable?: boolean\n disabled?: boolean\n}\n\nexport interface GrListItemEmits {\n (e: 'click', event: MouseEvent): void\n}\n\nconst props = withDefaults(defineProps<GrListItemProps>(), {\n title: undefined,\n description: undefined,\n density: 'regular',\n href: undefined,\n as: undefined,\n clickable: false,\n hoverable: false,\n disabled: false,\n})\n\nconst emit = defineEmits<GrListItemEmits>()\n\nconst slots = useSlots()\n\nconst hasTitle = computed(() => !!slots.title || !!props.title)\nconst hasDescription = computed(() => !!slots.description || !!props.description)\n\nconst isInteractive = computed(() => !props.disabled && (!!props.as || !!props.href || props.clickable))\n\n/**\n * `role=\"listitem\"` остаётся на обёртке, а строка целиком — вложенный элемент:\n * `<a role=\"listitem\">` потерял бы роль ссылки, а интерактив снаружи разорвал бы\n * связку `list` → `listitem`. Обычная строка идёт по той же схеме, чтобы\n * разметка содержимого была написана один раз, а не по копии на ветку.\n */\nconst rowTag = computed<string | Component>(() => {\n if (!isInteractive.value)\n return 'div'\n\n if (props.as)\n return typeof props.as === 'string' ? props.as : markRaw(props.as)\n\n return props.href ? 'a' : 'button'\n})\n\nconst rowClass = computed(() => [\n itemLayoutClass,\n grListItemPaddingClass(props.density),\n isInteractive.value ? `${itemInteractiveClass} ${itemHoverClass}` : '',\n !isInteractive.value && props.hoverable && !props.disabled ? itemHoverClass : '',\n props.disabled ? itemDisabledClass : '',\n].filter(Boolean).join(' '))\n\nfunction onClick(event: MouseEvent): void {\n // `disabled` сюда попадает вместе с обычной строкой: и то и другое —\n // не-интерактив, а кликов не эмитит ни один.\n if (!isInteractive.value)\n return\n\n emit('click', event)\n}\n\n/** Теги, попадающие в таб-порядок сами. `<a>` — только со ссылкой. */\nfunction isFocusableTag(tag: string): boolean {\n return tag === 'button' || (tag === 'a' && !!props.href)\n}\n\nif (import.meta.env?.DEV) {\n watch(\n () => [isInteractive.value, props.as] as const,\n ([interactive, as]) => {\n // Компонент из `as` (`RouterLink`, Inertia `Link`) рендерит `<a>`, но узнать\n // это до рендера нельзя — предупреждаем только по явно названному тегу.\n if (!interactive || typeof as !== 'string' || isFocusableTag(as)) return\n\n console.warn(\n `[granularity] GrListItem: as=\"${as}\" не попадает в таб-порядок — строка кликается `\n + 'мышью, но не с клавиатуры. Возьмите тег, умеющий фокус (`button`, `a` со ссылкой), '\n + 'или компонент роутера.',\n )\n },\n { immediate: true },\n )\n}\n</script>\n\n<template>\n <div\n data-gr-list-item\n role=\"listitem\"\n :aria-disabled=\"disabled ? 'true' : undefined\"\n >\n <component\n :is=\"rowTag\"\n :data-gr-list-item-action=\"isInteractive ? '' : undefined\"\n :type=\"rowTag === 'button' ? 'button' : undefined\"\n :href=\"isInteractive ? href : undefined\"\n :class=\"rowClass\"\n @click=\"onClick\"\n >\n <div v-if=\"$slots.prefix\" class=\"shrink-0\">\n <slot name=\"prefix\" />\n </div>\n <div class=\"min-w-0 flex-1\">\n <div v-if=\"hasTitle\" :class=\"itemTitleClass\">\n <slot name=\"title\">\n{{ title }}\n</slot>\n </div>\n <div\n v-if=\"hasDescription\"\n :class=\"itemDescriptionClass\"\n >\n <slot name=\"description\">\n{{ description }}\n</slot>\n </div>\n </div>\n <div v-if=\"$slots.default\" class=\"shrink-0\">\n <slot />\n </div>\n </component>\n </div>\n</template>\n"],"mappings":"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"}
@@ -1,3 +1,3 @@
1
1
  import { n as grListSafelist, t as grListConfig } from "../../chunks/config-BsuDM3Hb.js";
2
- import { n as GrList_default, t as GrListItem_default } from "./chunks/GrList-4YU1NZtM.js";
2
+ import { n as GrList_default, t as GrListItem_default } from "./chunks/GrList-CHibO0xA.js";
3
3
  export { GrList_default as GrList, GrList_default as default, GrListItem_default as GrListItem, grListConfig, grListSafelist };
@@ -1,6 +1,6 @@
1
1
  import { n as useGranularityTranslations } from "../../../chunks/granularityI18n-BC5zsj_d.js";
2
2
  import { t as loader_circle_default } from "../../../chunks/loader-circle-CfVLz7lb.js";
3
- import { t as GrIcon_default } from "../../GrIcon/chunks/GrIcon-BvA2ZGXP.js";
3
+ import { t as GrIcon_default } from "../../GrIcon/chunks/GrIcon-bQwtZtYT.js";
4
4
  import { n as grLoadingRootClass } from "../../../chunks/grLoadingStyles-DEmji2wv.js";
5
5
  import { computed, createBlock, createCommentVNode, createElementBlock, createElementVNode, createVNode, defineComponent, normalizeClass, normalizeStyle, onBeforeUnmount, onMounted, openBlock, ref, renderSlot, resolveDynamicComponent, toDisplayString, withCtx } from "vue";
6
6
  //#region src/components/GrLoading/GrLoading.vue?vue&type=script&setup=true&lang.ts
@@ -1 +1 @@
1
- {"version":3,"file":"GrLoading-CH95CFzS.js","names":[],"sources":["../../../../src/components/GrLoading/GrLoading.vue","../../../../src/components/GrLoading/GrLoading.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, onMounted, ref, type Component } from 'vue'\n\nimport IconLoader from '~icons/lucide/loader-circle'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport type { GrIconSize, GrIconTone } from '../GrIcon/grIconStyles'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { grLoadingRootClass } from './grLoadingStyles'\n\n/**\n * Пропы {@link GrLoading}.\n *\n * Оверлей загрузки: спиннер с подписью поверх соседнего контента. `fullscreen`\n * накрывает весь экран, иначе оверлей ложится на ближайшего позиционированного\n * предка.\n */\nexport interface GrLoadingProps {\n /** Подпись под спиннером. Пустая строка убирает её совсем. По умолчанию — из локали. */\n text?: string\n /** Свой компонент спиннера вместо иконки по умолчанию. */\n spinner?: Component\n /** Дополнительные классы обёртки спиннера. */\n spinnerClass?: string\n /** Размер спиннера: шкала пакета либо произвольный в пикселях. */\n spinnerSize?: GrIconSize | number\n /** Тон спиннера из палитры. */\n spinnerTone?: GrIconTone\n /** Вращение спиннера. По умолчанию включено. */\n animated?: boolean\n /** Свой `background-color`. Задан — дефолтный скрим `--gr-overlay-bg` снимается. */\n background?: string\n /** Накрыть весь экран (`position: fixed`) вместо ближайшего позиционированного предка. */\n fullscreen?: boolean\n /** Имя CSS-переменной слоя — escape-hatch мимо `--gr-z-loading`. */\n zIndexVar?: string\n /** Задержка показа в миллисекундах: короткая загрузка не мигает оверлеем. */\n delay?: number\n /** Дополнительные классы корня оверлея. */\n customClass?: string\n}\n\nexport interface GrLoadingEmits {\n /**\n * Оверлей появился на экране — сразу или по истечении `delay`. По этому\n * событию директива блокирует контент под оверлеем: до показа блокировать\n * нечего, иначе быстрый запрос молча «замораживал» бы форму.\n */\n (e: 'show'): void\n}\n\nconst props = withDefaults(\n defineProps<GrLoadingProps>(),\n {\n text: undefined,\n spinner: undefined,\n spinnerClass: undefined,\n // 28px не входит в шкалу иконок (14–20): спиннер загрузки — самостоятельный\n // акцент панели, а не иконка рядом с текстом.\n spinnerSize: 28,\n spinnerTone: 'neutral',\n animated: true,\n background: undefined,\n fullscreen: false,\n zIndexVar: undefined,\n delay: 0,\n customClass: undefined,\n },\n)\n\nconst emit = defineEmits<GrLoadingEmits>()\n\ndefineSlots<{\n /** Содержимое панели целиком вместо спиннера с подписью. */\n default?: () => any\n}>()\n\nconst { t } = useGranularityTranslations()\n\nconst Spinner = computed(() => props.spinner ?? IconLoader)\n\nconst displayText = computed(() => props.text ?? t('gr.loading.defaultText', 'Loading...'))\n\nconst rootClass = computed(() => {\n return grLoadingRootClass({\n fullscreen: props.fullscreen,\n hasBackground: props.background !== undefined,\n customClass: props.customClass,\n })\n})\n\nconst rootStyle = computed(() => {\n return {\n backgroundColor: props.background,\n zIndex: props.zIndexVar ? `var(${props.zIndexVar})` : undefined,\n } as Record<string, string | undefined>\n})\n\n// Оверлей на быстром запросе успевает мигнуть и раздражает сильнее, чем его\n// отсутствие. Отсчёт начинается с монтирования: компонент создаётся ровно в\n// момент старта загрузки — и в `v-if`, и в директиве.\nconst visible = ref(props.delay <= 0)\nlet delayTimer: ReturnType<typeof setTimeout> | undefined\n\nonMounted(() => {\n if (visible.value) {\n emit('show')\n return\n }\n\n delayTimer = setTimeout(() => {\n visible.value = true\n emit('show')\n }, props.delay)\n})\n\nonBeforeUnmount(() => {\n clearTimeout(delayTimer)\n})\n</script>\n\n<template>\n <div\n v-if=\"visible\"\n data-gr-loading\n class=\"flex items-center justify-center cursor-wait select-none pointer-events-auto\"\n :class=\"rootClass\"\n :style=\"rootStyle\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <div\n data-gr-loading-panel\n class=\"flex flex-col items-center justify-center gap-2 text-center rounded-[var(--gr-radius-md)] bg-[var(--gr-bg)]/55 px-5 py-4 shadow-lg\"\n >\n <slot>\n <GrIcon\n data-gr-loading-spinner\n :size=\"spinnerSize\"\n :tone=\"spinnerTone\"\n :spin=\"animated\"\n :class=\"spinnerClass\"\n >\n <component :is=\"Spinner\" />\n </GrIcon>\n <div v-if=\"displayText\" data-gr-loading-text class=\"text-[length:var(--gr-text-sm)] leading-[var(--gr-leading-sm)] text-[var(--gr-muted-fg)]\">\n {{ displayText }}\n </div>\n </slot>\n </div>\n </div>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, onMounted, ref, type Component } from 'vue'\n\nimport IconLoader from '~icons/lucide/loader-circle'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport type { GrIconSize, GrIconTone } from '../GrIcon/grIconStyles'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { grLoadingRootClass } from './grLoadingStyles'\n\n/**\n * Пропы {@link GrLoading}.\n *\n * Оверлей загрузки: спиннер с подписью поверх соседнего контента. `fullscreen`\n * накрывает весь экран, иначе оверлей ложится на ближайшего позиционированного\n * предка.\n */\nexport interface GrLoadingProps {\n /** Подпись под спиннером. Пустая строка убирает её совсем. По умолчанию — из локали. */\n text?: string\n /** Свой компонент спиннера вместо иконки по умолчанию. */\n spinner?: Component\n /** Дополнительные классы обёртки спиннера. */\n spinnerClass?: string\n /** Размер спиннера: шкала пакета либо произвольный в пикселях. */\n spinnerSize?: GrIconSize | number\n /** Тон спиннера из палитры. */\n spinnerTone?: GrIconTone\n /** Вращение спиннера. По умолчанию включено. */\n animated?: boolean\n /** Свой `background-color`. Задан — дефолтный скрим `--gr-overlay-bg` снимается. */\n background?: string\n /** Накрыть весь экран (`position: fixed`) вместо ближайшего позиционированного предка. */\n fullscreen?: boolean\n /** Имя CSS-переменной слоя — escape-hatch мимо `--gr-z-loading`. */\n zIndexVar?: string\n /** Задержка показа в миллисекундах: короткая загрузка не мигает оверлеем. */\n delay?: number\n /** Дополнительные классы корня оверлея. */\n customClass?: string\n}\n\nexport interface GrLoadingEmits {\n /**\n * Оверлей появился на экране — сразу или по истечении `delay`. По этому\n * событию директива блокирует контент под оверлеем: до показа блокировать\n * нечего, иначе быстрый запрос молча «замораживал» бы форму.\n */\n (e: 'show'): void\n}\n\nconst props = withDefaults(\n defineProps<GrLoadingProps>(),\n {\n text: undefined,\n spinner: undefined,\n spinnerClass: undefined,\n // 28px не входит в шкалу иконок (14–20): спиннер загрузки — самостоятельный\n // акцент панели, а не иконка рядом с текстом.\n spinnerSize: 28,\n spinnerTone: 'neutral',\n animated: true,\n background: undefined,\n fullscreen: false,\n zIndexVar: undefined,\n delay: 0,\n customClass: undefined,\n },\n)\n\nconst emit = defineEmits<GrLoadingEmits>()\n\ndefineSlots<{\n /** Содержимое панели целиком вместо спиннера с подписью. */\n default?: () => any\n}>()\n\nconst { t } = useGranularityTranslations()\n\nconst Spinner = computed(() => props.spinner ?? IconLoader)\n\nconst displayText = computed(() => props.text ?? t('gr.loading.defaultText', 'Loading...'))\n\nconst rootClass = computed(() => {\n return grLoadingRootClass({\n fullscreen: props.fullscreen,\n hasBackground: props.background !== undefined,\n customClass: props.customClass,\n })\n})\n\nconst rootStyle = computed(() => {\n return {\n backgroundColor: props.background,\n zIndex: props.zIndexVar ? `var(${props.zIndexVar})` : undefined,\n } as Record<string, string | undefined>\n})\n\n// Оверлей на быстром запросе успевает мигнуть и раздражает сильнее, чем его\n// отсутствие. Отсчёт начинается с монтирования: компонент создаётся ровно в\n// момент старта загрузки — и в `v-if`, и в директиве.\nconst visible = ref(props.delay <= 0)\nlet delayTimer: ReturnType<typeof setTimeout> | undefined\n\nonMounted(() => {\n if (visible.value) {\n emit('show')\n return\n }\n\n delayTimer = setTimeout(() => {\n visible.value = true\n emit('show')\n }, props.delay)\n})\n\nonBeforeUnmount(() => {\n clearTimeout(delayTimer)\n})\n</script>\n\n<template>\n <div\n v-if=\"visible\"\n data-gr-loading\n class=\"flex items-center justify-center cursor-wait select-none pointer-events-auto\"\n :class=\"rootClass\"\n :style=\"rootStyle\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <div\n data-gr-loading-panel\n class=\"flex flex-col items-center justify-center gap-2 text-center rounded-[var(--gr-radius-md)] bg-[var(--gr-bg)]/55 px-5 py-4 shadow-lg\"\n >\n <slot>\n <GrIcon\n data-gr-loading-spinner\n :size=\"spinnerSize\"\n :tone=\"spinnerTone\"\n :spin=\"animated\"\n :class=\"spinnerClass\"\n >\n <component :is=\"Spinner\" />\n </GrIcon>\n <div v-if=\"displayText\" data-gr-loading-text class=\"text-[length:var(--gr-text-sm)] leading-[var(--gr-leading-sm)] text-[var(--gr-muted-fg)]\">\n {{ displayText }}\n </div>\n </slot>\n </div>\n </div>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAmDA,MAAM,QAAQ;EAmBd,MAAM,OAAO;EAOb,MAAM,EAAE,MAAM,2BAA2B;EAEzC,MAAM,UAAU,eAAe,MAAM,WAAW,qBAAU;EAE1D,MAAM,cAAc,eAAe,MAAM,QAAQ,EAAE,0BAA0B,YAAY,CAAC;EAE1F,MAAM,YAAY,eAAe;GAC/B,OAAO,mBAAmB;IACxB,YAAY,MAAM;IAClB,eAAe,MAAM,eAAe,KAAA;IACpC,aAAa,MAAM;GACrB,CAAC;EACH,CAAC;EAED,MAAM,YAAY,eAAe;GAC/B,OAAO;IACL,iBAAiB,MAAM;IACvB,QAAQ,MAAM,YAAY,OAAO,MAAM,UAAU,KAAK,KAAA;GACxD;EACF,CAAC;EAKD,MAAM,UAAU,IAAI,MAAM,SAAS,CAAC;EACpC,IAAI;EAEJ,gBAAgB;GACd,IAAI,QAAQ,OAAO;IACjB,KAAK,MAAM;IACX;GACF;GAEA,aAAa,iBAAiB;IAC5B,QAAQ,QAAQ;IAChB,KAAK,MAAM;GACb,GAAG,MAAM,KAAK;EAChB,CAAC;EAED,sBAAsB;GACpB,aAAa,UAAU;EACzB,CAAC;;UAKS,QAAA,SAAA,UAAA,GADR,mBA4BM,OAAA;;IA1BJ,mBAAA;IACA,OAAK,eAAA,CAAC,gFACE,UAAA,KAAS,CAAA;IAChB,OAAK,eAAE,UAAA,KAAS;IACjB,MAAK;IACL,aAAU;OAEV,mBAkBM,OAlBN,YAkBM,CAdJ,WAaO,KAAA,QAAA,WAAA,CAAA,SAAA,CAZL,YAQS,gBAAA;IAPP,2BAAA;IACC,MAAM,QAAA;IACN,MAAM,QAAA;IACN,MAAM,QAAA;IACN,OAAK,eAAE,QAAA,YAAY;;2BAEO,EAAA,UAAA,GAA3B,YAA2B,wBAAX,QAAA,KAAO,CAAA,EAAA,CAAA;;;;;;;OAEd,YAAA,SAAA,UAAA,GAAX,mBAEM,OAFN,YAEM,gBADD,YAAA,KAAW,GAAA,CAAA,KAAA,mBAAA,IAAA,IAAA,CAAA,CAAA,CAAA,CAAA,CAAA,GAAA,CAAA,KAAA,mBAAA,IAAA,IAAA"}
1
+ {"version":3,"file":"GrLoading-C3DZSSuh.js","names":[],"sources":["../../../../src/components/GrLoading/GrLoading.vue","../../../../src/components/GrLoading/GrLoading.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, onMounted, ref, type Component } from 'vue'\n\nimport IconLoader from '~icons/lucide/loader-circle'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport type { GrIconSize, GrIconTone } from '../GrIcon/grIconStyles'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { grLoadingRootClass } from './grLoadingStyles'\n\n/**\n * Пропы {@link GrLoading}.\n *\n * Оверлей загрузки: спиннер с подписью поверх соседнего контента. `fullscreen`\n * накрывает весь экран, иначе оверлей ложится на ближайшего позиционированного\n * предка.\n */\nexport interface GrLoadingProps {\n /** Подпись под спиннером. Пустая строка убирает её совсем. По умолчанию — из локали. */\n text?: string\n /** Свой компонент спиннера вместо иконки по умолчанию. */\n spinner?: Component\n /** Дополнительные классы обёртки спиннера. */\n spinnerClass?: string\n /** Размер спиннера: шкала пакета либо произвольный в пикселях. */\n spinnerSize?: GrIconSize | number\n /** Тон спиннера из палитры. */\n spinnerTone?: GrIconTone\n /** Вращение спиннера. По умолчанию включено. */\n animated?: boolean\n /** Свой `background-color`. Задан — дефолтный скрим `--gr-overlay-bg` снимается. */\n background?: string\n /** Накрыть весь экран (`position: fixed`) вместо ближайшего позиционированного предка. */\n fullscreen?: boolean\n /** Имя CSS-переменной слоя — escape-hatch мимо `--gr-z-loading`. */\n zIndexVar?: string\n /** Задержка показа в миллисекундах: короткая загрузка не мигает оверлеем. */\n delay?: number\n /** Дополнительные классы корня оверлея. */\n customClass?: string\n}\n\nexport interface GrLoadingEmits {\n /**\n * Оверлей появился на экране — сразу или по истечении `delay`. По этому\n * событию директива блокирует контент под оверлеем: до показа блокировать\n * нечего, иначе быстрый запрос молча «замораживал» бы форму.\n */\n (e: 'show'): void\n}\n\nconst props = withDefaults(\n defineProps<GrLoadingProps>(),\n {\n text: undefined,\n spinner: undefined,\n spinnerClass: undefined,\n // 28px не входит в шкалу иконок (14–20): спиннер загрузки — самостоятельный\n // акцент панели, а не иконка рядом с текстом.\n spinnerSize: 28,\n spinnerTone: 'neutral',\n animated: true,\n background: undefined,\n fullscreen: false,\n zIndexVar: undefined,\n delay: 0,\n customClass: undefined,\n },\n)\n\nconst emit = defineEmits<GrLoadingEmits>()\n\ndefineSlots<{\n /** Содержимое панели целиком вместо спиннера с подписью. */\n default?: () => any\n}>()\n\nconst { t } = useGranularityTranslations()\n\nconst Spinner = computed(() => props.spinner ?? IconLoader)\n\nconst displayText = computed(() => props.text ?? t('gr.loading.defaultText', 'Loading...'))\n\nconst rootClass = computed(() => {\n return grLoadingRootClass({\n fullscreen: props.fullscreen,\n hasBackground: props.background !== undefined,\n customClass: props.customClass,\n })\n})\n\nconst rootStyle = computed(() => {\n return {\n backgroundColor: props.background,\n zIndex: props.zIndexVar ? `var(${props.zIndexVar})` : undefined,\n } as Record<string, string | undefined>\n})\n\n// Оверлей на быстром запросе успевает мигнуть и раздражает сильнее, чем его\n// отсутствие. Отсчёт начинается с монтирования: компонент создаётся ровно в\n// момент старта загрузки — и в `v-if`, и в директиве.\nconst visible = ref(props.delay <= 0)\nlet delayTimer: ReturnType<typeof setTimeout> | undefined\n\nonMounted(() => {\n if (visible.value) {\n emit('show')\n return\n }\n\n delayTimer = setTimeout(() => {\n visible.value = true\n emit('show')\n }, props.delay)\n})\n\nonBeforeUnmount(() => {\n clearTimeout(delayTimer)\n})\n</script>\n\n<template>\n <div\n v-if=\"visible\"\n data-gr-loading\n class=\"flex items-center justify-center cursor-wait select-none pointer-events-auto\"\n :class=\"rootClass\"\n :style=\"rootStyle\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <div\n data-gr-loading-panel\n class=\"flex flex-col items-center justify-center gap-2 text-center rounded-[var(--gr-radius-md)] bg-[var(--gr-bg)]/55 px-5 py-4 shadow-lg\"\n >\n <slot>\n <GrIcon\n data-gr-loading-spinner\n :size=\"spinnerSize\"\n :tone=\"spinnerTone\"\n :spin=\"animated\"\n :class=\"spinnerClass\"\n >\n <component :is=\"Spinner\" />\n </GrIcon>\n <div v-if=\"displayText\" data-gr-loading-text class=\"text-[length:var(--gr-text-sm)] leading-[var(--gr-leading-sm)] text-[var(--gr-muted-fg)]\">\n {{ displayText }}\n </div>\n </slot>\n </div>\n </div>\n</template>\n","<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, onMounted, ref, type Component } from 'vue'\n\nimport IconLoader from '~icons/lucide/loader-circle'\n\nimport GrIcon from '../GrIcon/GrIcon.vue'\nimport type { GrIconSize, GrIconTone } from '../GrIcon/grIconStyles'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { grLoadingRootClass } from './grLoadingStyles'\n\n/**\n * Пропы {@link GrLoading}.\n *\n * Оверлей загрузки: спиннер с подписью поверх соседнего контента. `fullscreen`\n * накрывает весь экран, иначе оверлей ложится на ближайшего позиционированного\n * предка.\n */\nexport interface GrLoadingProps {\n /** Подпись под спиннером. Пустая строка убирает её совсем. По умолчанию — из локали. */\n text?: string\n /** Свой компонент спиннера вместо иконки по умолчанию. */\n spinner?: Component\n /** Дополнительные классы обёртки спиннера. */\n spinnerClass?: string\n /** Размер спиннера: шкала пакета либо произвольный в пикселях. */\n spinnerSize?: GrIconSize | number\n /** Тон спиннера из палитры. */\n spinnerTone?: GrIconTone\n /** Вращение спиннера. По умолчанию включено. */\n animated?: boolean\n /** Свой `background-color`. Задан — дефолтный скрим `--gr-overlay-bg` снимается. */\n background?: string\n /** Накрыть весь экран (`position: fixed`) вместо ближайшего позиционированного предка. */\n fullscreen?: boolean\n /** Имя CSS-переменной слоя — escape-hatch мимо `--gr-z-loading`. */\n zIndexVar?: string\n /** Задержка показа в миллисекундах: короткая загрузка не мигает оверлеем. */\n delay?: number\n /** Дополнительные классы корня оверлея. */\n customClass?: string\n}\n\nexport interface GrLoadingEmits {\n /**\n * Оверлей появился на экране — сразу или по истечении `delay`. По этому\n * событию директива блокирует контент под оверлеем: до показа блокировать\n * нечего, иначе быстрый запрос молча «замораживал» бы форму.\n */\n (e: 'show'): void\n}\n\nconst props = withDefaults(\n defineProps<GrLoadingProps>(),\n {\n text: undefined,\n spinner: undefined,\n spinnerClass: undefined,\n // 28px не входит в шкалу иконок (14–20): спиннер загрузки — самостоятельный\n // акцент панели, а не иконка рядом с текстом.\n spinnerSize: 28,\n spinnerTone: 'neutral',\n animated: true,\n background: undefined,\n fullscreen: false,\n zIndexVar: undefined,\n delay: 0,\n customClass: undefined,\n },\n)\n\nconst emit = defineEmits<GrLoadingEmits>()\n\ndefineSlots<{\n /** Содержимое панели целиком вместо спиннера с подписью. */\n default?: () => any\n}>()\n\nconst { t } = useGranularityTranslations()\n\nconst Spinner = computed(() => props.spinner ?? IconLoader)\n\nconst displayText = computed(() => props.text ?? t('gr.loading.defaultText', 'Loading...'))\n\nconst rootClass = computed(() => {\n return grLoadingRootClass({\n fullscreen: props.fullscreen,\n hasBackground: props.background !== undefined,\n customClass: props.customClass,\n })\n})\n\nconst rootStyle = computed(() => {\n return {\n backgroundColor: props.background,\n zIndex: props.zIndexVar ? `var(${props.zIndexVar})` : undefined,\n } as Record<string, string | undefined>\n})\n\n// Оверлей на быстром запросе успевает мигнуть и раздражает сильнее, чем его\n// отсутствие. Отсчёт начинается с монтирования: компонент создаётся ровно в\n// момент старта загрузки — и в `v-if`, и в директиве.\nconst visible = ref(props.delay <= 0)\nlet delayTimer: ReturnType<typeof setTimeout> | undefined\n\nonMounted(() => {\n if (visible.value) {\n emit('show')\n return\n }\n\n delayTimer = setTimeout(() => {\n visible.value = true\n emit('show')\n }, props.delay)\n})\n\nonBeforeUnmount(() => {\n clearTimeout(delayTimer)\n})\n</script>\n\n<template>\n <div\n v-if=\"visible\"\n data-gr-loading\n class=\"flex items-center justify-center cursor-wait select-none pointer-events-auto\"\n :class=\"rootClass\"\n :style=\"rootStyle\"\n role=\"status\"\n aria-live=\"polite\"\n >\n <div\n data-gr-loading-panel\n class=\"flex flex-col items-center justify-center gap-2 text-center rounded-[var(--gr-radius-md)] bg-[var(--gr-bg)]/55 px-5 py-4 shadow-lg\"\n >\n <slot>\n <GrIcon\n data-gr-loading-spinner\n :size=\"spinnerSize\"\n :tone=\"spinnerTone\"\n :spin=\"animated\"\n :class=\"spinnerClass\"\n >\n <component :is=\"Spinner\" />\n </GrIcon>\n <div v-if=\"displayText\" data-gr-loading-text class=\"text-[length:var(--gr-text-sm)] leading-[var(--gr-leading-sm)] text-[var(--gr-muted-fg)]\">\n {{ displayText }}\n </div>\n </slot>\n </div>\n </div>\n</template>\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAmDA,MAAM,QAAQ;EAmBd,MAAM,OAAO;EAOb,MAAM,EAAE,MAAM,2BAA2B;EAEzC,MAAM,UAAU,eAAe,MAAM,WAAW,qBAAU;EAE1D,MAAM,cAAc,eAAe,MAAM,QAAQ,EAAE,0BAA0B,YAAY,CAAC;EAE1F,MAAM,YAAY,eAAe;GAC/B,OAAO,mBAAmB;IACxB,YAAY,MAAM;IAClB,eAAe,MAAM,eAAe,KAAA;IACpC,aAAa,MAAM;GACrB,CAAC;EACH,CAAC;EAED,MAAM,YAAY,eAAe;GAC/B,OAAO;IACL,iBAAiB,MAAM;IACvB,QAAQ,MAAM,YAAY,OAAO,MAAM,UAAU,KAAK,KAAA;GACxD;EACF,CAAC;EAKD,MAAM,UAAU,IAAI,MAAM,SAAS,CAAC;EACpC,IAAI;EAEJ,gBAAgB;GACd,IAAI,QAAQ,OAAO;IACjB,KAAK,MAAM;IACX;GACF;GAEA,aAAa,iBAAiB;IAC5B,QAAQ,QAAQ;IAChB,KAAK,MAAM;GACb,GAAG,MAAM,KAAK;EAChB,CAAC;EAED,sBAAsB;GACpB,aAAa,UAAU;EACzB,CAAC;;UAKS,QAAA,SAAA,UAAA,GADR,mBA4BM,OAAA;;IA1BJ,mBAAA;IACA,OAAK,eAAA,CAAC,gFACE,UAAA,KAAS,CAAA;IAChB,OAAK,eAAE,UAAA,KAAS;IACjB,MAAK;IACL,aAAU;OAEV,mBAkBM,OAlBN,YAkBM,CAdJ,WAaO,KAAA,QAAA,WAAA,CAAA,SAAA,CAZL,YAQS,gBAAA;IAPP,2BAAA;IACC,MAAM,QAAA;IACN,MAAM,QAAA;IACN,MAAM,QAAA;IACN,OAAK,eAAE,QAAA,YAAY;;2BAEO,EAAA,UAAA,GAA3B,YAA2B,wBAAX,QAAA,KAAO,CAAA,EAAA,CAAA;;;;;;;OAEd,YAAA,SAAA,UAAA,GAAX,mBAEM,OAFN,YAEM,gBADD,YAAA,KAAW,GAAA,CAAA,KAAA,mBAAA,IAAA,IAAA,CAAA,CAAA,CAAA,CAAA,CAAA,GAAA,CAAA,KAAA,mBAAA,IAAA,IAAA"}