@wix/patterns-fields 1.72.0 → 1.74.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/dist/cjs/components/address/form-address.js +5 -3
- package/dist/cjs/components/address/form-address.js.map +1 -1
- package/dist/cjs/components/address/input/address-input.st.css.js +3 -3
- package/dist/cjs/components/address/input/address-input.st.css.js.map +1 -1
- package/dist/cjs/components/address/input/form-address-input.js +5 -16
- package/dist/cjs/components/address/input/form-address-input.js.map +1 -1
- package/dist/cjs/components/audio/actions/actions-menu/actions-menu.st.css.js +3 -3
- package/dist/cjs/components/audio/actions/actions-menu/actions-menu.st.css.js.map +1 -1
- package/dist/cjs/components/audio/audio-field/form-audio-field.js +14 -13
- package/dist/cjs/components/audio/audio-field/form-audio-field.js.map +1 -1
- package/dist/cjs/components/audio/audio-field/form-audio-field.st.css.js +4 -4
- package/dist/cjs/components/audio/audio-field/form-audio-field.st.css.js.map +1 -1
- package/dist/cjs/components/audio/audio-field/form-audio.js +10 -3
- package/dist/cjs/components/audio/audio-field/form-audio.js.map +1 -1
- package/dist/cjs/components/audio/audio-player/audio-player.st.css.js +2 -2
- package/dist/cjs/components/audio/audio-player/audio-player.st.css.js.map +1 -1
- package/dist/cjs/components/color-view/cell-color-view.st.css.js +3 -3
- package/dist/cjs/components/color-view/cell-color-view.st.css.js.map +1 -1
- package/dist/cjs/components/color-view/color-input.js +6 -5
- package/dist/cjs/components/color-view/color-input.js.map +1 -1
- package/dist/cjs/components/color-view/color-view.st.css.js +4 -4
- package/dist/cjs/components/color-view/color-view.st.css.js.map +1 -1
- package/dist/cjs/components/color-view/form-color.driver.js +8 -2
- package/dist/cjs/components/color-view/form-color.driver.js.map +1 -1
- package/dist/cjs/components/datetime-input/form-date-time.driver.js +4 -1
- package/dist/cjs/components/datetime-input/form-date-time.driver.js.map +1 -1
- package/dist/cjs/components/datetime-input/form-date-time.js +1 -0
- package/dist/cjs/components/datetime-input/form-date-time.js.map +1 -1
- package/dist/cjs/components/delete-dialog/delete-dialog.st.css.js +3 -3
- package/dist/cjs/components/delete-dialog/delete-dialog.st.css.js.map +1 -1
- package/dist/cjs/components/document/form-document-field.js +7 -6
- package/dist/cjs/components/document/form-document-field.js.map +1 -1
- package/dist/cjs/components/document/form-document-field.st.css.js +7 -7
- package/dist/cjs/components/document/form-document-field.st.css.js.map +1 -1
- package/dist/cjs/components/document/form-document.js +10 -3
- package/dist/cjs/components/document/form-document.js.map +1 -1
- package/dist/cjs/components/exclamation/exclamation.st.css.js +5 -5
- package/dist/cjs/components/exclamation/exclamation.st.css.js.map +1 -1
- package/dist/cjs/components/highlighted-text/highlighted-text.st.css.js +5 -5
- package/dist/cjs/components/highlighted-text/highlighted-text.st.css.js.map +1 -1
- package/dist/cjs/components/image/form-image-input.js +11 -4
- package/dist/cjs/components/image/form-image-input.js.map +1 -1
- package/dist/cjs/components/image/thumbnail-replace-overlay.st.css.js +3 -3
- package/dist/cjs/components/image/thumbnail-replace-overlay.st.css.js.map +1 -1
- package/dist/cjs/components/media-control/cell-media-edit-shell.st.css.js +2 -2
- package/dist/cjs/components/media-control/cell-media-edit-shell.st.css.js.map +1 -1
- package/dist/cjs/components/media-control/paste-url-button.st.css.js +4 -4
- package/dist/cjs/components/media-control/paste-url-button.st.css.js.map +1 -1
- package/dist/cjs/components/media-gallery/form-media-gallery-field.js +24 -21
- package/dist/cjs/components/media-gallery/form-media-gallery-field.js.map +1 -1
- package/dist/cjs/components/media-gallery/form-media-gallery-field.st.css.js +10 -10
- package/dist/cjs/components/media-gallery/form-media-gallery-field.st.css.js.map +1 -1
- package/dist/cjs/components/media-gallery/form-media-gallery.js +10 -3
- package/dist/cjs/components/media-gallery/form-media-gallery.js.map +1 -1
- package/dist/cjs/components/media-image/media-image.st.css.js +4 -4
- package/dist/cjs/components/media-image/media-image.st.css.js.map +1 -1
- package/dist/cjs/components/media-image/overlays/overlay.st.css.js +3 -3
- package/dist/cjs/components/media-image/overlays/overlay.st.css.js.map +1 -1
- package/dist/cjs/components/media-loader/media-loader.st.css.js +3 -3
- package/dist/cjs/components/media-loader/media-loader.st.css.js.map +1 -1
- package/dist/cjs/components/media-tag/web-media-tag/media-tag.st.css.js +2 -2
- package/dist/cjs/components/media-tag/web-media-tag/media-tag.st.css.js.map +1 -1
- package/dist/cjs/components/multi-document/cell-multi-document-edit.st.css.js +3 -3
- package/dist/cjs/components/multi-document/cell-multi-document-edit.st.css.js.map +1 -1
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document-field.js +7 -6
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document-field.js.map +1 -1
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document.js +10 -3
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document.js.map +1 -1
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document.st.css.js +5 -5
- package/dist/cjs/components/multi-document/multi-document-input/form-multi-document.st.css.js.map +1 -1
- package/dist/cjs/components/reference/cell-multi-reference-input.st.css.js +2 -2
- package/dist/cjs/components/reference/cell-multi-reference-input.st.css.js.map +1 -1
- package/dist/cjs/components/reference/cell-reference-input.st.css.js +3 -3
- package/dist/cjs/components/reference/cell-reference-input.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/form-rich-content.js +20 -5
- package/dist/cjs/components/rich-content/form-rich-content.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/default-value-input/rich-content-default-value-input.st.css.js +4 -4
- package/dist/cjs/components/rich-content/rich-content-input/default-value-input/rich-content-default-value-input.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css +15 -7
- package/dist/cjs/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.js +11 -7
- package/dist/cjs/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.js +2 -2
- package/dist/cjs/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/fullscreen-modal/fullscreen-modal.st.css.js +3 -3
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/fullscreen-modal/fullscreen-modal.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/publish-loader/publish-loader.st.css.js +3 -3
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/publish-loader/publish-loader.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/toggle-fullscreen-button/toggle-fullscreen-button.st.css.js +2 -2
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-common/toggle-fullscreen-button/toggle-fullscreen-button.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.js +7 -7
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-editor/rich-content-toolbar.st.css.js +5 -5
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-editor/rich-content-toolbar.st.css.js.map +1 -1
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-viewer/rich-content-viewer.st.css.js +4 -4
- package/dist/cjs/components/rich-content/rich-content-input/rich-content-viewer/rich-content-viewer.st.css.js.map +1 -1
- package/dist/cjs/components/rich-text/form-rich-text.js +18 -5
- package/dist/cjs/components/rich-text/form-rich-text.js.map +1 -1
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.js +18 -18
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.js.map +1 -1
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css +32 -19
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.js +20 -12
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.js.map +1 -1
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.js +18 -18
- package/dist/cjs/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.js.map +1 -1
- package/dist/cjs/components/text/text-view.st.css.js +3 -3
- package/dist/cjs/components/text/text-view.st.css.js.map +1 -1
- package/dist/cjs/components/time-input/form-time.js +9 -10
- package/dist/cjs/components/time-input/form-time.js.map +1 -1
- package/dist/cjs/components/video/form-video.js +30 -29
- package/dist/cjs/components/video/form-video.js.map +1 -1
- package/dist/cjs/hooks/index.js +18 -0
- package/dist/cjs/hooks/index.js.map +1 -1
- package/dist/cjs/hooks/pr-5746-kobiburnley-comments.md +54 -0
- package/dist/cjs/hooks/use-field-ref.js +60 -0
- package/dist/cjs/hooks/use-field-ref.js.map +1 -0
- package/dist/cjs/hooks/use-merged-ref.js +27 -0
- package/dist/cjs/hooks/use-merged-ref.js.map +1 -0
- package/dist/cjs/hooks/use-scroll-to-error-ref.js +34 -0
- package/dist/cjs/hooks/use-scroll-to-error-ref.js.map +1 -0
- package/dist/cjs/styles.global.css +1 -1
- package/dist/esm/components/address/form-address.js +3 -1
- package/dist/esm/components/address/form-address.js.map +1 -1
- package/dist/esm/components/address/input/address-input.st.css.js +2 -2
- package/dist/esm/components/address/input/address-input.st.css.js.map +1 -1
- package/dist/esm/components/address/input/form-address-input.js +4 -15
- package/dist/esm/components/address/input/form-address-input.js.map +1 -1
- package/dist/esm/components/audio/actions/actions-menu/actions-menu.st.css.js +2 -2
- package/dist/esm/components/audio/actions/actions-menu/actions-menu.st.css.js.map +1 -1
- package/dist/esm/components/audio/audio-field/form-audio-field.js +4 -4
- package/dist/esm/components/audio/audio-field/form-audio-field.js.map +1 -1
- package/dist/esm/components/audio/audio-field/form-audio-field.st.css.js +2 -2
- package/dist/esm/components/audio/audio-field/form-audio.js +11 -1
- package/dist/esm/components/audio/audio-field/form-audio.js.map +1 -1
- package/dist/esm/components/audio/audio-player/audio-player.st.css.js +2 -2
- package/dist/esm/components/color-view/cell-color-view.st.css.js +2 -2
- package/dist/esm/components/color-view/color-input.js +1 -1
- package/dist/esm/components/color-view/color-input.js.map +1 -1
- package/dist/esm/components/color-view/color-view.st.css.js +2 -2
- package/dist/esm/components/color-view/form-color.driver.js +8 -2
- package/dist/esm/components/color-view/form-color.driver.js.map +1 -1
- package/dist/esm/components/datetime-input/form-date-time.driver.js +3 -0
- package/dist/esm/components/datetime-input/form-date-time.driver.js.map +1 -1
- package/dist/esm/components/datetime-input/form-date-time.js +1 -1
- package/dist/esm/components/datetime-input/form-date-time.js.map +1 -1
- package/dist/esm/components/delete-dialog/delete-dialog.st.css.js +2 -2
- package/dist/esm/components/delete-dialog/delete-dialog.st.css.js.map +1 -1
- package/dist/esm/components/document/form-document-field.js +4 -4
- package/dist/esm/components/document/form-document-field.js.map +1 -1
- package/dist/esm/components/document/form-document-field.st.css.js +2 -2
- package/dist/esm/components/document/form-document-field.st.css.js.map +1 -1
- package/dist/esm/components/document/form-document.js +11 -1
- package/dist/esm/components/document/form-document.js.map +1 -1
- package/dist/esm/components/exclamation/exclamation.st.css.js +2 -2
- package/dist/esm/components/highlighted-text/highlighted-text.st.css.js +3 -3
- package/dist/esm/components/highlighted-text/highlighted-text.st.css.js.map +1 -1
- package/dist/esm/components/image/form-image-input.js +11 -1
- package/dist/esm/components/image/form-image-input.js.map +1 -1
- package/dist/esm/components/image/thumbnail-replace-overlay.st.css.js +2 -2
- package/dist/esm/components/media-control/cell-media-edit-shell.st.css.js +2 -2
- package/dist/esm/components/media-control/cell-media-edit-shell.st.css.js.map +1 -1
- package/dist/esm/components/media-control/paste-url-button.st.css.js +2 -2
- package/dist/esm/components/media-gallery/form-media-gallery-field.js +7 -5
- package/dist/esm/components/media-gallery/form-media-gallery-field.js.map +1 -1
- package/dist/esm/components/media-gallery/form-media-gallery-field.st.css.js +2 -2
- package/dist/esm/components/media-gallery/form-media-gallery.js +11 -1
- package/dist/esm/components/media-gallery/form-media-gallery.js.map +1 -1
- package/dist/esm/components/media-image/media-image.st.css.js +3 -3
- package/dist/esm/components/media-image/overlays/overlay.st.css.js +2 -2
- package/dist/esm/components/media-loader/media-loader.st.css.js +2 -2
- package/dist/esm/components/media-tag/web-media-tag/media-tag.st.css.js +2 -2
- package/dist/esm/components/multi-document/cell-multi-document-edit.st.css.js +2 -2
- package/dist/esm/components/multi-document/cell-multi-document-edit.st.css.js.map +1 -1
- package/dist/esm/components/multi-document/multi-document-input/form-multi-document-field.js +4 -4
- package/dist/esm/components/multi-document/multi-document-input/form-multi-document-field.js.map +1 -1
- package/dist/esm/components/multi-document/multi-document-input/form-multi-document.js +11 -1
- package/dist/esm/components/multi-document/multi-document-input/form-multi-document.js.map +1 -1
- package/dist/esm/components/multi-document/multi-document-input/form-multi-document.st.css.js +2 -2
- package/dist/esm/components/reference/cell-multi-reference-input.st.css.js +2 -2
- package/dist/esm/components/reference/cell-reference-input.st.css.js +2 -2
- package/dist/esm/components/rich-content/form-rich-content.js +8 -3
- package/dist/esm/components/rich-content/form-rich-content.js.map +1 -1
- package/dist/esm/components/rich-content/rich-content-input/default-value-input/rich-content-default-value-input.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css +15 -7
- package/dist/esm/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.js +3 -3
- package/dist/esm/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.js.map +1 -1
- package/dist/esm/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.js.map +1 -1
- package/dist/esm/components/rich-content/rich-content-input/rich-content-common/fullscreen-modal/fullscreen-modal.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/rich-content-common/publish-loader/publish-loader.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/rich-content-common/toggle-fullscreen-button/toggle-fullscreen-button.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.js.map +1 -1
- package/dist/esm/components/rich-content/rich-content-input/rich-content-editor/rich-content-toolbar.st.css.js +2 -2
- package/dist/esm/components/rich-content/rich-content-input/rich-content-viewer/rich-content-viewer.st.css.js +2 -2
- package/dist/esm/components/rich-text/form-rich-text.js +7 -3
- package/dist/esm/components/rich-text/form-rich-text.js.map +1 -1
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.js +2 -2
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.js.map +1 -1
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css +32 -19
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.js +3 -3
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.js.map +1 -1
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.js +2 -2
- package/dist/esm/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.js.map +1 -1
- package/dist/esm/components/text/text-view.st.css.js +2 -2
- package/dist/esm/components/time-input/form-time.js +4 -3
- package/dist/esm/components/time-input/form-time.js.map +1 -1
- package/dist/esm/components/video/form-video.js +3 -2
- package/dist/esm/components/video/form-video.js.map +1 -1
- package/dist/esm/hooks/index.js +3 -0
- package/dist/esm/hooks/index.js.map +1 -1
- package/dist/esm/hooks/pr-5746-kobiburnley-comments.md +54 -0
- package/dist/esm/hooks/use-field-ref.js +36 -0
- package/dist/esm/hooks/use-field-ref.js.map +1 -0
- package/dist/esm/hooks/use-merged-ref.js +23 -0
- package/dist/esm/hooks/use-merged-ref.js.map +1 -0
- package/dist/esm/hooks/use-scroll-to-error-ref.js +26 -0
- package/dist/esm/hooks/use-scroll-to-error-ref.js.map +1 -0
- package/dist/esm/styles.global.css +1 -1
- package/dist/types/components/address/form-address.d.ts.map +1 -1
- package/dist/types/components/address/input/address-input.st.css.d.ts.map +1 -1
- package/dist/types/components/address/input/form-address-input.d.ts.map +1 -1
- package/dist/types/components/audio/actions/actions-menu/actions-menu.st.css.d.ts.map +1 -1
- package/dist/types/components/audio/audio-field/form-audio-field.d.ts.map +1 -1
- package/dist/types/components/audio/audio-field/form-audio.d.ts.map +1 -1
- package/dist/types/components/color-view/color-input.d.ts.map +1 -1
- package/dist/types/components/color-view/form-color.driver.d.ts +5 -15
- package/dist/types/components/color-view/form-color.driver.d.ts.map +1 -1
- package/dist/types/components/datetime-input/form-date-time.driver.d.ts +1 -0
- package/dist/types/components/datetime-input/form-date-time.driver.d.ts.map +1 -1
- package/dist/types/components/delete-dialog/delete-dialog.st.css.d.ts.map +1 -1
- package/dist/types/components/document/form-document-field.d.ts.map +1 -1
- package/dist/types/components/document/form-document-field.st.css.d.ts.map +1 -1
- package/dist/types/components/document/form-document.d.ts.map +1 -1
- package/dist/types/components/highlighted-text/highlighted-text.st.css.d.ts.map +1 -1
- package/dist/types/components/image/form-image-input.d.ts.map +1 -1
- package/dist/types/components/media-control/cell-media-edit-shell.st.css.d.ts.map +1 -1
- package/dist/types/components/media-gallery/form-media-gallery-field.d.ts +3 -0
- package/dist/types/components/media-gallery/form-media-gallery-field.d.ts.map +1 -1
- package/dist/types/components/media-gallery/form-media-gallery.d.ts.map +1 -1
- package/dist/types/components/multi-document/cell-multi-document-edit.st.css.d.ts.map +1 -1
- package/dist/types/components/multi-document/multi-document-input/form-multi-document-field.d.ts.map +1 -1
- package/dist/types/components/multi-document/multi-document-input/form-multi-document.d.ts.map +1 -1
- package/dist/types/components/rich-content/form-rich-content.d.ts.map +1 -1
- package/dist/types/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.d.ts +7 -3
- package/dist/types/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.d.ts.map +1 -1
- package/dist/types/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.d.ts.map +1 -1
- package/dist/types/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.d.ts.map +1 -1
- package/dist/types/components/rich-text/form-rich-text.d.ts.map +1 -1
- package/dist/types/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.d.ts.map +1 -1
- package/dist/types/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.d.ts +16 -8
- package/dist/types/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.d.ts.map +1 -1
- package/dist/types/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.d.ts.map +1 -1
- package/dist/types/components/time-input/form-time.d.ts.map +1 -1
- package/dist/types/components/video/form-video.d.ts.map +1 -1
- package/dist/types/hooks/index.d.ts +3 -0
- package/dist/types/hooks/index.d.ts.map +1 -1
- package/dist/types/hooks/use-field-ref.d.ts +36 -0
- package/dist/types/hooks/use-field-ref.d.ts.map +1 -0
- package/dist/types/hooks/use-merged-ref.d.ts +11 -0
- package/dist/types/hooks/use-merged-ref.d.ts.map +1 -0
- package/dist/types/hooks/use-scroll-to-error-ref.d.ts +14 -0
- package/dist/types/hooks/use-scroll-to-error-ref.d.ts.map +1 -0
- package/package.json +5 -5
- package/src/__tests__/components/audio/form-audio.spec.tsx +22 -0
- package/src/__tests__/components/color-view/form-color.spec.tsx +46 -3
- package/src/__tests__/components/document/form-document.spec.tsx +22 -0
- package/src/__tests__/components/image/form-image-input.spec.tsx +22 -0
- package/src/__tests__/components/media-gallery/form-media-gallery.spec.tsx +21 -0
- package/src/__tests__/components/multi-document/form-multi-document.spec.tsx +21 -0
- package/src/__tests__/components/rich-content/form-rich-content.spec.tsx +22 -0
- package/src/__tests__/components/rich-editors-border.spec.ts +45 -0
- package/src/__tests__/components/rich-text/form-rich-text.spec.tsx +18 -0
- package/src/__tests__/hooks/use-field-ref.spec.tsx +132 -0
- package/src/components/address/form-address.tsx +4 -1
- package/src/components/address/input/address-input.st.css.ts +2 -2
- package/src/components/address/input/form-address-input.tsx +5 -20
- package/src/components/audio/actions/actions-menu/actions-menu.st.css.ts +2 -2
- package/src/components/audio/audio-field/form-audio-field.st.css.ts +2 -2
- package/src/components/audio/audio-field/form-audio-field.tsx +4 -3
- package/src/components/audio/audio-field/form-audio.tsx +7 -0
- package/src/components/audio/audio-player/audio-player.st.css.ts +2 -2
- package/src/components/color-view/cell-color-view.st.css.ts +2 -2
- package/src/components/color-view/color-input.tsx +13 -2
- package/src/components/color-view/color-view.st.css.ts +2 -2
- package/src/components/color-view/form-color.driver.ts +8 -2
- package/src/components/datetime-input/form-date-time.driver.ts +3 -0
- package/src/components/datetime-input/form-date-time.tsx +1 -1
- package/src/components/delete-dialog/delete-dialog.st.css.ts +2 -2
- package/src/components/document/form-document-field.st.css.ts +2 -2
- package/src/components/document/form-document-field.tsx +4 -3
- package/src/components/document/form-document.tsx +7 -0
- package/src/components/exclamation/exclamation.st.css.ts +2 -2
- package/src/components/highlighted-text/highlighted-text.st.css.ts +3 -3
- package/src/components/image/form-image-input.tsx +7 -0
- package/src/components/image/thumbnail-replace-overlay.st.css.ts +2 -2
- package/src/components/media-control/cell-media-edit-shell.st.css.ts +2 -2
- package/src/components/media-control/paste-url-button.st.css.ts +2 -2
- package/src/components/media-gallery/form-media-gallery-field.st.css.ts +2 -2
- package/src/components/media-gallery/form-media-gallery-field.tsx +9 -4
- package/src/components/media-gallery/form-media-gallery.tsx +7 -0
- package/src/components/media-image/media-image.st.css.ts +3 -3
- package/src/components/media-image/overlays/overlay.st.css.ts +2 -2
- package/src/components/media-loader/media-loader.st.css.ts +2 -2
- package/src/components/media-tag/web-media-tag/media-tag.st.css.ts +2 -2
- package/src/components/multi-document/cell-multi-document-edit.st.css.ts +2 -2
- package/src/components/multi-document/multi-document-input/form-multi-document-field.tsx +4 -3
- package/src/components/multi-document/multi-document-input/form-multi-document.st.css.ts +2 -2
- package/src/components/multi-document/multi-document-input/form-multi-document.tsx +7 -0
- package/src/components/reference/cell-multi-reference-input.st.css.ts +2 -2
- package/src/components/reference/cell-reference-input.st.css.ts +2 -2
- package/src/components/rich-content/form-rich-content.tsx +24 -14
- package/src/components/rich-content/rich-content-input/default-value-input/rich-content-default-value-input.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css +15 -7
- package/src/components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css.ts +3 -3
- package/src/components/rich-content/rich-content-input/form-read-only-input/rich-content-form-read-only-input.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-common/fullscreen-modal/fullscreen-modal.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-common/publish-loader/publish-loader.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-common/toggle-fullscreen-button/toggle-fullscreen-button.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-editor/rich-content-editor.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-editor/rich-content-toolbar.st.css.ts +2 -2
- package/src/components/rich-content/rich-content-input/rich-content-viewer/rich-content-viewer.st.css.ts +2 -2
- package/src/components/rich-text/form-rich-text.tsx +18 -9
- package/src/components/rich-text/rich-text-input/rich-text-editor/rich-editor.st.css.ts +2 -2
- package/src/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css +32 -19
- package/src/components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css.ts +3 -3
- package/src/components/rich-text/rich-text-input/rich-text-editor/toolbar/toolbar.st.css.ts +2 -2
- package/src/components/text/text-view.st.css.ts +2 -2
- package/src/components/time-input/form-time.tsx +9 -3
- package/src/components/video/form-video.tsx +4 -2
- package/src/hooks/index.ts +3 -0
- package/src/hooks/pr-5746-kobiburnley-comments.md +54 -0
- package/src/hooks/use-field-ref.ts +65 -0
- package/src/hooks/use-merged-ref.ts +30 -0
- package/src/hooks/use-scroll-to-error-ref.ts +39 -0
- package/src/styles.global.css +1 -1
|
@@ -60,4 +60,26 @@ describe('FormAudio field', () => {
|
|
|
60
60
|
'cairo.fieldValidation.requiredField',
|
|
61
61
|
);
|
|
62
62
|
});
|
|
63
|
+
|
|
64
|
+
// Only the empty state can fail `required`, so its add button is where
|
|
65
|
+
// react-hook-form should land. Nothing focuses a field whose input never
|
|
66
|
+
// reached controller.field.ref.
|
|
67
|
+
it('focuses the add button when a required value blocks submit', async () => {
|
|
68
|
+
const field = makeField({
|
|
69
|
+
type: 'AUDIO',
|
|
70
|
+
validation: { required: true },
|
|
71
|
+
});
|
|
72
|
+
const driver = setup({ field });
|
|
73
|
+
|
|
74
|
+
await driver.submit();
|
|
75
|
+
|
|
76
|
+
const active = document.activeElement;
|
|
77
|
+
expect(active?.tagName).toBe('BUTTON');
|
|
78
|
+
expect(
|
|
79
|
+
document
|
|
80
|
+
.querySelector(`[data-hook="audio-field-${field.id}"]`)
|
|
81
|
+
?.contains(active),
|
|
82
|
+
).toBe(true);
|
|
83
|
+
});
|
|
84
|
+
|
|
63
85
|
});
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import '../../../testkit/test-polyfills';
|
|
2
2
|
|
|
3
|
+
import { act, createEvent, fireEvent } from '@testing-library/react';
|
|
4
|
+
|
|
3
5
|
import { FormColor } from '../../../components/color-view/form-color';
|
|
4
6
|
import { FormColorDriver } from '../../../components/color-view/form-color.driver';
|
|
5
7
|
import { FormFieldDriver, makeField } from '../../form-field.driver';
|
|
@@ -35,15 +37,56 @@ describe('FormColor field', () => {
|
|
|
35
37
|
expect(await driver.tk.getValue()).toBe('');
|
|
36
38
|
});
|
|
37
39
|
|
|
38
|
-
it('renders the
|
|
40
|
+
it('renders the FillPreview when no color is set and the field is at rest', async () => {
|
|
41
|
+
const driver = setup('');
|
|
42
|
+
|
|
43
|
+
expect(await driver.tk.hasFillPreview()).toBe(true);
|
|
44
|
+
expect(await driver.tk.hasFillButton()).toBe(false);
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
it('renders the FillButton once the input is focused with no color set', async () => {
|
|
39
48
|
const driver = setup('');
|
|
40
49
|
|
|
41
|
-
|
|
50
|
+
const input = document.querySelector('input')!;
|
|
51
|
+
await act(async () => {
|
|
52
|
+
input.focus();
|
|
53
|
+
fireEvent.focus(input);
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
expect(await driver.tk.hasFillButton()).toBe(true);
|
|
42
57
|
});
|
|
43
58
|
|
|
44
59
|
it('renders the FillPreview when a color is set', async () => {
|
|
45
60
|
const driver = setup('#FF5733');
|
|
46
61
|
|
|
47
|
-
expect(await driver.tk.
|
|
62
|
+
expect(await driver.tk.hasFillPreview()).toBe(true);
|
|
63
|
+
});
|
|
64
|
+
|
|
65
|
+
it('opens the color picker on the first press of the swatch', async () => {
|
|
66
|
+
const driver = setup('');
|
|
67
|
+
|
|
68
|
+
const swatch = document.querySelector<HTMLElement>(
|
|
69
|
+
'[data-hook="fill-preview-button"]',
|
|
70
|
+
)!;
|
|
71
|
+
|
|
72
|
+
await act(async () => {
|
|
73
|
+
// jsdom does not implement the browser's focus-on-mousedown default, so
|
|
74
|
+
// drive it here: the browser focuses the pressed button unless the
|
|
75
|
+
// handler prevents it. Without that guard the click sets `showPicker`,
|
|
76
|
+
// the swatch swaps to a FillButton, and the focused element is torn out
|
|
77
|
+
// from under the pointer.
|
|
78
|
+
const mouseDown = createEvent.mouseDown(swatch);
|
|
79
|
+
fireEvent(swatch, mouseDown);
|
|
80
|
+
if (!mouseDown.defaultPrevented) {
|
|
81
|
+
swatch.focus();
|
|
82
|
+
}
|
|
83
|
+
fireEvent.mouseUp(swatch);
|
|
84
|
+
fireEvent.click(swatch);
|
|
85
|
+
});
|
|
86
|
+
|
|
87
|
+
expect(await driver.tk.isPickerOpen()).toBe(true);
|
|
88
|
+
// The swatch has to survive its own click. WDS Popover reads a click whose
|
|
89
|
+
// target has been detached as a click outside itself and closes again.
|
|
90
|
+
expect(document.contains(swatch)).toBe(true);
|
|
48
91
|
});
|
|
49
92
|
});
|
|
@@ -51,4 +51,26 @@ describe('FormDocument field', () => {
|
|
|
51
51
|
'cairo.fieldValidation.requiredField',
|
|
52
52
|
);
|
|
53
53
|
});
|
|
54
|
+
|
|
55
|
+
// Only the empty state can fail `required`, so its add button is where
|
|
56
|
+
// react-hook-form should land. Nothing focuses a field whose input never
|
|
57
|
+
// reached controller.field.ref.
|
|
58
|
+
it('focuses the add button when a required value blocks submit', async () => {
|
|
59
|
+
const field = makeField({
|
|
60
|
+
type: 'DOCUMENT',
|
|
61
|
+
validation: { required: true },
|
|
62
|
+
});
|
|
63
|
+
const driver = setup({ field });
|
|
64
|
+
|
|
65
|
+
await driver.submit();
|
|
66
|
+
|
|
67
|
+
const active = document.activeElement;
|
|
68
|
+
expect(active?.tagName).toBe('BUTTON');
|
|
69
|
+
expect(
|
|
70
|
+
document
|
|
71
|
+
.querySelector(`[data-hook="document-field-${field.id}"]`)
|
|
72
|
+
?.contains(active),
|
|
73
|
+
).toBe(true);
|
|
74
|
+
});
|
|
75
|
+
|
|
54
76
|
});
|
|
@@ -72,4 +72,26 @@ describe('FormImageInput field', () => {
|
|
|
72
72
|
'cairo.fieldValidation.requiredField',
|
|
73
73
|
);
|
|
74
74
|
});
|
|
75
|
+
|
|
76
|
+
// Only the empty state can fail `required`, so its add button is where
|
|
77
|
+
// react-hook-form should land. Nothing focuses a field whose input never
|
|
78
|
+
// reached controller.field.ref.
|
|
79
|
+
it('focuses the add button when a required value blocks submit', async () => {
|
|
80
|
+
const field = makeField({
|
|
81
|
+
type: 'IMAGE',
|
|
82
|
+
validation: { required: true },
|
|
83
|
+
});
|
|
84
|
+
const driver = setup({ field });
|
|
85
|
+
|
|
86
|
+
await driver.submit();
|
|
87
|
+
|
|
88
|
+
const active = document.activeElement;
|
|
89
|
+
expect(active?.tagName).toBe('BUTTON');
|
|
90
|
+
expect(
|
|
91
|
+
document
|
|
92
|
+
.querySelector(`[data-hook="image-field-${field.id}"]`)
|
|
93
|
+
?.contains(active),
|
|
94
|
+
).toBe(true);
|
|
95
|
+
});
|
|
96
|
+
|
|
75
97
|
});
|
|
@@ -71,4 +71,25 @@ describe('FormMediaGallery field', () => {
|
|
|
71
71
|
|
|
72
72
|
expect(await driver.tk.hasError()).toBe(false);
|
|
73
73
|
});
|
|
74
|
+
|
|
75
|
+
// Only the empty state can fail `required`, so its add button is where
|
|
76
|
+
// react-hook-form should land. Nothing focuses a field whose input never
|
|
77
|
+
// reached controller.field.ref.
|
|
78
|
+
it('focuses the add button when a required value blocks submit', async () => {
|
|
79
|
+
const field = makeField({
|
|
80
|
+
type: 'MEDIA_GALLERY',
|
|
81
|
+
validation: { required: true },
|
|
82
|
+
});
|
|
83
|
+
const driver = setup({ field });
|
|
84
|
+
|
|
85
|
+
await driver.submit();
|
|
86
|
+
|
|
87
|
+
const active = document.activeElement;
|
|
88
|
+
expect(active?.tagName).toBe('BUTTON');
|
|
89
|
+
expect(
|
|
90
|
+
document
|
|
91
|
+
.querySelector(`[data-hook="media-gallery-field-${field.id}"]`)
|
|
92
|
+
?.contains(active),
|
|
93
|
+
).toBe(true);
|
|
94
|
+
});
|
|
74
95
|
});
|
|
@@ -57,4 +57,25 @@ describe('FormMultiDocument field', () => {
|
|
|
57
57
|
'cairo.fieldValidation.requiredField',
|
|
58
58
|
);
|
|
59
59
|
});
|
|
60
|
+
|
|
61
|
+
// Only the empty state can fail `required`, so its add button is where
|
|
62
|
+
// react-hook-form should land. Nothing focuses a field whose input never
|
|
63
|
+
// reached controller.field.ref.
|
|
64
|
+
it('focuses the add button when a required value blocks submit', async () => {
|
|
65
|
+
const field = makeField({
|
|
66
|
+
type: 'MULTI_DOCUMENT',
|
|
67
|
+
validation: { required: true },
|
|
68
|
+
});
|
|
69
|
+
const driver = setup({ field });
|
|
70
|
+
|
|
71
|
+
await driver.submit();
|
|
72
|
+
|
|
73
|
+
const active = document.activeElement;
|
|
74
|
+
expect(active?.tagName).toBe('BUTTON');
|
|
75
|
+
expect(
|
|
76
|
+
document
|
|
77
|
+
.querySelector(`[data-hook="multi-document-field-${field.id}"]`)
|
|
78
|
+
?.contains(active),
|
|
79
|
+
).toBe(true);
|
|
80
|
+
});
|
|
60
81
|
});
|
|
@@ -77,4 +77,26 @@ describe('FormRichContent field', () => {
|
|
|
77
77
|
'cairo.fieldValidation.requiredField',
|
|
78
78
|
);
|
|
79
79
|
});
|
|
80
|
+
|
|
81
|
+
// Ricos is lazy and renders no editable node here, so there is nothing to
|
|
82
|
+
// focus — the wrapper still has to bring the field into view. Without the
|
|
83
|
+
// ref registered, react-hook-form calls nothing at all.
|
|
84
|
+
it('brings the field into view when a required value blocks submit', async () => {
|
|
85
|
+
const scrollIntoView = jest.fn();
|
|
86
|
+
// Not implemented in jsdom.
|
|
87
|
+
Element.prototype.scrollIntoView = scrollIntoView;
|
|
88
|
+
|
|
89
|
+
const field = makeField({
|
|
90
|
+
type: 'RICH_CONTENT',
|
|
91
|
+
validation: { required: true },
|
|
92
|
+
});
|
|
93
|
+
const driver = setup({ field, initialValue: '' });
|
|
94
|
+
|
|
95
|
+
await driver.submit();
|
|
96
|
+
|
|
97
|
+
expect(scrollIntoView).toHaveBeenCalled();
|
|
98
|
+
|
|
99
|
+
delete (Element.prototype as Partial<Element>).scrollIntoView;
|
|
100
|
+
});
|
|
101
|
+
|
|
80
102
|
});
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import fs from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
|
|
4
|
+
// CAIRO-4561: both editors rendered with no border at all. The rules were
|
|
5
|
+
// there, but they read `var(--wds-color-blue-300)` with no fallback, and a
|
|
6
|
+
// custom property that resolves to nothing makes the whole declaration invalid
|
|
7
|
+
// — so the border was dropped rather than falling back to a default. WDS Input
|
|
8
|
+
// spells every one of these as `var(--token, var(--wsr-token, #literal))`.
|
|
9
|
+
const STYLESHEETS = [
|
|
10
|
+
'components/rich-text/rich-text-input/rich-text-editor/rich-text-editor.st.css',
|
|
11
|
+
'components/rich-content/rich-content-input/form-input/rich-content-form-input.st.css',
|
|
12
|
+
];
|
|
13
|
+
|
|
14
|
+
const read = (relative: string) =>
|
|
15
|
+
fs.readFileSync(path.join(__dirname, '../../', relative), 'utf8');
|
|
16
|
+
|
|
17
|
+
/** Every declaration whose property is border-ish or a shadow. */
|
|
18
|
+
const borderDeclarations = (css: string) =>
|
|
19
|
+
css
|
|
20
|
+
.split(/[;{}]/)
|
|
21
|
+
.map((chunk) => chunk.trim())
|
|
22
|
+
.filter((chunk) => /^(border[\w-]*|box-shadow)\s*:/.test(chunk));
|
|
23
|
+
|
|
24
|
+
describe('rich editor borders', () => {
|
|
25
|
+
it.each(STYLESHEETS)('declares a visible border in %s', (relative) => {
|
|
26
|
+
const declarations = borderDeclarations(read(relative));
|
|
27
|
+
|
|
28
|
+
expect(
|
|
29
|
+
declarations.some((d) => d.includes('var(--wds-input-border-color,')),
|
|
30
|
+
).toBe(true);
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
it.each(STYLESHEETS)(
|
|
34
|
+
'gives every custom property in a border declaration a fallback in %s',
|
|
35
|
+
(relative) => {
|
|
36
|
+
const withoutFallback = borderDeclarations(read(relative)).filter((d) =>
|
|
37
|
+
Array.from(d.matchAll(/var\(\s*(--[\w-]+)\s*([,)])/g)).some(
|
|
38
|
+
([, , delimiter]) => delimiter === ')',
|
|
39
|
+
),
|
|
40
|
+
);
|
|
41
|
+
|
|
42
|
+
expect(withoutFallback).toEqual([]);
|
|
43
|
+
},
|
|
44
|
+
);
|
|
45
|
+
});
|
|
@@ -76,4 +76,22 @@ describe('FormRichText field', () => {
|
|
|
76
76
|
'cairo.fieldValidation.requiredField',
|
|
77
77
|
);
|
|
78
78
|
});
|
|
79
|
+
|
|
80
|
+
// The editor exposes no focus handle, so react-hook-form gets a wrapper
|
|
81
|
+
// whose focus() brings the field into view and then focuses the editor if
|
|
82
|
+
// it has rendered. Nothing happens at all when the ref is not registered.
|
|
83
|
+
it('focuses the editor when a required value blocks submit', async () => {
|
|
84
|
+
const field = makeField({
|
|
85
|
+
type: 'RICH_TEXT',
|
|
86
|
+
validation: { required: true },
|
|
87
|
+
});
|
|
88
|
+
const driver = setup({ field, initialValue: '' });
|
|
89
|
+
|
|
90
|
+
await driver.submit();
|
|
91
|
+
|
|
92
|
+
const editable = document.querySelector('[contenteditable]');
|
|
93
|
+
expect(editable).toBeTruthy();
|
|
94
|
+
expect(document.activeElement).toBe(editable);
|
|
95
|
+
});
|
|
96
|
+
|
|
79
97
|
});
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
import '../../testkit/test-polyfills';
|
|
2
|
+
|
|
3
|
+
import React from 'react';
|
|
4
|
+
import { act, render } from '@testing-library/react';
|
|
5
|
+
import type { Field } from '@wix/bex-core';
|
|
6
|
+
import { useForm } from '@wix/bex-core/form';
|
|
7
|
+
import type { Control, FieldValues } from '@wix/bex-core/form';
|
|
8
|
+
|
|
9
|
+
import { PatternsFieldsTestProvider } from '../../testkit/patterns-fields-test-provider';
|
|
10
|
+
import { FormAddress } from '../../components/address/form-address';
|
|
11
|
+
import { FormTime } from '../../components/time-input/form-time';
|
|
12
|
+
import { FormDocument } from '../../components/document/form-document';
|
|
13
|
+
import { FormImageInput } from '../../components/image/form-image-input';
|
|
14
|
+
import { fieldRefHandle } from '../../hooks';
|
|
15
|
+
|
|
16
|
+
interface Case {
|
|
17
|
+
name: string;
|
|
18
|
+
Component: React.ComponentType<any>;
|
|
19
|
+
field: Field;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
const field = (id: string, type: string): Field =>
|
|
23
|
+
({
|
|
24
|
+
id,
|
|
25
|
+
displayName: id,
|
|
26
|
+
type,
|
|
27
|
+
validation: { required: true },
|
|
28
|
+
} as Field);
|
|
29
|
+
|
|
30
|
+
// Every control here answers focus() and nothing else, which is the shape that
|
|
31
|
+
// used to make setFocus with shouldSelect throw.
|
|
32
|
+
const CASES: Case[] = [
|
|
33
|
+
// AddressInputImperativeHandle: { focus, clear }
|
|
34
|
+
{
|
|
35
|
+
name: 'FormAddress',
|
|
36
|
+
Component: FormAddress,
|
|
37
|
+
field: field('location', 'ADDRESS'),
|
|
38
|
+
},
|
|
39
|
+
// TimeInputImperativeActions: no select()
|
|
40
|
+
{ name: 'FormTime', Component: FormTime, field: field('start', 'TIME') },
|
|
41
|
+
// AddItemActions: { blur, focus }. Shared with audio, multi-document and
|
|
42
|
+
// media-gallery, so one of the four covers that shape.
|
|
43
|
+
{
|
|
44
|
+
name: 'FormDocument',
|
|
45
|
+
Component: FormDocument,
|
|
46
|
+
field: field('spec', 'DOCUMENT'),
|
|
47
|
+
},
|
|
48
|
+
// ImageViewer instance, shared with video.
|
|
49
|
+
{
|
|
50
|
+
name: 'FormImageInput',
|
|
51
|
+
Component: FormImageInput,
|
|
52
|
+
field: field('cover', 'IMAGE'),
|
|
53
|
+
},
|
|
54
|
+
];
|
|
55
|
+
|
|
56
|
+
describe('fieldRefHandle', () => {
|
|
57
|
+
it('sends focus to the given callback', () => {
|
|
58
|
+
const focus = jest.fn();
|
|
59
|
+
|
|
60
|
+
fieldRefHandle(focus, () => undefined).focus();
|
|
61
|
+
|
|
62
|
+
expect(focus).toHaveBeenCalled();
|
|
63
|
+
});
|
|
64
|
+
|
|
65
|
+
// The whole point: a control with only focus() must not make the other
|
|
66
|
+
// calls blow up, because react-hook-form makes them unconditionally.
|
|
67
|
+
it('absorbs the calls a focus-only control cannot answer', () => {
|
|
68
|
+
const handle = fieldRefHandle(
|
|
69
|
+
() => {},
|
|
70
|
+
() => ({ focus: () => {} }),
|
|
71
|
+
);
|
|
72
|
+
|
|
73
|
+
expect(() => handle.select()).not.toThrow();
|
|
74
|
+
expect(() => handle.setCustomValidity('nope')).not.toThrow();
|
|
75
|
+
expect(handle.reportValidity()).toBe(true);
|
|
76
|
+
});
|
|
77
|
+
|
|
78
|
+
it('passes the calls on to a control that does answer them', () => {
|
|
79
|
+
const control = {
|
|
80
|
+
focus: jest.fn(),
|
|
81
|
+
select: jest.fn(),
|
|
82
|
+
setCustomValidity: jest.fn(),
|
|
83
|
+
reportValidity: jest.fn().mockReturnValue(false),
|
|
84
|
+
};
|
|
85
|
+
const handle = fieldRefHandle(control.focus, () => control);
|
|
86
|
+
|
|
87
|
+
handle.select();
|
|
88
|
+
handle.setCustomValidity('bad');
|
|
89
|
+
|
|
90
|
+
expect(control.select).toHaveBeenCalled();
|
|
91
|
+
expect(control.setCustomValidity).toHaveBeenCalledWith('bad');
|
|
92
|
+
expect(handle.reportValidity()).toBe(false);
|
|
93
|
+
});
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
describe.each(CASES)(
|
|
97
|
+
'$name, whose control only has focus',
|
|
98
|
+
({ Component, field: f }) => {
|
|
99
|
+
let form: ReturnType<typeof useForm<FieldValues>> | undefined;
|
|
100
|
+
|
|
101
|
+
const Harness = () => {
|
|
102
|
+
const methods = useForm<FieldValues>({ mode: 'onChange' });
|
|
103
|
+
form = methods;
|
|
104
|
+
return (
|
|
105
|
+
<Component
|
|
106
|
+
field={f}
|
|
107
|
+
value={undefined as never}
|
|
108
|
+
onChange={() => {}}
|
|
109
|
+
dataHook={`${f.id}-field`}
|
|
110
|
+
formControl={methods.control as Control<FieldValues>}
|
|
111
|
+
data={{}}
|
|
112
|
+
/>
|
|
113
|
+
);
|
|
114
|
+
};
|
|
115
|
+
|
|
116
|
+
// react-hook-form reaches select() through the handle it wraps around
|
|
117
|
+
// whatever was registered, so a focus-only control used to throw here.
|
|
118
|
+
it('survives setFocus with shouldSelect', () => {
|
|
119
|
+
render(
|
|
120
|
+
<PatternsFieldsTestProvider>
|
|
121
|
+
<Harness />
|
|
122
|
+
</PatternsFieldsTestProvider>,
|
|
123
|
+
);
|
|
124
|
+
|
|
125
|
+
expect(() =>
|
|
126
|
+
act(() => {
|
|
127
|
+
form!.setFocus(f.id, { shouldSelect: true });
|
|
128
|
+
}),
|
|
129
|
+
).not.toThrow();
|
|
130
|
+
});
|
|
131
|
+
},
|
|
132
|
+
);
|
|
@@ -9,6 +9,7 @@ import type { Address } from '../../types/address';
|
|
|
9
9
|
import { isEmpty } from '../../validations/value';
|
|
10
10
|
|
|
11
11
|
import { FormAddressInput } from './input/form-address-input';
|
|
12
|
+
import { useFieldRef } from '../../hooks';
|
|
12
13
|
|
|
13
14
|
export interface FormAddressProps extends BaseInputProps<Address> {}
|
|
14
15
|
|
|
@@ -31,6 +32,8 @@ const _FormAddress = (props: FormAddressProps) => {
|
|
|
31
32
|
},
|
|
32
33
|
});
|
|
33
34
|
|
|
35
|
+
const setFieldRef = useFieldRef(controller.field.ref);
|
|
36
|
+
|
|
34
37
|
return (
|
|
35
38
|
<FormField
|
|
36
39
|
label={field.displayName}
|
|
@@ -45,7 +48,7 @@ const _FormAddress = (props: FormAddressProps) => {
|
|
|
45
48
|
onChange={(value) => controller.field.onChange?.(value)}
|
|
46
49
|
// Hand the input to react-hook-form so shouldFocusError scrolls to +
|
|
47
50
|
// focuses this field when it blocks save.
|
|
48
|
-
inputRef={
|
|
51
|
+
inputRef={setFieldRef}
|
|
49
52
|
dataHook={`address-${field.id}`}
|
|
50
53
|
field={field.id}
|
|
51
54
|
/>
|
|
@@ -5,7 +5,7 @@ import { classesRuntime, statesRuntime } from "../../../stylable-esm-runtime.js"
|
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
var _namespace_ = "
|
|
8
|
+
var _namespace_ = "addressinput517975534";
|
|
9
9
|
var _style_ = classesRuntime.bind(null, _namespace_);
|
|
10
10
|
|
|
11
11
|
export var cssStates = statesRuntime.bind(null, _namespace_);
|
|
@@ -13,7 +13,7 @@ export var style: import("@stylable/runtime").STFunction = _style_;
|
|
|
13
13
|
export var st: import("@stylable/runtime").STFunction = _style_;
|
|
14
14
|
|
|
15
15
|
export var namespace = _namespace_;
|
|
16
|
-
export var classes = {"root":"
|
|
16
|
+
export var classes = {"root":"addressinput517975534__root","tableAddressInput":"addressinput517975534__tableAddressInput"};
|
|
17
17
|
export var keyframes = {};
|
|
18
18
|
export var layers = {};
|
|
19
19
|
export var containers = {};
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import React
|
|
1
|
+
import React from 'react';
|
|
2
2
|
|
|
3
3
|
import type { Address } from '../../../types/address';
|
|
4
4
|
import type { FormInputProps } from '../../../types/form-input';
|
|
5
5
|
import { Z_INDEX_MODAL_POPOVER } from '../../common';
|
|
6
|
-
import { useAutoFocus } from '../../../hooks';
|
|
6
|
+
import { useAutoFocus, useMergedRef } from '../../../hooks';
|
|
7
7
|
|
|
8
8
|
import type { AddressInputImperativeHandle } from './address-input';
|
|
9
9
|
import { AddressInput } from './address-input';
|
|
@@ -25,28 +25,13 @@ export const FormAddressInput: React.FC<FormAddressInputProps> = ({
|
|
|
25
25
|
dataHook,
|
|
26
26
|
inputRef: forwardedRef,
|
|
27
27
|
}) => {
|
|
28
|
-
const inputRef =
|
|
28
|
+
const [inputRef, setInputRef] =
|
|
29
|
+
useMergedRef<AddressInputImperativeHandle>(forwardedRef);
|
|
29
30
|
useAutoFocus(inputRef, autoFocus);
|
|
30
31
|
|
|
31
|
-
// autoFocus reads the handle from here, so a caller's ref has to be filled
|
|
32
|
-
// alongside it rather than replacing it.
|
|
33
|
-
const setRef = useCallback(
|
|
34
|
-
(handle: AddressInputImperativeHandle | null) => {
|
|
35
|
-
inputRef.current = handle;
|
|
36
|
-
if (typeof forwardedRef === 'function') {
|
|
37
|
-
forwardedRef(handle);
|
|
38
|
-
} else if (forwardedRef) {
|
|
39
|
-
(
|
|
40
|
-
forwardedRef as React.MutableRefObject<AddressInputImperativeHandle | null>
|
|
41
|
-
).current = handle;
|
|
42
|
-
}
|
|
43
|
-
},
|
|
44
|
-
[forwardedRef],
|
|
45
|
-
);
|
|
46
|
-
|
|
47
32
|
return (
|
|
48
33
|
<AddressInput
|
|
49
|
-
ref={
|
|
34
|
+
ref={setInputRef}
|
|
50
35
|
dataHook={dataHook}
|
|
51
36
|
value={data}
|
|
52
37
|
onChange={onChange}
|
|
@@ -5,7 +5,7 @@ import { classesRuntime, statesRuntime } from "../../../../stylable-esm-runtime.
|
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
var _namespace_ = "
|
|
8
|
+
var _namespace_ = "actionsmenu425944360";
|
|
9
9
|
var _style_ = classesRuntime.bind(null, _namespace_);
|
|
10
10
|
|
|
11
11
|
export var cssStates = statesRuntime.bind(null, _namespace_);
|
|
@@ -13,7 +13,7 @@ export var style: import("@stylable/runtime").STFunction = _style_;
|
|
|
13
13
|
export var st: import("@stylable/runtime").STFunction = _style_;
|
|
14
14
|
|
|
15
15
|
export var namespace = _namespace_;
|
|
16
|
-
export var classes = {"root":"
|
|
16
|
+
export var classes = {"root":"actionsmenu425944360__root","action":"actionsmenu425944360__action"};
|
|
17
17
|
export var keyframes = {};
|
|
18
18
|
export var layers = {};
|
|
19
19
|
export var containers = {};
|
|
@@ -5,7 +5,7 @@ import { classesRuntime, statesRuntime } from "../../../stylable-esm-runtime.js"
|
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
var _namespace_ = "
|
|
8
|
+
var _namespace_ = "formaudiofield4018066963";
|
|
9
9
|
var _style_ = classesRuntime.bind(null, _namespace_);
|
|
10
10
|
|
|
11
11
|
export var cssStates = statesRuntime.bind(null, _namespace_);
|
|
@@ -13,7 +13,7 @@ export var style: import("@stylable/runtime").STFunction = _style_;
|
|
|
13
13
|
export var st: import("@stylable/runtime").STFunction = _style_;
|
|
14
14
|
|
|
15
15
|
export var namespace = _namespace_;
|
|
16
|
-
export var classes = {"root":"
|
|
16
|
+
export var classes = {"root":"formaudiofield4018066963__root","addItem":"formaudiofield4018066963__addItem","mediaTitle":"formaudiofield4018066963__mediaTitle"};
|
|
17
17
|
export var keyframes = {};
|
|
18
18
|
export var layers = {};
|
|
19
19
|
export var containers = {};
|
|
@@ -5,7 +5,7 @@ import { getMediaURL } from '../../../auto-field-types';
|
|
|
5
5
|
import type { AddItemActions } from '@wix/design-system';
|
|
6
6
|
import { AddItem, AudioPlayer, Box, Text } from '@wix/design-system';
|
|
7
7
|
|
|
8
|
-
import { useTranslations, useWithCallback } from '../../../hooks';
|
|
8
|
+
import { useMergedRef, useTranslations, useWithCallback } from '../../../hooks';
|
|
9
9
|
import { getMediaTitle, MEDIA_TYPES } from '../../../utils';
|
|
10
10
|
|
|
11
11
|
import { Z_INDEX_MODAL_POPOVER } from '../../common';
|
|
@@ -26,13 +26,14 @@ export const FormAudioField: FC<FormMediaControlProps> = ({
|
|
|
26
26
|
readOnly,
|
|
27
27
|
invalid,
|
|
28
28
|
dataHook,
|
|
29
|
+
inputRef: forwardedRef,
|
|
29
30
|
}) => {
|
|
30
31
|
const { t } = useTranslations();
|
|
31
32
|
|
|
32
33
|
const onChange = useWithCallback(onChangeAudio, onInput);
|
|
33
34
|
const onClear = useWithCallback(onClearAudio, onInput);
|
|
34
35
|
|
|
35
|
-
const inputRef =
|
|
36
|
+
const [inputRef, setInputRef] = useMergedRef<AddItemActions>(forwardedRef);
|
|
36
37
|
const viewRef = useRef<HTMLDivElement>(null);
|
|
37
38
|
|
|
38
39
|
const { callMedia, onMediaLoad, downloadMedia, loading } = useMediaControl({
|
|
@@ -91,7 +92,7 @@ export const FormAudioField: FC<FormMediaControlProps> = ({
|
|
|
91
92
|
if (!data) {
|
|
92
93
|
return (
|
|
93
94
|
<AddItem
|
|
94
|
-
ref={
|
|
95
|
+
ref={setInputRef}
|
|
95
96
|
dataHook={dataHook}
|
|
96
97
|
className={style(classes.addItem, {
|
|
97
98
|
disabled: !!readOnly,
|
|
@@ -7,6 +7,7 @@ import { useController } from '@wix/bex-core/form';
|
|
|
7
7
|
import { BaseInputProps } from '../../../types/base-input';
|
|
8
8
|
import { isEmpty } from '../../../validations/string';
|
|
9
9
|
import { FormAudioField } from './form-audio-field';
|
|
10
|
+
import { useFieldRef } from '../../../hooks';
|
|
10
11
|
|
|
11
12
|
export interface FormAudioProps extends BaseInputProps<string> {}
|
|
12
13
|
|
|
@@ -30,6 +31,8 @@ const _FormAudio = (props: FormAudioProps) => {
|
|
|
30
31
|
},
|
|
31
32
|
});
|
|
32
33
|
|
|
34
|
+
const setFieldRef = useFieldRef(controller.field.ref);
|
|
35
|
+
|
|
33
36
|
return (
|
|
34
37
|
<FormField
|
|
35
38
|
label={field.displayName}
|
|
@@ -39,6 +42,10 @@ const _FormAudio = (props: FormAudioProps) => {
|
|
|
39
42
|
dataHook={dataHook}
|
|
40
43
|
>
|
|
41
44
|
<FormAudioField
|
|
45
|
+
// Hand the add button to react-hook-form so
|
|
46
|
+
// shouldFocusError scrolls to + focuses this field when it
|
|
47
|
+
// blocks save.
|
|
48
|
+
inputRef={setFieldRef}
|
|
42
49
|
data={controller.field.value}
|
|
43
50
|
onChange={(value) => controller.field.onChange(value)}
|
|
44
51
|
onClear={() => controller.field.onChange(null)}
|
|
@@ -5,7 +5,7 @@ import { classesRuntime, statesRuntime } from "../../../stylable-esm-runtime.js"
|
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
var _namespace_ = "
|
|
8
|
+
var _namespace_ = "audioplayer1561698613";
|
|
9
9
|
var _style_ = classesRuntime.bind(null, _namespace_);
|
|
10
10
|
|
|
11
11
|
export var cssStates = statesRuntime.bind(null, _namespace_);
|
|
@@ -13,7 +13,7 @@ export var style: import("@stylable/runtime").STFunction = _style_;
|
|
|
13
13
|
export var st: import("@stylable/runtime").STFunction = _style_;
|
|
14
14
|
|
|
15
15
|
export var namespace = _namespace_;
|
|
16
|
-
export var classes = {"root":"
|
|
16
|
+
export var classes = {"root":"audioplayer1561698613__root"};
|
|
17
17
|
export var keyframes = {};
|
|
18
18
|
export var layers = {};
|
|
19
19
|
export var containers = {};
|
|
@@ -5,7 +5,7 @@ import { classesRuntime, statesRuntime } from "../../stylable-esm-runtime.js";
|
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
8
|
-
var _namespace_ = "
|
|
8
|
+
var _namespace_ = "cellcolorview1736640766";
|
|
9
9
|
var _style_ = classesRuntime.bind(null, _namespace_);
|
|
10
10
|
|
|
11
11
|
export var cssStates = statesRuntime.bind(null, _namespace_);
|
|
@@ -13,7 +13,7 @@ export var style: import("@stylable/runtime").STFunction = _style_;
|
|
|
13
13
|
export var st: import("@stylable/runtime").STFunction = _style_;
|
|
14
14
|
|
|
15
15
|
export var namespace = _namespace_;
|
|
16
|
-
export var classes = {"root":"
|
|
16
|
+
export var classes = {"root":"cellcolorview1736640766__root","hashPrefix":"cellcolorview1736640766__hashPrefix"};
|
|
17
17
|
export var keyframes = {};
|
|
18
18
|
export var layers = {};
|
|
19
19
|
export var containers = {};
|