@rowsncolumns/ui 15.0.38
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/LICENSE.md +100 -0
- package/dist/cjs/arrow/index.d.ts +17 -0
- package/dist/cjs/arrow/index.d.ts.map +1 -0
- package/dist/cjs/arrow/index.js +46 -0
- package/dist/cjs/button/index.d.ts +14 -0
- package/dist/cjs/button/index.d.ts.map +1 -0
- package/dist/cjs/button/index.js +46 -0
- package/dist/cjs/calendar/index.d.ts +5 -0
- package/dist/cjs/calendar/index.d.ts.map +1 -0
- package/dist/cjs/calendar/index.js +13 -0
- package/dist/cjs/card/index.d.ts +10 -0
- package/dist/cjs/card/index.d.ts.map +1 -0
- package/dist/cjs/card/index.js +32 -0
- package/dist/cjs/cell-tooltip/index.d.ts +17 -0
- package/dist/cjs/cell-tooltip/index.d.ts.map +1 -0
- package/dist/cjs/cell-tooltip/index.js +38 -0
- package/dist/cjs/circular-loader/index.d.ts +9 -0
- package/dist/cjs/circular-loader/index.d.ts.map +1 -0
- package/dist/cjs/circular-loader/index.js +11 -0
- package/dist/cjs/color-picker/index.d.ts +12 -0
- package/dist/cjs/color-picker/index.d.ts.map +1 -0
- package/dist/cjs/color-picker/index.js +101 -0
- package/dist/cjs/color-picker/style.d.ts +5 -0
- package/dist/cjs/color-picker/style.d.ts.map +1 -0
- package/dist/cjs/color-picker/style.js +11 -0
- package/dist/cjs/command/index.d.ts +74 -0
- package/dist/cjs/command/index.d.ts.map +1 -0
- package/dist/cjs/command/index.js +37 -0
- package/dist/cjs/conditional-wrapper/index.d.ts +9 -0
- package/dist/cjs/conditional-wrapper/index.d.ts.map +1 -0
- package/dist/cjs/conditional-wrapper/index.js +4 -0
- package/dist/cjs/dialog/index.d.ts +17 -0
- package/dist/cjs/dialog/index.d.ts.map +1 -0
- package/dist/cjs/dialog/index.js +50 -0
- package/dist/cjs/dropdown/index.d.ts +34 -0
- package/dist/cjs/dropdown/index.d.ts.map +1 -0
- package/dist/cjs/dropdown/index.js +73 -0
- package/dist/cjs/editor/constants.d.ts +7 -0
- package/dist/cjs/editor/constants.d.ts.map +1 -0
- package/dist/cjs/editor/constants.js +50 -0
- package/dist/cjs/editor/editor-error-boundary.d.ts +3 -0
- package/dist/cjs/editor/editor-error-boundary.d.ts.map +1 -0
- package/dist/cjs/editor/editor-error-boundary.js +9 -0
- package/dist/cjs/editor/style.d.ts +12 -0
- package/dist/cjs/editor/style.d.ts.map +1 -0
- package/dist/cjs/editor/style.js +24 -0
- package/dist/cjs/editor/suggestions-dropdown.d.ts +25 -0
- package/dist/cjs/editor/suggestions-dropdown.d.ts.map +1 -0
- package/dist/cjs/editor/suggestions-dropdown.js +120 -0
- package/dist/cjs/editor-pm/constants.d.ts +2 -0
- package/dist/cjs/editor-pm/constants.d.ts.map +1 -0
- package/dist/cjs/editor-pm/constants.js +2 -0
- package/dist/cjs/editor-pm/decoration-plugin.d.ts +15 -0
- package/dist/cjs/editor-pm/decoration-plugin.d.ts.map +1 -0
- package/dist/cjs/editor-pm/decoration-plugin.js +38 -0
- package/dist/cjs/editor-pm/helpers.d.ts +197 -0
- package/dist/cjs/editor-pm/helpers.d.ts.map +1 -0
- package/dist/cjs/editor-pm/helpers.js +1170 -0
- package/dist/cjs/editor-pm/index.d.ts +10 -0
- package/dist/cjs/editor-pm/index.d.ts.map +1 -0
- package/dist/cjs/editor-pm/index.js +9 -0
- package/dist/cjs/editor-pm/mention-nodeview.d.ts +31 -0
- package/dist/cjs/editor-pm/mention-nodeview.d.ts.map +1 -0
- package/dist/cjs/editor-pm/mention-nodeview.js +105 -0
- package/dist/cjs/editor-pm/mentions-dropdown.d.ts +13 -0
- package/dist/cjs/editor-pm/mentions-dropdown.d.ts.map +1 -0
- package/dist/cjs/editor-pm/mentions-dropdown.js +19 -0
- package/dist/cjs/editor-pm/mentions-plugin.d.ts +18 -0
- package/dist/cjs/editor-pm/mentions-plugin.d.ts.map +1 -0
- package/dist/cjs/editor-pm/mentions-plugin.js +72 -0
- package/dist/cjs/editor-pm/placeholder-plugin.d.ts +4 -0
- package/dist/cjs/editor-pm/placeholder-plugin.d.ts.map +1 -0
- package/dist/cjs/editor-pm/placeholder-plugin.js +20 -0
- package/dist/cjs/editor-pm/prosemirror-editor.d.ts +493 -0
- package/dist/cjs/editor-pm/prosemirror-editor.d.ts.map +1 -0
- package/dist/cjs/editor-pm/prosemirror-editor.js +1145 -0
- package/dist/cjs/editor-pm/schema.d.ts +3 -0
- package/dist/cjs/editor-pm/schema.d.ts.map +1 -0
- package/dist/cjs/editor-pm/schema.js +183 -0
- package/dist/cjs/editor-pm/types.d.ts +8 -0
- package/dist/cjs/editor-pm/types.d.ts.map +1 -0
- package/dist/cjs/editor-pm/types.js +1 -0
- package/dist/cjs/editor-pm/unfocused-selection-plugin.d.ts +25 -0
- package/dist/cjs/editor-pm/unfocused-selection-plugin.d.ts.map +1 -0
- package/dist/cjs/editor-pm/unfocused-selection-plugin.js +61 -0
- package/dist/cjs/editor-pm/use-dropdown-change-pm.d.ts +24 -0
- package/dist/cjs/editor-pm/use-dropdown-change-pm.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-dropdown-change-pm.js +140 -0
- package/dist/cjs/editor-pm/use-editor-change-pm.d.ts +29 -0
- package/dist/cjs/editor-pm/use-editor-change-pm.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-editor-change-pm.js +154 -0
- package/dist/cjs/editor-pm/use-editor-decorator-pm.d.ts +17 -0
- package/dist/cjs/editor-pm/use-editor-decorator-pm.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-editor-decorator-pm.js +59 -0
- package/dist/cjs/editor-pm/use-editor-keydown-pm.d.ts +21 -0
- package/dist/cjs/editor-pm/use-editor-keydown-pm.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-editor-keydown-pm.js +81 -0
- package/dist/cjs/editor-pm/use-mention-keydown.d.ts +11 -0
- package/dist/cjs/editor-pm/use-mention-keydown.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-mention-keydown.js +59 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.d.ts +19 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.js +79 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.test.d.ts +2 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.test.d.ts.map +1 -0
- package/dist/cjs/editor-pm/use-parameter-suggestions.test.js +122 -0
- package/dist/cjs/eye-dropper/index.d.ts +10 -0
- package/dist/cjs/eye-dropper/index.d.ts.map +1 -0
- package/dist/cjs/eye-dropper/index.js +24 -0
- package/dist/cjs/function-info/helpers.d.ts +10 -0
- package/dist/cjs/function-info/helpers.d.ts.map +1 -0
- package/dist/cjs/function-info/helpers.js +20 -0
- package/dist/cjs/function-info/index.d.ts +11 -0
- package/dist/cjs/function-info/index.d.ts.map +1 -0
- package/dist/cjs/function-info/index.js +71 -0
- package/dist/cjs/function-info/style.d.ts +7 -0
- package/dist/cjs/function-info/style.d.ts.map +1 -0
- package/dist/cjs/function-info/style.js +13 -0
- package/dist/cjs/hex-color-picker/index.d.ts +8 -0
- package/dist/cjs/hex-color-picker/index.d.ts.map +1 -0
- package/dist/cjs/hex-color-picker/index.js +47 -0
- package/dist/cjs/hooks/use-cycle-reference.d.ts +16 -0
- package/dist/cjs/hooks/use-cycle-reference.d.ts.map +1 -0
- package/dist/cjs/hooks/use-cycle-reference.js +72 -0
- package/dist/cjs/hooks/use-dropdown-categories.d.ts +9 -0
- package/dist/cjs/hooks/use-dropdown-categories.d.ts.map +1 -0
- package/dist/cjs/hooks/use-dropdown-categories.js +45 -0
- package/dist/cjs/hooks/use-dropdown.d.ts +38 -0
- package/dist/cjs/hooks/use-dropdown.d.ts.map +1 -0
- package/dist/cjs/hooks/use-dropdown.js +236 -0
- package/dist/cjs/hooks/use-isomorphic-layout-effect.ts.d.ts +6 -0
- package/dist/cjs/hooks/use-isomorphic-layout-effect.ts.d.ts.map +1 -0
- package/dist/cjs/hooks/use-isomorphic-layout-effect.ts.js +8 -0
- package/dist/cjs/hooks/use-modal.d.ts +28 -0
- package/dist/cjs/hooks/use-modal.d.ts.map +1 -0
- package/dist/cjs/hooks/use-modal.js +101 -0
- package/dist/cjs/hooks/use-visibility.d.ts +2 -0
- package/dist/cjs/hooks/use-visibility.d.ts.map +1 -0
- package/dist/cjs/hooks/use-visibility.js +12 -0
- package/dist/cjs/icon-button/index.d.ts +15 -0
- package/dist/cjs/icon-button/index.d.ts.map +1 -0
- package/dist/cjs/icon-button/index.js +34 -0
- package/dist/cjs/index.d.ts +34 -0
- package/dist/cjs/index.d.ts.map +1 -0
- package/dist/cjs/index.js +33 -0
- package/dist/cjs/input/index.d.ts +9 -0
- package/dist/cjs/input/index.d.ts.map +1 -0
- package/dist/cjs/input/index.js +9 -0
- package/dist/cjs/popover/index.d.ts +13 -0
- package/dist/cjs/popover/index.d.ts.map +1 -0
- package/dist/cjs/popover/index.js +29 -0
- package/dist/cjs/progress/index.d.ts +10 -0
- package/dist/cjs/progress/index.d.ts.map +1 -0
- package/dist/cjs/progress/index.js +15 -0
- package/dist/cjs/select/index.d.ts +14 -0
- package/dist/cjs/select/index.d.ts.map +1 -0
- package/dist/cjs/select/index.js +46 -0
- package/dist/cjs/separator/index.d.ts +5 -0
- package/dist/cjs/separator/index.d.ts.map +1 -0
- package/dist/cjs/separator/index.js +10 -0
- package/dist/cjs/skeleton/index.d.ts +7 -0
- package/dist/cjs/skeleton/index.d.ts.map +1 -0
- package/dist/cjs/skeleton/index.js +11 -0
- package/dist/cjs/stack/index.d.ts +11 -0
- package/dist/cjs/stack/index.d.ts.map +1 -0
- package/dist/cjs/stack/index.js +22 -0
- package/dist/cjs/tabs/index.d.ts +8 -0
- package/dist/cjs/tabs/index.d.ts.map +1 -0
- package/dist/cjs/tabs/index.js +21 -0
- package/dist/cjs/tooltip/index.d.ts +12 -0
- package/dist/cjs/tooltip/index.d.ts.map +1 -0
- package/dist/cjs/tooltip/index.js +20 -0
- package/dist/cjs/tsconfig.cjs.tsbuildinfo +1 -0
- package/dist/cjs/utils.d.ts +3 -0
- package/dist/cjs/utils.d.ts.map +1 -0
- package/dist/cjs/utils.js +9 -0
- package/dist/cjs/vitest.config.d.ts +3 -0
- package/dist/cjs/vitest.config.d.ts.map +1 -0
- package/dist/cjs/vitest.config.js +21 -0
- package/dist/esm/arrow/index.d.ts +17 -0
- package/dist/esm/arrow/index.d.ts.map +1 -0
- package/dist/esm/arrow/index.js +45 -0
- package/dist/esm/button/index.d.ts +14 -0
- package/dist/esm/button/index.d.ts.map +1 -0
- package/dist/esm/button/index.js +44 -0
- package/dist/esm/calendar/index.d.ts +5 -0
- package/dist/esm/calendar/index.d.ts.map +1 -0
- package/dist/esm/calendar/index.js +34 -0
- package/dist/esm/card/index.d.ts +10 -0
- package/dist/esm/card/index.d.ts.map +1 -0
- package/dist/esm/card/index.js +24 -0
- package/dist/esm/cell-tooltip/index.d.ts +17 -0
- package/dist/esm/cell-tooltip/index.d.ts.map +1 -0
- package/dist/esm/cell-tooltip/index.js +31 -0
- package/dist/esm/circular-loader/index.d.ts +9 -0
- package/dist/esm/circular-loader/index.d.ts.map +1 -0
- package/dist/esm/circular-loader/index.js +7 -0
- package/dist/esm/color-picker/index.d.ts +12 -0
- package/dist/esm/color-picker/index.d.ts.map +1 -0
- package/dist/esm/color-picker/index.js +99 -0
- package/dist/esm/color-picker/style.d.ts +5 -0
- package/dist/esm/color-picker/style.d.ts.map +1 -0
- package/dist/esm/color-picker/style.js +7 -0
- package/dist/esm/command/index.d.ts +74 -0
- package/dist/esm/command/index.d.ts.map +1 -0
- package/dist/esm/command/index.js +18 -0
- package/dist/esm/conditional-wrapper/index.d.ts +9 -0
- package/dist/esm/conditional-wrapper/index.d.ts.map +1 -0
- package/dist/esm/conditional-wrapper/index.js +1 -0
- package/dist/esm/dialog/index.d.ts +17 -0
- package/dist/esm/dialog/index.d.ts.map +1 -0
- package/dist/esm/dialog/index.js +30 -0
- package/dist/esm/dropdown/index.d.ts +34 -0
- package/dist/esm/dropdown/index.d.ts.map +1 -0
- package/dist/esm/dropdown/index.js +42 -0
- package/dist/esm/editor/constants.d.ts +7 -0
- package/dist/esm/editor/constants.d.ts.map +1 -0
- package/dist/esm/editor/constants.js +51 -0
- package/dist/esm/editor/editor-error-boundary.d.ts +3 -0
- package/dist/esm/editor/editor-error-boundary.d.ts.map +1 -0
- package/dist/esm/editor/editor-error-boundary.js +9 -0
- package/dist/esm/editor/style.d.ts +12 -0
- package/dist/esm/editor/style.d.ts.map +1 -0
- package/dist/esm/editor/style.js +17 -0
- package/dist/esm/editor/suggestions-dropdown.d.ts +25 -0
- package/dist/esm/editor/suggestions-dropdown.d.ts.map +1 -0
- package/dist/esm/editor/suggestions-dropdown.js +115 -0
- package/dist/esm/editor-pm/constants.d.ts +2 -0
- package/dist/esm/editor-pm/constants.d.ts.map +1 -0
- package/dist/esm/editor-pm/constants.js +2 -0
- package/dist/esm/editor-pm/decoration-plugin.d.ts +15 -0
- package/dist/esm/editor-pm/decoration-plugin.d.ts.map +1 -0
- package/dist/esm/editor-pm/decoration-plugin.js +38 -0
- package/dist/esm/editor-pm/helpers.d.ts +197 -0
- package/dist/esm/editor-pm/helpers.d.ts.map +1 -0
- package/dist/esm/editor-pm/helpers.js +1113 -0
- package/dist/esm/editor-pm/index.d.ts +10 -0
- package/dist/esm/editor-pm/index.d.ts.map +1 -0
- package/dist/esm/editor-pm/index.js +9 -0
- package/dist/esm/editor-pm/mention-nodeview.d.ts +31 -0
- package/dist/esm/editor-pm/mention-nodeview.d.ts.map +1 -0
- package/dist/esm/editor-pm/mention-nodeview.js +88 -0
- package/dist/esm/editor-pm/mentions-dropdown.d.ts +13 -0
- package/dist/esm/editor-pm/mentions-dropdown.d.ts.map +1 -0
- package/dist/esm/editor-pm/mentions-dropdown.js +17 -0
- package/dist/esm/editor-pm/mentions-plugin.d.ts +18 -0
- package/dist/esm/editor-pm/mentions-plugin.d.ts.map +1 -0
- package/dist/esm/editor-pm/mentions-plugin.js +92 -0
- package/dist/esm/editor-pm/placeholder-plugin.d.ts +4 -0
- package/dist/esm/editor-pm/placeholder-plugin.d.ts.map +1 -0
- package/dist/esm/editor-pm/placeholder-plugin.js +20 -0
- package/dist/esm/editor-pm/prosemirror-editor.d.ts +493 -0
- package/dist/esm/editor-pm/prosemirror-editor.d.ts.map +1 -0
- package/dist/esm/editor-pm/prosemirror-editor.js +1135 -0
- package/dist/esm/editor-pm/schema.d.ts +3 -0
- package/dist/esm/editor-pm/schema.d.ts.map +1 -0
- package/dist/esm/editor-pm/schema.js +179 -0
- package/dist/esm/editor-pm/types.d.ts +8 -0
- package/dist/esm/editor-pm/types.d.ts.map +1 -0
- package/dist/esm/editor-pm/types.js +1 -0
- package/dist/esm/editor-pm/unfocused-selection-plugin.d.ts +25 -0
- package/dist/esm/editor-pm/unfocused-selection-plugin.d.ts.map +1 -0
- package/dist/esm/editor-pm/unfocused-selection-plugin.js +61 -0
- package/dist/esm/editor-pm/use-dropdown-change-pm.d.ts +24 -0
- package/dist/esm/editor-pm/use-dropdown-change-pm.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-dropdown-change-pm.js +137 -0
- package/dist/esm/editor-pm/use-editor-change-pm.d.ts +29 -0
- package/dist/esm/editor-pm/use-editor-change-pm.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-editor-change-pm.js +152 -0
- package/dist/esm/editor-pm/use-editor-decorator-pm.d.ts +17 -0
- package/dist/esm/editor-pm/use-editor-decorator-pm.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-editor-decorator-pm.js +57 -0
- package/dist/esm/editor-pm/use-editor-keydown-pm.d.ts +21 -0
- package/dist/esm/editor-pm/use-editor-keydown-pm.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-editor-keydown-pm.js +79 -0
- package/dist/esm/editor-pm/use-mention-keydown.d.ts +11 -0
- package/dist/esm/editor-pm/use-mention-keydown.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-mention-keydown.js +57 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.d.ts +19 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.js +66 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.test.d.ts +2 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.test.d.ts.map +1 -0
- package/dist/esm/editor-pm/use-parameter-suggestions.test.js +66 -0
- package/dist/esm/eye-dropper/index.d.ts +10 -0
- package/dist/esm/eye-dropper/index.d.ts.map +1 -0
- package/dist/esm/eye-dropper/index.js +23 -0
- package/dist/esm/function-info/helpers.d.ts +10 -0
- package/dist/esm/function-info/helpers.d.ts.map +1 -0
- package/dist/esm/function-info/helpers.js +20 -0
- package/dist/esm/function-info/index.d.ts +11 -0
- package/dist/esm/function-info/index.d.ts.map +1 -0
- package/dist/esm/function-info/index.js +68 -0
- package/dist/esm/function-info/style.d.ts +7 -0
- package/dist/esm/function-info/style.d.ts.map +1 -0
- package/dist/esm/function-info/style.js +10 -0
- package/dist/esm/hex-color-picker/index.d.ts +8 -0
- package/dist/esm/hex-color-picker/index.d.ts.map +1 -0
- package/dist/esm/hex-color-picker/index.js +44 -0
- package/dist/esm/hooks/use-cycle-reference.d.ts +16 -0
- package/dist/esm/hooks/use-cycle-reference.d.ts.map +1 -0
- package/dist/esm/hooks/use-cycle-reference.js +70 -0
- package/dist/esm/hooks/use-dropdown-categories.d.ts +9 -0
- package/dist/esm/hooks/use-dropdown-categories.d.ts.map +1 -0
- package/dist/esm/hooks/use-dropdown-categories.js +38 -0
- package/dist/esm/hooks/use-dropdown.d.ts +38 -0
- package/dist/esm/hooks/use-dropdown.d.ts.map +1 -0
- package/dist/esm/hooks/use-dropdown.js +236 -0
- package/dist/esm/hooks/use-isomorphic-layout-effect.ts.d.ts +6 -0
- package/dist/esm/hooks/use-isomorphic-layout-effect.ts.d.ts.map +1 -0
- package/dist/esm/hooks/use-isomorphic-layout-effect.ts.js +8 -0
- package/dist/esm/hooks/use-modal.d.ts +28 -0
- package/dist/esm/hooks/use-modal.d.ts.map +1 -0
- package/dist/esm/hooks/use-modal.js +93 -0
- package/dist/esm/hooks/use-visibility.d.ts +2 -0
- package/dist/esm/hooks/use-visibility.d.ts.map +1 -0
- package/dist/esm/hooks/use-visibility.js +12 -0
- package/dist/esm/icon-button/index.d.ts +15 -0
- package/dist/esm/icon-button/index.d.ts.map +1 -0
- package/dist/esm/icon-button/index.js +32 -0
- package/dist/esm/index.d.ts +34 -0
- package/dist/esm/index.d.ts.map +1 -0
- package/dist/esm/index.js +33 -0
- package/dist/esm/input/index.d.ts +9 -0
- package/dist/esm/input/index.d.ts.map +1 -0
- package/dist/esm/input/index.js +7 -0
- package/dist/esm/popover/index.d.ts +13 -0
- package/dist/esm/popover/index.d.ts.map +1 -0
- package/dist/esm/popover/index.js +22 -0
- package/dist/esm/progress/index.d.ts +10 -0
- package/dist/esm/progress/index.d.ts.map +1 -0
- package/dist/esm/progress/index.js +12 -0
- package/dist/esm/select/index.d.ts +14 -0
- package/dist/esm/select/index.d.ts.map +1 -0
- package/dist/esm/select/index.js +30 -0
- package/dist/esm/separator/index.d.ts +5 -0
- package/dist/esm/separator/index.d.ts.map +1 -0
- package/dist/esm/separator/index.js +6 -0
- package/dist/esm/skeleton/index.d.ts +7 -0
- package/dist/esm/skeleton/index.d.ts.map +1 -0
- package/dist/esm/skeleton/index.js +9 -0
- package/dist/esm/stack/index.d.ts +11 -0
- package/dist/esm/stack/index.d.ts.map +1 -0
- package/dist/esm/stack/index.js +20 -0
- package/dist/esm/tabs/index.d.ts +8 -0
- package/dist/esm/tabs/index.d.ts.map +1 -0
- package/dist/esm/tabs/index.js +11 -0
- package/dist/esm/tooltip/index.d.ts +12 -0
- package/dist/esm/tooltip/index.d.ts.map +1 -0
- package/dist/esm/tooltip/index.js +13 -0
- package/dist/esm/tsconfig.esm.tsbuildinfo +1 -0
- package/dist/esm/utils.d.ts +3 -0
- package/dist/esm/utils.d.ts.map +1 -0
- package/dist/esm/utils.js +5 -0
- package/dist/esm/vitest.config.d.ts +3 -0
- package/dist/esm/vitest.config.d.ts.map +1 -0
- package/dist/esm/vitest.config.js +21 -0
- package/package.json +78 -0
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import React, { useState } from "react";
|
|
2
|
+
import { IconButton } from "../icon-button";
|
|
3
|
+
import { PlusCircledIcon } from "@rowsncolumns/icons";
|
|
4
|
+
import { Popover, PopoverContent, PopoverTrigger } from "../popover";
|
|
5
|
+
import { Button } from "../button";
|
|
6
|
+
import isNil from "lodash/isNil";
|
|
7
|
+
import { HexColorPicker as ReactColorPicker } from "react-colorful";
|
|
8
|
+
import { Input } from "../input";
|
|
9
|
+
export const HexColorPicker = ({ value, onChange }) => {
|
|
10
|
+
const [isOpen, onOpenChange] = useState(false);
|
|
11
|
+
const close = () => onOpenChange(false);
|
|
12
|
+
return (React.createElement(Popover, { open: isOpen, onOpenChange: onOpenChange, modal: true },
|
|
13
|
+
React.createElement(PopoverTrigger, { asChild: true },
|
|
14
|
+
React.createElement(IconButton, { tooltip: "Add a custom color" },
|
|
15
|
+
React.createElement(PlusCircledIcon, null))),
|
|
16
|
+
React.createElement(PopoverContent, null,
|
|
17
|
+
React.createElement(ColorPickerContent, { initialValue: value, onCancel: () => {
|
|
18
|
+
close();
|
|
19
|
+
}, onSubmit: (value) => {
|
|
20
|
+
onChange?.(value);
|
|
21
|
+
close();
|
|
22
|
+
} }))));
|
|
23
|
+
};
|
|
24
|
+
const ColorPickerContent = ({ initialValue, onCancel, onSubmit, }) => {
|
|
25
|
+
const defaultColor = isNil(initialValue) || initialValue === "transparent"
|
|
26
|
+
? "#000000"
|
|
27
|
+
: initialValue;
|
|
28
|
+
const [value, onChange] = useState(defaultColor);
|
|
29
|
+
return (React.createElement("div", { className: "flex flex-col gap-2" },
|
|
30
|
+
React.createElement(ReactColorPicker, { className: "rnc-colorpicker", color: value, onChange: (color) => onChange(color) }),
|
|
31
|
+
React.createElement(Input, { value: value, onChange: (e) => {
|
|
32
|
+
onChange?.(e.target.value);
|
|
33
|
+
}, onFocus: (e) => {
|
|
34
|
+
// Select on focus
|
|
35
|
+
e.target.select();
|
|
36
|
+
}, className: "text-xs" }),
|
|
37
|
+
React.createElement("div", { className: "flex gap-2 justify-end" },
|
|
38
|
+
React.createElement(Button, { size: "xs", onClick: () => {
|
|
39
|
+
onCancel?.();
|
|
40
|
+
} }, "Cancel"),
|
|
41
|
+
React.createElement(Button, { size: "xs", variant: "primary", onClick: () => {
|
|
42
|
+
onSubmit?.(value);
|
|
43
|
+
} }, "OK"))));
|
|
44
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { ParsedToken } from "@rowsncolumns/calculator";
|
|
2
|
+
type UseCycleFormulaReferenceProps = {
|
|
3
|
+
onUpdate: (address: string, selectionMode?: string) => void;
|
|
4
|
+
};
|
|
5
|
+
/**
|
|
6
|
+
* Detect the current reference type from a cell address
|
|
7
|
+
* e.g. $A$1 -> absolute, A$1 -> absolute-row, $A1 -> absolute-column, A1 -> relative
|
|
8
|
+
*/
|
|
9
|
+
export declare const detectReferenceType: (address: string) => string;
|
|
10
|
+
/**
|
|
11
|
+
* Get the next reference type in the cycle based on the current address
|
|
12
|
+
*/
|
|
13
|
+
export declare const getNextReference: (currentAddress: string) => string;
|
|
14
|
+
export declare const useCycleFormulaReference: ({ onUpdate, }: UseCycleFormulaReferenceProps) => (token: ParsedToken | undefined) => void;
|
|
15
|
+
export {};
|
|
16
|
+
//# sourceMappingURL=use-cycle-reference.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-cycle-reference.d.ts","sourceRoot":"","sources":["../../../hooks/use-cycle-reference.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAS5D,KAAK,6BAA6B,GAAG;IACnC,QAAQ,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;CAC7D,CAAC;AASF;;;GAGG;AACH,eAAO,MAAM,mBAAmB,GAAI,SAAS,MAAM,KAAG,MAUrD,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,gBAAgB,GAAI,gBAAgB,MAAM,KAAG,MAKzD,CAAC;AAEF,eAAO,MAAM,wBAAwB,GAAI,eAEtC,6BAA6B,aAEpB,WAAW,GAAG,SAAS,SA8ClC,CAAC"}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { tokenVocabulary } from "@rowsncolumns/fast-formula-parser";
|
|
2
|
+
import { addressToCell, cellToAddress, sanitizeSheetName, } from "@rowsncolumns/utils";
|
|
3
|
+
import { useCallback } from "react";
|
|
4
|
+
const referenceCycleOrder = [
|
|
5
|
+
"absolute",
|
|
6
|
+
"absolute-row",
|
|
7
|
+
"absolute-column",
|
|
8
|
+
"relative",
|
|
9
|
+
];
|
|
10
|
+
/**
|
|
11
|
+
* Detect the current reference type from a cell address
|
|
12
|
+
* e.g. $A$1 -> absolute, A$1 -> absolute-row, $A1 -> absolute-column, A1 -> relative
|
|
13
|
+
*/
|
|
14
|
+
export const detectReferenceType = (address) => {
|
|
15
|
+
// Check if column is absolute ($ before the letter)
|
|
16
|
+
const hasAbsoluteColumn = address.startsWith("$");
|
|
17
|
+
// Check if row is absolute ($ before the number)
|
|
18
|
+
const hasAbsoluteRow = /\$\d/.test(address);
|
|
19
|
+
if (hasAbsoluteColumn && hasAbsoluteRow)
|
|
20
|
+
return "absolute";
|
|
21
|
+
if (hasAbsoluteRow)
|
|
22
|
+
return "absolute-row";
|
|
23
|
+
if (hasAbsoluteColumn)
|
|
24
|
+
return "absolute-column";
|
|
25
|
+
return "relative";
|
|
26
|
+
};
|
|
27
|
+
/**
|
|
28
|
+
* Get the next reference type in the cycle based on the current address
|
|
29
|
+
*/
|
|
30
|
+
export const getNextReference = (currentAddress) => {
|
|
31
|
+
const currentType = detectReferenceType(currentAddress);
|
|
32
|
+
const currentIndex = referenceCycleOrder.indexOf(currentType);
|
|
33
|
+
const nextIndex = (currentIndex + 1) % referenceCycleOrder.length;
|
|
34
|
+
return referenceCycleOrder[nextIndex];
|
|
35
|
+
};
|
|
36
|
+
export const useCycleFormulaReference = ({ onUpdate, }) => {
|
|
37
|
+
return useCallback((token) => {
|
|
38
|
+
// Cell token
|
|
39
|
+
if (token?.tokenType.name === tokenVocabulary.Cell.name && token.image) {
|
|
40
|
+
const sheetName = token.sheetName;
|
|
41
|
+
const sheetNameStr = sheetName
|
|
42
|
+
? sanitizeSheetName(sheetName) + "!"
|
|
43
|
+
: "";
|
|
44
|
+
const [from, to] = token.image.split(":");
|
|
45
|
+
// Detect current reference type and get the next one in cycle
|
|
46
|
+
const reference = getNextReference(from);
|
|
47
|
+
const fromCell = addressToCell(from);
|
|
48
|
+
const toCell = to ? addressToCell(to) : undefined;
|
|
49
|
+
let fromCellAddress = null;
|
|
50
|
+
let toCellAddress = "";
|
|
51
|
+
fromCellAddress = cellToAddress(fromCell, reference === "relative"
|
|
52
|
+
? false
|
|
53
|
+
: reference === "absolute" || reference === "absolute-column", reference === "relative"
|
|
54
|
+
? false
|
|
55
|
+
: reference === "absolute" || reference === "absolute-row");
|
|
56
|
+
if (toCell) {
|
|
57
|
+
toCellAddress = cellToAddress(toCell, reference === "relative"
|
|
58
|
+
? false
|
|
59
|
+
: reference === "absolute" || reference === "absolute-column", reference === "relative"
|
|
60
|
+
? false
|
|
61
|
+
: reference === "absolute" || reference === "absolute-row");
|
|
62
|
+
}
|
|
63
|
+
const address = `${sheetNameStr}${fromCellAddress}${toCellAddress ? ":" + toCellAddress : ""}`;
|
|
64
|
+
onUpdate(address, "modify");
|
|
65
|
+
}
|
|
66
|
+
else {
|
|
67
|
+
console.log("Token not processed - not a Cell token or missing image");
|
|
68
|
+
}
|
|
69
|
+
}, [onUpdate]);
|
|
70
|
+
};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { CalculatorFunction } from "@rowsncolumns/common-types";
|
|
2
|
+
import { OptionItem } from "../editor-pm/types";
|
|
3
|
+
type InputProps = {
|
|
4
|
+
items: (OptionItem | CalculatorFunction)[];
|
|
5
|
+
formulaMode?: boolean;
|
|
6
|
+
};
|
|
7
|
+
export declare const useDropdownCategories: ({ items, formulaMode }: InputProps) => [OptionItem[], OptionItem[], CalculatorFunction[], OptionItem[], OptionItem[], OptionItem[]];
|
|
8
|
+
export {};
|
|
9
|
+
//# sourceMappingURL=use-dropdown-categories.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-dropdown-categories.d.ts","sourceRoot":"","sources":["../../../hooks/use-dropdown-categories.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,4BAA4B,CAAC;AAErE,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAEhD,KAAK,UAAU,GAAG;IAChB,KAAK,EAAE,CAAC,UAAU,GAAG,kBAAkB,CAAC,EAAE,CAAC;IAC3C,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB,CAAC;AAEF,eAAO,MAAM,qBAAqB,GAAI,wBAAwB,UAAU,iGAgEvE,CAAC"}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { useMemo } from "react";
|
|
2
|
+
export const useDropdownCategories = ({ items, formulaMode }) => {
|
|
3
|
+
return useMemo(() => {
|
|
4
|
+
// Structured references: table, column, specialitem
|
|
5
|
+
const structuredReferences = items.filter((item) => item.category === "table" ||
|
|
6
|
+
item.category === "column" ||
|
|
7
|
+
item.category === "specialitem" ||
|
|
8
|
+
item.category === "thisrow");
|
|
9
|
+
// Named ranges
|
|
10
|
+
const namedRanges = items.filter((item) => item.category === "namedrange");
|
|
11
|
+
// Property references
|
|
12
|
+
const propertyReferences = items.filter((item) => item.category === "property");
|
|
13
|
+
// Parameter references
|
|
14
|
+
const parameterSuggestions = items.filter((item) => item.category === "parameter");
|
|
15
|
+
// Function suggestions (only CalculatorFunctions)
|
|
16
|
+
const functionSuggestions = formulaMode
|
|
17
|
+
? items.filter((item) => item.title !== undefined &&
|
|
18
|
+
!("category" in item))
|
|
19
|
+
: [];
|
|
20
|
+
// Dropdown options: everything else that is not structured, named, property, or function
|
|
21
|
+
const dropdownOptions = formulaMode
|
|
22
|
+
? []
|
|
23
|
+
: items.filter((item) => !structuredReferences.includes(item) &&
|
|
24
|
+
!namedRanges.includes(item) &&
|
|
25
|
+
!propertyReferences.includes(item) &&
|
|
26
|
+
!parameterSuggestions.includes(item) &&
|
|
27
|
+
item.title !== undefined &&
|
|
28
|
+
!("category" in item));
|
|
29
|
+
return [
|
|
30
|
+
structuredReferences,
|
|
31
|
+
dropdownOptions,
|
|
32
|
+
functionSuggestions,
|
|
33
|
+
namedRanges,
|
|
34
|
+
propertyReferences,
|
|
35
|
+
parameterSuggestions,
|
|
36
|
+
];
|
|
37
|
+
}, [items, formulaMode]);
|
|
38
|
+
};
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import type React from "react";
|
|
2
|
+
import { Maybe } from "@rowsncolumns/common-types";
|
|
3
|
+
import { OptionItem } from "../editor-pm/types.js";
|
|
4
|
+
type UseDropdownProps<T> = {
|
|
5
|
+
items: T[] | undefined;
|
|
6
|
+
initialQuery?: string;
|
|
7
|
+
initialOpen: boolean;
|
|
8
|
+
initialHighlightedIndex: number;
|
|
9
|
+
limit?: number;
|
|
10
|
+
showAllIfEmpty?: boolean;
|
|
11
|
+
isNewValue?: boolean;
|
|
12
|
+
itemsWhenEmpty?: T[];
|
|
13
|
+
itemToString(item: T): string;
|
|
14
|
+
onChange(value: T): void;
|
|
15
|
+
/**
|
|
16
|
+
* Marks the item that matches the current (pre-edit) value so the dropdown
|
|
17
|
+
* opens with it highlighted — e.g. a data-validation list highlighting the
|
|
18
|
+
* cell's current entry (Excel behavior). Only applied while the user hasn't
|
|
19
|
+
* typed yet; typing hands the highlight to the filter.
|
|
20
|
+
*/
|
|
21
|
+
isItemSelected?(item: T): boolean;
|
|
22
|
+
};
|
|
23
|
+
export declare const sortByUnderscore: <T extends OptionItem>(a: Maybe<T>, b: Maybe<T>) => 0 | 1 | -1;
|
|
24
|
+
export declare const sanitizeDropdownQuery: (value: string) => string;
|
|
25
|
+
export declare const useDropdown: <T extends OptionItem>({ initialOpen, initialHighlightedIndex, initialQuery, onChange, items, isNewValue, itemToString, limit, showAllIfEmpty, itemsWhenEmpty, isItemSelected, }: UseDropdownProps<T>) => {
|
|
26
|
+
isOpen: boolean;
|
|
27
|
+
highlightedIndex: number;
|
|
28
|
+
onKeyDown: (e: React.KeyboardEvent<HTMLDivElement>) => void;
|
|
29
|
+
onSelect: (value: T) => void;
|
|
30
|
+
onChangeHighlightedIndex: React.Dispatch<React.SetStateAction<number>>;
|
|
31
|
+
items: T[];
|
|
32
|
+
setQuery: (value: string) => void;
|
|
33
|
+
openMenu: () => void;
|
|
34
|
+
closeMenu: () => void;
|
|
35
|
+
query: string;
|
|
36
|
+
};
|
|
37
|
+
export {};
|
|
38
|
+
//# sourceMappingURL=use-dropdown.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-dropdown.d.ts","sourceRoot":"","sources":["../../../hooks/use-dropdown.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAK/B,OAAO,EAAE,KAAK,EAAE,MAAM,4BAA4B,CAAC;AACnD,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AAEnD,KAAK,gBAAgB,CAAC,CAAC,IAAI;IACzB,KAAK,EAAE,CAAC,EAAE,GAAG,SAAS,CAAC;IACvB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,OAAO,CAAC;IACrB,uBAAuB,EAAE,MAAM,CAAC;IAChC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,cAAc,CAAC,EAAE,CAAC,EAAE,CAAC;IACrB,YAAY,CAAC,IAAI,EAAE,CAAC,GAAG,MAAM,CAAC;IAC9B,QAAQ,CAAC,KAAK,EAAE,CAAC,GAAG,IAAI,CAAC;IACzB;;;;;OAKG;IACH,cAAc,CAAC,CAAC,IAAI,EAAE,CAAC,GAAG,OAAO,CAAC;CACnC,CAAC;AAEF,eAAO,MAAM,gBAAgB,GAAI,CAAC,SAAS,UAAU,EACnD,GAAG,KAAK,CAAC,CAAC,CAAC,EACX,GAAG,KAAK,CAAC,CAAC,CAAC,eAQZ,CAAC;AAuDF,eAAO,MAAM,qBAAqB,GAAI,OAAO,MAAM,WACtB,CAAC;AAE9B,eAAO,MAAM,WAAW,GAAI,CAAC,SAAS,UAAU,EAAE,2JAY/C,gBAAgB,CAAC,CAAC,CAAC;;;mBAgGd,KAAK,CAAC,aAAa,CAAC,cAAc,CAAC;sBAd/B,CAAC;;;sBAoGgC,MAAM;;;;CAoBlD,CAAC"}
|
|
@@ -0,0 +1,236 @@
|
|
|
1
|
+
import { useCallback, useEffect, useMemo, useRef, useState } from "react";
|
|
2
|
+
import { useIsomorphicLayoutEffect } from "./use-isomorphic-layout-effect.ts";
|
|
3
|
+
import { matchSorter } from "match-sorter";
|
|
4
|
+
export const sortByUnderscore = (a, b) => {
|
|
5
|
+
const aUnderscore = String(a?.title)?.startsWith("_");
|
|
6
|
+
const bUnderscore = String(b?.title)?.startsWith("_");
|
|
7
|
+
if (aUnderscore === bUnderscore) {
|
|
8
|
+
return 0;
|
|
9
|
+
}
|
|
10
|
+
return aUnderscore ? 1 : -1;
|
|
11
|
+
};
|
|
12
|
+
// Keep dropdown ordering consistent with our UI grouping so keyboard selection
|
|
13
|
+
// lines up with what the user sees.
|
|
14
|
+
const reorderByPriority = (list) => {
|
|
15
|
+
const buckets = {
|
|
16
|
+
0: [], // structured references
|
|
17
|
+
1: [], // properties
|
|
18
|
+
2: [], // parameters
|
|
19
|
+
3: [], // named ranges
|
|
20
|
+
4: [], // functions
|
|
21
|
+
5: [], // everything else
|
|
22
|
+
};
|
|
23
|
+
list.forEach((item) => {
|
|
24
|
+
const category = item?.category;
|
|
25
|
+
if (category === "table" ||
|
|
26
|
+
category === "column" ||
|
|
27
|
+
category === "specialitem" ||
|
|
28
|
+
category === "thisrow") {
|
|
29
|
+
buckets[0].push(item);
|
|
30
|
+
return;
|
|
31
|
+
}
|
|
32
|
+
if (category === "property") {
|
|
33
|
+
buckets[1].push(item);
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
if (category === "parameter") {
|
|
37
|
+
buckets[2].push(item);
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
if (category === "namedrange") {
|
|
41
|
+
buckets[3].push(item);
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
// Functions are CalculatorFunction (no category) or explicit category
|
|
45
|
+
if (category === "function" || "syntax" in item) {
|
|
46
|
+
buckets[4].push(item);
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
buckets[5].push(item);
|
|
50
|
+
});
|
|
51
|
+
return [
|
|
52
|
+
...buckets[0],
|
|
53
|
+
...buckets[1],
|
|
54
|
+
...buckets[2],
|
|
55
|
+
...buckets[3],
|
|
56
|
+
...buckets[4],
|
|
57
|
+
...buckets[5],
|
|
58
|
+
];
|
|
59
|
+
};
|
|
60
|
+
export const sanitizeDropdownQuery = (value) => value.replace(/["'`]/g, "");
|
|
61
|
+
export const useDropdown = ({ initialOpen, initialHighlightedIndex, initialQuery, onChange, items = [], isNewValue, itemToString, limit = 10, showAllIfEmpty, itemsWhenEmpty, isItemSelected, }) => {
|
|
62
|
+
const [isOpen, setIsOpen] = useState(initialOpen);
|
|
63
|
+
const [query, setQuery] = useState(initialQuery ?? "");
|
|
64
|
+
const [highlightedIndex, setHighlightedIndex] = useState(initialHighlightedIndex);
|
|
65
|
+
const openMenu = useCallback(() => setIsOpen(true), []);
|
|
66
|
+
const closeMenu = useCallback(() => setIsOpen(false), []);
|
|
67
|
+
// Refs
|
|
68
|
+
const isDirty = useRef(isNewValue);
|
|
69
|
+
const initialQueryRef = useRef(undefined);
|
|
70
|
+
const highlightedIndexRef = useRef(undefined);
|
|
71
|
+
const queryRef = useRef(undefined);
|
|
72
|
+
const filteredItemsRef = useRef(undefined);
|
|
73
|
+
useIsomorphicLayoutEffect(() => {
|
|
74
|
+
queryRef.current = query;
|
|
75
|
+
}, [query]);
|
|
76
|
+
useIsomorphicLayoutEffect(() => {
|
|
77
|
+
highlightedIndexRef.current = highlightedIndex;
|
|
78
|
+
}, [highlightedIndex]);
|
|
79
|
+
useIsomorphicLayoutEffect(() => {
|
|
80
|
+
initialQueryRef.current = initialQuery ?? "";
|
|
81
|
+
isDirty.current = Boolean(isNewValue);
|
|
82
|
+
// The hosting editor stays mounted (hidden) between editing sessions, so
|
|
83
|
+
// the query must be re-seeded when a new session starts — otherwise the
|
|
84
|
+
// previous session's filter narrows the next dropdown open.
|
|
85
|
+
setQuery(initialQuery ?? "");
|
|
86
|
+
}, [initialQuery, isNewValue]);
|
|
87
|
+
// Filtered items
|
|
88
|
+
const filteredItems = useMemo(() => {
|
|
89
|
+
if (!query) {
|
|
90
|
+
if (itemsWhenEmpty?.length) {
|
|
91
|
+
return reorderByPriority([...itemsWhenEmpty]);
|
|
92
|
+
}
|
|
93
|
+
if (!showAllIfEmpty) {
|
|
94
|
+
return [];
|
|
95
|
+
}
|
|
96
|
+
return reorderByPriority([...items].sort(sortByUnderscore));
|
|
97
|
+
}
|
|
98
|
+
if (!isDirty.current) {
|
|
99
|
+
return reorderByPriority([...items].sort(sortByUnderscore));
|
|
100
|
+
}
|
|
101
|
+
const cleanedQuery = sanitizeDropdownQuery(query);
|
|
102
|
+
// Break ties (e.g. "SU" matching both SUM and SUBSTITUTE) by preferring
|
|
103
|
+
// an exact-prefix match, then the shorter name, before the default
|
|
104
|
+
// alphabetical order — so the closest function is highlighted first.
|
|
105
|
+
const queryLower = cleanedQuery.toLowerCase();
|
|
106
|
+
const dropdownBaseSort = (a, b) => {
|
|
107
|
+
const aValue = String(a.rankedValue ?? "");
|
|
108
|
+
const bValue = String(b.rankedValue ?? "");
|
|
109
|
+
const aPrefix = aValue.toLowerCase().startsWith(queryLower);
|
|
110
|
+
const bPrefix = bValue.toLowerCase().startsWith(queryLower);
|
|
111
|
+
if (aPrefix !== bPrefix) {
|
|
112
|
+
return aPrefix ? -1 : 1;
|
|
113
|
+
}
|
|
114
|
+
if (aValue.length !== bValue.length) {
|
|
115
|
+
return aValue.length - bValue.length;
|
|
116
|
+
}
|
|
117
|
+
return aValue.localeCompare(bValue);
|
|
118
|
+
};
|
|
119
|
+
const sorted = matchSorter(items, cleanedQuery, {
|
|
120
|
+
keys: ["title"],
|
|
121
|
+
baseSort: dropdownBaseSort,
|
|
122
|
+
});
|
|
123
|
+
return reorderByPriority(sorted).slice(0, limit);
|
|
124
|
+
}, [items, query, limit, itemToString, showAllIfEmpty, itemsWhenEmpty]);
|
|
125
|
+
useIsomorphicLayoutEffect(() => {
|
|
126
|
+
filteredItemsRef.current = filteredItems;
|
|
127
|
+
}, [filteredItems]);
|
|
128
|
+
// User selects a value from the dropdown
|
|
129
|
+
const onSelect = useCallback((value) => {
|
|
130
|
+
onChange?.(value);
|
|
131
|
+
// Selecting an item consumes the filter; without this the selected
|
|
132
|
+
// text keeps filtering the list on the next dropdown open (e.g. a
|
|
133
|
+
// data-validation dropdown showing only the previously picked option).
|
|
134
|
+
isDirty.current = false;
|
|
135
|
+
setQuery("");
|
|
136
|
+
setHighlightedIndex(-1);
|
|
137
|
+
}, [onChange]);
|
|
138
|
+
const handleKeyDown = useCallback((e) => {
|
|
139
|
+
const query = queryRef.current;
|
|
140
|
+
const index = highlightedIndexRef.current;
|
|
141
|
+
const activeItems = filteredItemsRef.current ?? [];
|
|
142
|
+
const hasValue = activeItems.length || query;
|
|
143
|
+
const len = activeItems.length - 1;
|
|
144
|
+
// If there are no items, lets skip hiding showing menu
|
|
145
|
+
if (!activeItems.length) {
|
|
146
|
+
return;
|
|
147
|
+
}
|
|
148
|
+
switch (e.key) {
|
|
149
|
+
case "ArrowDown": {
|
|
150
|
+
if (!isOpen && hasValue) {
|
|
151
|
+
openMenu();
|
|
152
|
+
return;
|
|
153
|
+
}
|
|
154
|
+
setHighlightedIndex((prev) => {
|
|
155
|
+
if (prev === len) {
|
|
156
|
+
return 0;
|
|
157
|
+
}
|
|
158
|
+
return Math.min(prev + 1, len);
|
|
159
|
+
});
|
|
160
|
+
e.preventDefault();
|
|
161
|
+
break;
|
|
162
|
+
}
|
|
163
|
+
case "ArrowUp":
|
|
164
|
+
if (!isOpen && hasValue) {
|
|
165
|
+
openMenu();
|
|
166
|
+
}
|
|
167
|
+
setHighlightedIndex((prev) => {
|
|
168
|
+
if (prev === 0) {
|
|
169
|
+
return len;
|
|
170
|
+
}
|
|
171
|
+
return Math.max(0, prev - 1);
|
|
172
|
+
});
|
|
173
|
+
e.preventDefault();
|
|
174
|
+
break;
|
|
175
|
+
case "Escape":
|
|
176
|
+
if (isOpen) {
|
|
177
|
+
closeMenu();
|
|
178
|
+
e.preventDefault();
|
|
179
|
+
}
|
|
180
|
+
break;
|
|
181
|
+
case "Tab":
|
|
182
|
+
case "Enter": {
|
|
183
|
+
if (index === -1 || index === undefined) {
|
|
184
|
+
return;
|
|
185
|
+
}
|
|
186
|
+
const selectedItem = activeItems[index];
|
|
187
|
+
onSelect(selectedItem);
|
|
188
|
+
e.preventDefault();
|
|
189
|
+
break;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}, [isOpen, openMenu, onSelect, closeMenu]);
|
|
193
|
+
useEffect(() => {
|
|
194
|
+
if (filteredItems.length) {
|
|
195
|
+
openMenu();
|
|
196
|
+
}
|
|
197
|
+
else {
|
|
198
|
+
closeMenu();
|
|
199
|
+
}
|
|
200
|
+
// If user clears the
|
|
201
|
+
if (!query) {
|
|
202
|
+
setHighlightedIndex(-1);
|
|
203
|
+
}
|
|
204
|
+
}, [query, filteredItems, closeMenu, openMenu]);
|
|
205
|
+
// Pre-select the item matching the current value (e.g. a data-validation
|
|
206
|
+
// dropdown highlighting the cell's current entry — Excel behavior). Runs
|
|
207
|
+
// only while the session is pristine (`isDirty` flips on the first typed
|
|
208
|
+
// change, handing the highlight to the filter). Declared AFTER the reset
|
|
209
|
+
// effect above so the seed wins the mount-time ordering when the query is
|
|
210
|
+
// empty (a blank cell selecting the list's empty/text-prefix entry).
|
|
211
|
+
useEffect(() => {
|
|
212
|
+
if (!isItemSelected || isDirty.current) {
|
|
213
|
+
return;
|
|
214
|
+
}
|
|
215
|
+
setHighlightedIndex(filteredItems.findIndex(isItemSelected));
|
|
216
|
+
}, [filteredItems, isItemSelected]);
|
|
217
|
+
const handleSetQuery = useCallback((value) => {
|
|
218
|
+
setQuery(value);
|
|
219
|
+
setHighlightedIndex(0);
|
|
220
|
+
if (value !== initialQueryRef.current) {
|
|
221
|
+
isDirty.current = true;
|
|
222
|
+
}
|
|
223
|
+
}, []);
|
|
224
|
+
return {
|
|
225
|
+
isOpen,
|
|
226
|
+
highlightedIndex,
|
|
227
|
+
onKeyDown: handleKeyDown,
|
|
228
|
+
onSelect,
|
|
229
|
+
onChangeHighlightedIndex: setHighlightedIndex,
|
|
230
|
+
items: filteredItems,
|
|
231
|
+
setQuery: handleSetQuery,
|
|
232
|
+
openMenu,
|
|
233
|
+
closeMenu,
|
|
234
|
+
query,
|
|
235
|
+
};
|
|
236
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-isomorphic-layout-effect.ts.d.ts","sourceRoot":"","sources":["../../../hooks/use-isomorphic-layout-effect.ts.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAmB,MAAM,OAAO,CAAC;AAEnD;;GAEG;AAEH,eAAO,MAAM,yBAAyB,kBAEzB,CAAC"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { canUseDOM } from "@rowsncolumns/utils";
|
|
2
|
+
import { useEffect, useLayoutEffect } from "react";
|
|
3
|
+
/**
|
|
4
|
+
* Prevent warning on SSR by falling back to useEffect when DOM isn't available
|
|
5
|
+
*/
|
|
6
|
+
export const useIsomorphicLayoutEffect = canUseDOM
|
|
7
|
+
? useLayoutEffect
|
|
8
|
+
: useEffect;
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
type ConfirmOptions = {
|
|
3
|
+
title?: string;
|
|
4
|
+
description?: React.ReactNode;
|
|
5
|
+
confirmText?: string;
|
|
6
|
+
cancelText?: string;
|
|
7
|
+
container?: HTMLElement | HTMLDivElement | null;
|
|
8
|
+
};
|
|
9
|
+
type PromptOptions = {
|
|
10
|
+
title?: string;
|
|
11
|
+
description?: React.ReactNode;
|
|
12
|
+
confirmText?: string;
|
|
13
|
+
cancelText?: string;
|
|
14
|
+
placeholder?: string;
|
|
15
|
+
inputType?: "text" | "password";
|
|
16
|
+
defaultValue?: string;
|
|
17
|
+
container?: HTMLElement | HTMLDivElement | null;
|
|
18
|
+
};
|
|
19
|
+
type ModalContextValue = {
|
|
20
|
+
confirm: (message: string, options?: ConfirmOptions) => Promise<boolean>;
|
|
21
|
+
prompt: (message: string, options?: PromptOptions) => Promise<string | null>;
|
|
22
|
+
};
|
|
23
|
+
export declare const ModalProvider: ({ children }: {
|
|
24
|
+
children: React.ReactNode;
|
|
25
|
+
}) => React.JSX.Element;
|
|
26
|
+
export declare const useModal: () => ModalContextValue;
|
|
27
|
+
export {};
|
|
28
|
+
//# sourceMappingURL=use-modal.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-modal.d.ts","sourceRoot":"","sources":["../../../hooks/use-modal.tsx"],"names":[],"mappings":"AACA,OAAO,KAON,MAAM,OAAO,CAAC;AAgBf,KAAK,cAAc,GAAG;IACpB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC9B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,WAAW,GAAG,cAAc,GAAG,IAAI,CAAC;CACjD,CAAC;AAEF,KAAK,aAAa,GAAG;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC9B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,GAAG,UAAU,CAAC;IAChC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,SAAS,CAAC,EAAE,WAAW,GAAG,cAAc,GAAG,IAAI,CAAC;CACjD,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,OAAO,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,cAAc,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;IACzE,MAAM,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,aAAa,KAAK,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;CAC9E,CAAC;AAIF,eAAO,MAAM,aAAa,GAAI,cAAc;IAAE,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;CAAE,sBAoKxE,CAAC;AAEF,eAAO,MAAM,QAAQ,QAAO,iBAM3B,CAAC"}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import { Cross2Icon, EyeNoneIcon, EyeOpenIcon } from "@rowsncolumns/icons";
|
|
2
|
+
import React, { createContext, useCallback, useContext, useMemo, useRef, useState, } from "react";
|
|
3
|
+
import { Button } from "../button";
|
|
4
|
+
import { Dialog, DialogBody, DialogClose, DialogCloseButton, DialogContent, DialogDescription, DialogTitle, } from "../dialog";
|
|
5
|
+
import { IconButton } from "../icon-button";
|
|
6
|
+
import { Input } from "../input";
|
|
7
|
+
import { Stack } from "../stack";
|
|
8
|
+
const ModalContext = createContext(undefined);
|
|
9
|
+
export const ModalProvider = ({ children }) => {
|
|
10
|
+
const resolverRef = useRef(null);
|
|
11
|
+
const [open, setOpen] = useState(false);
|
|
12
|
+
const [message, setMessage] = useState("");
|
|
13
|
+
const [mode, setMode] = useState("confirm");
|
|
14
|
+
const [options, setOptions] = useState();
|
|
15
|
+
const [inputValue, setInputValue] = useState("");
|
|
16
|
+
const [isPasswordVisible, setIsPasswordVisible] = useState(false);
|
|
17
|
+
const close = useCallback((result) => {
|
|
18
|
+
resolverRef.current?.(result);
|
|
19
|
+
resolverRef.current = null;
|
|
20
|
+
setOpen(false);
|
|
21
|
+
setInputValue("");
|
|
22
|
+
setIsPasswordVisible(false);
|
|
23
|
+
}, []);
|
|
24
|
+
const confirm = useCallback((msg, opts) => new Promise((resolve) => {
|
|
25
|
+
resolverRef.current = resolve;
|
|
26
|
+
setMessage(msg);
|
|
27
|
+
setOptions(opts);
|
|
28
|
+
setMode("confirm");
|
|
29
|
+
setOpen(true);
|
|
30
|
+
}), []);
|
|
31
|
+
const prompt = useCallback((msg, opts) => new Promise((resolve) => {
|
|
32
|
+
resolverRef.current = resolve;
|
|
33
|
+
setMessage(msg);
|
|
34
|
+
setOptions(opts);
|
|
35
|
+
setMode("prompt");
|
|
36
|
+
setInputValue(opts?.defaultValue || "");
|
|
37
|
+
setIsPasswordVisible(false);
|
|
38
|
+
setOpen(true);
|
|
39
|
+
}), []);
|
|
40
|
+
const handleOpenChange = useCallback((next) => {
|
|
41
|
+
if (!next && open) {
|
|
42
|
+
close(mode === "prompt" ? null : false);
|
|
43
|
+
}
|
|
44
|
+
else {
|
|
45
|
+
setOpen(next);
|
|
46
|
+
}
|
|
47
|
+
}, [close, open, mode]);
|
|
48
|
+
const contextValue = useMemo(() => ({ confirm, prompt }), [confirm, prompt]);
|
|
49
|
+
return (React.createElement(ModalContext.Provider, { value: contextValue },
|
|
50
|
+
children,
|
|
51
|
+
React.createElement(Dialog, { open: open, onOpenChange: handleOpenChange },
|
|
52
|
+
React.createElement(DialogContent, { container: options?.container ?? undefined },
|
|
53
|
+
React.createElement(DialogTitle, null, options?.title ?? (mode === "prompt" ? "Input" : "Confirm")),
|
|
54
|
+
React.createElement(DialogCloseButton, { onClick: () => close(mode === "prompt" ? null : false) }),
|
|
55
|
+
React.createElement(DialogBody, null,
|
|
56
|
+
React.createElement(DialogDescription, { asChild: true, className: "pl-0" },
|
|
57
|
+
React.createElement("div", { className: "pb-3" },
|
|
58
|
+
React.createElement("div", null, message),
|
|
59
|
+
options?.description ? (React.createElement("div", { className: "text-sm text-rnc-muted-foreground" }, options.description)) : null)),
|
|
60
|
+
mode === "prompt" && (React.createElement("div", { className: "pb-3" },
|
|
61
|
+
React.createElement("div", { className: "relative" },
|
|
62
|
+
React.createElement(Input, { type: options?.inputType === "password" &&
|
|
63
|
+
isPasswordVisible
|
|
64
|
+
? "text"
|
|
65
|
+
: options?.inputType || "text", value: inputValue, onChange: (e) => setInputValue(e.target.value), placeholder: options?.placeholder, className: "w-full px-3 py-2 border border-rnc-border rounded-md focus:outline-none focus:ring-2 focus:ring-rnc-primary pr-10", autoFocus: true, onKeyDown: (e) => {
|
|
66
|
+
if (e.key === "Enter" && inputValue.trim()) {
|
|
67
|
+
close(inputValue);
|
|
68
|
+
}
|
|
69
|
+
else if (e.key === "Escape") {
|
|
70
|
+
close(null);
|
|
71
|
+
}
|
|
72
|
+
} }),
|
|
73
|
+
options?.inputType === "password" ? (React.createElement(IconButton, { onClick: () => setIsPasswordVisible((prev) => !prev), className: "absolute right-2 top-1/2 -translate-y-1/2", "aria-label": isPasswordVisible ? "Hide password" : "Show password" }, isPasswordVisible ? React.createElement(EyeNoneIcon, null) : React.createElement(EyeOpenIcon, null))) : null))),
|
|
74
|
+
React.createElement(Stack, { className: "gap-2" }, mode === "confirm" ? (React.createElement(React.Fragment, null,
|
|
75
|
+
React.createElement(DialogClose, { asChild: true },
|
|
76
|
+
React.createElement(Button, { variant: "primary", onClick: () => close(true) }, options?.confirmText ?? "Confirm")),
|
|
77
|
+
React.createElement(DialogClose, { asChild: true },
|
|
78
|
+
React.createElement(Button, { onClick: () => close(false) }, options?.cancelText ?? "Cancel")))) : (React.createElement(React.Fragment, null,
|
|
79
|
+
React.createElement(DialogClose, { asChild: true },
|
|
80
|
+
React.createElement(Button, { variant: "primary", onClick: () => close(inputValue), disabled: !inputValue.trim() }, options?.confirmText ?? "OK")),
|
|
81
|
+
React.createElement(DialogClose, { asChild: true },
|
|
82
|
+
React.createElement(Button, { onClick: () => close(null) }, options?.cancelText ?? "Cancel")))))),
|
|
83
|
+
React.createElement(DialogClose, { asChild: true },
|
|
84
|
+
React.createElement(DialogCloseButton, null,
|
|
85
|
+
React.createElement(Cross2Icon, null)))))));
|
|
86
|
+
};
|
|
87
|
+
export const useModal = () => {
|
|
88
|
+
const ctx = useContext(ModalContext);
|
|
89
|
+
if (!ctx) {
|
|
90
|
+
throw new Error("useModal must be used within a ModalProvider");
|
|
91
|
+
}
|
|
92
|
+
return ctx;
|
|
93
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-visibility.d.ts","sourceRoot":"","sources":["../../../hooks/use-visibility.ts"],"names":[],"mappings":"AAEA,eAAO,MAAM,qBAAqB,GAChC,UAAU,CAAC,KAAK,EAAE,uBAAuB,KAAK,IAAI,SAYnD,CAAC"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { useIsomorphicLayoutEffect } from "./use-isomorphic-layout-effect.ts";
|
|
2
|
+
export const useOnVisibilityChange = (callback) => {
|
|
3
|
+
useIsomorphicLayoutEffect(() => {
|
|
4
|
+
const visibilityHandler = () => {
|
|
5
|
+
callback(document.visibilityState);
|
|
6
|
+
};
|
|
7
|
+
window.addEventListener("visibilitychange", visibilityHandler);
|
|
8
|
+
return () => {
|
|
9
|
+
window.removeEventListener("visibilitychange", visibilityHandler);
|
|
10
|
+
};
|
|
11
|
+
}, []);
|
|
12
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { VariantProps } from "class-variance-authority";
|
|
2
|
+
import React from "react";
|
|
3
|
+
import type { ButtonProps } from "./../button";
|
|
4
|
+
declare const iconButtonVariants: (props?: ({
|
|
5
|
+
size?: "default" | "xs" | "sm" | "md" | "lg" | "xl" | null | undefined;
|
|
6
|
+
isActive?: boolean | null | undefined;
|
|
7
|
+
shrink?: boolean | null | undefined;
|
|
8
|
+
} & import("class-variance-authority/dist/types").ClassProp) | undefined) => string;
|
|
9
|
+
export interface IconButtonProps extends ButtonProps, VariantProps<typeof iconButtonVariants> {
|
|
10
|
+
asChild?: boolean;
|
|
11
|
+
tooltip?: React.ReactNode;
|
|
12
|
+
}
|
|
13
|
+
export declare const IconButton: React.ForwardRefExoticComponent<IconButtonProps & React.RefAttributes<HTMLButtonElement>>;
|
|
14
|
+
export {};
|
|
15
|
+
//# sourceMappingURL=index.d.ts.map
|