@feugene/granularity 0.31.0 → 0.32.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +0 -1
- package/dist/chunks/adapter-CAOxmn2G.js.map +1 -1
- package/dist/chunks/{config-BHcS5Cwm.js → config-87fszqnD.js} +1 -1
- package/dist/chunks/{config-BHcS5Cwm.js.map → config-87fszqnD.js.map} +1 -1
- package/dist/chunks/config-A-bBiotF.js.map +1 -1
- package/dist/chunks/config-B3J0alyY.js.map +1 -1
- package/dist/chunks/config-BhfNgyWL.js.map +1 -1
- package/dist/chunks/config-Bjn30smH.js.map +1 -1
- package/dist/chunks/config-BqT6PMzO.js.map +1 -1
- package/dist/chunks/config-C0Ea9ePP.js.map +1 -1
- package/dist/chunks/config-C0Eu8jpG.js.map +1 -1
- package/dist/chunks/config-CDat1wXf.js.map +1 -1
- package/dist/chunks/config-CQLNjc9X2.js.map +1 -1
- package/dist/chunks/config-CbEbLyDE.js.map +1 -1
- package/dist/chunks/{config-jyr6AIZt2.js → config-CuQmUkMw2.js} +2 -2
- package/dist/chunks/{config-jyr6AIZt2.js.map → config-CuQmUkMw2.js.map} +1 -1
- package/dist/chunks/config-DeyT9dJl.js.map +1 -1
- package/dist/chunks/config-DnF472Ox.js.map +1 -1
- package/dist/chunks/config-DwABJHEo.js.map +1 -1
- package/dist/chunks/{config-tiUtEn4Q.js → config-E1cTyRVV.js} +1 -1
- package/dist/chunks/{config-tiUtEn4Q.js.map → config-E1cTyRVV.js.map} +1 -1
- package/dist/chunks/config-MmPym-Z72.js.map +1 -1
- package/dist/chunks/config-T3-DMXYm.js.map +1 -1
- package/dist/chunks/config-Yy67uWHY.js.map +1 -1
- package/dist/chunks/config-_jbgsFpw.js.map +1 -1
- package/dist/chunks/config-g8-JGZ_Y.js.map +1 -1
- package/dist/chunks/config-mlheIMtV.js.map +1 -1
- package/dist/chunks/config-rLkc9Zn2.js.map +1 -1
- package/dist/chunks/config-uzUuosv7.js.map +1 -1
- package/dist/chunks/context-CTbuwcYs.js.map +1 -1
- package/dist/chunks/deltaTone-B5OoS1vo.js.map +1 -1
- package/dist/chunks/es-Do2CNrC2.js.map +1 -1
- package/dist/chunks/fileValidation-D5TFBhbv.js.map +1 -1
- package/dist/chunks/focusables-BkzK42SQ.js.map +1 -1
- package/dist/chunks/{generated-DJ2dJ__C.js → generated-CSyPsWtM.js} +1 -1
- package/dist/chunks/{generated-DJ2dJ__C.js.map → generated-CSyPsWtM.js.map} +1 -1
- package/dist/chunks/grBadgeStyles-D8Mz73B5.js.map +1 -1
- package/dist/chunks/{grButtonStyles-B_-YRE__.js → grButtonStyles-B3wRWW_i.js} +4 -4
- package/dist/chunks/grButtonStyles-B3wRWW_i.js.map +1 -0
- package/dist/chunks/grLinkStyles-FME_qMpi.js.map +1 -1
- package/dist/chunks/grLoadingStyles-CnQaf5ry.js.map +1 -1
- package/dist/chunks/{grRadioStyles-D4gnU65n.js → grRadioStyles-DGL2QLy6.js} +1 -1
- package/dist/chunks/{grRadioStyles-D4gnU65n.js.map → grRadioStyles-DGL2QLy6.js.map} +1 -1
- package/dist/chunks/grSelectStyles-Cdtd10eY.js.map +1 -1
- package/dist/chunks/{grSliderStyles-B5uNxNJq.js → grSliderStyles-kaz6VXZ3.js} +9 -1
- package/dist/chunks/grSliderStyles-kaz6VXZ3.js.map +1 -0
- package/dist/chunks/{granular-provider-yJNX1g1G.js → granular-provider-Da2CJO6j.js} +3 -3
- package/dist/chunks/{granular-provider-yJNX1g1G.js.map → granular-provider-Da2CJO6j.js.map} +1 -1
- package/dist/chunks/granularityI18n-BC5zsj_d.js.map +1 -1
- package/dist/chunks/icon-Dag2tIMs.js.map +1 -1
- package/dist/chunks/inert-DIHCCn_1.js.map +1 -1
- package/dist/chunks/keyboard-DE2yhz_b.js.map +1 -1
- package/dist/chunks/numericStep-Bq2lj4ew.js.map +1 -1
- package/dist/chunks/optionFilter-DYw9XPPx.js.map +1 -1
- package/dist/chunks/{overlayStack-C8cfsqXa.js → overlayStack-0CZS99Da.js} +40 -6
- package/dist/chunks/overlayStack-0CZS99Da.js.map +1 -0
- package/dist/chunks/portalRoot-CVhCgdG6.js.map +1 -1
- package/dist/chunks/renamedProp-BwcN-SJg.js.map +1 -1
- package/dist/chunks/{safelist-BOq5Li7p.js → safelist-DxkMj5IW.js} +1 -1
- package/dist/chunks/{safelist-BOq5Li7p.js.map → safelist-DxkMj5IW.js.map} +1 -1
- package/dist/chunks/slotNodes-DxNXpC7v.js.map +1 -1
- package/dist/chunks/useControlAddons-asUr10Pf.js.map +1 -1
- package/dist/chunks/useControlledOpen-DV3SqLTP.js.map +1 -1
- package/dist/chunks/useDragSort-0l47h4yb.js.map +1 -1
- package/dist/chunks/useFilePreviews-DnwgdyBs.js.map +1 -1
- package/dist/chunks/useFocusWithin-BwHE0rzm.js.map +1 -1
- package/dist/chunks/{useModalOverlay-Cv5hF63W.js → useModalOverlay-D__CqLGn.js} +3 -0
- package/dist/chunks/useModalOverlay-D__CqLGn.js.map +1 -0
- package/dist/chunks/usePortalTarget-C0p-mhaM.js.map +1 -1
- package/dist/chunks/validation-5HhpanPP.js.map +1 -1
- package/dist/components/GrAlert/chunks/GrAlert-FAVf-ksH.js.map +1 -1
- package/dist/components/GrAutocomplete/chunks/{GrAutocomplete-X6RlmiJQ.js → GrAutocomplete-rYEY15UI.js} +1 -1
- package/dist/components/GrAutocomplete/chunks/GrAutocomplete-rYEY15UI.js.map +1 -0
- package/dist/components/GrAutocomplete/index.js +1 -1
- package/dist/components/GrAutocomplete/styles.css +1 -1
- package/dist/components/GrAvatar/chunks/GrAvatar-CNmLmgcr.js.map +1 -1
- package/dist/components/GrBadge/chunks/{GrBadge-BsoocpF-.js → GrBadge-D2MfThPz.js} +1 -1
- package/dist/components/GrBadge/chunks/GrBadge-D2MfThPz.js.map +1 -0
- package/dist/components/GrBadge/index.js +1 -1
- package/dist/components/GrBadge/styles.css +1 -1
- package/dist/components/GrBadgeWrap/chunks/GrBadgeWrap-B-A3PRkE.js.map +1 -1
- package/dist/components/GrBottomNav/chunks/GrBottomNav-wtFatLjB.js.map +1 -1
- package/dist/components/GrBreadcrumbs/chunks/GrBreadcrumbs-DRDNan_n.js.map +1 -1
- package/dist/components/GrButton/chunks/{GrButton-Bw2AH4uX.js → GrButton-7GP0zObj.js} +1 -1
- package/dist/components/GrButton/chunks/GrButton-7GP0zObj.js.map +1 -0
- package/dist/components/GrButton/index.js +3 -3
- package/dist/components/GrButtonGroup/chunks/GrButtonGroup-CKyiAV8K.js.map +1 -1
- package/dist/components/GrCard/chunks/GrCard-BttXz1pQ.js.map +1 -1
- package/dist/components/GrCheckbox/chunks/GrCheckbox-CEcHIsXM.js.map +1 -1
- package/dist/components/GrCheckboxGroup/chunks/GrCheckboxGroup-BOwrVcFr.js.map +1 -1
- package/dist/components/GrChip/chunks/GrChip-C0vU69tf.js.map +1 -1
- package/dist/components/GrChipGroup/chunks/GrChipGroup-C78Vcwos.js.map +1 -1
- package/dist/components/GrCodeBlock/chunks/{GrCodeBlock-Dkvkr91t.js → GrCodeBlock-Dp0eEBTZ.js} +1 -1
- package/dist/components/GrCodeBlock/chunks/GrCodeBlock-Dp0eEBTZ.js.map +1 -0
- package/dist/components/GrCodeBlock/index.js +1 -1
- package/dist/components/GrCollapse/chunks/GrCollapse-BlW6ybdL.js.map +1 -1
- package/dist/components/GrColorPicker/chunks/{GrColorPicker-C7ifyQ0R.js → GrColorPicker-p2XH_8cE.js} +2 -2
- package/dist/components/GrColorPicker/chunks/GrColorPicker-p2XH_8cE.js.map +1 -0
- package/dist/components/GrColorPicker/index.js +1 -1
- package/dist/components/GrCommandPalette/chunks/{GrCommandPalette-C5abL2Y7.js → GrCommandPalette-BXbh3q7O.js} +2 -2
- package/dist/components/GrCommandPalette/chunks/GrCommandPalette-BXbh3q7O.js.map +1 -0
- package/dist/components/GrCommandPalette/index.js +1 -1
- package/dist/components/GrCommandPalette/styles.css +1 -1
- package/dist/components/GrConfigProvider/chunks/GrConfigProvider-BF7R3hgg.js.map +1 -1
- package/dist/components/GrConfirmDialog/chunks/{GrConfirmDialog-B9mIU78E.js → GrConfirmDialog-CUP43q__.js} +3 -3
- package/dist/components/GrConfirmDialog/chunks/GrConfirmDialog-CUP43q__.js.map +1 -0
- package/dist/components/GrConfirmDialog/index.js +1 -1
- package/dist/components/GrContextMenu/chunks/{GrContextMenu-_FKwQvuQ.js → GrContextMenu-ClkVjdcP.js} +1 -1
- package/dist/components/GrContextMenu/chunks/GrContextMenu-ClkVjdcP.js.map +1 -0
- package/dist/components/GrContextMenu/index.js +1 -1
- package/dist/components/GrDataTable/chunks/{GrDataTable-C8a9_nCg.js → GrDataTable-CAGgRk27.js} +5 -3
- package/dist/components/GrDataTable/chunks/GrDataTable-CAGgRk27.js.map +1 -0
- package/dist/components/GrDataTable/index.js +1 -1
- package/dist/components/GrDelta/chunks/GrDelta-BZwkgQW-.js.map +1 -1
- package/dist/components/GrDescriptionList/chunks/GrDescriptionList-BMeCgFV3.js.map +1 -1
- package/dist/components/GrDialog/chunks/{GrDialog-bOUDYfmh.js → GrDialog-BiMJ9_T4.js} +2 -2
- package/dist/components/GrDialog/chunks/{GrDialog-bOUDYfmh.js.map → GrDialog-BiMJ9_T4.js.map} +1 -1
- package/dist/components/GrDialog/index.js +1 -1
- package/dist/components/GrDialogService/chunks/{GrDialogService-6s2cQ-_6.js → GrDialogService-BxNK6crD.js} +4 -4
- package/dist/components/GrDialogService/chunks/GrDialogService-BxNK6crD.js.map +1 -0
- package/dist/components/GrDialogService/index.js +1 -1
- package/dist/components/GrDivider/chunks/GrDivider-BXavGcMX.js.map +1 -1
- package/dist/components/GrDrawer/chunks/{GrDrawer-B7PiAcbU.js → GrDrawer-Ce2l3zaG.js} +6 -5
- package/dist/components/GrDrawer/chunks/GrDrawer-Ce2l3zaG.js.map +1 -0
- package/dist/components/GrDrawer/index.js +1 -1
- package/dist/components/GrDropdown/chunks/GrDropdown-13Wt9eB_.js.map +1 -1
- package/dist/components/GrDropdownMenu/chunks/GrDropdownMenu-GOzuAXsi.js.map +1 -1
- package/dist/components/GrDropdownMenu/chunks/GrDropdownMenuList-B33ZzwfB.js.map +1 -1
- package/dist/components/GrFilePreview/chunks/GrFilePreview-C9Z7hMK8.js.map +1 -1
- package/dist/components/GrFileUpload/chunks/GrFileUpload-NsHkRRIa.js.map +1 -1
- package/dist/components/GrForm/chunks/GrForm-CrnfCsgj.js.map +1 -1
- package/dist/components/GrFormField/chunks/GrFormField-DSylU7IU.js.map +1 -1
- package/dist/components/GrFormFile/chunks/{GrFormFile-CYtXU9HV.js → GrFormFile-B1jGZyIj.js} +2 -2
- package/dist/components/GrFormFile/chunks/GrFormFile-B1jGZyIj.js.map +1 -0
- package/dist/components/GrFormFile/index.js +1 -1
- package/dist/components/GrFormFile/styles.css +1 -1
- package/dist/components/GrIcon/chunks/GrIcon-Dmf0c9ba.js.map +1 -1
- package/dist/components/GrImageViewer/chunks/{GrImageViewer-CyVN6Zpc.js → GrImageViewer-CG4vUBg_.js} +4 -3
- package/dist/components/GrImageViewer/chunks/GrImageViewer-CG4vUBg_.js.map +1 -0
- package/dist/components/GrImageViewer/index.js +1 -1
- package/dist/components/GrInput/chunks/GrInput-BLywRZUN.js.map +1 -1
- package/dist/components/GrInputTag/chunks/GrInputTag-Cj4A9Xgs.js.map +1 -1
- package/dist/components/GrJsonViewer/chunks/{GrJsonViewer-Cy2bknHO.js → GrJsonViewer-BCZ7lE2k.js} +2 -2
- package/dist/components/GrJsonViewer/chunks/GrJsonViewer-BCZ7lE2k.js.map +1 -0
- package/dist/components/GrJsonViewer/index.js +1 -1
- package/dist/components/GrKbd/chunks/GrKbd-D2ga1H9i.js.map +1 -1
- package/dist/components/GrLink/chunks/GrLink-DYXw3W9w.js.map +1 -1
- package/dist/components/GrList/chunks/{GrList-DmT4qzLO.js → GrList-B_CRJB4c.js} +1 -1
- package/dist/components/GrList/chunks/GrList-B_CRJB4c.js.map +1 -0
- package/dist/components/GrList/index.js +1 -1
- package/dist/components/GrList/styles.css +1 -1
- package/dist/components/GrModal/chunks/{GrModal-CCoWZuIl.js → GrModal-D0mf1SAx.js} +3 -2
- package/dist/components/GrModal/chunks/GrModal-D0mf1SAx.js.map +1 -0
- package/dist/components/GrModal/index.js +1 -1
- package/dist/components/GrNavbar/chunks/{GrNavbar-C5EjMKaC.js → GrNavbar-_rtHKwTf.js} +1 -1
- package/dist/components/GrNavbar/chunks/{GrNavbar-C5EjMKaC.js.map → GrNavbar-_rtHKwTf.js.map} +1 -1
- package/dist/components/GrNavbar/index.js +1 -1
- package/dist/components/GrNumberInput/chunks/GrNumberInput-DQ59YICu.js.map +1 -1
- package/dist/components/GrPagination/chunks/{GrPagination-Cw3R21dp.js → GrPagination-B_kAhoAV.js} +2 -2
- package/dist/components/GrPagination/chunks/{GrPagination-Cw3R21dp.js.map → GrPagination-B_kAhoAV.js.map} +1 -1
- package/dist/components/GrPagination/index.js +1 -1
- package/dist/components/GrPopover/chunks/{GrPopover-CofG-Tfe.js → GrPopover-faJanmGs.js} +1 -1
- package/dist/components/GrPopover/chunks/GrPopover-faJanmGs.js.map +1 -0
- package/dist/components/GrPopover/index.js +1 -1
- package/dist/components/GrPromptDialog/chunks/{GrPromptDialog-DLcl1xiq.js → GrPromptDialog-C6QGC7QJ.js} +4 -4
- package/dist/components/GrPromptDialog/chunks/GrPromptDialog-C6QGC7QJ.js.map +1 -0
- package/dist/components/GrPromptDialog/index.js +1 -1
- package/dist/components/GrRadio/chunks/{GrRadio-C_rESc5g.js → GrRadio-Aq3v8XgG.js} +1 -1
- package/dist/components/GrRadio/chunks/GrRadio-Aq3v8XgG.js.map +1 -0
- package/dist/components/GrRadio/index.js +2 -2
- package/dist/components/GrRadioGroup/chunks/{GrRadioGroup-CdQO4G-U.js → GrRadioGroup-y9LVdTWh.js} +1 -1
- package/dist/components/GrRadioGroup/chunks/GrRadioGroup-y9LVdTWh.js.map +1 -0
- package/dist/components/GrRadioGroup/index.js +1 -1
- package/dist/components/GrRating/chunks/GrRating-IEiTOdnF.js.map +1 -1
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-C_skObtv.js → GrResponseErrorBanner-CBVRpgIG.js} +1 -1
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-C_skObtv.js.map → GrResponseErrorBanner-CBVRpgIG.js.map} +1 -1
- package/dist/components/GrResponseErrorBanner/chunks/{GrResponseErrorBanner-DudGc9LO.js → GrResponseErrorBanner-DMeOWlzj.js} +1 -1
- package/dist/components/GrResponseErrorBanner/chunks/GrResponseErrorBanner-DMeOWlzj.js.map +1 -0
- package/dist/components/GrResponseErrorBanner/index.js +2 -2
- package/dist/components/GrSegmented/chunks/GrSegmented-CB-VR-yL.js.map +1 -1
- package/dist/components/GrSelect/chunks/{GrSelect-BiUrSSxc.js → GrSelect-gCeRFgQo.js} +1 -1
- package/dist/components/GrSelect/chunks/GrSelect-gCeRFgQo.js.map +1 -0
- package/dist/components/GrSelect/index.js +1 -1
- package/dist/components/GrSelect/styles.css +1 -1
- package/dist/components/GrSidebar/chunks/{GrSidebar-B8EQIlfW.js → GrSidebar-alkwBUzL.js} +1 -1
- package/dist/components/GrSidebar/chunks/GrSidebar-alkwBUzL.js.map +1 -0
- package/dist/components/GrSidebar/index.js +1 -1
- package/dist/components/GrSkeleton/chunks/GrSkeleton-CgfXxPQ2.js.map +1 -1
- package/dist/components/GrSlider/chunks/{GrSlider-DJfeEl4h.js → GrSlider-DTTrZTHK.js} +3 -3
- package/dist/components/GrSlider/chunks/GrSlider-DTTrZTHK.js.map +1 -0
- package/dist/components/GrSlider/index.js +2 -2
- package/dist/components/GrSortableList/chunks/GrSortableList-HyKX--rO.js.map +1 -1
- package/dist/components/GrSplitter/chunks/GrSplitter-MltjaADn.js.map +1 -1
- package/dist/components/GrStatistic/chunks/GrStatistic-qHVasK37.js.map +1 -1
- package/dist/components/GrSteps/chunks/GrSteps-C2jxpZoN.js.map +1 -1
- package/dist/components/GrSwitch/chunks/{GrSwitch-g_OOSkh7.js → GrSwitch-7Oe5QfQZ.js} +1 -1
- package/dist/components/GrSwitch/chunks/GrSwitch-7Oe5QfQZ.js.map +1 -0
- package/dist/components/GrSwitch/index.js +1 -1
- package/dist/components/GrTabPanels/chunks/GrTabPanels-BZQS8-JM.js.map +1 -1
- package/dist/components/GrTable/chunks/GrTable-Zcdz2St_.js.map +1 -1
- package/dist/components/GrTextarea/chunks/{GrTextarea-KREK75Bu.js → GrTextarea-DinXG12-.js} +10 -10
- package/dist/components/GrTextarea/chunks/GrTextarea-DinXG12-.js.map +1 -0
- package/dist/components/GrTextarea/index.js +1 -1
- package/dist/components/GrTimeline/chunks/GrTimeline-BiHpArsg.js.map +1 -1
- package/dist/components/GrToaster/chunks/{GrToaster-Dp7-4B8k.js → GrToaster-COXIBKzq.js} +2 -2
- package/dist/components/GrToaster/chunks/GrToaster-COXIBKzq.js.map +1 -0
- package/dist/components/GrToaster/index.js +1 -1
- package/dist/components/GrToaster/styles.css +1 -1
- package/dist/components/GrTooltip/chunks/GrTooltip-uYETdbCD.js.map +1 -1
- package/dist/components/GrTree/chunks/{GrTree-DC89I4AP.js → GrTree-Ci6CZfKR.js} +5 -5
- package/dist/components/GrTree/chunks/GrTree-Ci6CZfKR.js.map +1 -0
- package/dist/components/GrTree/index.js +1 -1
- package/dist/components/GrTree/styles.css +1 -1
- package/dist/components/GrTreeSelect/chunks/{GrTreeSelect-iJnMl2t9.js → GrTreeSelect-BHwgGJcT.js} +1 -1
- package/dist/components/GrTreeSelect/chunks/GrTreeSelect-BHwgGJcT.js.map +1 -0
- package/dist/components/GrTreeSelect/index.js +1 -1
- package/dist/composables/useAnnouncer.js.map +1 -1
- package/dist/composables/useComboboxNavigation.js.map +1 -1
- package/dist/composables/useDragGesture.js.map +1 -1
- package/dist/composables/useFloating.js +2 -22
- package/dist/composables/useFloating.js.map +1 -1
- package/dist/composables/useFocusTrap.js.map +1 -1
- package/dist/composables/useOverlayLayer.js +10 -3
- package/dist/composables/useOverlayLayer.js.map +1 -1
- package/dist/composables/useRovingFocus.js.map +1 -1
- package/dist/composables/useTheme.js.map +1 -1
- package/dist/composables/useToast.js.map +1 -1
- package/dist/composables/useVirtualList.js.map +1 -1
- package/dist/directives/autofocus.js.map +1 -1
- package/dist/directives/autosize.js.map +1 -1
- package/dist/directives/clickOutside.js.map +1 -1
- package/dist/directives/dropzone.js.map +1 -1
- package/dist/directives/hotkey.js.map +1 -1
- package/dist/directives/loading.js.map +1 -1
- package/dist/granular-provider-node.js +1 -1
- package/dist/granular-provider.js +1 -1
- package/dist/index.js +37 -37
- package/dist/testing.js +2 -2
- package/dist/testing.js.map +1 -1
- package/dist/theme-apply.js.map +1 -1
- package/dist/theme.js +1 -1
- package/dist/theme.js.map +1 -1
- package/dist/tokens.js +1 -1
- package/dist/types/components/GrCodeBlock/tokenizeJson.d.ts +1 -3
- package/dist/types/components/GrImageViewer/GrImageViewer.vue.d.ts +1 -1
- package/dist/types/components/GrInput/GrInput.vue.d.ts +24 -24
- package/dist/types/components/GrSlider/grSliderStyles.d.ts +9 -1
- package/dist/types/components/GrTabPanels/GrTabPanel.vue.d.ts +3 -3
- package/dist/types/composables/internal/overlayStack.d.ts +30 -0
- package/dist/types/composables/internal/useModalOverlay.d.ts +14 -0
- package/dist/types/composables/useOverlayLayer.d.ts +8 -0
- package/dist/vue/index.js.map +1 -1
- package/dist/web-types.json +1 -1
- package/package.json +3 -3
- package/dist/chunks/grButtonStyles-B_-YRE__.js.map +0 -1
- package/dist/chunks/grSliderStyles-B5uNxNJq.js.map +0 -1
- package/dist/chunks/overlayStack-C8cfsqXa.js.map +0 -1
- package/dist/chunks/useModalOverlay-Cv5hF63W.js.map +0 -1
- package/dist/components/GrAutocomplete/chunks/GrAutocomplete-X6RlmiJQ.js.map +0 -1
- package/dist/components/GrBadge/chunks/GrBadge-BsoocpF-.js.map +0 -1
- package/dist/components/GrButton/chunks/GrButton-Bw2AH4uX.js.map +0 -1
- package/dist/components/GrCodeBlock/chunks/GrCodeBlock-Dkvkr91t.js.map +0 -1
- package/dist/components/GrColorPicker/chunks/GrColorPicker-C7ifyQ0R.js.map +0 -1
- package/dist/components/GrCommandPalette/chunks/GrCommandPalette-C5abL2Y7.js.map +0 -1
- package/dist/components/GrConfirmDialog/chunks/GrConfirmDialog-B9mIU78E.js.map +0 -1
- package/dist/components/GrContextMenu/chunks/GrContextMenu-_FKwQvuQ.js.map +0 -1
- package/dist/components/GrDataTable/chunks/GrDataTable-C8a9_nCg.js.map +0 -1
- package/dist/components/GrDialogService/chunks/GrDialogService-6s2cQ-_6.js.map +0 -1
- package/dist/components/GrDrawer/chunks/GrDrawer-B7PiAcbU.js.map +0 -1
- package/dist/components/GrFormFile/chunks/GrFormFile-CYtXU9HV.js.map +0 -1
- package/dist/components/GrImageViewer/chunks/GrImageViewer-CyVN6Zpc.js.map +0 -1
- package/dist/components/GrJsonViewer/chunks/GrJsonViewer-Cy2bknHO.js.map +0 -1
- package/dist/components/GrList/chunks/GrList-DmT4qzLO.js.map +0 -1
- package/dist/components/GrModal/chunks/GrModal-CCoWZuIl.js.map +0 -1
- package/dist/components/GrPopover/chunks/GrPopover-CofG-Tfe.js.map +0 -1
- package/dist/components/GrPromptDialog/chunks/GrPromptDialog-DLcl1xiq.js.map +0 -1
- package/dist/components/GrRadio/chunks/GrRadio-C_rESc5g.js.map +0 -1
- package/dist/components/GrRadioGroup/chunks/GrRadioGroup-CdQO4G-U.js.map +0 -1
- package/dist/components/GrResponseErrorBanner/chunks/GrResponseErrorBanner-DudGc9LO.js.map +0 -1
- package/dist/components/GrSelect/chunks/GrSelect-BiUrSSxc.js.map +0 -1
- package/dist/components/GrSidebar/chunks/GrSidebar-B8EQIlfW.js.map +0 -1
- package/dist/components/GrSlider/chunks/GrSlider-DJfeEl4h.js.map +0 -1
- package/dist/components/GrSwitch/chunks/GrSwitch-g_OOSkh7.js.map +0 -1
- package/dist/components/GrTextarea/chunks/GrTextarea-KREK75Bu.js.map +0 -1
- package/dist/components/GrToaster/chunks/GrToaster-Dp7-4B8k.js.map +0 -1
- package/dist/components/GrTree/chunks/GrTree-DC89I4AP.js.map +0 -1
- package/dist/components/GrTreeSelect/chunks/GrTreeSelect-iJnMl2t9.js.map +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"GrTree-Ci6CZfKR.js","names":[],"sources":["../../../../src/components/GrTree/grTreeDataAdapter.ts","../../../../src/components/GrTree/grTreeInteractionContext.ts","../../../../src/components/GrTree/grTreeChecking.ts","../../../../src/components/GrTree/grTreeStore.ts","../../../../src/components/GrTree/grTreeStyles.ts","../../../../src/components/GrTree/GrTree.vue","../../../../src/components/GrTree/GrTree.vue"],"sourcesContent":["import type { GrTreeKey } from './grTreeTypes'\nimport type {\n GrTreeDataProps,\n GrTreePropsMap,\n} from './grTreeProps'\n\nconst DEFAULT_CHILDREN_KEY = 'children'\nconst DEFAULT_LABEL_KEY = 'label'\nconst DEFAULT_IS_LEAF_KEY = 'isLeaf'\n\nexport type GrTreeDataAdapterOptions<T extends object> = Pick<GrTreeDataProps<T>, 'props' | 'nodeKey'>\n\nexport type GrTreeDataAdapter<T extends object> = {\n hasNodeKey: () => boolean\n getChildrenKey: () => string\n getLabelKey: () => string\n getLabel: (data: T) => string\n /** Признак «лист» из данных. `undefined` — данные молчат, решает вызывающий. */\n getIsLeaf: (data: T) => boolean | undefined\n getChildren: (data: T) => T[]\n ensureChildren: (data: T) => T[]\n getNodeKey: (data: T, index: number, parentKey: GrTreeKey | undefined) => GrTreeKey\n getExplicitNodeKey: (data: T) => GrTreeKey | undefined\n}\n\nfunction isTreeKey(value: unknown): value is GrTreeKey {\n return typeof value === 'string' || typeof value === 'number'\n}\n\nfunction resolveMapValue(map: GrTreePropsMap | undefined, key: keyof GrTreePropsMap, fallback: string) {\n return map?.[key] ?? fallback\n}\n\nexport function createGrTreeDataAdapter<T extends Record<string, any> = any>(\n options: GrTreeDataAdapterOptions<T>,\n): GrTreeDataAdapter<T> {\n function hasNodeKey() {\n return options.nodeKey != null\n }\n\n function getChildrenKey() {\n return resolveMapValue(options.props, 'children', DEFAULT_CHILDREN_KEY)\n }\n\n function getLabelKey() {\n return resolveMapValue(options.props, 'label', DEFAULT_LABEL_KEY)\n }\n\n function getLabel(data: T): string {\n const key = getLabelKey() as keyof T\n const value = data[key]\n return value == null ? '' : String(value)\n }\n\n function getIsLeaf(data: T): boolean | undefined {\n const key = resolveMapValue(options.props, 'isLeaf', DEFAULT_IS_LEAF_KEY)\n const value = (data as Record<string, unknown>)[key]\n return typeof value === 'boolean' ? value : undefined\n }\n\n function getChildren(data: T): T[] {\n const key = getChildrenKey() as keyof T\n const value = data[key]\n return Array.isArray(value) ? (value as T[]) : []\n }\n\n function ensureChildren(data: T): T[] {\n const key = getChildrenKey()\n const record = data as Record<string, unknown>\n if (Array.isArray(record[key])) {\n return record[key] as T[]\n }\n\n record[key] = []\n\n // Читаем обратно, а не возвращаем только что созданный массив: у\n // реактивных данных чтение отдаёт прокси, и только запись через него\n // видна дереву. Иначе `push` уходит мимо реактивности, и добавленные\n // дети не появляются на экране.\n return record[key] as T[]\n }\n\n function getExplicitNodeKey(data: T): GrTreeKey | undefined {\n if (options.nodeKey == null)\n return undefined\n\n const keyName = options.nodeKey as keyof T\n const value = data[keyName] as unknown\n return isTreeKey(value) ? value : undefined\n }\n\n function getNodeKey(data: T, index: number, parentKey: GrTreeKey | undefined): GrTreeKey {\n const explicitKey = getExplicitNodeKey(data)\n if (explicitKey != null)\n return explicitKey\n\n return parentKey == null ? index : `${String(parentKey)}:${index}`\n }\n\n return {\n hasNodeKey,\n getChildrenKey,\n getLabelKey,\n getLabel,\n getIsLeaf,\n getChildren,\n ensureChildren,\n getNodeKey,\n getExplicitNodeKey,\n }\n}\n","import type { Ref, ShallowRef } from 'vue'\nimport { ref, shallowRef } from 'vue'\nimport type {\n GrTreeAllowDropType,\n GrTreeKey,\n GrTreeNode,\n GrTreeNodeDropType,\n} from './grTreeTypes'\n\nexport type GrTreeDropTarget = {\n key: GrTreeKey\n type: GrTreeNodeDropType\n allowed: boolean\n}\n\nexport type GrTreeInteractionOptions<T> = {\n draggable?: boolean\n allowDrop?: (draggingNode: GrTreeNode<T>, dropNode: GrTreeNode<T>, type: GrTreeAllowDropType) => boolean\n allowDrag?: (draggingNode: GrTreeNode<T>) => boolean\n}\n\nexport type GrTreeInteractionEmitters<T> = {\n emitNodeClick: (data: T, node: GrTreeNode<T>) => void\n emitNodeExpand: (data: T, node: GrTreeNode<T>) => void\n emitNodeCollapse: (data: T, node: GrTreeNode<T>) => void\n emitNodeDrop: (draggingNode: GrTreeNode<T>, dropNode: GrTreeNode<T>, dropType: GrTreeNodeDropType) => void\n emitNodeContextMenu: (evt: MouseEvent, data: T, node: GrTreeNode<T>) => void\n}\n\nexport type GrTreeInteractionContext<T> = {\n hoveredKey: Ref<GrTreeKey | undefined>\n /** Клавиша узла, держащего roving-фокус (единственный tabindex=0 во всём дереве). */\n /**\n * Реестр DOM-узлов строк, общий на все уровни дерева. Нужен клавиатуре: без\n * него каждое нажатие стрелки обходило бы весь DOM поддерева в поисках\n * строки по `data`-атрибуту.\n */\n nodeEls: Map<GrTreeKey, HTMLElement>\n registerNodeEl: (key: GrTreeKey, el: HTMLElement | null) => void\n draggingNode: ShallowRef<GrTreeNode<T> | null>\n dropTarget: ShallowRef<GrTreeDropTarget | null>\n canDrag: (node: GrTreeNode<T>) => boolean\n canDrop: (drag: GrTreeNode<T>, target: GrTreeNode<T>, type: GrTreeAllowDropType) => boolean\n resetDragState: () => void\n emitNodeClick: (data: T, node: GrTreeNode<T>) => void\n emitNodeExpand: (data: T, node: GrTreeNode<T>) => void\n emitNodeCollapse: (data: T, node: GrTreeNode<T>) => void\n emitNodeDrop: (draggingNode: GrTreeNode<T>, dropNode: GrTreeNode<T>, dropType: GrTreeNodeDropType) => void\n emitNodeContextMenu: (evt: MouseEvent, data: T, node: GrTreeNode<T>) => void\n}\n\nexport function createGrTreeInteractionContext<T>(\n options: GrTreeInteractionOptions<T>,\n emitters: GrTreeInteractionEmitters<T>,\n): GrTreeInteractionContext<T> {\n const hoveredKey = ref<GrTreeKey | undefined>(undefined)\n const draggingNode = shallowRef<GrTreeNode<T> | null>(null)\n const dropTarget = shallowRef<GrTreeDropTarget | null>(null)\n const nodeEls = new Map<GrTreeKey, HTMLElement>()\n\n function registerNodeEl(key: GrTreeKey, el: HTMLElement | null) {\n if (el) {\n nodeEls.set(key, el)\n return\n }\n\n // Перенос узла в другую ветку размонтирует старый элемент уже после того,\n // как зарегистрировался новый: снимаем запись, только если она протухла.\n const previous = nodeEls.get(key)\n if (previous && !previous.isConnected)\n nodeEls.delete(key)\n }\n\n function canDrag(node: GrTreeNode<T>): boolean {\n if (!options.draggable)\n return false\n\n if (options.allowDrag)\n return options.allowDrag(node)\n\n return true\n }\n\n function canDrop(drag: GrTreeNode<T>, target: GrTreeNode<T>, type: GrTreeAllowDropType): boolean {\n if (!options.allowDrop)\n return true\n\n return options.allowDrop(drag, target, type)\n }\n\n function resetDragState() {\n draggingNode.value = null\n dropTarget.value = null\n }\n\n return {\n hoveredKey,\n nodeEls,\n registerNodeEl,\n draggingNode,\n dropTarget,\n canDrag,\n canDrop,\n resetDragState,\n ...emitters,\n }\n}\n","import type { GrTreeKey, GrTreeNode } from './grTreeTypes'\n\n/**\n * Состояние отметки узла. `half` — часть потомков отмечена: в ARIA это\n * `aria-checked=\"mixed\"`.\n */\nexport const GR_TREE_CHECK_STATES = ['checked', 'half', 'unchecked'] as const\n\nexport type GrTreeCheckState = typeof GR_TREE_CHECK_STATES[number]\n\nexport type GrTreeCheckStates = Map<GrTreeKey, GrTreeCheckState>\n\n/**\n * Раскладывает отмеченные ключи по всему дереву: родитель отмечен, когда\n * отмечены все дети, и наполовину — когда часть.\n *\n * Считается от листьев вверх, поэтому `checkedKeys` снаружи может содержать\n * только листья (типовой формат ответа сервера) — родители посчитаются сами.\n * При `strict` дерево не связывает узлы вовсе: каждый отвечает сам за себя.\n */\nexport function resolveCheckStates<T>(\n roots: GrTreeNode<T>[],\n checkedKeys: Set<GrTreeKey>,\n strict: boolean,\n): GrTreeCheckStates {\n const states: GrTreeCheckStates = new Map()\n\n const walk = (node: GrTreeNode<T>): GrTreeCheckState => {\n if (strict || node.childNodes.length === 0) {\n const state: GrTreeCheckState = checkedKeys.has(node.key) ? 'checked' : 'unchecked'\n // В strict-режиме потомков всё равно нужно обойти: у них своё состояние.\n if (strict)\n node.childNodes.forEach(walk)\n states.set(node.key, state)\n return state\n }\n\n const childStates = node.childNodes.map(walk)\n const allChecked = childStates.every(s => s === 'checked')\n const someMarked = childStates.some(s => s !== 'unchecked')\n\n const state: GrTreeCheckState = allChecked\n ? 'checked'\n : (someMarked || checkedKeys.has(node.key) ? 'half' : 'unchecked')\n\n states.set(node.key, state)\n return state\n }\n\n roots.forEach(walk)\n return states\n}\n\n/**\n * Новый набор отмеченных ключей после переключения узла.\n *\n * Каскад идёт вниз (все потомки повторяют решение) и вверх (родитель отмечен,\n * только если отмечены все его дети). Возвращается набор с родителями —\n * `getCheckedKeys({ leafOnly: true })` при необходимости отбросит их обратно.\n */\nexport function toggleCheckedKeys<T>(\n roots: GrTreeNode<T>[],\n checkedKeys: Set<GrTreeKey>,\n node: GrTreeNode<T>,\n checked: boolean,\n strict: boolean,\n): Set<GrTreeKey> {\n const next = new Set(checkedKeys)\n\n if (strict) {\n if (checked)\n next.add(node.key)\n else next.delete(node.key)\n return next\n }\n\n const applyDown = (target: GrTreeNode<T>): void => {\n if (checked)\n next.add(target.key)\n else next.delete(target.key)\n target.childNodes.forEach(applyDown)\n }\n applyDown(node)\n\n for (let parent = node.parent; parent; parent = parent.parent) {\n const allChecked = parent.childNodes.every(child => next.has(child.key))\n if (allChecked)\n next.add(parent.key)\n else next.delete(parent.key)\n }\n\n // Отметки узлов, которых уже нет в дереве, тянуть незачем.\n return pruneToTree(roots, next)\n}\n\n/** Отбрасывает ключи, которых нет в текущей модели (данные могли смениться). */\nexport function pruneToTree<T>(roots: GrTreeNode<T>[], keys: Set<GrTreeKey>): Set<GrTreeKey> {\n const known = new Set<GrTreeKey>()\n const walk = (node: GrTreeNode<T>): void => {\n known.add(node.key)\n node.childNodes.forEach(walk)\n }\n roots.forEach(walk)\n\n const next = new Set<GrTreeKey>()\n for (const key of keys) {\n if (known.has(key))\n next.add(key)\n }\n return next\n}\n\n/** Ключи в состоянии `checked`; `leafOnly` оставляет только листья. */\nexport function collectCheckedKeys<T>(\n roots: GrTreeNode<T>[],\n states: GrTreeCheckStates,\n leafOnly: boolean,\n): GrTreeKey[] {\n const out: GrTreeKey[] = []\n\n const walk = (node: GrTreeNode<T>): void => {\n const isLeaf = node.childNodes.length === 0\n if (states.get(node.key) === 'checked' && (!leafOnly || isLeaf))\n out.push(node.key)\n node.childNodes.forEach(walk)\n }\n\n roots.forEach(walk)\n return out\n}\n\n/** Ключи в состоянии `half` — родители с частично отмеченными потомками. */\nexport function collectHalfCheckedKeys(states: GrTreeCheckStates): GrTreeKey[] {\n const out: GrTreeKey[] = []\n for (const [key, state] of states) {\n if (state === 'half')\n out.push(key)\n }\n return out\n}\n","import type { ComputedRef, MaybeRefOrGetter, Ref, ShallowRef } from 'vue'\nimport { computed, ref, shallowRef, toValue, watch } from 'vue'\nimport type {\n GrTreeKey,\n GrTreeNode,\n GrTreeNodeDropType,\n GrTreeNodeTarget,\n} from './grTreeTypes'\nimport type { GrTreeDataAdapter } from './grTreeDataAdapter'\nimport type { GrTreeDataProps, GrTreeFilterNodeMethod, GrTreeLoad } from './grTreeProps'\nimport type { GrTreeCheckState, GrTreeCheckStates } from './grTreeChecking'\nimport {\n collectCheckedKeys,\n collectHalfCheckedKeys,\n pruneToTree,\n resolveCheckStates,\n toggleCheckedKeys,\n} from './grTreeChecking'\n\ntype TreeModel<T extends object> = {\n roots: GrTreeNode<T>[]\n byKey: Map<GrTreeKey, GrTreeNode<T>>\n byData: WeakMap<T, GrTreeNode<T>>\n}\n\ntype FilterInfo = {\n isActive: boolean\n subtreeHasMatch: Map<GrTreeKey, boolean>\n matchedKeys: Set<GrTreeKey>\n autoExpandKeys: Set<GrTreeKey>\n}\n\nexport type GrTreeStoreOptions<T extends object> = {\n data: MaybeRefOrGetter<GrTreeDataProps<T>['data']>\n defaultExpandedKeys?: MaybeRefOrGetter<GrTreeDataProps<T>['defaultExpandedKeys']>\n defaultExpandAll?: MaybeRefOrGetter<boolean | undefined>\n filterNodeMethod?: MaybeRefOrGetter<GrTreeFilterNodeMethod<T> | undefined>\n defaultCheckedKeys?: MaybeRefOrGetter<GrTreeKey[] | undefined>\n /** Внешние отмеченные ключи (`v-model:checked-keys`), если потребитель их ведёт. */\n checkedKeys?: MaybeRefOrGetter<GrTreeKey[] | undefined>\n checkStrictly?: MaybeRefOrGetter<boolean | undefined>\n lazy?: MaybeRefOrGetter<boolean | undefined>\n load?: MaybeRefOrGetter<GrTreeLoad<T> | undefined>\n adapter: GrTreeDataAdapter<T>\n}\n\nexport type GrTreeStore<T extends object> = {\n filterValue: Ref<string>\n expandedKeys: ShallowRef<Set<GrTreeKey>>\n checkedKeys: ShallowRef<Set<GrTreeKey>>\n checkStates: ComputedRef<GrTreeCheckStates>\n loadingKeys: ShallowRef<Set<GrTreeKey>>\n loadedKeys: ShallowRef<Set<GrTreeKey>>\n loadedChildren: ShallowRef<Map<GrTreeKey, T[]>>\n currentKey: Ref<GrTreeKey | undefined>\n treeModel: ComputedRef<TreeModel<T>>\n filterInfo: ComputedRef<FilterInfo>\n filter: (value: string) => void\n isExpandedKey: (key: GrTreeKey) => boolean\n setExpandedKey: (key: GrTreeKey, expanded: boolean) => void\n toggleExpand: (node: GrTreeNode<T>) => void\n setCurrentKey: (key?: GrTreeKey) => void\n getCurrentKey: () => GrTreeKey | undefined\n getCurrentNode: () => GrTreeNode<T> | undefined\n setCurrentNode: (node?: GrTreeNodeTarget<T>) => boolean\n getNode: (key: GrTreeKey) => GrTreeNode<T> | undefined\n canMoveNode: (node: GrTreeNodeTarget<T>, referenceNode: GrTreeNodeTarget<T>, dropType: GrTreeNodeDropType) => boolean\n moveNode: (node: GrTreeNodeTarget<T>, referenceNode: GrTreeNodeTarget<T>, dropType: GrTreeNodeDropType) => GrTreeNode<T> | undefined\n appendNode: (data: T, parent: GrTreeNodeTarget<T>) => GrTreeNode<T> | undefined\n removeNode: (node: GrTreeNodeTarget<T>) => boolean\n insertNodeBefore: (data: T, referenceNode: GrTreeNodeTarget<T>) => GrTreeNode<T> | undefined\n insertNodeAfter: (data: T, referenceNode: GrTreeNodeTarget<T>) => GrTreeNode<T> | undefined\n getCheckState: (key: GrTreeKey) => GrTreeCheckState\n setChecked: (node: GrTreeNodeTarget<T>, checked: boolean) => GrTreeNode<T> | undefined\n toggleChecked: (node: GrTreeNode<T>) => GrTreeNode<T> | undefined\n getCheckedKeys: (options?: { leafOnly?: boolean }) => GrTreeKey[]\n setCheckedKeys: (keys: GrTreeKey[]) => void\n getHalfCheckedKeys: () => GrTreeKey[]\n /** Лист ли узел с точки зрения раскрытия: в ленивом режиме решают данные и факт загрузки. */\n isLeafNode: (node: GrTreeNode<T>) => boolean\n isLoadingKey: (key: GrTreeKey) => boolean\n /** Грузит детей ветки, если это нужно и ещё не делалось. */\n ensureLoaded: (node: GrTreeNode<T>) => void\n}\n\nexport function createGrTreeStore<T extends Record<string, any> = any>(\n options: GrTreeStoreOptions<T>,\n): GrTreeStore<T> {\n const filterValue = ref('')\n const expandedKeys = shallowRef<Set<GrTreeKey>>(new Set())\n const checkedKeys = shallowRef<Set<GrTreeKey>>(new Set(toValue(options.defaultCheckedKeys) ?? []))\n const loadingKeys = shallowRef<Set<GrTreeKey>>(new Set())\n const loadedKeys = shallowRef<Set<GrTreeKey>>(new Set())\n // Дети, пришедшие ленивой загрузкой, живут в сторе, а не в данных потребителя:\n // `data` — обычный проп и реактивным быть не обязан, а дерево обязано\n // показать загруженное в любом случае.\n const loadedChildren = shallowRef<Map<GrTreeKey, T[]>>(new Map())\n const currentKey = ref<GrTreeKey | undefined>(undefined)\n const getData = () => toValue(options.data) ?? []\n const getFilterNodeMethod = () => toValue(options.filterNodeMethod)\n\n watch(\n () => toValue(options.defaultExpandedKeys),\n (keys) => {\n expandedKeys.value = new Set(keys ?? [])\n },\n { immediate: true },\n )\n\n // Внешние отметки: компонент управляемый, пока проп задан. Не задан — ведёт\n // набор сам, начиная с `defaultCheckedKeys`.\n watch(\n () => toValue(options.checkedKeys),\n (keys) => {\n if (keys)\n checkedKeys.value = new Set(keys)\n },\n { immediate: true },\n )\n\n const treeModel = computed<TreeModel<T>>(() => {\n const byKey = new Map<GrTreeKey, GrTreeNode<T>>()\n const byData = new WeakMap<T, GrTreeNode<T>>()\n\n const build = (items: T[], parent: GrTreeNode<T> | undefined, level: number): GrTreeNode<T>[] => {\n return items.map((item, index) => {\n const node: GrTreeNode<T> = {\n key: options.adapter.getNodeKey(item, index, parent?.key),\n label: options.adapter.getLabel(item),\n data: item,\n level,\n parent,\n childNodes: [],\n }\n\n byKey.set(node.key, node)\n byData.set(item, node)\n\n const ownChildren = options.adapter.getChildren(item)\n const lazyChildren = loadedChildren.value.get(node.key) ?? []\n node.childNodes = build([...ownChildren, ...lazyChildren], node, level + 1)\n\n return node\n })\n }\n\n return {\n roots: build(getData(), undefined, 1),\n byKey,\n byData,\n }\n })\n\n // `defaultExpandAll` раскрывает узел один раз — в момент его появления в\n // данных. Иначе любое обновление `data` отменяло бы всё, что пользователь\n // свернул руками.\n const autoExpandedKeys = new Set<GrTreeKey>()\n watch(treeModel, (model) => {\n if (!toValue(options.defaultExpandAll))\n return\n\n const next = new Set(expandedKeys.value)\n let changed = false\n\n for (const key of model.byKey.keys()) {\n if (autoExpandedKeys.has(key))\n continue\n\n autoExpandedKeys.add(key)\n next.add(key)\n changed = true\n }\n\n if (changed)\n expandedKeys.value = next\n }, { immediate: true })\n\n const filterInfo = computed<FilterInfo>(() => {\n const value = filterValue.value\n const isActive = value.trim().length > 0\n const valueLower = value.toLowerCase()\n const subtreeHasMatch = new Map<GrTreeKey, boolean>()\n const matchedKeys = new Set<GrTreeKey>()\n const autoExpandKeys = new Set<GrTreeKey>()\n\n if (!isActive) {\n return {\n isActive,\n subtreeHasMatch,\n matchedKeys,\n autoExpandKeys,\n }\n }\n\n const match = (node: GrTreeNode<T>): boolean => {\n const filterNodeMethod = getFilterNodeMethod()\n if (filterNodeMethod)\n return filterNodeMethod(value, node.data, node)\n\n return node.label.toLowerCase().includes(valueLower)\n }\n\n const walk = (nodes: GrTreeNode<T>[]): boolean => {\n let any = false\n\n for (const node of nodes) {\n const self = match(node)\n const childAny = walk(node.childNodes)\n const has = self || childAny\n\n subtreeHasMatch.set(node.key, has)\n\n if (self)\n matchedKeys.add(node.key)\n\n if (childAny)\n autoExpandKeys.add(node.key)\n\n any ||= has\n }\n\n return any\n }\n\n walk(treeModel.value.roots)\n\n return {\n isActive,\n subtreeHasMatch,\n matchedKeys,\n autoExpandKeys,\n }\n })\n\n function getNode(key: GrTreeKey) {\n return treeModel.value.byKey.get(key)\n }\n\n function findNodeByData(data: T): GrTreeNode<T> | undefined {\n return treeModel.value.byData.get(data)\n }\n\n function isTreeNode(target: GrTreeNodeTarget<T>): target is GrTreeNode<T> {\n return typeof target === 'object'\n && target !== null\n && 'key' in target\n && 'data' in target\n && 'childNodes' in target\n }\n\n function resolveNodeTarget(target?: GrTreeNodeTarget<T>): GrTreeNode<T> | undefined {\n if (target == null)\n return undefined\n\n if (typeof target === 'string' || typeof target === 'number')\n return getNode(target)\n\n if (isTreeNode(target))\n return getNode(target.key) ?? target\n\n const key = options.adapter.getExplicitNodeKey(target)\n if (key != null)\n return getNode(key)\n\n return findNodeByData(target)\n }\n\n function getNodeContainer(node: GrTreeNode<T>) {\n const items = node.parent ? options.adapter.ensureChildren(node.parent.data) : getData()\n\n let index = items.findIndex(item => item === node.data)\n if (index >= 0)\n return { items, index }\n\n const key = options.adapter.getExplicitNodeKey(node.data)\n if (key == null)\n return undefined\n\n index = items.findIndex(item => options.adapter.getExplicitNodeKey(item) === key)\n if (index < 0)\n return undefined\n\n return { items, index }\n }\n\n function isDescendantNode(ancestor: GrTreeNode<T>, node: GrTreeNode<T>) {\n let current = node.parent\n\n while (current) {\n if (current.key === ancestor.key)\n return true\n\n current = current.parent\n }\n\n return false\n }\n\n function canMoveNode(node: GrTreeNodeTarget<T>, referenceNode: GrTreeNodeTarget<T>, dropType: GrTreeNodeDropType) {\n const sourceNode = resolveNodeTarget(node)\n const targetNode = resolveNodeTarget(referenceNode)\n\n if (!sourceNode || !targetNode)\n return false\n\n if (sourceNode.key === targetNode.key)\n return false\n\n if (isDescendantNode(sourceNode, targetNode))\n return false\n\n const sourceContainer = getNodeContainer(sourceNode)\n if (!sourceContainer)\n return false\n\n if (dropType === 'inner')\n return true\n\n return Boolean(getNodeContainer(targetNode))\n }\n\n function sanitizeTreeState() {\n const byKey = treeModel.value.byKey\n\n if (currentKey.value != null && !byKey.has(currentKey.value))\n currentKey.value = undefined\n\n const nextExpandedKeys = new Set(Array.from(expandedKeys.value).filter(key => byKey.has(key)))\n if (nextExpandedKeys.size !== expandedKeys.value.size)\n expandedKeys.value = nextExpandedKeys\n\n const nextCheckedKeys = new Set(Array.from(checkedKeys.value).filter(key => byKey.has(key)))\n if (nextCheckedKeys.size !== checkedKeys.value.size)\n checkedKeys.value = nextCheckedKeys\n }\n\n function isExpandedKey(key: GrTreeKey): boolean {\n return expandedKeys.value.has(key)\n }\n\n function setExpandedKey(key: GrTreeKey, expanded: boolean) {\n const next = new Set(expandedKeys.value)\n\n if (expanded)\n next.add(key)\n else\n next.delete(key)\n\n expandedKeys.value = next\n }\n\n function toggleExpand(node: GrTreeNode<T>) {\n setExpandedKey(node.key, !isExpandedKey(node.key))\n }\n\n function setCurrentKey(key?: GrTreeKey) {\n currentKey.value = key\n }\n\n function getCurrentKey() {\n return currentKey.value\n }\n\n function getCurrentNode() {\n const key = currentKey.value\n return key == null ? undefined : getNode(key)\n }\n\n function setCurrentNode(node?: GrTreeNodeTarget<T>) {\n if (node == null) {\n currentKey.value = undefined\n return true\n }\n\n const targetNode = resolveNodeTarget(node)\n if (!targetNode)\n return false\n\n currentKey.value = targetNode.key\n return true\n }\n\n function resolveInsertedNode(data: T) {\n const key = options.adapter.getExplicitNodeKey(data)\n if (key != null)\n return getNode(key)\n\n return findNodeByData(data)\n }\n\n function moveNode(node: GrTreeNodeTarget<T>, referenceNode: GrTreeNodeTarget<T>, dropType: GrTreeNodeDropType) {\n const sourceNode = resolveNodeTarget(node)\n const targetNode = resolveNodeTarget(referenceNode)\n\n if (!sourceNode || !targetNode)\n return undefined\n\n if (!canMoveNode(sourceNode, targetNode, dropType))\n return undefined\n\n const sourceContainer = getNodeContainer(sourceNode)\n if (!sourceContainer)\n return undefined\n\n let destinationItems: T[]\n let destinationIndex: number\n\n if (dropType === 'inner') {\n destinationItems = options.adapter.ensureChildren(targetNode.data)\n destinationIndex = destinationItems.length\n }\n else {\n const targetContainer = getNodeContainer(targetNode)\n if (!targetContainer)\n return undefined\n\n destinationItems = targetContainer.items\n destinationIndex = dropType === 'prev'\n ? targetContainer.index\n : targetContainer.index + 1\n }\n\n if (destinationItems === sourceContainer.items && sourceContainer.index < destinationIndex)\n destinationIndex -= 1\n\n const [movedData] = sourceContainer.items.splice(sourceContainer.index, 1)\n destinationItems.splice(destinationIndex, 0, movedData)\n\n if (dropType === 'inner')\n setExpandedKey(targetNode.key, true)\n\n sanitizeTreeState()\n return resolveInsertedNode(movedData)\n }\n\n function appendNode(data: T, parent: GrTreeNodeTarget<T>) {\n const parentNode = resolveNodeTarget(parent)\n if (!parentNode)\n return undefined\n\n options.adapter.ensureChildren(parentNode.data).push(data)\n setExpandedKey(parentNode.key, true)\n sanitizeTreeState()\n return resolveInsertedNode(data)\n }\n\n function removeNode(node: GrTreeNodeTarget<T>) {\n if (!options.adapter.hasNodeKey())\n return false\n\n const targetNode = resolveNodeTarget(node)\n if (!targetNode)\n return false\n\n const container = getNodeContainer(targetNode)\n if (!container)\n return false\n\n container.items.splice(container.index, 1)\n sanitizeTreeState()\n return true\n }\n\n function insertNodeBefore(data: T, referenceNode: GrTreeNodeTarget<T>) {\n const targetNode = resolveNodeTarget(referenceNode)\n if (!targetNode)\n return undefined\n\n const container = getNodeContainer(targetNode)\n if (!container)\n return undefined\n\n container.items.splice(container.index, 0, data)\n sanitizeTreeState()\n return resolveInsertedNode(data)\n }\n\n function insertNodeAfter(data: T, referenceNode: GrTreeNodeTarget<T>) {\n const targetNode = resolveNodeTarget(referenceNode)\n if (!targetNode)\n return undefined\n\n const container = getNodeContainer(targetNode)\n if (!container)\n return undefined\n\n container.items.splice(container.index + 1, 0, data)\n sanitizeTreeState()\n return resolveInsertedNode(data)\n }\n\n // ————— Отметки (чекбоксы).\n\n const checkStates = computed<GrTreeCheckStates>(() => resolveCheckStates(\n treeModel.value.roots,\n checkedKeys.value,\n Boolean(toValue(options.checkStrictly)),\n ))\n\n function getCheckState(key: GrTreeKey): GrTreeCheckState {\n return checkStates.value.get(key) ?? 'unchecked'\n }\n\n function setChecked(node: GrTreeNodeTarget<T>, checked: boolean) {\n const targetNode = resolveNodeTarget(node)\n if (!targetNode)\n return undefined\n\n checkedKeys.value = toggleCheckedKeys(\n treeModel.value.roots,\n checkedKeys.value,\n targetNode,\n checked,\n Boolean(toValue(options.checkStrictly)),\n )\n\n return targetNode\n }\n\n function toggleChecked(node: GrTreeNode<T>) {\n return setChecked(node, getCheckState(node.key) !== 'checked')\n }\n\n function getCheckedKeys(opts?: { leafOnly?: boolean }) {\n return collectCheckedKeys(treeModel.value.roots, checkStates.value, Boolean(opts?.leafOnly))\n }\n\n function setCheckedKeys(keys: GrTreeKey[]) {\n checkedKeys.value = pruneToTree(treeModel.value.roots, new Set(keys))\n }\n\n function getHalfCheckedKeys() {\n return collectHalfCheckedKeys(checkStates.value)\n }\n\n // ————— Ленивая подгрузка ветки.\n\n function isLeafNode(node: GrTreeNode<T>): boolean {\n if (node.childNodes.length > 0)\n return false\n\n if (!toValue(options.lazy))\n return true\n\n const declared = options.adapter.getIsLeaf(node.data)\n if (declared !== undefined)\n return declared\n\n // Данные молчат: пока ветку не грузили, считаем её разворачиваемой —\n // иначе до первого запроса дело бы не дошло.\n return loadedKeys.value.has(node.key)\n }\n\n function isLoadingKey(key: GrTreeKey): boolean {\n return loadingKeys.value.has(key)\n }\n\n function markLoading(key: GrTreeKey, loading: boolean) {\n const next = new Set(loadingKeys.value)\n if (loading)\n next.add(key)\n else\n next.delete(key)\n loadingKeys.value = next\n }\n\n function ensureLoaded(node: GrTreeNode<T>) {\n const load = toValue(options.load)\n if (!toValue(options.lazy) || !load)\n return\n\n if (loadedKeys.value.has(node.key) || loadingKeys.value.has(node.key) || isLeafNode(node))\n return\n\n markLoading(node.key, true)\n\n let settled = false\n load(node, (children) => {\n // Ответ приходит от потребителя: второй вызов `resolve` — его ошибка, но\n // дублировать детей из-за неё дерево не обязано.\n if (settled)\n return\n settled = true\n\n const next = new Map(loadedChildren.value)\n next.set(node.key, [...(children ?? [])])\n loadedChildren.value = next\n loadedKeys.value = new Set(loadedKeys.value).add(node.key)\n markLoading(node.key, false)\n })\n }\n function filter(value: string) {\n filterValue.value = value\n }\n\n return {\n filterValue,\n expandedKeys,\n loadedChildren,\n checkedKeys,\n checkStates,\n loadingKeys,\n loadedKeys,\n currentKey,\n treeModel,\n filterInfo,\n filter,\n isExpandedKey,\n setExpandedKey,\n toggleExpand,\n setCurrentKey,\n getCurrentKey,\n getCurrentNode,\n setCurrentNode,\n getNode,\n canMoveNode,\n moveNode,\n appendNode,\n removeNode,\n insertNodeBefore,\n insertNodeAfter,\n getCheckState,\n setChecked,\n toggleChecked,\n getCheckedKeys,\n setCheckedKeys,\n getHalfCheckedKeys,\n isLeafNode,\n isLoadingKey,\n ensureLoaded,\n }\n}\n","import type { GrComponentSize } from '../shared/sizes'\n\nexport type GrTreeSize = GrComponentSize\n\n/**\n * Размер дерева выражен переменными, а не утилитарными классами: те же\n * `--gr-tree-*` уже объявлены точками кастомизации в `GrTree.vue`, и size\n * обязан задавать им дефолты, а не спорить с ними отдельным каналом.\n *\n * `font-size` на `md` намеренно `inherit`: дерево по умолчанию набирается\n * кеглем родителя, и подстановка конкретных пикселей сменила бы вид всем,\n * кто ничего не просил.\n */\nexport type GrTreeSizeVars = {\n '--gr-tree-row-min-height': string\n '--gr-tree-row-px': string\n '--gr-tree-row-py': string\n '--gr-tree-toggle-size': string\n '--gr-tree-drag-handle-size': string\n '--gr-tree-icon-size': string\n '--gr-tree-content-gap': string\n '--gr-tree-font-size': string\n}\n\nexport const treeSizeVars: Record<GrTreeSize, GrTreeSizeVars> = {\n xs: {\n '--gr-tree-row-min-height': '22px',\n '--gr-tree-row-px': '4px',\n '--gr-tree-row-py': '3px',\n '--gr-tree-toggle-size': '18px',\n '--gr-tree-drag-handle-size': '18px',\n '--gr-tree-icon-size': '12px',\n '--gr-tree-content-gap': '4px',\n '--gr-tree-font-size': '12px',\n },\n sm: {\n '--gr-tree-row-min-height': '24px',\n '--gr-tree-row-px': '6px',\n '--gr-tree-row-py': '5px',\n '--gr-tree-toggle-size': '20px',\n '--gr-tree-drag-handle-size': '20px',\n '--gr-tree-icon-size': '14px',\n '--gr-tree-content-gap': '6px',\n '--gr-tree-font-size': '13px',\n },\n md: {\n '--gr-tree-row-min-height': '28px',\n '--gr-tree-row-px': '8px',\n '--gr-tree-row-py': '8px',\n '--gr-tree-toggle-size': '24px',\n '--gr-tree-drag-handle-size': '24px',\n '--gr-tree-icon-size': '16px',\n '--gr-tree-content-gap': '8px',\n '--gr-tree-font-size': 'inherit',\n },\n lg: {\n '--gr-tree-row-min-height': '32px',\n '--gr-tree-row-px': '10px',\n '--gr-tree-row-py': '10px',\n '--gr-tree-toggle-size': '28px',\n '--gr-tree-drag-handle-size': '28px',\n '--gr-tree-icon-size': '20px',\n '--gr-tree-content-gap': '10px',\n '--gr-tree-font-size': '15px',\n },\n}\n","<script setup lang=\"ts\" generic=\"T extends Record<string, any> = any\">\nimport { computed, nextTick, onBeforeUnmount, ref, watch } from 'vue'\nimport type {\n GrTreeAllowDropType,\n GrTreeInstance,\n GrTreeKey,\n GrTreeNode,\n GrTreeNodeDropType,\n} from './grTreeTypes'\nimport { createGrTreeDataAdapter } from './grTreeDataAdapter'\nimport type { GrTreeDropTarget } from './grTreeInteractionContext'\nimport { createGrTreeInteractionContext } from './grTreeInteractionContext'\nimport type { GrTreeCheckState } from './grTreeChecking'\nimport { createGrTreeStore } from './grTreeStore'\nimport { treeSizeVars } from './grTreeStyles'\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport { useAnnouncer } from '../../composables/useAnnouncer'\nimport { useDragSort } from '../../composables/useDragSort'\nimport { useTypeahead } from '../../composables/internal/useTypeahead'\nimport { useRovingFocus } from '../../composables/useRovingFocus'\nimport { useVirtualList } from '../../composables/useVirtualList'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { iconClass, iconTag } from '../shared/icon'\n\nimport IconCheck from '~icons/lucide/check'\nimport IconChevronRight from '~icons/lucide/chevron-right'\nimport IconGripVertical from '~icons/lucide/grip-vertical'\nimport IconLoaderCircle from '~icons/lucide/loader-circle'\nimport IconMinus from '~icons/lucide/minus'\nimport type {\n GrTreeBranchLineColor,\n GrTreeNodeClass,\n GrTreeProps,\n GrTreeVisibleRow,\n} from './grTreeProps'\n\nexport interface GrTreeEmits<T extends Record<string, any> = any> {\n (e: 'nodeClick', data: T, node: GrTreeNode<T>): void\n (e: 'nodeExpand', data: T, node: GrTreeNode<T>): void\n (e: 'nodeCollapse', data: T, node: GrTreeNode<T>): void\n (e: 'nodeDrop', draggingNode: GrTreeNode<T>, dropNode: GrTreeNode<T>, dropType: GrTreeNodeDropType): void\n (e: 'nodeContextMenu', evt: MouseEvent, data: T, node: GrTreeNode<T>): void\n (e: 'update:currentKey', key: GrTreeKey | undefined): void\n /**\n * Результат фильтрации. Без него потребитель не отличит «данных нет» от\n * «поиск ничего не нашёл» — а это разные пустые экраны: второй пользователь\n * может исправить сам.\n */\n (e: 'filter', info: { value: string, visibleCount: number, matchedCount: number }): void\n (e: 'update:checkedKeys', keys: GrTreeKey[]): void\n (e: 'check', data: T, node: GrTreeNode<T>, info: { checkedKeys: GrTreeKey[], halfCheckedKeys: GrTreeKey[] }): void\n}\n\nconst DEFAULT_BRANCH_LINE_COLOR = 'var(--gr-tree-branch-line-default-color, var(--gr-brd))'\n\n/** Стрелки, которые вместе с `Shift` двигают узел, а не фокус. */\nconst MOVE_KEYS = new Set(['ArrowUp', 'ArrowDown', 'ArrowLeft', 'ArrowRight'])\n\nconst props = withDefaults(defineProps<GrTreeProps<T>>(), {\n props: () => ({\n children: 'children',\n label: 'label',\n }),\n nodeKey: 'id' as any,\n defaultExpandedKeys: () => [],\n defaultExpandAll: false,\n expandOnClickNode: false,\n accordion: false,\n size: undefined,\n highlightCurrent: true,\n indent: 0,\n virtual: false,\n maxHeight: undefined,\n showCheckbox: false,\n currentKey: undefined,\n filterValue: undefined,\n dragHandleVisibility: 'auto',\n checkedKeys: undefined,\n defaultCheckedKeys: () => [],\n checkStrictly: false,\n lazy: false,\n load: undefined,\n expandIcon: undefined,\n collapseIcon: undefined,\n toggleIconRotate: true,\n branchLine: false,\n branchLineColor: undefined,\n branchLineActiveColor: undefined,\n draggable: false,\n dragHandleIcon: undefined,\n dragLabel: undefined,\n expandLabel: undefined,\n collapseLabel: undefined,\n rowClass: undefined,\n dragHandleClass: undefined,\n toggleClass: undefined,\n toggleIconClass: undefined,\n toggleSpacerClass: undefined,\n contentClass: undefined,\n})\n\nconst emit = defineEmits<GrTreeEmits<T>>()\n\ndefineSlots<{\n default?: (props: { node: GrTreeNode<T>, data: T }) => any\n}>()\n\nconst dataAdapter = createGrTreeDataAdapter(props)\nconst treeStore = createGrTreeStore({\n adapter: dataAdapter,\n data: () => props.data,\n defaultExpandedKeys: () => props.defaultExpandedKeys,\n defaultExpandAll: () => props.defaultExpandAll,\n filterNodeMethod: () => props.filterNodeMethod,\n defaultCheckedKeys: () => props.defaultCheckedKeys,\n checkedKeys: () => props.checkedKeys,\n checkStrictly: () => props.checkStrictly,\n lazy: () => props.lazy,\n load: () => props.load,\n})\nconst interactionContext = createGrTreeInteractionContext(props, {\n emitNodeClick: (data, node) => emit('nodeClick', data, node),\n emitNodeExpand: (data, node) => emit('nodeExpand', data, node),\n emitNodeCollapse: (data, node) => emit('nodeCollapse', data, node),\n emitNodeDrop: (draggingNode, dropNode, dropType) => emit('nodeDrop', draggingNode, dropNode, dropType),\n emitNodeContextMenu: (evt, data, node) => emit('nodeContextMenu', evt, data, node),\n})\n\nconst treeProps = props as Readonly<GrTreeProps<T>>\n\nconst { t } = useGranularityTranslations()\nconst { announce } = useAnnouncer()\nconst dragLabel = computed(() => treeProps.dragLabel ?? t('gr.tree.drag', 'Drag'))\nconst expandLabel = computed(() => treeProps.expandLabel ?? t('gr.tree.expand', 'Expand'))\nconst collapseLabel = computed(() => treeProps.collapseLabel ?? t('gr.tree.collapse', 'Collapse'))\nconst currentKey = treeStore.currentKey\nconst hoveredKey = interactionContext.hoveredKey\nconst dropTarget = interactionContext.dropTarget\n\n/**\n * Текущий узел: управляемый режим включает сам факт того, что проп задан.\n *\n * Иначе у одного понятия два владельца — подсветку рисует дерево по своему\n * ключу, а обёртка считает остальное по своему пропу; разойдись они на такт, и\n * строка подсвечена, а подпись не выделена. С `v-model:current-key` источник\n * правды один, и `nextTick` вокруг `setCurrentKey()` больше не нужен.\n */\nconst currentKeyControlled = computed(() => treeProps.currentKey !== undefined)\n\nwatch(() => treeProps.currentKey, (key) => {\n if (!currentKeyControlled.value)\n return\n if (treeStore.currentKey.value === (key ?? undefined))\n return\n\n treeStore.setCurrentKey(key ?? undefined)\n}, { immediate: true })\n\n/** Значение фильтра приходит пропом; метод `filter()` остаётся для императивных сценариев. */\nwatch(() => treeProps.filterValue, (value) => {\n if (value === undefined)\n return\n\n applyFilter(value)\n}, { immediate: true })\n\n// Корневой элемент дерева — область для делегированной клавиатуры (WAI-ARIA tree).\nconst treeRootEl = ref<HTMLElement | null>(null)\n\n/**\n * Видимые строки одним плоским списком в порядке отображения.\n *\n * Плоско — потому что рекурсивный рендер стоил по инстансу компонента на каждый\n * раскрытый узел: дерево на 2 000 видимых строк превращалось в 2 000\n * компонентов со своими вычислениями и подписками. Иерархию несут `aria-level`,\n * `aria-posinset` и `aria-setsize`, отступ — `padding-left` строки.\n */\nconst visibleRows = computed<GrTreeVisibleRow<T>[]>(() => {\n const { roots } = treeStore.treeModel.value\n const { isActive, subtreeHasMatch, matchedKeys, autoExpandKeys } = treeStore.filterInfo.value\n const branch = treeProps.branchLine\n const rows: GrTreeVisibleRow<T>[] = []\n\n const walk = (nodes: GrTreeNode<T>[], ancestorColors: string[]): void => {\n const siblings = isActive ? nodes.filter(node => subtreeHasMatch.get(node.key)) : nodes\n\n siblings.forEach((node, index) => {\n const isLeaf = treeStore.isLeafNode(node)\n const isExpanded = treeStore.isExpandedKey(node.key) || (isActive && autoExpandKeys.has(node.key))\n\n rows.push({\n node,\n isExpanded,\n isLeaf,\n isMatched: matchedKeys.has(node.key),\n posInSet: index + 1,\n setSize: siblings.length,\n isLoading: treeStore.isLoadingKey(node.key),\n branchColors: ancestorColors,\n })\n\n if (isExpanded && node.childNodes.length)\n walk(node.childNodes, branch ? [...ancestorColors, resolveBranchLineColor(node)] : ancestorColors)\n })\n }\n\n walk(roots, [])\n return rows\n})\n\n/**\n * Кольцо roving-фокуса: ровно один `treeitem` на всё дерево держит `tabindex=0`.\n *\n * Ориентация вертикальная намеренно: влево-вправо в дереве заняты раскрытием\n * ветки и переходом к родителю, и примитив их не трогает — это доменная логика,\n * она осталась в `onTreeKeydown`.\n */\nconst roving = useRovingFocus<GrTreeNode<T>['key']>({\n items: () => visibleRows.value.map(row => row.node.key),\n elementFor: key => interactionContext.nodeEls.get(key),\n orientation: () => 'vertical',\n // У дерева есть верх и низ: с последней строки вниз идти некуда.\n wrap: () => false,\n // Но клавишу на краю всё равно гасим: иначе `ArrowDown` на последнем узле\n // прокрутит страницу под деревом.\n onOverflow: () => true,\n // Пока фокус не трогали, остановку держит текущий (выбранный) узел, а если\n // его не видно — первая видимая строка.\n initialKey: () => currentKey.value ?? undefined,\n beforeFocus: key => scrollRowIntoView(key),\n})\n\nfunction onRowClick(node: GrTreeNode<T>) {\n // В управляемом режиме дерево ведёт подсветку до ответа снаружи: строка\n // отзывается на клик сразу, а расхождение снимет наблюдатель за пропом.\n treeStore.setCurrentKey(node.key)\n emit('update:currentKey', node.key)\n roving.setActive(node.key)\n interactionContext.emitNodeClick(node.data, node)\n}\n\n// Клик мышью, в отличие от Enter, умеет ещё и раскрывать узел: `Enter` в\n// паттерне tree закреплён за выбором, и подмешивать в него раскрытие нельзя.\nfunction onRowActivate(row: GrTreeVisibleRow<T>) {\n onRowClick(row.node)\n\n if (treeProps.expandOnClickNode && !row.isLeaf)\n toggleExpand(row.node)\n}\n\nfunction onRowContextMenu(evt: MouseEvent, node: GrTreeNode<T>) {\n interactionContext.emitNodeContextMenu(evt, node.data, node)\n}\n\n// ————— Клавиатурная навигация по WAI-ARIA tree pattern (только корневой инстанс).\n\nfunction isRovingItem(key: GrTreeNode<T>['key']): boolean {\n return roving.rovingKey.value === key\n}\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrTree' })\n\n// Переменные ставим и вложенным уровням тоже: `v-bind=\"props\"` доносит до них\n// `size`, а значения одинаковые — наследование от корня не нарушается.\nconst sizeStyle = computed(() => treeSizeVars[resolvedSize.value])\n\n/**\n * Виртуализация: в DOM живёт только окно вокруг вьюпорта.\n *\n * Корень дерева и есть скроллер — обёрток-распорок между `role=\"tree\"` и\n * `role=\"treeitem\"` быть не должно, поэтому срезанное сверху и снизу держат\n * отступы самого корня.\n */\nconst TREE_ROW_GAP = 2\n\nconst rowEstimate = computed(() => Number.parseFloat(sizeStyle.value['--gr-tree-row-min-height']))\n\nconst virtualMaxHeight = computed(() => {\n const value = treeProps.maxHeight\n if (value == null)\n return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst virtualizer = useVirtualList({\n container: treeRootEl,\n count: () => (treeProps.virtual ? visibleRows.value.length : 0),\n // Раскрытие/фильтр сдвигают индексы строк — замеры прошлого набора невалидны.\n source: () => visibleRows.value,\n itemSize: () => rowEstimate.value,\n gap: TREE_ROW_GAP,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof treeProps.maxHeight === 'number' ? treeProps.maxHeight : undefined),\n})\n\n/** Строки к отрисовке: при выключенной виртуализации — все. */\nconst renderedRows = computed(() => {\n if (!treeProps.virtual)\n return visibleRows.value\n\n const { start, end } = virtualizer.range.value\n return visibleRows.value.slice(start, end)\n})\n\n/**\n * Срезанное сверху и снизу держат псевдоэлементы контейнера.\n *\n * Ни один из трёх напрашивающихся вариантов не годится:\n *\n * - `padding` контейнера — `max-height` меряет ту же коробку, и распорка в сто\n * тысяч пикселей либо раздувает скроллер до той же сотни тысяч, либо съедает\n * всю его высоту;\n * - обёртка-распорка внутри — между `role=\"tree\"` и `role=\"treeitem\"` не должно\n * быть посторонних узлов, роль потеряла бы обязательных потомков;\n * - отступы крайних отрисованных строк — распорка исчезает ровно в тот момент,\n * когда строки заменяются целиком (прыжок прокрутки), содержимое схлопывается\n * до высоты окна, и браузер обрезает `scrollTop` до почти нуля.\n *\n * `::before`/`::after` не узлы DOM: их не за что размонтировать, в дереве\n * доступности их нет, а высота приезжает переменными в том же патче, что и сами\n * строки, — схлопнуться между кадрами нечему.\n */\nconst rootStyle = computed(() => {\n if (!treeProps.virtual)\n return sizeStyle.value\n\n return {\n ...sizeStyle.value,\n overflow: 'auto',\n maxHeight: virtualMaxHeight.value,\n ...virtualizer.spacerStyle.value,\n }\n})\n\n/** Абсолютный индекс отрисованной строки: поиск по массиву стоил бы O(n) на строку. */\nfunction absoluteIndex(offsetInWindow: number): number {\n return treeProps.virtual ? virtualizer.range.value.start + offsetInWindow : offsetInWindow\n}\n\n/**\n * Строка размонтируется: снимаем регистрацию и, если фокус был на ней, уводим\n * его на корень — делегированный keydown живёт там, первая же стрелка вернёт\n * видимую строку через `focusRow`. Иначе фокус упал бы на `body` и клавиатура\n * дерева умерла бы до клика мышью.\n *\n * Спрашиваем сам элемент, а не `document.activeElement === body`: Vue обнуляет\n * function ref ДО удаления узла, поэтому в момент вызова фокус ещё на строке —\n * а «фокус на body» означает лишь то, что страницу никто не трогал.\n */\nlet isUnmounting = false\n\nfunction releaseNodeEl(key: GrTreeKey): void {\n const el = interactionContext.nodeEls.get(key)\n const active = typeof document === 'undefined' ? null : document.activeElement\n const heldFocus = Boolean(el && active && (el === active || el.contains(active)))\n\n interactionContext.registerNodeEl(key, null)\n\n if (heldFocus && !isUnmounting)\n treeRootEl.value?.focus({ preventScroll: true })\n}\n\n/**\n * При виртуализации узла вне окна в DOM нет: `nodeEls.get` вернул бы\n * `undefined`, а фокус уехал бы на `body` вместе с размонтированной строкой.\n * Поэтому сперва прокрутка, и только следующим тиком — фокус.\n */\nfunction scrollRowIntoView(key: GrTreeNode<T>['key']): Promise<void> {\n if (treeProps.virtual) {\n const index = visibleRows.value.findIndex(row => row.node.key === key)\n if (index >= 0)\n virtualizer.scrollToIndex(index)\n }\n\n return nextTick()\n}\n\nfunction focusRow(key: GrTreeNode<T>['key']): void {\n void roving.focusKey(key)\n}\n\n/**\n * Typeahead паттерна tree: печатные символы копятся в буфер и переводят фокус\n * на первый подходящий видимый узел, начиная со следующего за текущим.\n *\n * Поиск идёт по данным (`visibleRows`), а не по DOM: при виртуализации узла вне\n * окна в разметке нет, и поиск по тексту элементов находил бы только видимое.\n */\nconst typeahead = useTypeahead<GrTreeVisibleRow<T>>({\n items: () => visibleRows.value,\n textOf: row => row.node.label,\n // Без наведённого фокуса ищем с начала списка, а не от конца: `findIndex`\n // вернул бы `-1`, и первая строка выпала бы из обхода.\n currentIndex: rows => Math.max(0, rows.findIndex(row => row.node.key === roving.rovingKey.value)),\n onMatch: row => focusRow(row.node.key),\n})\n\n/** `*` — раскрыть всех соседей узла, на котором фокус (уровень целиком). */\nfunction expandSiblings(node: GrTreeNode<T>): void {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n\n for (const sibling of siblings) {\n if (sibling.childNodes.length === 0 || treeStore.isExpandedKey(sibling.key))\n continue\n\n treeStore.setExpandedKey(sibling.key, true)\n interactionContext.emitNodeExpand(sibling.data, sibling)\n }\n}\n\nfunction onTreeKeydown(event: KeyboardEvent): void {\n // Делегированная клавиатура уважает интерактивные цели: печать в инпуте слота\n // узла — ввод текста, а не typeahead. Без гарда preventDefault отменял бы это.\n const target = event.target as HTMLElement | null\n const interactive = target?.closest<HTMLElement>('button, a[href], input, select, textarea, [contenteditable]')\n if (interactive && interactive !== event.currentTarget) {\n // Табируемая цель — самостоятельный таб-стоп: клавиатура целиком её.\n if (interactive.tabIndex >= 0)\n return\n\n // Кнопки строки (toggle, drag-handle) не табируемы: фокус попадает на них\n // только мышью. За ними остаётся активация — Enter на toggle это его клик, —\n // а навигация принадлежит дереву, иначе клик мышью убивал бы стрелки.\n if (event.key === 'Enter' || event.key === ' ')\n return\n }\n\n const rows = visibleRows.value\n if (rows.length === 0)\n return\n\n const idx = Math.max(0, rows.findIndex(r => r.node.key === roving.rovingKey.value))\n const cur = rows[idx]\n\n if (event.key === '*') {\n event.preventDefault()\n expandSiblings(cur.node)\n return\n }\n\n // Печатный символ без модификаторов — typeahead, а не команда.\n if (event.key.length === 1 && event.key !== ' ' && !event.ctrlKey && !event.metaKey && !event.altKey) {\n event.preventDefault()\n typeahead.type(event.key)\n return\n }\n\n // `Shift` со стрелкой двигает сам узел — раскладка аутлайнера. Проверяется\n // раньше навигации: иначе примитив увёл бы фокус вместо переноса.\n if (event.shiftKey && MOVE_KEYS.has(event.key)) {\n if (!treeProps.draggable)\n return\n\n event.preventDefault()\n void onNodeMoveKey(cur.node, event.key)\n return\n }\n\n // Вертикаль, `Home` и `End` ведёт примитив. Влево-вправо он не трогает: в\n // дереве это раскрытие ветки и переход к родителю, а не движение по списку.\n if (roving.handleNavigationKeys(event))\n return\n\n switch (event.key) {\n case 'ArrowRight':\n event.preventDefault()\n if (!cur.isLeaf) {\n if (!cur.isExpanded)\n toggleExpand(cur.node)\n else if (idx < rows.length - 1)\n focusRow(rows[idx + 1].node.key)\n }\n break\n case 'ArrowLeft':\n event.preventDefault()\n if (!cur.isLeaf && cur.isExpanded)\n toggleExpand(cur.node)\n else if (cur.node.parent && rows.some(r => r.node.key === cur.node.parent!.key))\n focusRow(cur.node.parent.key)\n break\n case 'Enter':\n event.preventDefault()\n onRowClick(cur.node)\n break\n // Space при чекбоксах переключает отметку — это и есть выбор в\n // multi-select дереве; без них он остаётся вторым способом выбрать узел.\n case ' ':\n event.preventDefault()\n if (treeProps.showCheckbox)\n toggleChecked(cur.node)\n else\n onRowClick(cur.node)\n break\n }\n}\n\nfunction onRowMouseEnter(node: GrTreeNode<T>) {\n hoveredKey.value = node.key\n}\n\nfunction onRowMouseLeave(node: GrTreeNode<T>) {\n if (hoveredKey.value === node.key)\n hoveredKey.value = undefined\n}\n\nfunction collapseSiblings(node: GrTreeNode<T>) {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n\n for (const sibling of siblings) {\n if (sibling.key === node.key || !treeStore.isExpandedKey(sibling.key))\n continue\n\n treeStore.setExpandedKey(sibling.key, false)\n interactionContext.emitNodeCollapse(sibling.data, sibling)\n }\n}\n\nfunction toggleExpand(node: GrTreeNode<T>) {\n const expanded = !treeStore.isExpandedKey(node.key)\n\n if (expanded && treeProps.accordion)\n collapseSiblings(node)\n\n // Ленивая ветка грузится по первому раскрытию; повторное ничего не запрашивает.\n if (expanded)\n treeStore.ensureLoaded(node)\n\n treeStore.toggleExpand(node)\n\n if (expanded)\n interactionContext.emitNodeExpand(node.data, node)\n else\n interactionContext.emitNodeCollapse(node.data, node)\n}\n\n// ————— Отметки (чекбоксы).\n\nfunction checkStateOf(key: GrTreeKey): GrTreeCheckState {\n return treeStore.getCheckState(key)\n}\n\nfunction ariaCheckedOf(row: GrTreeVisibleRow<T>): 'true' | 'false' | 'mixed' | undefined {\n if (!treeProps.showCheckbox)\n return undefined\n\n const state = checkStateOf(row.node.key)\n return state === 'checked' ? 'true' : state === 'half' ? 'mixed' : 'false'\n}\n\nfunction emitCheck(node: GrTreeNode<T>): void {\n const checkedKeys = treeStore.getCheckedKeys()\n emit('update:checkedKeys', checkedKeys)\n emit('check', node.data, node, { checkedKeys, halfCheckedKeys: treeStore.getHalfCheckedKeys() })\n}\n\nfunction toggleChecked(node: GrTreeNode<T>): void {\n if (!treeProps.showCheckbox)\n return\n\n const changed = treeStore.toggleChecked(node)\n if (changed)\n emitCheck(changed)\n}\n\n// ————— Геометрия строки: отступ уровня и направляющие ветвей.\n\nfunction rowStyle(row: GrTreeVisibleRow<T>) {\n const step = treeProps.indent && treeProps.indent > 0\n ? `${treeProps.indent}px`\n : 'var(--gr-tree-indent-step)'\n\n return { '--gr-tree-row-indent': `calc(${step} * ${row.node.level - 1})` }\n}\n\n/**\n * Направляющая уровня-предка. Считается от того же шага отступа, что и сам\n * отступ строки, — иначе линия и содержимое разъедутся на вложенных уровнях.\n */\nfunction branchGuideStyle(row: GrTreeVisibleRow<T>, index: number) {\n const step = treeProps.indent && treeProps.indent > 0\n ? `${treeProps.indent}px`\n : 'var(--gr-tree-indent-step)'\n\n return {\n 'left': `calc(${step} * ${index} + var(--gr-tree-branch-line-offset))`,\n '--gr-tree-branch-line-color': row.branchColors[index],\n }\n}\n\n// Drag & drop\nfunction canDrag(node: GrTreeNode<T>): boolean {\n return interactionContext.canDrag(node)\n}\n\n/**\n * Ручка «по наведению» на тач-устройстве недостижима: событий наведения там нет,\n * ключ не выставляется, класс видимости не появляется — то есть перетаскивания\n * нет вовсе, хотя `touch-action: none` у ручки стоит ровно ради него.\n *\n * Режим `auto` решает это без JS: класс-модификатор на корне, а показ включает\n * `@media (hover: none)` — так поведение остаётся верным и на сервере, где\n * никакого `matchMedia` спрашивать нельзя.\n */\nfunction shouldShowDragHandle(node: GrTreeNode<T>): boolean {\n if (!canDrag(node))\n return false\n\n return treeProps.dragHandleVisibility === 'always' || hoveredKey.value === node.key\n}\n\n/**\n * Треть строки сверху — «до», треть снизу — «после», середина — «внутрь».\n * Зоны нарезает компонент: примитив отдаёт только долю вдоль строки.\n */\nfunction dropTypeFromFraction(fraction: number): GrTreeNodeDropType {\n if (fraction < 1 / 3)\n return 'prev'\n if (fraction > 2 / 3)\n return 'next'\n\n return 'inner'\n}\n\nfunction canDrop(drag: GrTreeNode<T>, target: GrTreeNode<T>, type: GrTreeAllowDropType): boolean {\n return interactionContext.canDrop(drag, target, type)\n}\n\n/** Перенос состоялся: одна дорога и для указателя, и для клавиатуры. */\nfunction applyMove(source: GrTreeNode<T>, targetKey: GrTreeKey, type: GrTreeNodeDropType): boolean {\n const reference = treeStore.getNode(targetKey)\n if (!reference)\n return false\n\n const movedNode = treeStore.moveNode(source, reference, type)\n if (!movedNode)\n return false\n\n const dropNode = treeStore.getNode(reference.key) ?? reference\n interactionContext.emitNodeDrop(movedNode, dropNode, type)\n\n return true\n}\n\nconst dragSort = useDragSort<GrTreeKey, GrTreeDropTarget>({\n items: () => visibleRows.value.map(row => row.node.key),\n elementFor: key => interactionContext.nodeEls.get(key) ?? null,\n scroller: () => treeRootEl.value,\n disabled: () => !treeProps.draggable,\n canDrag: (key) => {\n const node = treeStore.getNode(key)\n\n return node ? canDrag(node) : false\n },\n resolveTarget: (hit, sourceKey, previous) => {\n const source = treeStore.getNode(sourceKey)\n const node = treeStore.getNode(hit.key)\n if (!source || !node)\n return null\n\n const type = dropTypeFromFraction(hit.fraction)\n const allowed = treeStore.canMoveNode(source, node, type) && canDrop(source, node, type)\n\n // Та же ссылка, пока смысл не изменился: иначе подсветка перерисовывалась бы\n // на каждом движении указателя.\n if (previous && previous.key === node.key && previous.type === type && previous.allowed === allowed)\n return previous\n\n return { key: node.key, type, allowed }\n },\n onDrop: (sourceKey, target) => {\n const source = treeStore.getNode(sourceKey)\n if (!source || !target.allowed)\n return\n\n applyMove(source, target.key, target.type)\n },\n onUpdate: (sourceKey, target) => {\n interactionContext.draggingNode.value = sourceKey === null ? null : treeStore.getNode(sourceKey) ?? null\n interactionContext.dropTarget.value = target\n },\n})\n\nfunction onHandlePointerDown(event: PointerEvent, node: GrTreeNode<T>): void {\n if (!treeProps.draggable)\n return\n\n dragSort.startFrom(node.key)(event)\n}\n\n/**\n * Клавиатурный перенос — раскладка аутлайнера: `Shift` со стрелкой сразу\n * двигает узел, без режима «взято». Режим здесь был бы лишним: `Space` в дереве\n * уже отмечает чекбокс, а стрелки водят фокус по веткам.\n */\nfunction moveByKeyboard(node: GrTreeNode<T>, key: string): boolean {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n const index = siblings.findIndex(sibling => sibling.key === node.key)\n\n if (key === 'ArrowUp' && index > 0)\n return applyMove(node, siblings[index - 1].key, 'prev')\n\n if (key === 'ArrowDown' && index >= 0 && index < siblings.length - 1)\n return applyMove(node, siblings[index + 1].key, 'next')\n\n // Вправо — в предыдущего соседа: у первого в уровне такого соседа нет.\n if (key === 'ArrowRight' && index > 0)\n return applyMove(node, siblings[index - 1].key, 'inner')\n\n if (key === 'ArrowLeft' && node.parent)\n return applyMove(node, node.parent.key, 'next')\n\n return false\n}\n\nasync function onNodeMoveKey(node: GrTreeNode<T>, key: string): Promise<void> {\n if (!treeProps.draggable || !canDrag(node))\n return\n if (!moveByKeyboard(node, key))\n return\n\n announce(t('gr.tree.moved', 'Moved {label}', { label: node.label }))\n\n // Перестановка перерисовывает уровень: без возврата фокуса следующий Shift\n // уже некуда было бы адресовать.\n await nextTick()\n focusRow(node.key)\n}\n\n/**\n * Фильтрация и отчёт о её результате.\n *\n * Счёт снимается после пересчёта видимых строк: `visibleCount` — то, что\n * пользователь реально видит, а `matchedCount` — сколько узлов совпало само,\n * без учёта родителей, раскрытых ради показа совпадения.\n */\nasync function applyFilter(value: string) {\n treeStore.filter(value)\n await nextTick()\n\n emit('filter', {\n value,\n visibleCount: visibleRows.value.length,\n matchedCount: treeStore.filterInfo.value.matchedKeys.size,\n })\n}\n\nfunction filter(value: string) {\n void applyFilter(value)\n}\n\nfunction resolveNodeClass(classValue: GrTreeNodeClass<T> | undefined, row: GrTreeVisibleRow<T>) {\n if (!classValue)\n return undefined\n\n return typeof classValue === 'function'\n ? classValue(row)\n : classValue\n}\n\nfunction resolveBranchLineColorValue(color: GrTreeBranchLineColor<T> | undefined, node: GrTreeNode<T>) {\n if (!color)\n return undefined\n\n return typeof color === 'function'\n ? color(node) ?? undefined\n : color\n}\n\nfunction isBranchLineActive(node: GrTreeNode<T>) {\n const selectedKey = currentKey.value\n\n if (selectedKey == null)\n return false\n\n if (node.key === selectedKey)\n return true\n\n return node.childNodes.some(child => child.key === selectedKey && !treeStore.isExpandedKey(child.key))\n}\n\nfunction resolveBranchLineColor(node: GrTreeNode<T>) {\n const defaultColor = resolveBranchLineColorValue(treeProps.branchLineColor, node) ?? DEFAULT_BRANCH_LINE_COLOR\n\n if (!isBranchLineActive(node))\n return defaultColor\n\n return resolveBranchLineColorValue(treeProps.branchLineActiveColor, node) ?? defaultColor\n}\n\n/**\n * Переводит фокус на узел (по умолчанию — на тот, что держит roving tabindex).\n * Нужен снаружи: `GrTreeSelect` открывает панель и обязан отдать клавиатуру\n * дереву, иначе стрелки из триггера никуда не ведут.\n */\nfunction focus(key?: GrTreeKey): boolean {\n const rows = visibleRows.value\n if (rows.length === 0)\n return false\n\n const target = key != null && rows.some(row => row.node.key === key)\n ? key\n : roving.rovingKey.value ?? rows[0].node.key\n\n focusRow(target)\n return true\n}\n\n// Дерево уничтожают целиком — строки размонтируются вместе с ним, и возвращать\n// фокус на умирающий корень нельзя: он уедет из документа вместе с деревом.\nonBeforeUnmount(() => {\n isUnmounting = true\n})\n\ndefineExpose<GrTreeInstance<T>>({\n appendNode: treeStore.appendNode,\n getCheckedKeys: options => treeStore.getCheckedKeys(options),\n setCheckedKeys: (keys) => {\n treeStore.setCheckedKeys(keys)\n emit('update:checkedKeys', treeStore.getCheckedKeys())\n },\n getHalfCheckedKeys: treeStore.getHalfCheckedKeys,\n setChecked: (node, checked) => {\n const changed = treeStore.setChecked(node, checked)\n if (changed)\n emitCheck(changed)\n return Boolean(changed)\n },\n filter,\n focus,\n getCurrentNode: treeStore.getCurrentNode,\n setCurrentKey: treeStore.setCurrentKey,\n getCurrentKey: treeStore.getCurrentKey,\n getNode: treeStore.getNode,\n insertNodeAfter: treeStore.insertNodeAfter,\n insertNodeBefore: treeStore.insertNodeBefore,\n removeNode: treeStore.removeNode,\n setCurrentNode: treeStore.setCurrentNode,\n})\n</script>\n\n<template>\n <div\n ref=\"treeRootEl\"\n data-gr-tree\n class=\"gr-tree\"\n :class=\"treeProps.dragHandleVisibility === 'auto' ? 'gr-tree--drag-handle-auto' : ''\"\n tabindex=\"-1\"\n :data-gr-virtual=\"treeProps.virtual ? '' : undefined\"\n role=\"tree\"\n :aria-multiselectable=\"treeProps.showCheckbox ? 'true' : undefined\"\n :style=\"rootStyle\"\n @keydown=\"onTreeKeydown\"\n >\n <div\n v-for=\"(row, windowIndex) in renderedRows\"\n :key=\"row.node.key\"\n :ref=\"(el) => {\n if (el) interactionContext.registerNodeEl(row.node.key, el as HTMLElement)\n else releaseNodeEl(row.node.key)\n if (treeProps.virtual) virtualizer.measure(absoluteIndex(windowIndex), el as Element | null)\n }\"\n data-gr-tree-node\n :data-gr-tree-node-key=\"row.node.key\"\n role=\"treeitem\"\n :aria-level=\"row.node.level\"\n :aria-posinset=\"row.posInSet\"\n :aria-setsize=\"row.setSize\"\n :aria-expanded=\"row.isLeaf ? undefined : row.isExpanded\"\n :aria-selected=\"currentKey === row.node.key ? 'true' : undefined\"\n :aria-checked=\"ariaCheckedOf(row)\"\n :aria-busy=\"row.isLoading ? 'true' : undefined\"\n :tabindex=\"isRovingItem(row.node.key) ? 0 : -1\"\n >\n <div\n data-gr-tree-row\n class=\"gr-tree__row\"\n :class=\"[\n treeProps.highlightCurrent && currentKey === row.node.key ? 'gr-tree__row--current' : '',\n row.isMatched ? 'gr-tree__row--matched' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'inner' ? 'gr-tree__row--drop-inner' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'prev' ? 'gr-tree__row--drop-prev' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'next' ? 'gr-tree__row--drop-next' : '',\n resolveNodeClass(treeProps.rowClass, row),\n ]\"\n :style=\"rowStyle(row)\"\n @click=\"onRowActivate(row)\"\n @contextmenu=\"onRowContextMenu($event, row.node)\"\n @drop.prevent\n @mouseenter=\"onRowMouseEnter(row.node)\"\n @mouseleave=\"onRowMouseLeave(row.node)\"\n >\n <!--\n Направляющие ветвей: по одной на каждый уровень предка. Вложенной\n обёртки с `border-left` больше нет, поэтому линию рисует сама строка —\n и заходит в зазор между строками, иначе она распалась бы на штрихи.\n -->\n <span\n v-for=\"(color, guideIndex) in row.branchColors\"\n :key=\"guideIndex\"\n data-gr-tree-branch-guide\n class=\"gr-tree__branch-guide\"\n :style=\"branchGuideStyle(row, guideIndex)\"\n aria-hidden=\"true\"\n />\n\n <button\n v-if=\"treeProps.draggable\"\n type=\"button\"\n tabindex=\"-1\"\n data-gr-tree-drag-handle\n class=\"gr-tree__drag-handle\"\n :class=\"[\n shouldShowDragHandle(row.node) ? 'gr-tree__drag-handle--visible' : '',\n canDrag(row.node) ? '' : 'gr-tree__drag-handle--disabled',\n resolveNodeClass(treeProps.dragHandleClass, row),\n ]\"\n :aria-label=\"dragLabel\"\n :aria-disabled=\"canDrag(row.node) ? undefined : 'true'\"\n @click.stop\n @pointerdown=\"onHandlePointerDown($event, row.node)\"\n >\n <component\n :is=\"iconTag(treeProps.dragHandleIcon, IconGripVertical)\"\n class=\"gr-tree__drag-icon\"\n :class=\"iconClass(treeProps.dragHandleIcon)\"\n />\n </button>\n\n <!-- tabindex=\"-1\": внутри roving-композита интерактив не табируется,\n клавиатурный эквивалент — ArrowRight/ArrowLeft на строке. -->\n <button\n v-if=\"!row.isLeaf\"\n data-gr-tree-toggle\n type=\"button\"\n tabindex=\"-1\"\n class=\"gr-tree__toggle\"\n :class=\"resolveNodeClass(treeProps.toggleClass, row)\"\n :aria-label=\"row.isExpanded ? collapseLabel : expandLabel\"\n @click.stop=\"toggleExpand(row.node)\"\n >\n <IconLoaderCircle\n v-if=\"row.isLoading\"\n data-gr-tree-loading\n class=\"gr-tree__toggle-icon animate-spin\"\n />\n <component\n :is=\"iconTag(row.isExpanded ? treeProps.collapseIcon : treeProps.expandIcon, IconChevronRight)\"\n v-else\n class=\"gr-tree__toggle-icon\"\n :class=\"[\n iconClass(row.isExpanded ? treeProps.collapseIcon : treeProps.expandIcon),\n row.isExpanded && treeProps.toggleIconRotate ? 'gr-tree__toggle-icon--expanded' : '',\n resolveNodeClass(treeProps.toggleIconClass, row),\n ]\"\n />\n </button>\n <span\n v-else\n class=\"gr-tree__toggle-spacer\"\n :class=\"resolveNodeClass(treeProps.toggleSpacerClass, row)\"\n />\n\n <!--\n Квадратик отметки декоративен: состояние живёт на самом `treeitem`\n (`aria-checked`), а вложить интерактивный чекбокс внутрь роли-виджета\n нельзя — роль объявляет потомков презентационными.\n -->\n <span\n v-if=\"treeProps.showCheckbox\"\n data-gr-tree-checkbox\n class=\"gr-tree__checkbox\"\n :class=\"[\n checkStateOf(row.node.key) === 'checked' ? 'gr-tree__checkbox--checked' : '',\n checkStateOf(row.node.key) === 'half' ? 'gr-tree__checkbox--half' : '',\n ]\"\n aria-hidden=\"true\"\n @click.stop=\"toggleChecked(row.node)\"\n >\n <component\n :is=\"checkStateOf(row.node.key) === 'half' ? IconMinus : IconCheck\"\n v-if=\"checkStateOf(row.node.key) !== 'unchecked'\"\n class=\"gr-tree__checkbox-mark\"\n />\n </span>\n\n <div class=\"gr-tree__content\" :class=\"resolveNodeClass(treeProps.contentClass, row)\">\n <slot\n :node=\"row.node\"\n :data=\"row.node.data\"\n >\n <span class=\"gr-tree__label\">{{ row.node.label }}</span>\n </slot>\n </div>\n </div>\n </div>\n </div>\n</template>\n\n<style scoped>\n.gr-tree {\n --gr-tree-gap: 2px;\n --gr-tree-children-pl: 10px;\n --gr-tree-row-min-height: 28px;\n --gr-tree-row-radius: 8px;\n --gr-tree-row-px: 8px;\n --gr-tree-row-py: 8px;\n --gr-tree-row-pr: var(--gr-tree-row-px);\n --gr-tree-font-size: inherit;\n --gr-tree-row-color: var(--gr-fg);\n --gr-tree-row-hover-bg: color-mix(in srgb, var(--gr-primary) 10%, transparent);\n --gr-tree-row-current-bg: color-mix(in srgb, var(--gr-primary) 5%, transparent);\n --gr-tree-row-current-hover-bg: color-mix(in srgb, var(--gr-primary) 16%, transparent);\n --gr-tree-drag-handle-size: 24px;\n --gr-tree-drag-handle-mr: 0;\n --gr-tree-drag-handle-radius: 6px;\n --gr-tree-drag-handle-color: inherit;\n --gr-tree-drag-handle-opacity: 0.55;\n --gr-tree-drag-handle-hover-bg: color-mix(in srgb, var(--gr-muted) 22%, transparent);\n --gr-tree-drag-handle-hover-color: var(--gr-tree-drag-handle-color);\n --gr-tree-drag-handle-hover-opacity: 0.9;\n --gr-tree-drag-handle-disabled-opacity: 0.25;\n --gr-tree-toggle-size: 24px;\n --gr-tree-toggle-mr: 0;\n --gr-tree-toggle-radius: 6px;\n --gr-tree-toggle-color: inherit;\n --gr-tree-toggle-hover-bg: color-mix(in srgb, var(--gr-muted) 25%, transparent);\n --gr-tree-toggle-hover-color: var(--gr-tree-toggle-color);\n --gr-tree-icon-size: 16px;\n --gr-tree-content-gap: 8px;\n --gr-tree-branch-line-default-color: var(--gr-tree-row-current-bg);\n --gr-tree-branch-line-width: 2px;\n /* Шаг отступа уровня: переключатель, отступ вложенного списка и толщина\n направляющей — линия обязана попадать между ними. */\n --gr-tree-indent-step: calc(24px + var(--gr-tree-children-pl) + var(--gr-tree-branch-line-width));\n --gr-tree-branch-line-offset: 24px;\n --gr-tree-checkbox-size: 16px;\n --gr-tree-checkbox-radius: 4px;\n --gr-tree-checkbox-brd: var(--gr-brd);\n --gr-tree-checkbox-bg: transparent;\n --gr-tree-checkbox-checked-bg: var(--gr-primary);\n --gr-tree-checkbox-checked-fg: var(--gr-primary-fg);\n --gr-tree-checkbox-mr: 4px;\n display: flex;\n flex-direction: column;\n gap: var(--gr-tree-gap);\n}\n\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\n.gr-tree__row {\n position: relative;\n display: flex;\n align-items: center;\n min-height: var(--gr-tree-row-min-height);\n padding: var(--gr-tree-row-py) var(--gr-tree-row-pr) var(--gr-tree-row-py)\n calc(var(--gr-tree-row-px) + var(--gr-tree-row-indent, 0px));\n font-size: var(--gr-tree-font-size);\n cursor: default;\n user-select: none;\n outline: none;\n color: var(--gr-tree-row-color);\n isolation: isolate;\n}\n\n/* Поверхность строки — отдельный слой, вставленный слева на отступ уровня.\n Фон на самой коробке шёл от левого края дерева и накрывал направляющие\n предков: линия ветки исчезала под подсветкой ровно там, где она и нужна.\n Слой лежит ниже направляющих (они — следующие элементы строки), поэтому\n линия остаётся видна при любом наложении.\n\n `z-index: -1` уводит слой под содержимое строки. Без него позиционированный\n `::before` красится ПОВЕРХ потоковых подписи, шеврона и отметки — при\n полупрозрачном фоне это лишь лёгкое затенение, а при непрозрачном значении\n публичного токена содержимое исчезает целиком. Поднимать вместо этого\n содержимое пришлось бы у каждого элемента строки и у каждого нового.\n\n `isolation` на самой строке обязателен в паре: без своего контекста\n наложения отрицательный слой уезжает за фон ближайшего предка с заливкой, и\n подсветка пропадает на карточке. */\n.gr-tree__row::before {\n content: '';\n position: absolute;\n inset: 0 0 0 var(--gr-tree-row-indent, 0px);\n border-radius: var(--gr-tree-row-radius);\n pointer-events: none;\n z-index: -1;\n}\n\n.gr-tree__row:hover::before {\n background: var(--gr-tree-row-hover-bg);\n}\n\n/* Направляющая тянется в зазор между строками: иначе линия ветки распалась бы\n на штрихи по числу строк. */\n.gr-tree__branch-guide {\n position: absolute;\n top: calc(var(--gr-tree-gap) / -2);\n bottom: calc(var(--gr-tree-gap) / -2);\n width: var(--gr-tree-branch-line-width);\n background: var(--gr-tree-branch-line-color, var(--gr-tree-branch-line-default-color));\n pointer-events: none;\n}\n\n.gr-tree__checkbox {\n display: inline-flex;\n align-items: center;\n justify-content: center;\n flex-shrink: 0;\n width: var(--gr-tree-checkbox-size);\n height: var(--gr-tree-checkbox-size);\n margin-right: var(--gr-tree-checkbox-mr);\n border: 1px solid var(--gr-tree-checkbox-brd);\n border-radius: var(--gr-tree-checkbox-radius);\n background: var(--gr-tree-checkbox-bg);\n color: var(--gr-tree-checkbox-checked-fg);\n cursor: pointer;\n}\n\n.gr-tree__checkbox--checked,\n.gr-tree__checkbox--half {\n border-color: var(--gr-tree-checkbox-checked-bg);\n background: var(--gr-tree-checkbox-checked-bg);\n}\n\n.gr-tree__checkbox-mark {\n width: calc(var(--gr-tree-checkbox-size) - 4px);\n height: calc(var(--gr-tree-checkbox-size) - 4px);\n}\n\n[data-gr-tree-node] {\n outline: none;\n}\n\n/* Кольцо фокуса — на той же поверхности, что подсветка: иначе строка читалась бы\n двумя разными прямоугольниками. `outline` для этого не годится — он рисуется по\n границе коробки, а не по инсету. */\n[data-gr-tree-node]:focus-visible > .gr-tree__row::before {\n box-shadow: inset 0 0 0 2px var(--gr-primary);\n}\n\n.gr-tree__row--current::before {\n background: var(--gr-tree-row-current-bg);\n}\n\n.gr-tree__row--current:hover::before {\n background: var(--gr-tree-row-current-hover-bg);\n}\n\n.gr-tree__row--matched .gr-tree__label {\n font-weight: 600;\n}\n\n.gr-tree__drag-handle {\n width: var(--gr-tree-drag-handle-size);\n height: var(--gr-tree-drag-handle-size);\n display: inline-flex;\n align-items: center;\n justify-content: center;\n margin-right: var(--gr-tree-drag-handle-mr);\n border-radius: var(--gr-tree-drag-handle-radius);\n color: var(--gr-tree-drag-handle-color);\n cursor: grab;\n /* Без этого вертикальный свайп по ручке уходит в прокрутку страницы,\n браузер отзывает указатель, и пальцем узел неперетаскиваем. */\n touch-action: none;\n visibility: hidden;\n pointer-events: none;\n opacity: 0;\n}\n\n/* Где наведения не бывает, ручка «по наведению» недостижима — то есть\n перетаскивания нет вовсе. Медиазапрос, а не `matchMedia`: ответ нужен и на\n сервере, а спрашивать среду в первом рендере нельзя. */\n@media (hover: none) {\n .gr-tree--drag-handle-auto .gr-tree__drag-handle {\n visibility: visible;\n pointer-events: auto;\n opacity: var(--gr-tree-drag-handle-opacity);\n }\n}\n\n.gr-tree__drag-handle--visible {\n visibility: visible;\n pointer-events: auto;\n opacity: var(--gr-tree-drag-handle-opacity);\n}\n\n.gr-tree__drag-handle:hover {\n background: var(--gr-tree-drag-handle-hover-bg);\n color: var(--gr-tree-drag-handle-hover-color);\n opacity: var(--gr-tree-drag-handle-hover-opacity);\n}\n\n.gr-tree__drag-handle:active {\n cursor: grabbing;\n}\n\n.gr-tree__drag-handle--disabled {\n cursor: default;\n opacity: var(--gr-tree-drag-handle-disabled-opacity);\n}\n\n.gr-tree__drag-icon {\n width: var(--gr-tree-icon-size);\n height: var(--gr-tree-icon-size);\n}\n\n.gr-tree__toggle {\n width: var(--gr-tree-toggle-size);\n height: var(--gr-tree-toggle-size);\n display: inline-flex;\n align-items: center;\n justify-content: center;\n margin-right: var(--gr-tree-toggle-mr);\n border-radius: var(--gr-tree-toggle-radius);\n color: var(--gr-tree-toggle-color);\n}\n\n.gr-tree__toggle:hover {\n background: var(--gr-tree-toggle-hover-bg);\n color: var(--gr-tree-toggle-hover-color);\n}\n\n.gr-tree__toggle-icon {\n width: var(--gr-tree-icon-size);\n height: var(--gr-tree-icon-size);\n transition: transform var(--gr-duration-fast) var(--gr-ease-out);\n}\n\n.gr-tree__toggle-icon--expanded {\n transform: rotate(90deg);\n}\n\n.gr-tree__toggle-spacer {\n width: var(--gr-tree-toggle-size);\n height: var(--gr-tree-toggle-size);\n margin-right: var(--gr-tree-toggle-mr);\n display: inline-block;\n}\n\n.gr-tree__content {\n min-width: 0;\n display: flex;\n align-items: center;\n gap: var(--gr-tree-content-gap);\n}\n\n.gr-tree__label {\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.gr-tree__row--drop-inner {\n outline: 2px solid color-mix(in srgb, var(--gr-primary) 40%, transparent);\n}\n\n.gr-tree__row--drop-prev::before,\n.gr-tree__row--drop-next::after {\n content: '';\n position: absolute;\n left: 8px;\n right: 8px;\n height: 2px;\n background: color-mix(in srgb, var(--gr-primary) 55%, transparent);\n}\n\n.gr-tree__row--drop-prev::before {\n top: 2px;\n}\n\n.gr-tree__row--drop-next::after {\n bottom: 2px;\n}\n</style>\n","<script setup lang=\"ts\" generic=\"T extends Record<string, any> = any\">\nimport { computed, nextTick, onBeforeUnmount, ref, watch } from 'vue'\nimport type {\n GrTreeAllowDropType,\n GrTreeInstance,\n GrTreeKey,\n GrTreeNode,\n GrTreeNodeDropType,\n} from './grTreeTypes'\nimport { createGrTreeDataAdapter } from './grTreeDataAdapter'\nimport type { GrTreeDropTarget } from './grTreeInteractionContext'\nimport { createGrTreeInteractionContext } from './grTreeInteractionContext'\nimport type { GrTreeCheckState } from './grTreeChecking'\nimport { createGrTreeStore } from './grTreeStore'\nimport { treeSizeVars } from './grTreeStyles'\nimport { useGrComponentSize } from '../GrConfigProvider/context'\nimport { useAnnouncer } from '../../composables/useAnnouncer'\nimport { useDragSort } from '../../composables/useDragSort'\nimport { useTypeahead } from '../../composables/internal/useTypeahead'\nimport { useRovingFocus } from '../../composables/useRovingFocus'\nimport { useVirtualList } from '../../composables/useVirtualList'\nimport { useGranularityTranslations } from '../../internal/granularityI18n'\nimport { iconClass, iconTag } from '../shared/icon'\n\nimport IconCheck from '~icons/lucide/check'\nimport IconChevronRight from '~icons/lucide/chevron-right'\nimport IconGripVertical from '~icons/lucide/grip-vertical'\nimport IconLoaderCircle from '~icons/lucide/loader-circle'\nimport IconMinus from '~icons/lucide/minus'\nimport type {\n GrTreeBranchLineColor,\n GrTreeNodeClass,\n GrTreeProps,\n GrTreeVisibleRow,\n} from './grTreeProps'\n\nexport interface GrTreeEmits<T extends Record<string, any> = any> {\n (e: 'nodeClick', data: T, node: GrTreeNode<T>): void\n (e: 'nodeExpand', data: T, node: GrTreeNode<T>): void\n (e: 'nodeCollapse', data: T, node: GrTreeNode<T>): void\n (e: 'nodeDrop', draggingNode: GrTreeNode<T>, dropNode: GrTreeNode<T>, dropType: GrTreeNodeDropType): void\n (e: 'nodeContextMenu', evt: MouseEvent, data: T, node: GrTreeNode<T>): void\n (e: 'update:currentKey', key: GrTreeKey | undefined): void\n /**\n * Результат фильтрации. Без него потребитель не отличит «данных нет» от\n * «поиск ничего не нашёл» — а это разные пустые экраны: второй пользователь\n * может исправить сам.\n */\n (e: 'filter', info: { value: string, visibleCount: number, matchedCount: number }): void\n (e: 'update:checkedKeys', keys: GrTreeKey[]): void\n (e: 'check', data: T, node: GrTreeNode<T>, info: { checkedKeys: GrTreeKey[], halfCheckedKeys: GrTreeKey[] }): void\n}\n\nconst DEFAULT_BRANCH_LINE_COLOR = 'var(--gr-tree-branch-line-default-color, var(--gr-brd))'\n\n/** Стрелки, которые вместе с `Shift` двигают узел, а не фокус. */\nconst MOVE_KEYS = new Set(['ArrowUp', 'ArrowDown', 'ArrowLeft', 'ArrowRight'])\n\nconst props = withDefaults(defineProps<GrTreeProps<T>>(), {\n props: () => ({\n children: 'children',\n label: 'label',\n }),\n nodeKey: 'id' as any,\n defaultExpandedKeys: () => [],\n defaultExpandAll: false,\n expandOnClickNode: false,\n accordion: false,\n size: undefined,\n highlightCurrent: true,\n indent: 0,\n virtual: false,\n maxHeight: undefined,\n showCheckbox: false,\n currentKey: undefined,\n filterValue: undefined,\n dragHandleVisibility: 'auto',\n checkedKeys: undefined,\n defaultCheckedKeys: () => [],\n checkStrictly: false,\n lazy: false,\n load: undefined,\n expandIcon: undefined,\n collapseIcon: undefined,\n toggleIconRotate: true,\n branchLine: false,\n branchLineColor: undefined,\n branchLineActiveColor: undefined,\n draggable: false,\n dragHandleIcon: undefined,\n dragLabel: undefined,\n expandLabel: undefined,\n collapseLabel: undefined,\n rowClass: undefined,\n dragHandleClass: undefined,\n toggleClass: undefined,\n toggleIconClass: undefined,\n toggleSpacerClass: undefined,\n contentClass: undefined,\n})\n\nconst emit = defineEmits<GrTreeEmits<T>>()\n\ndefineSlots<{\n default?: (props: { node: GrTreeNode<T>, data: T }) => any\n}>()\n\nconst dataAdapter = createGrTreeDataAdapter(props)\nconst treeStore = createGrTreeStore({\n adapter: dataAdapter,\n data: () => props.data,\n defaultExpandedKeys: () => props.defaultExpandedKeys,\n defaultExpandAll: () => props.defaultExpandAll,\n filterNodeMethod: () => props.filterNodeMethod,\n defaultCheckedKeys: () => props.defaultCheckedKeys,\n checkedKeys: () => props.checkedKeys,\n checkStrictly: () => props.checkStrictly,\n lazy: () => props.lazy,\n load: () => props.load,\n})\nconst interactionContext = createGrTreeInteractionContext(props, {\n emitNodeClick: (data, node) => emit('nodeClick', data, node),\n emitNodeExpand: (data, node) => emit('nodeExpand', data, node),\n emitNodeCollapse: (data, node) => emit('nodeCollapse', data, node),\n emitNodeDrop: (draggingNode, dropNode, dropType) => emit('nodeDrop', draggingNode, dropNode, dropType),\n emitNodeContextMenu: (evt, data, node) => emit('nodeContextMenu', evt, data, node),\n})\n\nconst treeProps = props as Readonly<GrTreeProps<T>>\n\nconst { t } = useGranularityTranslations()\nconst { announce } = useAnnouncer()\nconst dragLabel = computed(() => treeProps.dragLabel ?? t('gr.tree.drag', 'Drag'))\nconst expandLabel = computed(() => treeProps.expandLabel ?? t('gr.tree.expand', 'Expand'))\nconst collapseLabel = computed(() => treeProps.collapseLabel ?? t('gr.tree.collapse', 'Collapse'))\nconst currentKey = treeStore.currentKey\nconst hoveredKey = interactionContext.hoveredKey\nconst dropTarget = interactionContext.dropTarget\n\n/**\n * Текущий узел: управляемый режим включает сам факт того, что проп задан.\n *\n * Иначе у одного понятия два владельца — подсветку рисует дерево по своему\n * ключу, а обёртка считает остальное по своему пропу; разойдись они на такт, и\n * строка подсвечена, а подпись не выделена. С `v-model:current-key` источник\n * правды один, и `nextTick` вокруг `setCurrentKey()` больше не нужен.\n */\nconst currentKeyControlled = computed(() => treeProps.currentKey !== undefined)\n\nwatch(() => treeProps.currentKey, (key) => {\n if (!currentKeyControlled.value)\n return\n if (treeStore.currentKey.value === (key ?? undefined))\n return\n\n treeStore.setCurrentKey(key ?? undefined)\n}, { immediate: true })\n\n/** Значение фильтра приходит пропом; метод `filter()` остаётся для императивных сценариев. */\nwatch(() => treeProps.filterValue, (value) => {\n if (value === undefined)\n return\n\n applyFilter(value)\n}, { immediate: true })\n\n// Корневой элемент дерева — область для делегированной клавиатуры (WAI-ARIA tree).\nconst treeRootEl = ref<HTMLElement | null>(null)\n\n/**\n * Видимые строки одним плоским списком в порядке отображения.\n *\n * Плоско — потому что рекурсивный рендер стоил по инстансу компонента на каждый\n * раскрытый узел: дерево на 2 000 видимых строк превращалось в 2 000\n * компонентов со своими вычислениями и подписками. Иерархию несут `aria-level`,\n * `aria-posinset` и `aria-setsize`, отступ — `padding-left` строки.\n */\nconst visibleRows = computed<GrTreeVisibleRow<T>[]>(() => {\n const { roots } = treeStore.treeModel.value\n const { isActive, subtreeHasMatch, matchedKeys, autoExpandKeys } = treeStore.filterInfo.value\n const branch = treeProps.branchLine\n const rows: GrTreeVisibleRow<T>[] = []\n\n const walk = (nodes: GrTreeNode<T>[], ancestorColors: string[]): void => {\n const siblings = isActive ? nodes.filter(node => subtreeHasMatch.get(node.key)) : nodes\n\n siblings.forEach((node, index) => {\n const isLeaf = treeStore.isLeafNode(node)\n const isExpanded = treeStore.isExpandedKey(node.key) || (isActive && autoExpandKeys.has(node.key))\n\n rows.push({\n node,\n isExpanded,\n isLeaf,\n isMatched: matchedKeys.has(node.key),\n posInSet: index + 1,\n setSize: siblings.length,\n isLoading: treeStore.isLoadingKey(node.key),\n branchColors: ancestorColors,\n })\n\n if (isExpanded && node.childNodes.length)\n walk(node.childNodes, branch ? [...ancestorColors, resolveBranchLineColor(node)] : ancestorColors)\n })\n }\n\n walk(roots, [])\n return rows\n})\n\n/**\n * Кольцо roving-фокуса: ровно один `treeitem` на всё дерево держит `tabindex=0`.\n *\n * Ориентация вертикальная намеренно: влево-вправо в дереве заняты раскрытием\n * ветки и переходом к родителю, и примитив их не трогает — это доменная логика,\n * она осталась в `onTreeKeydown`.\n */\nconst roving = useRovingFocus<GrTreeNode<T>['key']>({\n items: () => visibleRows.value.map(row => row.node.key),\n elementFor: key => interactionContext.nodeEls.get(key),\n orientation: () => 'vertical',\n // У дерева есть верх и низ: с последней строки вниз идти некуда.\n wrap: () => false,\n // Но клавишу на краю всё равно гасим: иначе `ArrowDown` на последнем узле\n // прокрутит страницу под деревом.\n onOverflow: () => true,\n // Пока фокус не трогали, остановку держит текущий (выбранный) узел, а если\n // его не видно — первая видимая строка.\n initialKey: () => currentKey.value ?? undefined,\n beforeFocus: key => scrollRowIntoView(key),\n})\n\nfunction onRowClick(node: GrTreeNode<T>) {\n // В управляемом режиме дерево ведёт подсветку до ответа снаружи: строка\n // отзывается на клик сразу, а расхождение снимет наблюдатель за пропом.\n treeStore.setCurrentKey(node.key)\n emit('update:currentKey', node.key)\n roving.setActive(node.key)\n interactionContext.emitNodeClick(node.data, node)\n}\n\n// Клик мышью, в отличие от Enter, умеет ещё и раскрывать узел: `Enter` в\n// паттерне tree закреплён за выбором, и подмешивать в него раскрытие нельзя.\nfunction onRowActivate(row: GrTreeVisibleRow<T>) {\n onRowClick(row.node)\n\n if (treeProps.expandOnClickNode && !row.isLeaf)\n toggleExpand(row.node)\n}\n\nfunction onRowContextMenu(evt: MouseEvent, node: GrTreeNode<T>) {\n interactionContext.emitNodeContextMenu(evt, node.data, node)\n}\n\n// ————— Клавиатурная навигация по WAI-ARIA tree pattern (только корневой инстанс).\n\nfunction isRovingItem(key: GrTreeNode<T>['key']): boolean {\n return roving.rovingKey.value === key\n}\n\nconst resolvedSize = useGrComponentSize(() => props.size, { component: 'GrTree' })\n\n// Переменные ставим и вложенным уровням тоже: `v-bind=\"props\"` доносит до них\n// `size`, а значения одинаковые — наследование от корня не нарушается.\nconst sizeStyle = computed(() => treeSizeVars[resolvedSize.value])\n\n/**\n * Виртуализация: в DOM живёт только окно вокруг вьюпорта.\n *\n * Корень дерева и есть скроллер — обёрток-распорок между `role=\"tree\"` и\n * `role=\"treeitem\"` быть не должно, поэтому срезанное сверху и снизу держат\n * отступы самого корня.\n */\nconst TREE_ROW_GAP = 2\n\nconst rowEstimate = computed(() => Number.parseFloat(sizeStyle.value['--gr-tree-row-min-height']))\n\nconst virtualMaxHeight = computed(() => {\n const value = treeProps.maxHeight\n if (value == null)\n return undefined\n return typeof value === 'number' ? `${value}px` : value\n})\n\nconst virtualizer = useVirtualList({\n container: treeRootEl,\n count: () => (treeProps.virtual ? visibleRows.value.length : 0),\n // Раскрытие/фильтр сдвигают индексы строк — замеры прошлого набора невалидны.\n source: () => visibleRows.value,\n itemSize: () => rowEstimate.value,\n gap: TREE_ROW_GAP,\n // Первый рендер обязан совпасть с серверным: контейнера ещё нет, и окно\n // считается от объявленной высоты, а не от измеренной.\n viewportSize: () => (typeof treeProps.maxHeight === 'number' ? treeProps.maxHeight : undefined),\n})\n\n/** Строки к отрисовке: при выключенной виртуализации — все. */\nconst renderedRows = computed(() => {\n if (!treeProps.virtual)\n return visibleRows.value\n\n const { start, end } = virtualizer.range.value\n return visibleRows.value.slice(start, end)\n})\n\n/**\n * Срезанное сверху и снизу держат псевдоэлементы контейнера.\n *\n * Ни один из трёх напрашивающихся вариантов не годится:\n *\n * - `padding` контейнера — `max-height` меряет ту же коробку, и распорка в сто\n * тысяч пикселей либо раздувает скроллер до той же сотни тысяч, либо съедает\n * всю его высоту;\n * - обёртка-распорка внутри — между `role=\"tree\"` и `role=\"treeitem\"` не должно\n * быть посторонних узлов, роль потеряла бы обязательных потомков;\n * - отступы крайних отрисованных строк — распорка исчезает ровно в тот момент,\n * когда строки заменяются целиком (прыжок прокрутки), содержимое схлопывается\n * до высоты окна, и браузер обрезает `scrollTop` до почти нуля.\n *\n * `::before`/`::after` не узлы DOM: их не за что размонтировать, в дереве\n * доступности их нет, а высота приезжает переменными в том же патче, что и сами\n * строки, — схлопнуться между кадрами нечему.\n */\nconst rootStyle = computed(() => {\n if (!treeProps.virtual)\n return sizeStyle.value\n\n return {\n ...sizeStyle.value,\n overflow: 'auto',\n maxHeight: virtualMaxHeight.value,\n ...virtualizer.spacerStyle.value,\n }\n})\n\n/** Абсолютный индекс отрисованной строки: поиск по массиву стоил бы O(n) на строку. */\nfunction absoluteIndex(offsetInWindow: number): number {\n return treeProps.virtual ? virtualizer.range.value.start + offsetInWindow : offsetInWindow\n}\n\n/**\n * Строка размонтируется: снимаем регистрацию и, если фокус был на ней, уводим\n * его на корень — делегированный keydown живёт там, первая же стрелка вернёт\n * видимую строку через `focusRow`. Иначе фокус упал бы на `body` и клавиатура\n * дерева умерла бы до клика мышью.\n *\n * Спрашиваем сам элемент, а не `document.activeElement === body`: Vue обнуляет\n * function ref ДО удаления узла, поэтому в момент вызова фокус ещё на строке —\n * а «фокус на body» означает лишь то, что страницу никто не трогал.\n */\nlet isUnmounting = false\n\nfunction releaseNodeEl(key: GrTreeKey): void {\n const el = interactionContext.nodeEls.get(key)\n const active = typeof document === 'undefined' ? null : document.activeElement\n const heldFocus = Boolean(el && active && (el === active || el.contains(active)))\n\n interactionContext.registerNodeEl(key, null)\n\n if (heldFocus && !isUnmounting)\n treeRootEl.value?.focus({ preventScroll: true })\n}\n\n/**\n * При виртуализации узла вне окна в DOM нет: `nodeEls.get` вернул бы\n * `undefined`, а фокус уехал бы на `body` вместе с размонтированной строкой.\n * Поэтому сперва прокрутка, и только следующим тиком — фокус.\n */\nfunction scrollRowIntoView(key: GrTreeNode<T>['key']): Promise<void> {\n if (treeProps.virtual) {\n const index = visibleRows.value.findIndex(row => row.node.key === key)\n if (index >= 0)\n virtualizer.scrollToIndex(index)\n }\n\n return nextTick()\n}\n\nfunction focusRow(key: GrTreeNode<T>['key']): void {\n void roving.focusKey(key)\n}\n\n/**\n * Typeahead паттерна tree: печатные символы копятся в буфер и переводят фокус\n * на первый подходящий видимый узел, начиная со следующего за текущим.\n *\n * Поиск идёт по данным (`visibleRows`), а не по DOM: при виртуализации узла вне\n * окна в разметке нет, и поиск по тексту элементов находил бы только видимое.\n */\nconst typeahead = useTypeahead<GrTreeVisibleRow<T>>({\n items: () => visibleRows.value,\n textOf: row => row.node.label,\n // Без наведённого фокуса ищем с начала списка, а не от конца: `findIndex`\n // вернул бы `-1`, и первая строка выпала бы из обхода.\n currentIndex: rows => Math.max(0, rows.findIndex(row => row.node.key === roving.rovingKey.value)),\n onMatch: row => focusRow(row.node.key),\n})\n\n/** `*` — раскрыть всех соседей узла, на котором фокус (уровень целиком). */\nfunction expandSiblings(node: GrTreeNode<T>): void {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n\n for (const sibling of siblings) {\n if (sibling.childNodes.length === 0 || treeStore.isExpandedKey(sibling.key))\n continue\n\n treeStore.setExpandedKey(sibling.key, true)\n interactionContext.emitNodeExpand(sibling.data, sibling)\n }\n}\n\nfunction onTreeKeydown(event: KeyboardEvent): void {\n // Делегированная клавиатура уважает интерактивные цели: печать в инпуте слота\n // узла — ввод текста, а не typeahead. Без гарда preventDefault отменял бы это.\n const target = event.target as HTMLElement | null\n const interactive = target?.closest<HTMLElement>('button, a[href], input, select, textarea, [contenteditable]')\n if (interactive && interactive !== event.currentTarget) {\n // Табируемая цель — самостоятельный таб-стоп: клавиатура целиком её.\n if (interactive.tabIndex >= 0)\n return\n\n // Кнопки строки (toggle, drag-handle) не табируемы: фокус попадает на них\n // только мышью. За ними остаётся активация — Enter на toggle это его клик, —\n // а навигация принадлежит дереву, иначе клик мышью убивал бы стрелки.\n if (event.key === 'Enter' || event.key === ' ')\n return\n }\n\n const rows = visibleRows.value\n if (rows.length === 0)\n return\n\n const idx = Math.max(0, rows.findIndex(r => r.node.key === roving.rovingKey.value))\n const cur = rows[idx]\n\n if (event.key === '*') {\n event.preventDefault()\n expandSiblings(cur.node)\n return\n }\n\n // Печатный символ без модификаторов — typeahead, а не команда.\n if (event.key.length === 1 && event.key !== ' ' && !event.ctrlKey && !event.metaKey && !event.altKey) {\n event.preventDefault()\n typeahead.type(event.key)\n return\n }\n\n // `Shift` со стрелкой двигает сам узел — раскладка аутлайнера. Проверяется\n // раньше навигации: иначе примитив увёл бы фокус вместо переноса.\n if (event.shiftKey && MOVE_KEYS.has(event.key)) {\n if (!treeProps.draggable)\n return\n\n event.preventDefault()\n void onNodeMoveKey(cur.node, event.key)\n return\n }\n\n // Вертикаль, `Home` и `End` ведёт примитив. Влево-вправо он не трогает: в\n // дереве это раскрытие ветки и переход к родителю, а не движение по списку.\n if (roving.handleNavigationKeys(event))\n return\n\n switch (event.key) {\n case 'ArrowRight':\n event.preventDefault()\n if (!cur.isLeaf) {\n if (!cur.isExpanded)\n toggleExpand(cur.node)\n else if (idx < rows.length - 1)\n focusRow(rows[idx + 1].node.key)\n }\n break\n case 'ArrowLeft':\n event.preventDefault()\n if (!cur.isLeaf && cur.isExpanded)\n toggleExpand(cur.node)\n else if (cur.node.parent && rows.some(r => r.node.key === cur.node.parent!.key))\n focusRow(cur.node.parent.key)\n break\n case 'Enter':\n event.preventDefault()\n onRowClick(cur.node)\n break\n // Space при чекбоксах переключает отметку — это и есть выбор в\n // multi-select дереве; без них он остаётся вторым способом выбрать узел.\n case ' ':\n event.preventDefault()\n if (treeProps.showCheckbox)\n toggleChecked(cur.node)\n else\n onRowClick(cur.node)\n break\n }\n}\n\nfunction onRowMouseEnter(node: GrTreeNode<T>) {\n hoveredKey.value = node.key\n}\n\nfunction onRowMouseLeave(node: GrTreeNode<T>) {\n if (hoveredKey.value === node.key)\n hoveredKey.value = undefined\n}\n\nfunction collapseSiblings(node: GrTreeNode<T>) {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n\n for (const sibling of siblings) {\n if (sibling.key === node.key || !treeStore.isExpandedKey(sibling.key))\n continue\n\n treeStore.setExpandedKey(sibling.key, false)\n interactionContext.emitNodeCollapse(sibling.data, sibling)\n }\n}\n\nfunction toggleExpand(node: GrTreeNode<T>) {\n const expanded = !treeStore.isExpandedKey(node.key)\n\n if (expanded && treeProps.accordion)\n collapseSiblings(node)\n\n // Ленивая ветка грузится по первому раскрытию; повторное ничего не запрашивает.\n if (expanded)\n treeStore.ensureLoaded(node)\n\n treeStore.toggleExpand(node)\n\n if (expanded)\n interactionContext.emitNodeExpand(node.data, node)\n else\n interactionContext.emitNodeCollapse(node.data, node)\n}\n\n// ————— Отметки (чекбоксы).\n\nfunction checkStateOf(key: GrTreeKey): GrTreeCheckState {\n return treeStore.getCheckState(key)\n}\n\nfunction ariaCheckedOf(row: GrTreeVisibleRow<T>): 'true' | 'false' | 'mixed' | undefined {\n if (!treeProps.showCheckbox)\n return undefined\n\n const state = checkStateOf(row.node.key)\n return state === 'checked' ? 'true' : state === 'half' ? 'mixed' : 'false'\n}\n\nfunction emitCheck(node: GrTreeNode<T>): void {\n const checkedKeys = treeStore.getCheckedKeys()\n emit('update:checkedKeys', checkedKeys)\n emit('check', node.data, node, { checkedKeys, halfCheckedKeys: treeStore.getHalfCheckedKeys() })\n}\n\nfunction toggleChecked(node: GrTreeNode<T>): void {\n if (!treeProps.showCheckbox)\n return\n\n const changed = treeStore.toggleChecked(node)\n if (changed)\n emitCheck(changed)\n}\n\n// ————— Геометрия строки: отступ уровня и направляющие ветвей.\n\nfunction rowStyle(row: GrTreeVisibleRow<T>) {\n const step = treeProps.indent && treeProps.indent > 0\n ? `${treeProps.indent}px`\n : 'var(--gr-tree-indent-step)'\n\n return { '--gr-tree-row-indent': `calc(${step} * ${row.node.level - 1})` }\n}\n\n/**\n * Направляющая уровня-предка. Считается от того же шага отступа, что и сам\n * отступ строки, — иначе линия и содержимое разъедутся на вложенных уровнях.\n */\nfunction branchGuideStyle(row: GrTreeVisibleRow<T>, index: number) {\n const step = treeProps.indent && treeProps.indent > 0\n ? `${treeProps.indent}px`\n : 'var(--gr-tree-indent-step)'\n\n return {\n 'left': `calc(${step} * ${index} + var(--gr-tree-branch-line-offset))`,\n '--gr-tree-branch-line-color': row.branchColors[index],\n }\n}\n\n// Drag & drop\nfunction canDrag(node: GrTreeNode<T>): boolean {\n return interactionContext.canDrag(node)\n}\n\n/**\n * Ручка «по наведению» на тач-устройстве недостижима: событий наведения там нет,\n * ключ не выставляется, класс видимости не появляется — то есть перетаскивания\n * нет вовсе, хотя `touch-action: none` у ручки стоит ровно ради него.\n *\n * Режим `auto` решает это без JS: класс-модификатор на корне, а показ включает\n * `@media (hover: none)` — так поведение остаётся верным и на сервере, где\n * никакого `matchMedia` спрашивать нельзя.\n */\nfunction shouldShowDragHandle(node: GrTreeNode<T>): boolean {\n if (!canDrag(node))\n return false\n\n return treeProps.dragHandleVisibility === 'always' || hoveredKey.value === node.key\n}\n\n/**\n * Треть строки сверху — «до», треть снизу — «после», середина — «внутрь».\n * Зоны нарезает компонент: примитив отдаёт только долю вдоль строки.\n */\nfunction dropTypeFromFraction(fraction: number): GrTreeNodeDropType {\n if (fraction < 1 / 3)\n return 'prev'\n if (fraction > 2 / 3)\n return 'next'\n\n return 'inner'\n}\n\nfunction canDrop(drag: GrTreeNode<T>, target: GrTreeNode<T>, type: GrTreeAllowDropType): boolean {\n return interactionContext.canDrop(drag, target, type)\n}\n\n/** Перенос состоялся: одна дорога и для указателя, и для клавиатуры. */\nfunction applyMove(source: GrTreeNode<T>, targetKey: GrTreeKey, type: GrTreeNodeDropType): boolean {\n const reference = treeStore.getNode(targetKey)\n if (!reference)\n return false\n\n const movedNode = treeStore.moveNode(source, reference, type)\n if (!movedNode)\n return false\n\n const dropNode = treeStore.getNode(reference.key) ?? reference\n interactionContext.emitNodeDrop(movedNode, dropNode, type)\n\n return true\n}\n\nconst dragSort = useDragSort<GrTreeKey, GrTreeDropTarget>({\n items: () => visibleRows.value.map(row => row.node.key),\n elementFor: key => interactionContext.nodeEls.get(key) ?? null,\n scroller: () => treeRootEl.value,\n disabled: () => !treeProps.draggable,\n canDrag: (key) => {\n const node = treeStore.getNode(key)\n\n return node ? canDrag(node) : false\n },\n resolveTarget: (hit, sourceKey, previous) => {\n const source = treeStore.getNode(sourceKey)\n const node = treeStore.getNode(hit.key)\n if (!source || !node)\n return null\n\n const type = dropTypeFromFraction(hit.fraction)\n const allowed = treeStore.canMoveNode(source, node, type) && canDrop(source, node, type)\n\n // Та же ссылка, пока смысл не изменился: иначе подсветка перерисовывалась бы\n // на каждом движении указателя.\n if (previous && previous.key === node.key && previous.type === type && previous.allowed === allowed)\n return previous\n\n return { key: node.key, type, allowed }\n },\n onDrop: (sourceKey, target) => {\n const source = treeStore.getNode(sourceKey)\n if (!source || !target.allowed)\n return\n\n applyMove(source, target.key, target.type)\n },\n onUpdate: (sourceKey, target) => {\n interactionContext.draggingNode.value = sourceKey === null ? null : treeStore.getNode(sourceKey) ?? null\n interactionContext.dropTarget.value = target\n },\n})\n\nfunction onHandlePointerDown(event: PointerEvent, node: GrTreeNode<T>): void {\n if (!treeProps.draggable)\n return\n\n dragSort.startFrom(node.key)(event)\n}\n\n/**\n * Клавиатурный перенос — раскладка аутлайнера: `Shift` со стрелкой сразу\n * двигает узел, без режима «взято». Режим здесь был бы лишним: `Space` в дереве\n * уже отмечает чекбокс, а стрелки водят фокус по веткам.\n */\nfunction moveByKeyboard(node: GrTreeNode<T>, key: string): boolean {\n const siblings = node.parent ? node.parent.childNodes : treeStore.treeModel.value.roots\n const index = siblings.findIndex(sibling => sibling.key === node.key)\n\n if (key === 'ArrowUp' && index > 0)\n return applyMove(node, siblings[index - 1].key, 'prev')\n\n if (key === 'ArrowDown' && index >= 0 && index < siblings.length - 1)\n return applyMove(node, siblings[index + 1].key, 'next')\n\n // Вправо — в предыдущего соседа: у первого в уровне такого соседа нет.\n if (key === 'ArrowRight' && index > 0)\n return applyMove(node, siblings[index - 1].key, 'inner')\n\n if (key === 'ArrowLeft' && node.parent)\n return applyMove(node, node.parent.key, 'next')\n\n return false\n}\n\nasync function onNodeMoveKey(node: GrTreeNode<T>, key: string): Promise<void> {\n if (!treeProps.draggable || !canDrag(node))\n return\n if (!moveByKeyboard(node, key))\n return\n\n announce(t('gr.tree.moved', 'Moved {label}', { label: node.label }))\n\n // Перестановка перерисовывает уровень: без возврата фокуса следующий Shift\n // уже некуда было бы адресовать.\n await nextTick()\n focusRow(node.key)\n}\n\n/**\n * Фильтрация и отчёт о её результате.\n *\n * Счёт снимается после пересчёта видимых строк: `visibleCount` — то, что\n * пользователь реально видит, а `matchedCount` — сколько узлов совпало само,\n * без учёта родителей, раскрытых ради показа совпадения.\n */\nasync function applyFilter(value: string) {\n treeStore.filter(value)\n await nextTick()\n\n emit('filter', {\n value,\n visibleCount: visibleRows.value.length,\n matchedCount: treeStore.filterInfo.value.matchedKeys.size,\n })\n}\n\nfunction filter(value: string) {\n void applyFilter(value)\n}\n\nfunction resolveNodeClass(classValue: GrTreeNodeClass<T> | undefined, row: GrTreeVisibleRow<T>) {\n if (!classValue)\n return undefined\n\n return typeof classValue === 'function'\n ? classValue(row)\n : classValue\n}\n\nfunction resolveBranchLineColorValue(color: GrTreeBranchLineColor<T> | undefined, node: GrTreeNode<T>) {\n if (!color)\n return undefined\n\n return typeof color === 'function'\n ? color(node) ?? undefined\n : color\n}\n\nfunction isBranchLineActive(node: GrTreeNode<T>) {\n const selectedKey = currentKey.value\n\n if (selectedKey == null)\n return false\n\n if (node.key === selectedKey)\n return true\n\n return node.childNodes.some(child => child.key === selectedKey && !treeStore.isExpandedKey(child.key))\n}\n\nfunction resolveBranchLineColor(node: GrTreeNode<T>) {\n const defaultColor = resolveBranchLineColorValue(treeProps.branchLineColor, node) ?? DEFAULT_BRANCH_LINE_COLOR\n\n if (!isBranchLineActive(node))\n return defaultColor\n\n return resolveBranchLineColorValue(treeProps.branchLineActiveColor, node) ?? defaultColor\n}\n\n/**\n * Переводит фокус на узел (по умолчанию — на тот, что держит roving tabindex).\n * Нужен снаружи: `GrTreeSelect` открывает панель и обязан отдать клавиатуру\n * дереву, иначе стрелки из триггера никуда не ведут.\n */\nfunction focus(key?: GrTreeKey): boolean {\n const rows = visibleRows.value\n if (rows.length === 0)\n return false\n\n const target = key != null && rows.some(row => row.node.key === key)\n ? key\n : roving.rovingKey.value ?? rows[0].node.key\n\n focusRow(target)\n return true\n}\n\n// Дерево уничтожают целиком — строки размонтируются вместе с ним, и возвращать\n// фокус на умирающий корень нельзя: он уедет из документа вместе с деревом.\nonBeforeUnmount(() => {\n isUnmounting = true\n})\n\ndefineExpose<GrTreeInstance<T>>({\n appendNode: treeStore.appendNode,\n getCheckedKeys: options => treeStore.getCheckedKeys(options),\n setCheckedKeys: (keys) => {\n treeStore.setCheckedKeys(keys)\n emit('update:checkedKeys', treeStore.getCheckedKeys())\n },\n getHalfCheckedKeys: treeStore.getHalfCheckedKeys,\n setChecked: (node, checked) => {\n const changed = treeStore.setChecked(node, checked)\n if (changed)\n emitCheck(changed)\n return Boolean(changed)\n },\n filter,\n focus,\n getCurrentNode: treeStore.getCurrentNode,\n setCurrentKey: treeStore.setCurrentKey,\n getCurrentKey: treeStore.getCurrentKey,\n getNode: treeStore.getNode,\n insertNodeAfter: treeStore.insertNodeAfter,\n insertNodeBefore: treeStore.insertNodeBefore,\n removeNode: treeStore.removeNode,\n setCurrentNode: treeStore.setCurrentNode,\n})\n</script>\n\n<template>\n <div\n ref=\"treeRootEl\"\n data-gr-tree\n class=\"gr-tree\"\n :class=\"treeProps.dragHandleVisibility === 'auto' ? 'gr-tree--drag-handle-auto' : ''\"\n tabindex=\"-1\"\n :data-gr-virtual=\"treeProps.virtual ? '' : undefined\"\n role=\"tree\"\n :aria-multiselectable=\"treeProps.showCheckbox ? 'true' : undefined\"\n :style=\"rootStyle\"\n @keydown=\"onTreeKeydown\"\n >\n <div\n v-for=\"(row, windowIndex) in renderedRows\"\n :key=\"row.node.key\"\n :ref=\"(el) => {\n if (el) interactionContext.registerNodeEl(row.node.key, el as HTMLElement)\n else releaseNodeEl(row.node.key)\n if (treeProps.virtual) virtualizer.measure(absoluteIndex(windowIndex), el as Element | null)\n }\"\n data-gr-tree-node\n :data-gr-tree-node-key=\"row.node.key\"\n role=\"treeitem\"\n :aria-level=\"row.node.level\"\n :aria-posinset=\"row.posInSet\"\n :aria-setsize=\"row.setSize\"\n :aria-expanded=\"row.isLeaf ? undefined : row.isExpanded\"\n :aria-selected=\"currentKey === row.node.key ? 'true' : undefined\"\n :aria-checked=\"ariaCheckedOf(row)\"\n :aria-busy=\"row.isLoading ? 'true' : undefined\"\n :tabindex=\"isRovingItem(row.node.key) ? 0 : -1\"\n >\n <div\n data-gr-tree-row\n class=\"gr-tree__row\"\n :class=\"[\n treeProps.highlightCurrent && currentKey === row.node.key ? 'gr-tree__row--current' : '',\n row.isMatched ? 'gr-tree__row--matched' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'inner' ? 'gr-tree__row--drop-inner' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'prev' ? 'gr-tree__row--drop-prev' : '',\n dropTarget?.key === row.node.key && dropTarget.allowed && dropTarget.type === 'next' ? 'gr-tree__row--drop-next' : '',\n resolveNodeClass(treeProps.rowClass, row),\n ]\"\n :style=\"rowStyle(row)\"\n @click=\"onRowActivate(row)\"\n @contextmenu=\"onRowContextMenu($event, row.node)\"\n @drop.prevent\n @mouseenter=\"onRowMouseEnter(row.node)\"\n @mouseleave=\"onRowMouseLeave(row.node)\"\n >\n <!--\n Направляющие ветвей: по одной на каждый уровень предка. Вложенной\n обёртки с `border-left` больше нет, поэтому линию рисует сама строка —\n и заходит в зазор между строками, иначе она распалась бы на штрихи.\n -->\n <span\n v-for=\"(color, guideIndex) in row.branchColors\"\n :key=\"guideIndex\"\n data-gr-tree-branch-guide\n class=\"gr-tree__branch-guide\"\n :style=\"branchGuideStyle(row, guideIndex)\"\n aria-hidden=\"true\"\n />\n\n <button\n v-if=\"treeProps.draggable\"\n type=\"button\"\n tabindex=\"-1\"\n data-gr-tree-drag-handle\n class=\"gr-tree__drag-handle\"\n :class=\"[\n shouldShowDragHandle(row.node) ? 'gr-tree__drag-handle--visible' : '',\n canDrag(row.node) ? '' : 'gr-tree__drag-handle--disabled',\n resolveNodeClass(treeProps.dragHandleClass, row),\n ]\"\n :aria-label=\"dragLabel\"\n :aria-disabled=\"canDrag(row.node) ? undefined : 'true'\"\n @click.stop\n @pointerdown=\"onHandlePointerDown($event, row.node)\"\n >\n <component\n :is=\"iconTag(treeProps.dragHandleIcon, IconGripVertical)\"\n class=\"gr-tree__drag-icon\"\n :class=\"iconClass(treeProps.dragHandleIcon)\"\n />\n </button>\n\n <!-- tabindex=\"-1\": внутри roving-композита интерактив не табируется,\n клавиатурный эквивалент — ArrowRight/ArrowLeft на строке. -->\n <button\n v-if=\"!row.isLeaf\"\n data-gr-tree-toggle\n type=\"button\"\n tabindex=\"-1\"\n class=\"gr-tree__toggle\"\n :class=\"resolveNodeClass(treeProps.toggleClass, row)\"\n :aria-label=\"row.isExpanded ? collapseLabel : expandLabel\"\n @click.stop=\"toggleExpand(row.node)\"\n >\n <IconLoaderCircle\n v-if=\"row.isLoading\"\n data-gr-tree-loading\n class=\"gr-tree__toggle-icon animate-spin\"\n />\n <component\n :is=\"iconTag(row.isExpanded ? treeProps.collapseIcon : treeProps.expandIcon, IconChevronRight)\"\n v-else\n class=\"gr-tree__toggle-icon\"\n :class=\"[\n iconClass(row.isExpanded ? treeProps.collapseIcon : treeProps.expandIcon),\n row.isExpanded && treeProps.toggleIconRotate ? 'gr-tree__toggle-icon--expanded' : '',\n resolveNodeClass(treeProps.toggleIconClass, row),\n ]\"\n />\n </button>\n <span\n v-else\n class=\"gr-tree__toggle-spacer\"\n :class=\"resolveNodeClass(treeProps.toggleSpacerClass, row)\"\n />\n\n <!--\n Квадратик отметки декоративен: состояние живёт на самом `treeitem`\n (`aria-checked`), а вложить интерактивный чекбокс внутрь роли-виджета\n нельзя — роль объявляет потомков презентационными.\n -->\n <span\n v-if=\"treeProps.showCheckbox\"\n data-gr-tree-checkbox\n class=\"gr-tree__checkbox\"\n :class=\"[\n checkStateOf(row.node.key) === 'checked' ? 'gr-tree__checkbox--checked' : '',\n checkStateOf(row.node.key) === 'half' ? 'gr-tree__checkbox--half' : '',\n ]\"\n aria-hidden=\"true\"\n @click.stop=\"toggleChecked(row.node)\"\n >\n <component\n :is=\"checkStateOf(row.node.key) === 'half' ? IconMinus : IconCheck\"\n v-if=\"checkStateOf(row.node.key) !== 'unchecked'\"\n class=\"gr-tree__checkbox-mark\"\n />\n </span>\n\n <div class=\"gr-tree__content\" :class=\"resolveNodeClass(treeProps.contentClass, row)\">\n <slot\n :node=\"row.node\"\n :data=\"row.node.data\"\n >\n <span class=\"gr-tree__label\">{{ row.node.label }}</span>\n </slot>\n </div>\n </div>\n </div>\n </div>\n</template>\n\n<style scoped>\n.gr-tree {\n --gr-tree-gap: 2px;\n --gr-tree-children-pl: 10px;\n --gr-tree-row-min-height: 28px;\n --gr-tree-row-radius: 8px;\n --gr-tree-row-px: 8px;\n --gr-tree-row-py: 8px;\n --gr-tree-row-pr: var(--gr-tree-row-px);\n --gr-tree-font-size: inherit;\n --gr-tree-row-color: var(--gr-fg);\n --gr-tree-row-hover-bg: color-mix(in srgb, var(--gr-primary) 10%, transparent);\n --gr-tree-row-current-bg: color-mix(in srgb, var(--gr-primary) 5%, transparent);\n --gr-tree-row-current-hover-bg: color-mix(in srgb, var(--gr-primary) 16%, transparent);\n --gr-tree-drag-handle-size: 24px;\n --gr-tree-drag-handle-mr: 0;\n --gr-tree-drag-handle-radius: 6px;\n --gr-tree-drag-handle-color: inherit;\n --gr-tree-drag-handle-opacity: 0.55;\n --gr-tree-drag-handle-hover-bg: color-mix(in srgb, var(--gr-muted) 22%, transparent);\n --gr-tree-drag-handle-hover-color: var(--gr-tree-drag-handle-color);\n --gr-tree-drag-handle-hover-opacity: 0.9;\n --gr-tree-drag-handle-disabled-opacity: 0.25;\n --gr-tree-toggle-size: 24px;\n --gr-tree-toggle-mr: 0;\n --gr-tree-toggle-radius: 6px;\n --gr-tree-toggle-color: inherit;\n --gr-tree-toggle-hover-bg: color-mix(in srgb, var(--gr-muted) 25%, transparent);\n --gr-tree-toggle-hover-color: var(--gr-tree-toggle-color);\n --gr-tree-icon-size: 16px;\n --gr-tree-content-gap: 8px;\n --gr-tree-branch-line-default-color: var(--gr-tree-row-current-bg);\n --gr-tree-branch-line-width: 2px;\n /* Шаг отступа уровня: переключатель, отступ вложенного списка и толщина\n направляющей — линия обязана попадать между ними. */\n --gr-tree-indent-step: calc(24px + var(--gr-tree-children-pl) + var(--gr-tree-branch-line-width));\n --gr-tree-branch-line-offset: 24px;\n --gr-tree-checkbox-size: 16px;\n --gr-tree-checkbox-radius: 4px;\n --gr-tree-checkbox-brd: var(--gr-brd);\n --gr-tree-checkbox-bg: transparent;\n --gr-tree-checkbox-checked-bg: var(--gr-primary);\n --gr-tree-checkbox-checked-fg: var(--gr-primary-fg);\n --gr-tree-checkbox-mr: 4px;\n display: flex;\n flex-direction: column;\n gap: var(--gr-tree-gap);\n}\n\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\n.gr-tree__row {\n position: relative;\n display: flex;\n align-items: center;\n min-height: var(--gr-tree-row-min-height);\n padding: var(--gr-tree-row-py) var(--gr-tree-row-pr) var(--gr-tree-row-py)\n calc(var(--gr-tree-row-px) + var(--gr-tree-row-indent, 0px));\n font-size: var(--gr-tree-font-size);\n cursor: default;\n user-select: none;\n outline: none;\n color: var(--gr-tree-row-color);\n isolation: isolate;\n}\n\n/* Поверхность строки — отдельный слой, вставленный слева на отступ уровня.\n Фон на самой коробке шёл от левого края дерева и накрывал направляющие\n предков: линия ветки исчезала под подсветкой ровно там, где она и нужна.\n Слой лежит ниже направляющих (они — следующие элементы строки), поэтому\n линия остаётся видна при любом наложении.\n\n `z-index: -1` уводит слой под содержимое строки. Без него позиционированный\n `::before` красится ПОВЕРХ потоковых подписи, шеврона и отметки — при\n полупрозрачном фоне это лишь лёгкое затенение, а при непрозрачном значении\n публичного токена содержимое исчезает целиком. Поднимать вместо этого\n содержимое пришлось бы у каждого элемента строки и у каждого нового.\n\n `isolation` на самой строке обязателен в паре: без своего контекста\n наложения отрицательный слой уезжает за фон ближайшего предка с заливкой, и\n подсветка пропадает на карточке. */\n.gr-tree__row::before {\n content: '';\n position: absolute;\n inset: 0 0 0 var(--gr-tree-row-indent, 0px);\n border-radius: var(--gr-tree-row-radius);\n pointer-events: none;\n z-index: -1;\n}\n\n.gr-tree__row:hover::before {\n background: var(--gr-tree-row-hover-bg);\n}\n\n/* Направляющая тянется в зазор между строками: иначе линия ветки распалась бы\n на штрихи по числу строк. */\n.gr-tree__branch-guide {\n position: absolute;\n top: calc(var(--gr-tree-gap) / -2);\n bottom: calc(var(--gr-tree-gap) / -2);\n width: var(--gr-tree-branch-line-width);\n background: var(--gr-tree-branch-line-color, var(--gr-tree-branch-line-default-color));\n pointer-events: none;\n}\n\n.gr-tree__checkbox {\n display: inline-flex;\n align-items: center;\n justify-content: center;\n flex-shrink: 0;\n width: var(--gr-tree-checkbox-size);\n height: var(--gr-tree-checkbox-size);\n margin-right: var(--gr-tree-checkbox-mr);\n border: 1px solid var(--gr-tree-checkbox-brd);\n border-radius: var(--gr-tree-checkbox-radius);\n background: var(--gr-tree-checkbox-bg);\n color: var(--gr-tree-checkbox-checked-fg);\n cursor: pointer;\n}\n\n.gr-tree__checkbox--checked,\n.gr-tree__checkbox--half {\n border-color: var(--gr-tree-checkbox-checked-bg);\n background: var(--gr-tree-checkbox-checked-bg);\n}\n\n.gr-tree__checkbox-mark {\n width: calc(var(--gr-tree-checkbox-size) - 4px);\n height: calc(var(--gr-tree-checkbox-size) - 4px);\n}\n\n[data-gr-tree-node] {\n outline: none;\n}\n\n/* Кольцо фокуса — на той же поверхности, что подсветка: иначе строка читалась бы\n двумя разными прямоугольниками. `outline` для этого не годится — он рисуется по\n границе коробки, а не по инсету. */\n[data-gr-tree-node]:focus-visible > .gr-tree__row::before {\n box-shadow: inset 0 0 0 2px var(--gr-primary);\n}\n\n.gr-tree__row--current::before {\n background: var(--gr-tree-row-current-bg);\n}\n\n.gr-tree__row--current:hover::before {\n background: var(--gr-tree-row-current-hover-bg);\n}\n\n.gr-tree__row--matched .gr-tree__label {\n font-weight: 600;\n}\n\n.gr-tree__drag-handle {\n width: var(--gr-tree-drag-handle-size);\n height: var(--gr-tree-drag-handle-size);\n display: inline-flex;\n align-items: center;\n justify-content: center;\n margin-right: var(--gr-tree-drag-handle-mr);\n border-radius: var(--gr-tree-drag-handle-radius);\n color: var(--gr-tree-drag-handle-color);\n cursor: grab;\n /* Без этого вертикальный свайп по ручке уходит в прокрутку страницы,\n браузер отзывает указатель, и пальцем узел неперетаскиваем. */\n touch-action: none;\n visibility: hidden;\n pointer-events: none;\n opacity: 0;\n}\n\n/* Где наведения не бывает, ручка «по наведению» недостижима — то есть\n перетаскивания нет вовсе. Медиазапрос, а не `matchMedia`: ответ нужен и на\n сервере, а спрашивать среду в первом рендере нельзя. */\n@media (hover: none) {\n .gr-tree--drag-handle-auto .gr-tree__drag-handle {\n visibility: visible;\n pointer-events: auto;\n opacity: var(--gr-tree-drag-handle-opacity);\n }\n}\n\n.gr-tree__drag-handle--visible {\n visibility: visible;\n pointer-events: auto;\n opacity: var(--gr-tree-drag-handle-opacity);\n}\n\n.gr-tree__drag-handle:hover {\n background: var(--gr-tree-drag-handle-hover-bg);\n color: var(--gr-tree-drag-handle-hover-color);\n opacity: var(--gr-tree-drag-handle-hover-opacity);\n}\n\n.gr-tree__drag-handle:active {\n cursor: grabbing;\n}\n\n.gr-tree__drag-handle--disabled {\n cursor: default;\n opacity: var(--gr-tree-drag-handle-disabled-opacity);\n}\n\n.gr-tree__drag-icon {\n width: var(--gr-tree-icon-size);\n height: var(--gr-tree-icon-size);\n}\n\n.gr-tree__toggle {\n width: var(--gr-tree-toggle-size);\n height: var(--gr-tree-toggle-size);\n display: inline-flex;\n align-items: center;\n justify-content: center;\n margin-right: var(--gr-tree-toggle-mr);\n border-radius: var(--gr-tree-toggle-radius);\n color: var(--gr-tree-toggle-color);\n}\n\n.gr-tree__toggle:hover {\n background: var(--gr-tree-toggle-hover-bg);\n color: var(--gr-tree-toggle-hover-color);\n}\n\n.gr-tree__toggle-icon {\n width: var(--gr-tree-icon-size);\n height: var(--gr-tree-icon-size);\n transition: transform var(--gr-duration-fast) var(--gr-ease-out);\n}\n\n.gr-tree__toggle-icon--expanded {\n transform: rotate(90deg);\n}\n\n.gr-tree__toggle-spacer {\n width: var(--gr-tree-toggle-size);\n height: var(--gr-tree-toggle-size);\n margin-right: var(--gr-tree-toggle-mr);\n display: inline-block;\n}\n\n.gr-tree__content {\n min-width: 0;\n display: flex;\n align-items: center;\n gap: var(--gr-tree-content-gap);\n}\n\n.gr-tree__label {\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.gr-tree__row--drop-inner {\n outline: 2px solid color-mix(in srgb, var(--gr-primary) 40%, transparent);\n}\n\n.gr-tree__row--drop-prev::before,\n.gr-tree__row--drop-next::after {\n content: '';\n position: absolute;\n left: 8px;\n right: 8px;\n height: 2px;\n background: color-mix(in srgb, var(--gr-primary) 55%, transparent);\n}\n\n.gr-tree__row--drop-prev::before {\n top: 2px;\n}\n\n.gr-tree__row--drop-next::after {\n bottom: 2px;\n}\n</style>\n"],"mappings":"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"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as GrTree_default } from "./chunks/GrTree-
|
|
1
|
+
import { t as GrTree_default } from "./chunks/GrTree-Ci6CZfKR.js";
|
|
2
2
|
import { n as grTreeSafelist, t as grTreeConfig } from "../../chunks/config-CDat1wXf.js";
|
|
3
3
|
export { GrTree_default as GrTree, GrTree_default as default, grTreeConfig, grTreeSafelist };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
.gr-tree[data-v-
|
|
1
|
+
.gr-tree[data-v-0ff88d29]{--gr-tree-gap:2px;--gr-tree-children-pl:10px;--gr-tree-row-min-height:28px;--gr-tree-row-radius:8px;--gr-tree-row-px:8px;--gr-tree-row-py:8px;--gr-tree-row-pr:var(--gr-tree-row-px);--gr-tree-font-size:inherit;--gr-tree-row-color:var(--gr-fg);--gr-tree-row-hover-bg:color-mix(in srgb, var(--gr-primary) 10%, transparent);--gr-tree-row-current-bg:color-mix(in srgb, var(--gr-primary) 5%, transparent);--gr-tree-row-current-hover-bg:color-mix(in srgb, var(--gr-primary) 16%, transparent);--gr-tree-drag-handle-size:24px;--gr-tree-drag-handle-mr:0;--gr-tree-drag-handle-radius:6px;--gr-tree-drag-handle-color:inherit;--gr-tree-drag-handle-opacity:.55;--gr-tree-drag-handle-hover-bg:color-mix(in srgb, var(--gr-muted) 22%, transparent);--gr-tree-drag-handle-hover-color:var(--gr-tree-drag-handle-color);--gr-tree-drag-handle-hover-opacity:.9;--gr-tree-drag-handle-disabled-opacity:.25;--gr-tree-toggle-size:24px;--gr-tree-toggle-mr:0;--gr-tree-toggle-radius:6px;--gr-tree-toggle-color:inherit;--gr-tree-toggle-hover-bg:color-mix(in srgb, var(--gr-muted) 25%, transparent);--gr-tree-toggle-hover-color:var(--gr-tree-toggle-color);--gr-tree-icon-size:16px;--gr-tree-content-gap:8px;--gr-tree-branch-line-default-color:var(--gr-tree-row-current-bg);--gr-tree-branch-line-width:2px;--gr-tree-indent-step:calc(24px + var(--gr-tree-children-pl) + var(--gr-tree-branch-line-width));--gr-tree-branch-line-offset:24px;--gr-tree-checkbox-size:16px;--gr-tree-checkbox-radius:4px;--gr-tree-checkbox-brd:var(--gr-brd);--gr-tree-checkbox-bg:transparent;--gr-tree-checkbox-checked-bg:var(--gr-primary);--gr-tree-checkbox-checked-fg:var(--gr-primary-fg);--gr-tree-checkbox-mr:4px;gap:var(--gr-tree-gap);flex-direction:column;display:flex}[data-gr-virtual][data-v-0ff88d29]:before,[data-gr-virtual][data-v-0ff88d29]:after{content:"";flex:none;display:block}[data-gr-virtual][data-v-0ff88d29]:before{height:var(--gr-virtual-before,0px)}[data-gr-virtual][data-v-0ff88d29]:after{height:var(--gr-virtual-after,0px)}.gr-tree__row[data-v-0ff88d29]{min-height:var(--gr-tree-row-min-height);padding:var(--gr-tree-row-py) var(--gr-tree-row-pr) var(--gr-tree-row-py) calc(var(--gr-tree-row-px) + var(--gr-tree-row-indent,0px));font-size:var(--gr-tree-font-size);cursor:default;user-select:none;color:var(--gr-tree-row-color);isolation:isolate;outline:none;align-items:center;display:flex;position:relative}.gr-tree__row[data-v-0ff88d29]:before{content:"";inset:0 0 0 var(--gr-tree-row-indent,0px);border-radius:var(--gr-tree-row-radius);pointer-events:none;z-index:-1;position:absolute}.gr-tree__row[data-v-0ff88d29]:hover:before{background:var(--gr-tree-row-hover-bg)}.gr-tree__branch-guide[data-v-0ff88d29]{top:calc(var(--gr-tree-gap) / -2);bottom:calc(var(--gr-tree-gap) / -2);width:var(--gr-tree-branch-line-width);background:var(--gr-tree-branch-line-color,var(--gr-tree-branch-line-default-color));pointer-events:none;position:absolute}.gr-tree__checkbox[data-v-0ff88d29]{width:var(--gr-tree-checkbox-size);height:var(--gr-tree-checkbox-size);margin-right:var(--gr-tree-checkbox-mr);border:1px solid var(--gr-tree-checkbox-brd);border-radius:var(--gr-tree-checkbox-radius);background:var(--gr-tree-checkbox-bg);color:var(--gr-tree-checkbox-checked-fg);cursor:pointer;flex-shrink:0;justify-content:center;align-items:center;display:inline-flex}.gr-tree__checkbox--checked[data-v-0ff88d29],.gr-tree__checkbox--half[data-v-0ff88d29]{border-color:var(--gr-tree-checkbox-checked-bg);background:var(--gr-tree-checkbox-checked-bg)}.gr-tree__checkbox-mark[data-v-0ff88d29]{width:calc(var(--gr-tree-checkbox-size) - 4px);height:calc(var(--gr-tree-checkbox-size) - 4px)}[data-gr-tree-node][data-v-0ff88d29]{outline:none}[data-gr-tree-node]:focus-visible>.gr-tree__row[data-v-0ff88d29]:before{box-shadow:inset 0 0 0 2px var(--gr-primary)}.gr-tree__row--current[data-v-0ff88d29]:before{background:var(--gr-tree-row-current-bg)}.gr-tree__row--current[data-v-0ff88d29]:hover:before{background:var(--gr-tree-row-current-hover-bg)}.gr-tree__row--matched .gr-tree__label[data-v-0ff88d29]{font-weight:600}.gr-tree__drag-handle[data-v-0ff88d29]{width:var(--gr-tree-drag-handle-size);height:var(--gr-tree-drag-handle-size);margin-right:var(--gr-tree-drag-handle-mr);border-radius:var(--gr-tree-drag-handle-radius);color:var(--gr-tree-drag-handle-color);cursor:grab;touch-action:none;visibility:hidden;pointer-events:none;opacity:0;justify-content:center;align-items:center;display:inline-flex}@media (hover:none){.gr-tree--drag-handle-auto .gr-tree__drag-handle[data-v-0ff88d29]{visibility:visible;pointer-events:auto;opacity:var(--gr-tree-drag-handle-opacity)}}.gr-tree__drag-handle--visible[data-v-0ff88d29]{visibility:visible;pointer-events:auto;opacity:var(--gr-tree-drag-handle-opacity)}.gr-tree__drag-handle[data-v-0ff88d29]:hover{background:var(--gr-tree-drag-handle-hover-bg);color:var(--gr-tree-drag-handle-hover-color);opacity:var(--gr-tree-drag-handle-hover-opacity)}.gr-tree__drag-handle[data-v-0ff88d29]:active{cursor:grabbing}.gr-tree__drag-handle--disabled[data-v-0ff88d29]{cursor:default;opacity:var(--gr-tree-drag-handle-disabled-opacity)}.gr-tree__drag-icon[data-v-0ff88d29]{width:var(--gr-tree-icon-size);height:var(--gr-tree-icon-size)}.gr-tree__toggle[data-v-0ff88d29]{width:var(--gr-tree-toggle-size);height:var(--gr-tree-toggle-size);margin-right:var(--gr-tree-toggle-mr);border-radius:var(--gr-tree-toggle-radius);color:var(--gr-tree-toggle-color);justify-content:center;align-items:center;display:inline-flex}.gr-tree__toggle[data-v-0ff88d29]:hover{background:var(--gr-tree-toggle-hover-bg);color:var(--gr-tree-toggle-hover-color)}.gr-tree__toggle-icon[data-v-0ff88d29]{width:var(--gr-tree-icon-size);height:var(--gr-tree-icon-size);transition:transform var(--gr-duration-fast) var(--gr-ease-out)}.gr-tree__toggle-icon--expanded[data-v-0ff88d29]{transform:rotate(90deg)}.gr-tree__toggle-spacer[data-v-0ff88d29]{width:var(--gr-tree-toggle-size);height:var(--gr-tree-toggle-size);margin-right:var(--gr-tree-toggle-mr);display:inline-block}.gr-tree__content[data-v-0ff88d29]{align-items:center;gap:var(--gr-tree-content-gap);min-width:0;display:flex}.gr-tree__label[data-v-0ff88d29]{white-space:nowrap;text-overflow:ellipsis;overflow:hidden}.gr-tree__row--drop-inner[data-v-0ff88d29]{outline:2px solid color-mix(in srgb, var(--gr-primary) 40%, transparent)}.gr-tree__row--drop-prev[data-v-0ff88d29]:before,.gr-tree__row--drop-next[data-v-0ff88d29]:after{content:"";background:color-mix(in srgb, var(--gr-primary) 55%, transparent);height:2px;position:absolute;left:8px;right:8px}.gr-tree__row--drop-prev[data-v-0ff88d29]:before{top:2px}.gr-tree__row--drop-next[data-v-0ff88d29]:after{bottom:2px}
|
package/dist/components/GrTreeSelect/chunks/{GrTreeSelect-iJnMl2t9.js → GrTreeSelect-BHwgGJcT.js}
RENAMED
|
@@ -15,7 +15,7 @@ import { t as panelPopTransition } from "../../../chunks/overlayTransition-0Fj5t
|
|
|
15
15
|
import { t as check_default } from "../../../chunks/check-BZI24Qs4.js";
|
|
16
16
|
import { t as chevron_down_default } from "../../../chunks/chevron-down-CQS2OG_s.js";
|
|
17
17
|
import { t as GrInput_default } from "../../GrInput/chunks/GrInput-BLywRZUN.js";
|
|
18
|
-
import { t as GrTree_default } from "../../GrTree/chunks/GrTree-
|
|
18
|
+
import { t as GrTree_default } from "../../GrTree/chunks/GrTree-Ci6CZfKR.js";
|
|
19
19
|
import { a as grTreeSelectStateClass, i as grTreeSelectPanelClass, o as paddingX, r as grTreeSelectClass, s as trailingZoneWidth } from "../../../chunks/config-T3-DMXYm.js";
|
|
20
20
|
import { Fragment, Teleport, Transition, computed, createBlock, createCommentVNode, createElementBlock, createElementVNode, createTextVNode, createVNode, defineComponent, mergeProps, nextTick, normalizeClass, normalizeStyle, openBlock, ref, renderList, renderSlot, toDisplayString, unref, useId, useSlots, vShow, watch, withCtx, withDirectives, withModifiers } from "vue";
|
|
21
21
|
//#region src/components/GrTreeSelect/GrTreeSelect.vue?vue&type=script&setup=true&lang.ts
|