@expressivecss/expressive 0.16.0 → 0.17.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/CHANGELOG.md +306 -1
- package/README.md +1 -1
- package/dist/css/expressive.css +540 -646
- package/dist/css/expressive.css.map +1 -1
- package/dist/css/expressive.min.css +1 -1
- package/dist/css/expressive.min.css.map +1 -1
- package/dist/js/chunks/{chunk-PA7NU5AK.mjs → chunk-26VUH75M.mjs} +6 -3
- package/dist/js/chunks/chunk-26VUH75M.mjs.map +7 -0
- package/dist/js/chunks/{chunk-NBJAUGPP.mjs → chunk-2LFCOGC3.mjs} +12 -23
- package/dist/js/chunks/chunk-2LFCOGC3.mjs.map +7 -0
- package/dist/js/chunks/{chunk-OP43LLIC.mjs → chunk-36GELQGX.mjs} +4 -4
- package/dist/js/chunks/{chunk-OP43LLIC.mjs.map → chunk-36GELQGX.mjs.map} +2 -2
- package/dist/js/chunks/{chunk-EC26RU2D.mjs → chunk-3FKWIRHW.mjs} +6 -2
- package/dist/js/chunks/chunk-3FKWIRHW.mjs.map +7 -0
- package/dist/js/chunks/{chunk-Y6H2X7ZC.mjs → chunk-3KF65KGL.mjs} +3 -3
- package/dist/js/chunks/{chunk-4QUCNFSD.mjs → chunk-3KLZRQZI.mjs} +31 -10
- package/dist/js/chunks/chunk-3KLZRQZI.mjs.map +7 -0
- package/dist/js/chunks/{chunk-75E5EDJF.mjs → chunk-3XORNED5.mjs} +2 -2
- package/dist/js/chunks/{chunk-NNHVANQA.mjs → chunk-4WBGAQN3.mjs} +3 -3
- package/dist/js/chunks/{chunk-ZJNLAGY5.mjs → chunk-5F4URJHL.mjs} +2 -2
- package/dist/js/chunks/{chunk-ZVLOUDIJ.mjs → chunk-67UNY7RH.mjs} +50 -2
- package/dist/js/chunks/chunk-67UNY7RH.mjs.map +7 -0
- package/dist/js/chunks/{chunk-P6DRQ6KS.mjs → chunk-7CXNATJS.mjs} +6 -5
- package/dist/js/chunks/chunk-7CXNATJS.mjs.map +7 -0
- package/dist/js/chunks/{chunk-4TRZ2AER.mjs → chunk-7X44MKEQ.mjs} +15 -14
- package/dist/js/chunks/chunk-7X44MKEQ.mjs.map +7 -0
- package/dist/js/chunks/{chunk-GWZ76SR4.mjs → chunk-7ZAMOMGY.mjs} +12 -7
- package/dist/js/chunks/chunk-7ZAMOMGY.mjs.map +7 -0
- package/dist/js/chunks/{chunk-GVZQH2H5.mjs → chunk-AEG6LOAJ.mjs} +2 -2
- package/dist/js/chunks/{chunk-Y6TLRA3U.mjs → chunk-AQNFCJJ5.mjs} +27 -21
- package/dist/js/chunks/chunk-AQNFCJJ5.mjs.map +7 -0
- package/dist/js/chunks/{chunk-OUCHKSAW.mjs → chunk-B55LWKBM.mjs} +16 -4
- package/dist/js/chunks/chunk-B55LWKBM.mjs.map +7 -0
- package/dist/js/chunks/{chunk-AI73GJKG.mjs → chunk-BB5VXYXT.mjs} +2 -2
- package/dist/js/chunks/{chunk-2RLBDFH4.mjs → chunk-BDATLH3H.mjs} +4 -4
- package/dist/js/chunks/{chunk-2CS6TITK.mjs → chunk-CWMQOT4O.mjs} +23 -10
- package/dist/js/chunks/chunk-CWMQOT4O.mjs.map +7 -0
- package/dist/js/chunks/{chunk-ZKWUWBUB.mjs → chunk-CY2CTOVM.mjs} +2 -2
- package/dist/js/chunks/{chunk-CSYWKEK3.mjs → chunk-DWA5UYLJ.mjs} +58 -27
- package/dist/js/chunks/chunk-DWA5UYLJ.mjs.map +7 -0
- package/dist/js/chunks/{chunk-CMGXGYUC.mjs → chunk-EB2V4OKL.mjs} +14 -9
- package/dist/js/chunks/chunk-EB2V4OKL.mjs.map +7 -0
- package/dist/js/chunks/{chunk-Z4GICXR2.mjs → chunk-EWO662ZC.mjs} +5 -7
- package/dist/js/chunks/chunk-EWO662ZC.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VGY4M57S.mjs → chunk-F7LAKFMX.mjs} +67 -34
- package/dist/js/chunks/chunk-F7LAKFMX.mjs.map +7 -0
- package/dist/js/chunks/{chunk-67ZPPKXS.mjs → chunk-FNIIH2LU.mjs} +3 -3
- package/dist/js/chunks/chunk-GE3YMFS6.mjs +15 -0
- package/dist/js/chunks/chunk-GE3YMFS6.mjs.map +7 -0
- package/dist/js/chunks/{chunk-DZYVU75J.mjs → chunk-GFWYMWYN.mjs} +18 -14
- package/dist/js/chunks/chunk-GFWYMWYN.mjs.map +7 -0
- package/dist/js/chunks/{chunk-3L3QIYLC.mjs → chunk-H5ISU45X.mjs} +8 -6
- package/dist/js/chunks/chunk-H5ISU45X.mjs.map +7 -0
- package/dist/js/chunks/{chunk-QXKWVHBD.mjs → chunk-H6YIKFAQ.mjs} +67 -46
- package/dist/js/chunks/chunk-H6YIKFAQ.mjs.map +7 -0
- package/dist/js/chunks/{chunk-KZPSAXIU.mjs → chunk-HEH7E3KO.mjs} +22 -12
- package/dist/js/chunks/chunk-HEH7E3KO.mjs.map +7 -0
- package/dist/js/chunks/{chunk-T3BNSRP3.mjs → chunk-HQRLBTNM.mjs} +3 -3
- package/dist/js/chunks/{chunk-NAC72P7R.mjs → chunk-I2F7MLUU.mjs} +2 -2
- package/dist/js/chunks/{chunk-ZM3XBHWV.mjs → chunk-IQOTGGHX.mjs} +86 -35
- package/dist/js/chunks/chunk-IQOTGGHX.mjs.map +7 -0
- package/dist/js/chunks/{chunk-QACZ6TUP.mjs → chunk-JH3YWKA6.mjs} +5 -4
- package/dist/js/chunks/chunk-JH3YWKA6.mjs.map +7 -0
- package/dist/js/chunks/chunk-JOLJAYIJ.mjs +7 -0
- package/dist/js/chunks/{chunk-4IKVPCSU.mjs.map → chunk-JOLJAYIJ.mjs.map} +1 -1
- package/dist/js/chunks/{chunk-BPF3I2MN.mjs → chunk-KOTGMCMI.mjs} +9 -2
- package/dist/js/chunks/chunk-KOTGMCMI.mjs.map +7 -0
- package/dist/js/chunks/{chunk-ANKFWNWT.mjs → chunk-LC4O5LFS.mjs} +3 -3
- package/dist/js/chunks/{chunk-4PIXLDNJ.mjs → chunk-LEF33SCP.mjs} +2 -2
- package/dist/js/chunks/{chunk-ILDRRG7T.mjs → chunk-LFORZRPH.mjs} +3 -3
- package/dist/js/chunks/{chunk-Z4OARDZ7.mjs → chunk-LWLNV5EC.mjs} +26 -17
- package/dist/js/chunks/chunk-LWLNV5EC.mjs.map +7 -0
- package/dist/js/chunks/{chunk-WU7XJ4RR.mjs → chunk-LXRHUQAX.mjs} +66 -25
- package/dist/js/chunks/chunk-LXRHUQAX.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VMY55K2X.mjs → chunk-MA2SZZFB.mjs} +11 -7
- package/dist/js/chunks/chunk-MA2SZZFB.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VJVQIXHC.mjs → chunk-MDBZAMIV.mjs} +8 -10
- package/dist/js/chunks/chunk-MDBZAMIV.mjs.map +7 -0
- package/dist/js/chunks/{chunk-4EWGD4V2.mjs → chunk-NODZ5VAD.mjs} +2 -2
- package/dist/js/chunks/{chunk-UGJHCHXG.mjs → chunk-O2WJB6TH.mjs} +79 -55
- package/dist/js/chunks/chunk-O2WJB6TH.mjs.map +7 -0
- package/dist/js/chunks/{chunk-7YZ5CN3V.mjs → chunk-PCABY5BN.mjs} +5 -3
- package/dist/js/chunks/chunk-PCABY5BN.mjs.map +7 -0
- package/dist/js/chunks/{chunk-X7SDA2J5.mjs → chunk-PWKYVMND.mjs} +9 -5
- package/dist/js/chunks/{chunk-X7SDA2J5.mjs.map → chunk-PWKYVMND.mjs.map} +2 -2
- package/dist/js/chunks/{chunk-SPPHF7YZ.mjs → chunk-QHZZT7YO.mjs} +35 -14
- package/dist/js/chunks/chunk-QHZZT7YO.mjs.map +7 -0
- package/dist/js/chunks/{chunk-LDXCC2L3.mjs → chunk-QND56EW2.mjs} +5 -4
- package/dist/js/chunks/chunk-QND56EW2.mjs.map +7 -0
- package/dist/js/chunks/{chunk-NVQ5EHCU.mjs → chunk-QNODAANY.mjs} +4 -4
- package/dist/js/chunks/{chunk-7NLUI3RR.mjs → chunk-QRO5FV3I.mjs} +23 -13
- package/dist/js/chunks/chunk-QRO5FV3I.mjs.map +7 -0
- package/dist/js/chunks/{chunk-FCNF4GRJ.mjs → chunk-R7A7JRC5.mjs} +6 -11
- package/dist/js/chunks/chunk-R7A7JRC5.mjs.map +7 -0
- package/dist/js/chunks/{chunk-S23RJ3XY.mjs → chunk-RKG2CBFE.mjs} +4 -16
- package/dist/js/chunks/chunk-RKG2CBFE.mjs.map +7 -0
- package/dist/js/chunks/{chunk-6FSEUFVW.mjs → chunk-RSNS5OYS.mjs} +6 -6
- package/dist/js/chunks/chunk-RSNS5OYS.mjs.map +7 -0
- package/dist/js/chunks/{chunk-ROH2HDB4.mjs → chunk-RUDYMEJ3.mjs} +2 -2
- package/dist/js/chunks/{chunk-BIGU5RCJ.mjs → chunk-STJR62SU.mjs} +13 -5
- package/dist/js/chunks/chunk-STJR62SU.mjs.map +7 -0
- package/dist/js/chunks/{chunk-752ADW4M.mjs → chunk-SUSD4UTN.mjs} +27 -32
- package/dist/js/chunks/chunk-SUSD4UTN.mjs.map +7 -0
- package/dist/js/chunks/{chunk-B7DQFHA5.mjs → chunk-SYBOA5HC.mjs} +7 -12
- package/dist/js/chunks/chunk-SYBOA5HC.mjs.map +7 -0
- package/dist/js/chunks/{chunk-TFABTUAZ.mjs → chunk-T4MOBP3J.mjs} +2 -2
- package/dist/js/chunks/{chunk-GCWWEZKO.mjs → chunk-TM7HPGTV.mjs} +3 -3
- package/dist/js/chunks/{chunk-5KIHWJI2.mjs → chunk-TMQDZSDC.mjs} +34 -12
- package/dist/js/chunks/chunk-TMQDZSDC.mjs.map +7 -0
- package/dist/js/chunks/{chunk-ZO6ZLHFF.mjs → chunk-TVSX5YA2.mjs} +3 -3
- package/dist/js/chunks/{chunk-INLZWHLY.mjs → chunk-UHO5CV6K.mjs} +2 -2
- package/dist/js/chunks/{chunk-INLZWHLY.mjs.map → chunk-UHO5CV6K.mjs.map} +2 -2
- package/dist/js/chunks/{chunk-7YQBHTK3.mjs → chunk-UKCNELUN.mjs} +6 -8
- package/dist/js/chunks/chunk-UKCNELUN.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VH4BMAZS.mjs → chunk-UKQK5GWR.mjs} +13 -13
- package/dist/js/chunks/chunk-UKQK5GWR.mjs.map +7 -0
- package/dist/js/chunks/{chunk-OYNUDOHR.mjs → chunk-UTSLYQ65.mjs} +7 -6
- package/dist/js/chunks/{chunk-OYNUDOHR.mjs.map → chunk-UTSLYQ65.mjs.map} +2 -2
- package/dist/js/chunks/{chunk-7W7TV6NY.mjs → chunk-VS5OJBOD.mjs} +2 -2
- package/dist/js/chunks/{chunk-7W7TV6NY.mjs.map → chunk-VS5OJBOD.mjs.map} +2 -2
- package/dist/js/chunks/{chunk-KYIEG4U3.mjs → chunk-VZMROW5A.mjs} +43 -14
- package/dist/js/chunks/chunk-VZMROW5A.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VFV75DHF.mjs → chunk-XB6Y7P5W.mjs} +11 -12
- package/dist/js/chunks/chunk-XB6Y7P5W.mjs.map +7 -0
- package/dist/js/chunks/{chunk-CZSQHXEV.mjs → chunk-XDAMOMVD.mjs} +20 -21
- package/dist/js/chunks/chunk-XDAMOMVD.mjs.map +7 -0
- package/dist/js/chunks/{chunk-EVCVFEV3.mjs → chunk-XJPMW5SP.mjs} +21 -35
- package/dist/js/chunks/chunk-XJPMW5SP.mjs.map +7 -0
- package/dist/js/chunks/{chunk-VR3L2WN5.mjs → chunk-YKANQILZ.mjs} +7 -6
- package/dist/js/chunks/chunk-YKANQILZ.mjs.map +7 -0
- package/dist/js/chunks/{chunk-JUKBBN6P.mjs → chunk-YLZOJLDI.mjs} +2 -2
- package/dist/js/chunks/{chunk-U4B3VHFS.mjs → chunk-ZK7YY322.mjs} +28 -21
- package/dist/js/chunks/chunk-ZK7YY322.mjs.map +7 -0
- package/dist/js/expressive.cjs +2739 -2387
- package/dist/js/expressive.cjs.map +4 -4
- package/dist/js/expressive.js +2739 -2387
- package/dist/js/expressive.js.map +4 -4
- package/dist/js/expressive.min.js +7 -7
- package/dist/js/expressive.min.js.map +4 -4
- package/dist/js/expressive.mjs +76 -75
- package/dist/js/expressive.mjs.map +1 -1
- package/dist/js/internal/behaviors/bottomSheets.mjs +3 -3
- package/dist/js/internal/behaviors/copy.mjs +3 -3
- package/dist/js/internal/behaviors/dataTables.mjs +2 -4
- package/dist/js/internal/behaviors/dialogs.mjs +2 -2
- package/dist/js/internal/behaviors/forms.mjs +2 -2
- package/dist/js/internal/behaviors/imageCompare.mjs +2 -2
- package/dist/js/internal/behaviors/lists.mjs +2 -2
- package/dist/js/internal/behaviors/paneResize.mjs +2 -2
- package/dist/js/internal/behaviors/sheetDrag.mjs +2 -2
- package/dist/js/internal/behaviors/sideSheets.mjs +3 -3
- package/dist/js/internal/behaviors/sortable.mjs +2 -2
- package/dist/js/internal/behaviors/theme.mjs +2 -2
- package/dist/js/internal/behaviors/tour.mjs +2 -2
- package/dist/js/internal/behaviors/transferList.mjs +2 -2
- package/dist/js/internal/components/appBar.mjs +3 -3
- package/dist/js/internal/components/autocomplete.mjs +5 -4
- package/dist/js/internal/components/backToTop.mjs +3 -3
- package/dist/js/internal/components/barChart.mjs +5 -5
- package/dist/js/internal/components/buttonGroup.mjs +3 -3
- package/dist/js/internal/components/buttons.mjs +3 -3
- package/dist/js/internal/components/cards.mjs +3 -3
- package/dist/js/internal/components/carousel.mjs +3 -3
- package/dist/js/internal/components/cascader.mjs +4 -4
- package/dist/js/internal/components/characterCounter.mjs +3 -3
- package/dist/js/internal/components/chips.mjs +7 -6
- package/dist/js/internal/components/colorPicker.mjs +3 -3
- package/dist/js/internal/components/columnChart.mjs +4 -4
- package/dist/js/internal/components/commandPalette.mjs +3 -3
- package/dist/js/internal/components/confetti.mjs +3 -3
- package/dist/js/internal/components/currencyInput.mjs +3 -3
- package/dist/js/internal/components/datepicker.mjs +8 -7
- package/dist/js/internal/components/expandingCard.mjs +3 -3
- package/dist/js/internal/components/funnelChart.mjs +4 -4
- package/dist/js/internal/components/heatmapChart.mjs +4 -4
- package/dist/js/internal/components/hoverCard.mjs +3 -3
- package/dist/js/internal/components/index.mjs +60 -59
- package/dist/js/internal/components/inputMask.mjs +3 -3
- package/dist/js/internal/components/keypad.mjs +3 -3
- package/dist/js/internal/components/lightbox.mjs +3 -3
- package/dist/js/internal/components/lineChart.mjs +23 -7
- package/dist/js/internal/components/loadingOverlay.mjs +3 -3
- package/dist/js/internal/components/mapView.mjs +3 -3
- package/dist/js/internal/components/menu.mjs +3 -3
- package/dist/js/internal/components/menubar.mjs +4 -4
- package/dist/js/internal/components/messageScroller.mjs +3 -3
- package/dist/js/internal/components/mixedChart.mjs +5 -5
- package/dist/js/internal/components/navigationRail.mjs +3 -3
- package/dist/js/internal/components/particles.mjs +3 -3
- package/dist/js/internal/components/pieChart.mjs +4 -4
- package/dist/js/internal/components/pullToRefresh.mjs +3 -3
- package/dist/js/internal/components/questionnaire.mjs +3 -3
- package/dist/js/internal/components/radarChart.mjs +4 -4
- package/dist/js/internal/components/radialChart.mjs +4 -4
- package/dist/js/internal/components/registry.mjs +59 -58
- package/dist/js/internal/components/richTextEditor.mjs +3 -3
- package/dist/js/internal/components/sankeyChart.mjs +4 -4
- package/dist/js/internal/components/scatterChart.mjs +4 -4
- package/dist/js/internal/components/scrollspy.mjs +3 -3
- package/dist/js/internal/components/select.mjs +5 -4
- package/dist/js/internal/components/showMore.mjs +3 -3
- package/dist/js/internal/components/slider.mjs +3 -3
- package/dist/js/internal/components/snackbar.mjs +2 -2
- package/dist/js/internal/components/swipeActions.mjs +3 -3
- package/dist/js/internal/components/tabs.mjs +3 -3
- package/dist/js/internal/components/timepicker.mjs +5 -5
- package/dist/js/internal/components/tooltip.mjs +3 -3
- package/dist/js/internal/components/treeSelect.mjs +6 -5
- package/dist/js/internal/components/treemapChart.mjs +4 -4
- package/dist/js/internal/core/component.mjs +6 -4
- package/dist/js/internal/core/formControl.mjs +2 -2
- package/dist/js/internal/core/imageURL.mjs +7 -0
- package/dist/js/internal/core/imageURL.mjs.map +7 -0
- package/dist/js/internal/core/utils.mjs +11 -1
- package/dist/js/internal/plugins/dockedDisplayPlugin.mjs +2 -2
- package/dist/js/internal/plugins/modalDisplayPlugin.mjs +3 -3
- package/dist/js/modular.mjs +76 -75
- package/dist/types/behaviors/bottomSheets.d.ts +5 -3
- package/dist/types/behaviors/dataTables.d.ts +2 -6
- package/dist/types/behaviors/forms.d.ts +7 -7
- package/dist/types/behaviors/imageCompare.d.ts +2 -1
- package/dist/types/behaviors/transferList.d.ts +2 -0
- package/dist/types/components/autocomplete.d.ts +14 -3
- package/dist/types/components/carousel.d.ts +7 -0
- package/dist/types/components/chips.d.ts +15 -0
- package/dist/types/components/colorPicker.d.ts +14 -0
- package/dist/types/components/currencyInput.d.ts +5 -4
- package/dist/types/components/datepicker.d.ts +54 -27
- package/dist/types/components/funnelChart.d.ts +1 -4
- package/dist/types/components/heatmapChart.d.ts +3 -0
- package/dist/types/components/hoverCard.d.ts +1 -0
- package/dist/types/components/inputMask.d.ts +0 -2
- package/dist/types/components/lineChart.d.ts +43 -5
- package/dist/types/components/mapView.d.ts +113 -11
- package/dist/types/components/menu.d.ts +14 -0
- package/dist/types/components/particles.d.ts +14 -1
- package/dist/types/components/pieChart.d.ts +1 -2
- package/dist/types/components/richTextEditor.d.ts +40 -9
- package/dist/types/components/select.d.ts +1 -3
- package/dist/types/components/showMore.d.ts +2 -0
- package/dist/types/components/slider.d.ts +0 -1
- package/dist/types/components/snackbar.d.ts +7 -1
- package/dist/types/components/tabs.d.ts +3 -3
- package/dist/types/components/timepicker.d.ts +15 -6
- package/dist/types/components/tooltip.d.ts +1 -1
- package/dist/types/components/treemapChart.d.ts +2 -2
- package/dist/types/core/component.d.ts +9 -3
- package/dist/types/core/imageURL.d.ts +2 -0
- package/dist/types/core/utils.d.ts +39 -1
- package/dist/types/modular.d.ts +1 -1
- package/dist/types/plugins/modalDisplayPlugin.d.ts +8 -1
- package/package.json +8 -6
- package/src/sass/abstracts/_mixins.scss +459 -59
- package/src/sass/abstracts/_variables.scss +25 -0
- package/src/sass/components/_accordion.scss +1 -3
- package/src/sass/components/_aura.scss +1 -0
- package/src/sass/components/_back-to-top.scss +3 -3
- package/src/sass/components/_bar-chart.scss +2 -83
- package/src/sass/components/_bottom-sheet.scss +7 -0
- package/src/sass/components/_breadcrumb.scss +1 -7
- package/src/sass/components/_button-groups.scss +15 -38
- package/src/sass/components/_buttons.scss +24 -74
- package/src/sass/components/_calendar.scss +1 -3
- package/src/sass/components/_carousel.scss +10 -10
- package/src/sass/components/_cascader.scss +3 -14
- package/src/sass/components/_column-chart.scss +1 -19
- package/src/sass/components/_confetti.scss +3 -4
- package/src/sass/components/_data-table.scss +10 -0
- package/src/sass/components/_dialog.scss +10 -18
- package/src/sass/components/_expanding-card.scss +1 -5
- package/src/sass/components/_fab-menu.scss +4 -12
- package/src/sass/components/_funnel-chart.scss +1 -62
- package/src/sass/components/_heatmap-chart.scss +2 -6
- package/src/sass/components/_icon-buttons.scss +1 -4
- package/src/sass/components/_line-chart.scss +2 -70
- package/src/sass/components/_map.scss +4 -0
- package/src/sass/components/_marquee.scss +3 -3
- package/src/sass/components/_mega-menu.scss +8 -17
- package/src/sass/components/_menu.scss +10 -11
- package/src/sass/components/_menubar.scss +1 -13
- package/src/sass/components/_mixed-chart.scss +1 -37
- package/src/sass/components/_navbar.scss +11 -16
- package/src/sass/components/_navigation-bar.scss +2 -5
- package/src/sass/components/_navigation-rail.scss +25 -15
- package/src/sass/components/_page-footer.scss +1 -3
- package/src/sass/components/_pagination.scss +3 -14
- package/src/sass/components/_panes.scss +3 -16
- package/src/sass/components/_particles.scss +3 -4
- package/src/sass/components/_pie-chart.scss +8 -70
- package/src/sass/components/_progress.scss +31 -13
- package/src/sass/components/_radar-chart.scss +2 -32
- package/src/sass/components/_radial-chart.scss +2 -48
- package/src/sass/components/_sankey-chart.scss +5 -28
- package/src/sass/components/_scatter-chart.scss +2 -11
- package/src/sass/components/_search.scss +1 -4
- package/src/sass/components/_side-sheet.scss +9 -14
- package/src/sass/components/_skeleton.scss +24 -15
- package/src/sass/components/_snackbar.scss +11 -13
- package/src/sass/components/_table_of_contents.scss +1 -3
- package/src/sass/components/_tabs.scss +4 -20
- package/src/sass/components/_timepicker.scss +2 -1
- package/src/sass/components/_toolbar.scss +1 -4
- package/src/sass/components/_tooltip.scss +9 -5
- package/src/sass/components/_tree.scss +5 -17
- package/src/sass/components/_treemap-chart.scss +2 -26
- package/src/sass/components/forms/_checkboxes.scss +2 -21
- package/src/sass/components/forms/_drop-zone.scss +1 -4
- package/src/sass/components/forms/_fieldset.scss +1 -4
- package/src/sass/components/forms/_file-input.scss +6 -0
- package/src/sass/components/forms/_input-fields.scss +21 -4
- package/src/sass/components/forms/_radio-buttons.scss +2 -24
- package/src/sass/components/forms/_select.scss +6 -7
- package/src/sass/components/forms/_slider.scss +1 -4
- package/src/sass/components/forms/_switches.scss +14 -21
- package/src/sass/utilities/_helpers.scss +1 -1
- package/src/sass/utilities/_visibility.scss +1 -3
- package/dist/js/chunks/chunk-2CS6TITK.mjs.map +0 -7
- package/dist/js/chunks/chunk-3L3QIYLC.mjs.map +0 -7
- package/dist/js/chunks/chunk-4IKVPCSU.mjs +0 -7
- package/dist/js/chunks/chunk-4QUCNFSD.mjs.map +0 -7
- package/dist/js/chunks/chunk-4TRZ2AER.mjs.map +0 -7
- package/dist/js/chunks/chunk-5KIHWJI2.mjs.map +0 -7
- package/dist/js/chunks/chunk-6FSEUFVW.mjs.map +0 -7
- package/dist/js/chunks/chunk-752ADW4M.mjs.map +0 -7
- package/dist/js/chunks/chunk-7NLUI3RR.mjs.map +0 -7
- package/dist/js/chunks/chunk-7YQBHTK3.mjs.map +0 -7
- package/dist/js/chunks/chunk-7YZ5CN3V.mjs.map +0 -7
- package/dist/js/chunks/chunk-B7DQFHA5.mjs.map +0 -7
- package/dist/js/chunks/chunk-BIGU5RCJ.mjs.map +0 -7
- package/dist/js/chunks/chunk-BPF3I2MN.mjs.map +0 -7
- package/dist/js/chunks/chunk-CMGXGYUC.mjs.map +0 -7
- package/dist/js/chunks/chunk-CSYWKEK3.mjs.map +0 -7
- package/dist/js/chunks/chunk-CZSQHXEV.mjs.map +0 -7
- package/dist/js/chunks/chunk-DZYVU75J.mjs.map +0 -7
- package/dist/js/chunks/chunk-EC26RU2D.mjs.map +0 -7
- package/dist/js/chunks/chunk-EVCVFEV3.mjs.map +0 -7
- package/dist/js/chunks/chunk-FCNF4GRJ.mjs.map +0 -7
- package/dist/js/chunks/chunk-GWZ76SR4.mjs.map +0 -7
- package/dist/js/chunks/chunk-KYIEG4U3.mjs.map +0 -7
- package/dist/js/chunks/chunk-KZPSAXIU.mjs.map +0 -7
- package/dist/js/chunks/chunk-LDXCC2L3.mjs.map +0 -7
- package/dist/js/chunks/chunk-NBJAUGPP.mjs.map +0 -7
- package/dist/js/chunks/chunk-OUCHKSAW.mjs.map +0 -7
- package/dist/js/chunks/chunk-P6DRQ6KS.mjs.map +0 -7
- package/dist/js/chunks/chunk-PA7NU5AK.mjs.map +0 -7
- package/dist/js/chunks/chunk-QACZ6TUP.mjs.map +0 -7
- package/dist/js/chunks/chunk-QXKWVHBD.mjs.map +0 -7
- package/dist/js/chunks/chunk-S23RJ3XY.mjs.map +0 -7
- package/dist/js/chunks/chunk-SPPHF7YZ.mjs.map +0 -7
- package/dist/js/chunks/chunk-U4B3VHFS.mjs.map +0 -7
- package/dist/js/chunks/chunk-UGJHCHXG.mjs.map +0 -7
- package/dist/js/chunks/chunk-VFV75DHF.mjs.map +0 -7
- package/dist/js/chunks/chunk-VGY4M57S.mjs.map +0 -7
- package/dist/js/chunks/chunk-VH4BMAZS.mjs.map +0 -7
- package/dist/js/chunks/chunk-VJVQIXHC.mjs.map +0 -7
- package/dist/js/chunks/chunk-VMY55K2X.mjs.map +0 -7
- package/dist/js/chunks/chunk-VR3L2WN5.mjs.map +0 -7
- package/dist/js/chunks/chunk-WU7XJ4RR.mjs.map +0 -7
- package/dist/js/chunks/chunk-Y6TLRA3U.mjs.map +0 -7
- package/dist/js/chunks/chunk-Z4GICXR2.mjs.map +0 -7
- package/dist/js/chunks/chunk-Z4OARDZ7.mjs.map +0 -7
- package/dist/js/chunks/chunk-ZM3XBHWV.mjs.map +0 -7
- package/dist/js/chunks/chunk-ZVLOUDIJ.mjs.map +0 -7
- /package/dist/js/chunks/{chunk-Y6H2X7ZC.mjs.map → chunk-3KF65KGL.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-75E5EDJF.mjs.map → chunk-3XORNED5.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-NNHVANQA.mjs.map → chunk-4WBGAQN3.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ZJNLAGY5.mjs.map → chunk-5F4URJHL.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-GVZQH2H5.mjs.map → chunk-AEG6LOAJ.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-AI73GJKG.mjs.map → chunk-BB5VXYXT.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-2RLBDFH4.mjs.map → chunk-BDATLH3H.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ZKWUWBUB.mjs.map → chunk-CY2CTOVM.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-67ZPPKXS.mjs.map → chunk-FNIIH2LU.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-T3BNSRP3.mjs.map → chunk-HQRLBTNM.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-NAC72P7R.mjs.map → chunk-I2F7MLUU.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ANKFWNWT.mjs.map → chunk-LC4O5LFS.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-4PIXLDNJ.mjs.map → chunk-LEF33SCP.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ILDRRG7T.mjs.map → chunk-LFORZRPH.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-4EWGD4V2.mjs.map → chunk-NODZ5VAD.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-NVQ5EHCU.mjs.map → chunk-QNODAANY.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ROH2HDB4.mjs.map → chunk-RUDYMEJ3.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-TFABTUAZ.mjs.map → chunk-T4MOBP3J.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-GCWWEZKO.mjs.map → chunk-TM7HPGTV.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-ZO6ZLHFF.mjs.map → chunk-TVSX5YA2.mjs.map} +0 -0
- /package/dist/js/chunks/{chunk-JUKBBN6P.mjs.map → chunk-YLZOJLDI.mjs.map} +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
Utils
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-67UNY7RH.mjs";
|
|
4
4
|
|
|
5
5
|
// src/ts/behaviors/dialogs.ts
|
|
6
6
|
function textElement(tag, text) {
|
|
@@ -124,4 +124,4 @@ var Dialogs = _Dialogs;
|
|
|
124
124
|
export {
|
|
125
125
|
Dialogs
|
|
126
126
|
};
|
|
127
|
-
//# sourceMappingURL=chunk-
|
|
127
|
+
//# sourceMappingURL=chunk-LEF33SCP.mjs.map
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import {
|
|
2
2
|
Component
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-EB2V4OKL.mjs";
|
|
4
4
|
import {
|
|
5
5
|
restoreAttribute
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-67UNY7RH.mjs";
|
|
7
7
|
|
|
8
8
|
// src/ts/components/buttons.ts
|
|
9
9
|
var _defaults = {};
|
|
@@ -89,4 +89,4 @@ FloatingActionButton.key = "Expressive_FloatingActionButton";
|
|
|
89
89
|
export {
|
|
90
90
|
FloatingActionButton
|
|
91
91
|
};
|
|
92
|
-
//# sourceMappingURL=chunk-
|
|
92
|
+
//# sourceMappingURL=chunk-LFORZRPH.mjs.map
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
Utils
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-67UNY7RH.mjs";
|
|
4
4
|
|
|
5
5
|
// src/ts/behaviors/forms.ts
|
|
6
6
|
var FILE_RULES = '.drop-zone input[type="file"]:is([data-validate-types], [data-max-size], [data-max-files])';
|
|
@@ -102,7 +102,7 @@ var _Forms = class _Forms {
|
|
|
102
102
|
}
|
|
103
103
|
static _validateFiles(input) {
|
|
104
104
|
if (input.matches(":disabled")) return;
|
|
105
|
-
_Forms.
|
|
105
|
+
_Forms._bindShadowForm(input);
|
|
106
106
|
const failure = _Forms._checkFiles(input);
|
|
107
107
|
_Forms._showFileError(input, failure?.message ?? input.validationMessage);
|
|
108
108
|
return failure;
|
|
@@ -170,7 +170,7 @@ var _Forms = class _Forms {
|
|
|
170
170
|
error.hidden = !message;
|
|
171
171
|
}
|
|
172
172
|
static _updateDropZone(input) {
|
|
173
|
-
_Forms.
|
|
173
|
+
_Forms._bindShadowForm(input);
|
|
174
174
|
const zone = input.closest(".drop-zone");
|
|
175
175
|
const files = Array.from(input.files ?? []);
|
|
176
176
|
const failure = _Forms._validateDropZone(input);
|
|
@@ -196,12 +196,11 @@ var _Forms = class _Forms {
|
|
|
196
196
|
_Forms._fileSelections.set(input, { files, constraints });
|
|
197
197
|
return !previous || previous.constraints !== constraints || previous.files.length !== files.length || !previous.files.every((file, index) => file === files[index]);
|
|
198
198
|
}
|
|
199
|
-
|
|
199
|
+
// Submit and reset do not leave a shadow root, so the document never hears
|
|
200
|
+
// them. Adding the same listener again does nothing.
|
|
201
|
+
static _bindShadowForm(input) {
|
|
200
202
|
if (!input.getRootNode().host) return;
|
|
201
|
-
const
|
|
202
|
-
if (!form || _Forms._fileResetForms.has(form)) return;
|
|
203
|
-
_Forms._fileResetForms.add(form);
|
|
204
|
-
form.addEventListener("reset", _Forms.resetFormExtras);
|
|
203
|
+
for (const type of ["submit", "reset"]) input.form?.addEventListener(type, _Forms.resetFormExtras, true);
|
|
205
204
|
}
|
|
206
205
|
static _resetFileInput(input) {
|
|
207
206
|
if (input.files?.length) return;
|
|
@@ -222,8 +221,15 @@ var _Forms = class _Forms {
|
|
|
222
221
|
_Forms._fileErrors.delete(input);
|
|
223
222
|
_Forms._showFileError(input, input.validationMessage);
|
|
224
223
|
}
|
|
225
|
-
static
|
|
226
|
-
Array.from(form.elements)
|
|
224
|
+
static _afterReset(form) {
|
|
225
|
+
const fields = Array.from(form.elements);
|
|
226
|
+
fields.filter((field) => field instanceof HTMLInputElement && field.type === "file").forEach(_Forms._resetFileInput);
|
|
227
|
+
fields.filter((field) => field.classList.contains("validate")).forEach((field) => _Forms._markInvalid(field, false));
|
|
228
|
+
fields.filter((field) => field.classList.contains("expressive-textarea")).forEach(_Forms.textareaAutoResize);
|
|
229
|
+
const summary = form.querySelector(".error-summary");
|
|
230
|
+
if (!summary) return;
|
|
231
|
+
summary.hidden = true;
|
|
232
|
+
summary.querySelector("ul, ol")?.replaceChildren();
|
|
227
233
|
}
|
|
228
234
|
/**
|
|
229
235
|
* Safe to call more than once: the root entry calls it on import, and a page
|
|
@@ -271,6 +277,7 @@ var _Forms = class _Forms {
|
|
|
271
277
|
'input[type="password"], input[data-password]'
|
|
272
278
|
);
|
|
273
279
|
if (!input) return;
|
|
280
|
+
_Forms._bindShadowForm(input);
|
|
274
281
|
const show = input.type === "password";
|
|
275
282
|
input.toggleAttribute("data-password", show);
|
|
276
283
|
input.type = show ? "text" : "password";
|
|
@@ -279,7 +286,7 @@ var _Forms = class _Forms {
|
|
|
279
286
|
/**
|
|
280
287
|
* A [data-step="up"] or [data-step="down"] button in a .field steps the
|
|
281
288
|
* field's number input as the arrow keys would, within min, max and step,
|
|
282
|
-
* and fires input and change. A disabled, read-only or step="any" input
|
|
289
|
+
* and fires input and change if the value moved. A disabled, read-only or step="any" input
|
|
283
290
|
* is left alone; stepUp() would throw on step="any".
|
|
284
291
|
*/
|
|
285
292
|
static stepNumber(e) {
|
|
@@ -288,16 +295,19 @@ var _Forms = class _Forms {
|
|
|
288
295
|
':scope > input[type="number"]:not(:disabled, [readonly], [step="any"])'
|
|
289
296
|
);
|
|
290
297
|
if (!input) return;
|
|
298
|
+
const before = input.value;
|
|
291
299
|
input[button.dataset.step === "down" ? "stepDown" : "stepUp"]();
|
|
300
|
+
if (input.value === before) return;
|
|
292
301
|
input.dispatchEvent(new Event("input", { bubbles: true, composed: true }));
|
|
293
302
|
input.dispatchEvent(new Event("change", { bubbles: true }));
|
|
294
303
|
}
|
|
295
304
|
/**
|
|
296
305
|
* A revealed password goes back to type="password" when its form is
|
|
297
306
|
* submitted or reset, so it is never sent or autofilled as plain text and
|
|
298
|
-
* a reset field does not stay revealed.
|
|
299
|
-
*
|
|
300
|
-
*
|
|
307
|
+
* a reset field does not stay revealed. Reset fires no input or change
|
|
308
|
+
* event, so a reset form also drops its file lists, `.validate` errors and
|
|
309
|
+
* error summary, and fits each auto-resizing textarea to its restored text.
|
|
310
|
+
* That cleanup waits for the native reset and respects later cancellation.
|
|
301
311
|
*/
|
|
302
312
|
static resetFormExtras(e) {
|
|
303
313
|
const form = e.target;
|
|
@@ -309,7 +319,7 @@ var _Forms = class _Forms {
|
|
|
309
319
|
});
|
|
310
320
|
if (e.type === "reset") {
|
|
311
321
|
setTimeout(() => {
|
|
312
|
-
if (!e.defaultPrevented) _Forms.
|
|
322
|
+
if (!e.defaultPrevented) _Forms._afterReset(form);
|
|
313
323
|
}, 0);
|
|
314
324
|
}
|
|
315
325
|
}
|
|
@@ -427,7 +437,6 @@ var _Forms = class _Forms {
|
|
|
427
437
|
_Forms._initialized = false;
|
|
428
438
|
_Forms._fileErrors = /* @__PURE__ */ new WeakMap();
|
|
429
439
|
_Forms._fileSelections = /* @__PURE__ */ new WeakMap();
|
|
430
|
-
_Forms._fileResetForms = /* @__PURE__ */ new WeakSet();
|
|
431
440
|
_Forms._onFileInput = (event) => {
|
|
432
441
|
const input = Utils.closestInPath(event, '.drop-zone input[type="file"]');
|
|
433
442
|
if (!input) return;
|
|
@@ -439,4 +448,4 @@ var Forms = _Forms;
|
|
|
439
448
|
export {
|
|
440
449
|
Forms
|
|
441
450
|
};
|
|
442
|
-
//# sourceMappingURL=chunk-
|
|
451
|
+
//# sourceMappingURL=chunk-LWLNV5EC.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/ts/behaviors/forms.ts"],
|
|
4
|
+
"sourcesContent": ["import { Utils } from '../core/utils';\n\nconst FILE_RULES = '.drop-zone input[type=\"file\"]:is([data-validate-types], [data-max-size], [data-max-files])';\n\ninterface FileFailure {\n rejected: File[];\n reason: 'type' | 'size' | 'count';\n message: string;\n}\n\nfunction fileLimit(input: HTMLInputElement, attribute: string) {\n const value = (input.getAttribute(attribute) || '').trim();\n if (!/^\\d+$/.test(value)) return 0;\n const limit = Number(value);\n return Number.isSafeInteger(limit) ? limit : 0;\n}\n\nfunction fileSpecifier(value: string) {\n if (value.endsWith('/*')) return /^(image|audio|video)\\/\\*$/.test(value);\n return /^\\.[^\\s/\\\\]+$/.test(value) ||\n /^[!#$%&'*+.^_`|~0-9a-z-]+\\/[!#$%&'*+.^_`|~0-9a-z-]+$/.test(value);\n}\n\nfunction fileMatches(file: File, specifier: string) {\n if (specifier.startsWith('.')) return file.name.toLowerCase().endsWith(specifier);\n if (specifier.endsWith('/*')) return file.type.toLowerCase().startsWith(specifier.slice(0, -1));\n return file.type.toLowerCase() === specifier;\n}\n\nexport class Forms {\n /**\n * Validates a `.validate` field: marks it `invalid` and `aria-invalid`\n * when it fails its constraints or `data-length`, and clears both when it\n * passes. An empty optional field never fails. The field is described by\n * its `[data-error]` supporting text, so the error the CSS shows there is\n * read with it.\n * Marked drop-zone file inputs also validate type/size rules and synchronize their\n * native custom validity and zone-level error text, without emitting events.\n * @param textfield\n */\n static validateField(textfield: HTMLInputElement) {\n if (!textfield) {\n console.error('No text field element found');\n return;\n }\n if (Forms._validatedFile(textfield)) {\n Forms._validateFiles(textfield);\n return;\n }\n if (!textfield.classList.contains('validate')) return;\n Forms._markInvalid(textfield, Forms._fails(textfield));\n Forms._describeByError(textfield);\n }\n\n private static _markInvalid(field: HTMLInputElement, invalid: boolean) {\n field.classList.toggle('invalid', invalid);\n if (invalid) field.setAttribute('aria-invalid', 'true');\n else field.removeAttribute('aria-invalid');\n }\n\n /** Whether a field fails its constraints or is longer than `data-length`. */\n private static _fails(field: HTMLInputElement) {\n return !Forms._blankOptional(field) && (!field.validity.valid || field.value.length > parseInt(field.getAttribute('data-length')));\n }\n\n /** An empty field that is not required, and holds no half-typed number or date, never fails. */\n private static _blankOptional(field: HTMLInputElement) {\n return field.value.length === 0 && !field.validity.badInput && !field.required;\n }\n\n /** Adds the field's `[data-error]` supporting text to its aria-describedby. */\n private static _describeByError(field: HTMLInputElement) {\n const error = field.parentElement?.querySelector(':scope > [data-error]');\n if (error) Forms._addDescription(field, Forms._idOf(error));\n }\n\n private static _idOf(el: Element) {\n if (!el.id) el.id = `field-error-${Utils.guid()}`;\n return el.id;\n }\n\n /** Adds an id to a field's aria-describedby once, after the page's own. */\n private static _addDescription(field: HTMLInputElement, id: string) {\n const ids = (field.getAttribute('aria-describedby') ?? '').split(/\\s+/).filter(Boolean);\n if (!ids.includes(id)) field.setAttribute('aria-describedby', [...ids, id].join(' '));\n }\n\n /**\n * Resizes the given TextArea after updating the\n * value content dynamically.\n * @param e EventTarget\n */\n static textareaAutoResize(e: EventTarget) {\n const textarea = e as HTMLTextAreaElement;\n if (!textarea) return;\n\n // Measure the textarea against itself: collapse it to its natural height,\n // then read the content height back. `.expressive-textarea` is\n // `overflow-y: hidden`, so scrollHeight is the full content height and\n // offsetHeight - clientHeight is exactly the borders (no scrollbar to\n // account for) - which border-box sizing needs added back.\n //\n // This replaces a mirror div that the value was copied into via\n // `innerHTML = innerHTML.replace(...)` - a full serialize and reparse of\n // the text on every keystroke, plus getComputedStyle and seven style\n // writes, run twice per keystroke because it was bound to keydown and\n // keyup both.\n if (!textarea.hasAttribute('original-height')) Forms._measureTextarea(textarea);\n // Not measured yet when it was hidden.\n const originalHeight = parseInt(textarea.getAttribute('original-height'));\n if (isNaN(originalHeight)) return;\n\n textarea.style.height = 'auto';\n // Three reads after a single write: one layout flush for the whole resize.\n const borders = textarea.offsetHeight - textarea.clientHeight;\n const contentHeight = textarea.scrollHeight + borders;\n textarea.style.height = Math.max(originalHeight, contentHeight) + 'px';\n }\n\n // A hidden textarea (closed dialog, inactive tab) measures 0. Storing that\n // would pin it collapsed, so it waits for a focus or input to measure.\n private static _measureTextarea(textarea: HTMLTextAreaElement) {\n const height = textarea.getBoundingClientRect().height;\n if (height) textarea.setAttribute('original-height', height.toString());\n }\n\n private static _initialized = false;\n private static _fileErrors = new WeakMap<HTMLInputElement, string>();\n private static _fileSelections = new WeakMap<HTMLInputElement, { files: File[]; constraints: string }>();\n\n private static _validatedFile(input: HTMLInputElement) {\n return input.matches(FILE_RULES) || Forms._fileErrors.has(input);\n }\n\n private static _rejectedTypes(input: HTMLInputElement) {\n const accepted = input.accept.split(',').map((value) => value.trim().toLowerCase()).filter(fileSpecifier);\n if (!accepted.length) return [];\n return Array.from(input.files ?? []).filter((file) => !accepted.some((specifier) => fileMatches(file, specifier)));\n }\n\n private static _validateFiles(input: HTMLInputElement) {\n if (input.matches(':disabled')) return;\n Forms._bindShadowForm(input);\n const failure = Forms._checkFiles(input);\n Forms._showFileError(input, failure?.message ?? input.validationMessage);\n return failure;\n }\n\n private static _checkFiles(input: HTMLInputElement) {\n Forms._clearFileError(input);\n if (!input.matches(FILE_RULES)) {\n Forms._fileErrors.delete(input);\n return;\n }\n Forms._fileErrors.set(input, '');\n const failure = Forms._fileFailure(input);\n if (failure) Forms._setFileError(input, failure.message);\n return failure;\n }\n\n private static _fileFailure(input: HTMLInputElement) {\n return Forms._typeFailure(input) ?? Forms._sizeFailure(input) ?? Forms._countFailure(input);\n }\n\n private static _typeFailure(input: HTMLInputElement): FileFailure | undefined {\n if (!input.hasAttribute('data-validate-types')) return;\n const rejected = Forms._rejectedTypes(input);\n if (rejected.length) return { rejected, reason: 'type', message: Forms._fileTypeMessage(input) };\n }\n\n private static _sizeFailure(input: HTMLInputElement): FileFailure | undefined {\n const limit = fileLimit(input, 'data-max-size');\n if (!limit) return;\n const rejected = Array.from(input.files ?? []).filter((file) => file.size > limit);\n if (!rejected.length) return;\n return { rejected, reason: 'size', message: Forms._fileSizeMessage(input, limit) };\n }\n\n private static _fileSizeMessage(input: HTMLInputElement, limit: number) {\n return Forms._fileError(input)?.getAttribute('data-error-size')?.trim() || `Maximum file size: ${limit} bytes.`;\n }\n\n private static _countFailure(input: HTMLInputElement): FileFailure | undefined {\n const limit = fileLimit(input, 'data-max-files');\n if (!limit) return;\n const rejected = Array.from(input.files ?? []);\n if (rejected.length > limit) return { rejected, reason: 'count', message: Forms._fileCountMessage(input, limit) };\n }\n\n private static _fileCountMessage(input: HTMLInputElement, limit: number) {\n return Forms._fileError(input)?.getAttribute('data-error-count')?.trim() || `Maximum file count: ${limit}.`;\n }\n\n private static _clearFileError(input: HTMLInputElement) {\n const owned = Forms._fileErrors.get(input);\n if (owned && owned === input.validationMessage) input.setCustomValidity('');\n }\n\n private static _setFileError(input: HTMLInputElement, message: string) {\n if (input.validity.customError) return;\n input.setCustomValidity(message);\n Forms._fileErrors.set(input, message);\n }\n\n private static _fileTypeMessage(input: HTMLInputElement) {\n const error = Forms._fileError(input);\n return error?.getAttribute('data-error')?.trim() || `Choose files matching: ${input.accept}.`;\n }\n\n private static _fileError(input: HTMLInputElement) {\n return Array.from(input.closest('.drop-zone')?.children ?? [])\n .find((child) => child.hasAttribute('data-error')) as HTMLElement | undefined;\n }\n\n private static _showFileError(input: HTMLInputElement, message: string) {\n Forms._markInvalid(input, !input.validity.valid);\n const error = Forms._fileError(input);\n if (!error) return;\n Forms._addDescription(input, Forms._idOf(error));\n error.textContent = message;\n error.hidden = !message;\n }\n\n private static _onFileInput = (event: Event) => {\n const input = Utils.closestInPath<HTMLInputElement>(event, '.drop-zone input[type=\"file\"]');\n if (!input) return;\n if (input.matches(':disabled')) return;\n Forms._updateDropZone(input);\n };\n\n private static _updateDropZone(input: HTMLInputElement) {\n Forms._bindShadowForm(input);\n const zone = input.closest('.drop-zone');\n const files = Array.from(input.files ?? []);\n const failure = Forms._validateDropZone(input);\n Forms.listDropZoneFiles(zone, input);\n Forms._reportFileRejection(input, files, failure);\n }\n\n private static _validateDropZone(input: HTMLInputElement) {\n if (Forms._validatedFile(input)) return Forms._validateFiles(input);\n Forms.validateField(input);\n }\n\n private static _reportFileRejection(input: HTMLInputElement, files: File[], failure?: FileFailure) {\n if (!input.matches(FILE_RULES)) {\n Forms._fileSelections.delete(input);\n return;\n }\n if (!Forms._newFileSelection(input, files)) return;\n if (!failure) return;\n Utils.emit(input.closest('.drop-zone'), 'reject', { input, files: files.slice(), rejected: failure.rejected.slice(), reason: failure.reason });\n }\n\n private static _newFileSelection(input: HTMLInputElement, files: File[]) {\n const constraints = JSON.stringify([input.hasAttribute('data-validate-types'), input.accept, fileLimit(input, 'data-max-size'), fileLimit(input, 'data-max-files')]);\n const previous = Forms._fileSelections.get(input);\n Forms._fileSelections.set(input, { files, constraints });\n return !previous || previous.constraints !== constraints || previous.files.length !== files.length ||\n !previous.files.every((file, index) => file === files[index]);\n }\n\n // Submit and reset do not leave a shadow root, so the document never hears\n // them. Adding the same listener again does nothing.\n private static _bindShadowForm(input: HTMLInputElement) {\n if (!(input.getRootNode() as ShadowRoot).host) return;\n for (const type of ['submit', 'reset']) input.form?.addEventListener(type, Forms.resetFormExtras, true);\n }\n\n private static _resetFileInput(input: HTMLInputElement) {\n if (input.files?.length) return;\n Forms._fileSelections.delete(input);\n Forms._resetFileList(input);\n Forms._resetFileValidity(input);\n }\n\n private static _resetFileList(input: HTMLInputElement) {\n const zone = input.closest('.drop-zone');\n if (!zone) return;\n Forms.listDropZoneFiles(zone, input);\n zone.classList.remove('dragover');\n }\n\n private static _resetFileValidity(input: HTMLInputElement) {\n if (input.matches(':disabled')) return;\n if (!Forms._validatedFile(input)) return;\n Forms._clearFileError(input);\n Forms._fileErrors.delete(input);\n Forms._showFileError(input, input.validationMessage);\n }\n\n private static _afterReset(form: HTMLFormElement) {\n const fields = Array.from(form.elements);\n fields.filter((field): field is HTMLInputElement =>\n field instanceof HTMLInputElement && field.type === 'file').forEach(Forms._resetFileInput);\n fields.filter((field) => field.classList.contains('validate'))\n .forEach((field: HTMLInputElement) => Forms._markInvalid(field, false));\n fields.filter((field) => field.classList.contains('expressive-textarea')).forEach(Forms.textareaAutoResize);\n const summary = form.querySelector<HTMLElement>('.error-summary');\n if (!summary) return;\n summary.hidden = true;\n summary.querySelector('ul, ol')?.replaceChildren();\n }\n\n /**\n * Safe to call more than once: the root entry calls it on import, and a page\n * that also loads the modular entry may call it again.\n */\n static Init() {\n if (Forms._initialized) return;\n Forms._initialized = true;\n Utils.onDocumentReady(() => {\n document.addEventListener('input', Forms._onFileInput);\n document.addEventListener('change', (e: Event) => {\n const target = Utils.eventTarget(e);\n if (!(target instanceof HTMLInputElement)) return;\n if (target.matches('.drop-zone input[type=\"file\"]')) {\n Forms._onFileInput(e);\n return;\n }\n // The sibling-label loop that used to live here compared\n // `tagName == 'label'` (tagName is uppercase) so it never matched,\n // and no rule in the Sass styles `label.active` anyway - the\n // floating label is driven by CSS, not by a class from here.\n Forms.validateField(target);\n });\n\n document.addEventListener('click', Forms.togglePassword);\n document.addEventListener('click', Forms.stepNumber);\n // Capture, so the password is hidden again before any submit handler\n // reads the form or the browser offers to save it.\n document.addEventListener('submit', Forms.resetFormExtras, true);\n document.addEventListener('submit', Forms.summarizeErrors, true);\n document.addEventListener('click', Forms.focusSummaryField);\n document.addEventListener('reset', Forms.resetFormExtras, true);\n for (const type of ['dragenter', 'dragover', 'dragleave', 'drop']) {\n document.addEventListener(type, Forms.markDropZone);\n }\n\n document.querySelectorAll('.expressive-textarea').forEach((textArea: HTMLTextAreaElement) => {\n Forms.InitTextarea(textArea);\n });\n\n // File Input Path\n document\n .querySelectorAll('.file-field input[type=\"file\"]')\n .forEach((fileInput: HTMLInputElement) => {\n Forms.InitFileInputPath(fileInput);\n });\n });\n }\n\n /**\n * A .password-toggle button shows or hides the password in its field. The\n * button's own name stays put (\"Show password\"); aria-pressed carries the\n * state, so there is no generated text to translate.\n */\n static togglePassword(e: MouseEvent) {\n const button = Utils.closestInPath(e, '.password-toggle');\n const input = button?.closest('.field')?.querySelector<HTMLInputElement>(\n 'input[type=\"password\"], input[data-password]'\n );\n if (!input) return;\n Forms._bindShadowForm(input);\n const show = input.type === 'password';\n // Marked so the input is still found once it has become type=\"text\".\n input.toggleAttribute('data-password', show);\n input.type = show ? 'text' : 'password';\n button.setAttribute('aria-pressed', String(show));\n }\n\n /**\n * A [data-step=\"up\"] or [data-step=\"down\"] button in a .field steps the\n * field's number input as the arrow keys would, within min, max and step,\n * and fires input and change if the value moved. A disabled, read-only or step=\"any\" input\n * is left alone; stepUp() would throw on step=\"any\".\n */\n static stepNumber(e: MouseEvent) {\n const button = Utils.closestInPath(e, '.field > [data-step]:not(:disabled)') as HTMLElement | null;\n const input = button?.parentElement!.querySelector<HTMLInputElement>(\n ':scope > input[type=\"number\"]:not(:disabled, [readonly], [step=\"any\"])'\n );\n if (!input) return;\n const before = input.value;\n input[button!.dataset.step === 'down' ? 'stepDown' : 'stepUp']();\n if (input.value === before) return;\n input.dispatchEvent(new Event('input', { bubbles: true, composed: true }));\n input.dispatchEvent(new Event('change', { bubbles: true }));\n }\n\n /**\n * A revealed password goes back to type=\"password\" when its form is\n * submitted or reset, so it is never sent or autofilled as plain text and\n * a reset field does not stay revealed. Reset fires no input or change\n * event, so a reset form also drops its file lists, `.validate` errors and\n * error summary, and fits each auto-resizing textarea to its restored text.\n * That cleanup waits for the native reset and respects later cancellation.\n */\n static resetFormExtras(e: Event) {\n const form = e.target;\n if (!(form instanceof HTMLFormElement)) return;\n form.querySelectorAll<HTMLInputElement>('input[data-password]').forEach((input) => {\n input.removeAttribute('data-password');\n input.type = 'password';\n input.closest('.field')?.querySelector('.password-toggle')?.setAttribute('aria-pressed', 'false');\n });\n if (e.type === 'reset') {\n // Native events can run microtasks between listeners, before a later cancellation.\n setTimeout(() => {\n if (!e.defaultPrevented) Forms._afterReset(form);\n }, 0);\n }\n }\n\n /**\n * Error summary. A `novalidate` form holding a `.error-summary` is checked\n * when it is submitted. While any field is invalid the submit stops, as it\n * would natively, and the summary's list gets one link per invalid field,\n * \"Label: browser message\", before the summary is shown and focused. A\n * valid submit hides it again. A submitter with `formnovalidate` skips the\n * check.\n */\n static summarizeErrors(e: SubmitEvent) {\n const form = e.target;\n if (!(form instanceof HTMLFormElement)) return;\n const summary = form.querySelector<HTMLElement>('.error-summary');\n const list = summary?.querySelector('ul, ol');\n if (!list || e.submitter?.hasAttribute('formnovalidate')) return;\n // checkValidity fires `invalid` on each field, which FormSelect needs to\n // mark its generated field.\n if (form.checkValidity()) {\n summary.hidden = true;\n list.replaceChildren();\n return;\n }\n e.preventDefault();\n // Stop here, in the capture phase, so the page's own submit handlers do\n // not run for a form the browser would not have submitted.\n e.stopPropagation();\n const seen = new Set<string>();\n const items = [...form.elements].flatMap((field: HTMLInputElement) => {\n if (!field.willValidate || field.validity.valid) return [];\n // One entry per radio group.\n if (field.type === 'radio') {\n if (seen.has(field.name)) return [];\n seen.add(field.name);\n }\n if (!field.id) field.id = `field-${Utils.guid()}`;\n const group = field.type === 'radio' ? field.closest('fieldset')?.querySelector('legend') : null;\n // An enhanced select's label names the generated input, so fall back to\n // the label in the same .field.\n const named = group ?? field.labels?.[0] ?? field.closest('.field')?.querySelector('label');\n // A label can wrap its control; a select's options are not its name.\n const text = named?.cloneNode(true) as Element;\n text?.querySelectorAll('select, textarea').forEach((control) => control.remove());\n const label = text?.textContent ?? field.getAttribute('aria-label') ?? '';\n const link = document.createElement('a');\n link.href = `#${field.id}`;\n link.textContent = [label.replace(/\\s+/g, ' ').trim(), field.validationMessage].filter(Boolean).join(': ');\n const item = document.createElement('li');\n item.append(link);\n return [item];\n });\n list.replaceChildren(...items);\n if (!summary.hasAttribute('tabindex')) summary.tabIndex = -1;\n summary.hidden = false;\n summary.focus();\n }\n\n /**\n * A summary link focuses its field instead of only scrolling to it. An\n * enhanced select passes that focus on to its generated input itself.\n */\n static focusSummaryField(e: MouseEvent) {\n const link = Utils.closestInPath(e, '.error-summary a[href^=\"#\"]');\n const field = link && Utils.getElementById(link, link.getAttribute('href').slice(1));\n if (!field) return;\n e.preventDefault();\n field.focus();\n }\n\n /**\n * The native file input covers its .drop-zone, so the browser already takes\n * a dropped file. This only shows the drag: the input is the topmost\n * element, so every drag event over the zone targets it and leaving it is\n * leaving the zone.\n */\n static markDropZone(e: DragEvent) {\n const input = Utils.eventTarget(e);\n if (!(input instanceof HTMLInputElement) || input.type !== 'file') return;\n const zone = input.closest('.drop-zone');\n if (!zone) return;\n const over = e.type === 'dragenter' || e.type === 'dragover';\n zone.classList.toggle('dragover', over && !input.disabled);\n }\n\n /** Lists the chosen files, name and size, in the zone's .drop-zone-files. */\n static listDropZoneFiles(zone: Element, input: HTMLInputElement) {\n const list = Array.from(zone.querySelectorAll('.drop-zone-files')).find((list) => list.closest('.drop-zone') === zone);\n if (!list) return;\n const size = (bytes: number) => {\n const [value, unit] =\n bytes >= 1e6 ? [bytes / 1e6, 'megabyte'] : bytes >= 1e3 ? [bytes / 1e3, 'kilobyte'] : [bytes, 'byte'];\n return new Intl.NumberFormat(undefined, { style: 'unit', unit, maximumFractionDigits: 1 }).format(value);\n };\n list.replaceChildren(\n ...Array.from(input.files ?? [], (file) => {\n const item = document.createElement('li');\n const name = document.createElement('span');\n const meta = document.createElement('span');\n name.textContent = file.name;\n meta.textContent = size(file.size);\n item.append(name, meta);\n return item;\n })\n );\n }\n\n static InitTextarea(textarea: HTMLTextAreaElement) {\n // Measured afresh by textareaAutoResize, which skips a hidden textarea.\n textarea.removeAttribute('original-height');\n Forms.textareaAutoResize(textarea);\n // `input` rather than keydown + keyup: it fires once per actual value\n // change and also covers paste, drag-drop and IME composition, which the\n // key events missed.\n textarea.addEventListener('input', (e) => Forms.textareaAutoResize(e.target));\n // One that was hidden at init gets its first measurement once shown.\n textarea.addEventListener('focus', () => {\n if (!textarea.hasAttribute('original-height')) Forms.textareaAutoResize(textarea);\n });\n }\n\n static InitFileInputPath(fileInput: HTMLInputElement) {\n fileInput.addEventListener('change', () => {\n const fileField = fileInput.closest('.file-field');\n const pathInput = fileField?.querySelector<HTMLInputElement>('input.file-path');\n if (!pathInput) return;\n pathInput.value = Array.from(fileInput.files, (f) => f.name).join(', ');\n pathInput.dispatchEvent(\n new Event('change', { bubbles: true, cancelable: true, composed: true })\n );\n });\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["list"]
|
|
7
|
+
}
|
|
@@ -2,19 +2,20 @@ import {
|
|
|
2
2
|
formAssociated,
|
|
3
3
|
unwrapControl,
|
|
4
4
|
wrapInControl
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-UHO5CV6K.mjs";
|
|
6
6
|
import {
|
|
7
7
|
Autocomplete
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-F7LAKFMX.mjs";
|
|
9
9
|
import {
|
|
10
10
|
Component
|
|
11
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-EB2V4OKL.mjs";
|
|
12
12
|
import {
|
|
13
13
|
Utils,
|
|
14
14
|
restoreAttribute
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-67UNY7RH.mjs";
|
|
16
16
|
|
|
17
17
|
// src/ts/components/chips.ts
|
|
18
|
+
var isMoveKey = (e) => (e.key === "ArrowLeft" || e.key === "ArrowRight") && Utils.plainKey(e);
|
|
18
19
|
var CONTROL = "expressive-chips-control";
|
|
19
20
|
var pastedValues = (e) => (e.clipboardData?.getData("text") ?? "").split(/[,\t\n]/).map((value) => value.trim()).filter(Boolean);
|
|
20
21
|
var _defaults = {
|
|
@@ -38,6 +39,8 @@ var _Chips = class _Chips extends Component {
|
|
|
38
39
|
this._name = "";
|
|
39
40
|
/** The chips the field started with, which a form reset puts back. */
|
|
40
41
|
this._initialData = [];
|
|
42
|
+
/** Undoes each change setup made to the markup, newest last. */
|
|
43
|
+
this._undo = [];
|
|
41
44
|
/** The input's own aria-required, or null, put back on destroy. */
|
|
42
45
|
this._ariaRequired = null;
|
|
43
46
|
/** The form control wrapping a named input, which the form reads instead of it. */
|
|
@@ -90,25 +93,23 @@ var _Chips = class _Chips extends Component {
|
|
|
90
93
|
}
|
|
91
94
|
e.preventDefault();
|
|
92
95
|
if (!this.hasAutocomplete || !this.options.autocompleteOnly) {
|
|
93
|
-
this.addChip({ id: this._input.value });
|
|
96
|
+
this.addChip({ id: this._input.value.trim() });
|
|
94
97
|
}
|
|
95
98
|
this._input.value = "";
|
|
96
99
|
this.autocomplete?.close();
|
|
97
|
-
} else if (this.
|
|
100
|
+
} else if (this._leavesInput(e)) {
|
|
98
101
|
e.preventDefault();
|
|
99
102
|
this.selectChip(this.chipsData.length - 1);
|
|
100
103
|
}
|
|
101
104
|
};
|
|
102
|
-
this.el
|
|
105
|
+
this._addClass(this.el, "chips");
|
|
103
106
|
this.chipsData = [];
|
|
104
107
|
this._chips = [];
|
|
105
108
|
this._takeName();
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
this._renderChips();
|
|
109
|
-
}
|
|
109
|
+
this._takeInitialData(this.options.data);
|
|
110
|
+
if (this.chipsData.length) this._renderChips();
|
|
110
111
|
if (this.options.allowUserInput) {
|
|
111
|
-
this.el
|
|
112
|
+
this._addClass(this.el, "field");
|
|
112
113
|
this._setupInput();
|
|
113
114
|
this._setupEventHandlers();
|
|
114
115
|
this.el.append(this._end);
|
|
@@ -145,6 +146,9 @@ var _Chips = class _Chips extends Component {
|
|
|
145
146
|
this._chips.forEach((c) => c.remove());
|
|
146
147
|
this._chips = [];
|
|
147
148
|
this._giveNameBack();
|
|
149
|
+
this.el.classList.remove("focus");
|
|
150
|
+
this._undo.reverse().forEach((undo) => undo());
|
|
151
|
+
this._undo = [];
|
|
148
152
|
super.destroy();
|
|
149
153
|
}
|
|
150
154
|
_setupEventHandlers() {
|
|
@@ -258,14 +262,14 @@ var _Chips = class _Chips extends Component {
|
|
|
258
262
|
const chips = e.target.closest(".chips");
|
|
259
263
|
const tag = e.target.tagName;
|
|
260
264
|
if (tag === "INPUT" || tag === "TEXTAREA" || !chips) return;
|
|
261
|
-
const currChips = chips
|
|
265
|
+
const currChips = _Chips.getInstance(chips);
|
|
262
266
|
if (!currChips) return;
|
|
263
267
|
if (e.key === "Backspace" || e.key === "Delete") {
|
|
264
268
|
const index = currChips._chips.indexOf(e.target.closest(".chip"));
|
|
265
269
|
if (index < 0) return;
|
|
266
270
|
e.preventDefault();
|
|
267
271
|
currChips._deleteChip(index, "previous");
|
|
268
|
-
} else if (e
|
|
272
|
+
} else if (isMoveKey(e)) {
|
|
269
273
|
const current = e.target.closest(".chip") ?? currChips._selectedChip;
|
|
270
274
|
const index = currChips._chips.indexOf(current);
|
|
271
275
|
if (index < 0) return;
|
|
@@ -280,6 +284,10 @@ var _Chips = class _Chips extends Component {
|
|
|
280
284
|
}
|
|
281
285
|
}
|
|
282
286
|
}
|
|
287
|
+
/** Whether a key moves from the empty input back to the last chip. */
|
|
288
|
+
_leavesInput(e) {
|
|
289
|
+
return this._input.value === "" && this.chipsData.length > 0 && Utils.plainKey(e) && ["Backspace", _Chips._backKey(this.el)].includes(e.key);
|
|
290
|
+
}
|
|
283
291
|
_renderChip(chip) {
|
|
284
292
|
if (!chip.id && chip.id !== 0) return;
|
|
285
293
|
const label = chip.text || chip.id;
|
|
@@ -305,6 +313,17 @@ var _Chips = class _Chips extends Component {
|
|
|
305
313
|
}
|
|
306
314
|
return renderedChip;
|
|
307
315
|
}
|
|
316
|
+
/**
|
|
317
|
+
* Copies the starting chips, so adding or deleting one does not edit the
|
|
318
|
+
* caller's array and a batch init does not share one list. Blank ids,
|
|
319
|
+
* duplicates and chips past the limit are dropped, as addChip drops them: a
|
|
320
|
+
* blank id used to render nothing and throw from the constructor.
|
|
321
|
+
*/
|
|
322
|
+
_takeInitialData(data) {
|
|
323
|
+
for (const chip of data) {
|
|
324
|
+
if (this.chipsData.length < this.options.limit && this._isValidAndNotExist(chip)) this.chipsData.push(chip);
|
|
325
|
+
}
|
|
326
|
+
}
|
|
308
327
|
_renderChips() {
|
|
309
328
|
this._chips = [];
|
|
310
329
|
for (let i = 0; i < this.chipsData.length; i++) {
|
|
@@ -338,25 +357,47 @@ var _Chips = class _Chips extends Component {
|
|
|
338
357
|
/** The "Add" row is a deliberate choice, so it adds a chip even in an autocompleteOnly field. */
|
|
339
358
|
_addTyped(text) {
|
|
340
359
|
if (_Chips.getInstance(this.el) !== this) return;
|
|
341
|
-
this.addChip({ id: text });
|
|
360
|
+
this.addChip({ id: text.trim() });
|
|
342
361
|
this._input.value = "";
|
|
343
362
|
this._input.focus();
|
|
344
363
|
}
|
|
345
364
|
_setupInput() {
|
|
346
365
|
this._input = this.el.querySelector("input");
|
|
347
366
|
if (!this._input) {
|
|
348
|
-
this._input = document.createElement("input");
|
|
349
|
-
this.el.append(
|
|
367
|
+
const input = this._input = document.createElement("input");
|
|
368
|
+
this.el.append(input);
|
|
369
|
+
this._undo.push(() => input.remove());
|
|
350
370
|
}
|
|
351
|
-
this._input
|
|
371
|
+
this._addClass(this._input, "input");
|
|
372
|
+
this._keepAttribute(this._input, "placeholder");
|
|
352
373
|
this.hasAutocomplete = Object.keys(this.options.autocompleteOptions).length > 0;
|
|
353
374
|
if (this.hasAutocomplete) this._setupAutocomplete();
|
|
354
375
|
this._setPlaceholder();
|
|
355
|
-
if (!this._input.getAttribute("id"))
|
|
376
|
+
if (!this._input.getAttribute("id")) {
|
|
377
|
+
this._keepAttribute(this._input, "id");
|
|
378
|
+
this._input.setAttribute("id", Utils.guid());
|
|
379
|
+
}
|
|
356
380
|
}
|
|
357
381
|
_setupLabel() {
|
|
358
382
|
this._label = this.el.querySelector("label");
|
|
359
|
-
if (this._label
|
|
383
|
+
if (!this._label || !this._input) return;
|
|
384
|
+
this._keepAttribute(this._label, "for");
|
|
385
|
+
this._label.setAttribute("for", this._input.getAttribute("id"));
|
|
386
|
+
}
|
|
387
|
+
/** Adds a class the markup did not have, for destroy() to take off. */
|
|
388
|
+
_addClass(el, name) {
|
|
389
|
+
if (el.classList.contains(name)) return;
|
|
390
|
+
const hadClass = el.hasAttribute("class");
|
|
391
|
+
el.classList.add(name);
|
|
392
|
+
this._undo.push(() => {
|
|
393
|
+
el.classList.remove(name);
|
|
394
|
+
if (!hadClass && !el.classList.length) el.removeAttribute("class");
|
|
395
|
+
});
|
|
396
|
+
}
|
|
397
|
+
/** Keeps an attribute's value for destroy() to put back. */
|
|
398
|
+
_keepAttribute(el, name) {
|
|
399
|
+
const value = el.getAttribute(name);
|
|
400
|
+
this._undo.push(() => restoreAttribute(el, name, value));
|
|
360
401
|
}
|
|
361
402
|
_setPlaceholder() {
|
|
362
403
|
if (!this._input) return;
|
|
@@ -367,8 +408,8 @@ var _Chips = class _Chips extends Component {
|
|
|
367
408
|
}
|
|
368
409
|
}
|
|
369
410
|
_isValidAndNotExist(chip) {
|
|
370
|
-
const isValid = !!chip.id || chip.id === 0;
|
|
371
|
-
const doesNotExist = !this.chipsData.some((item) => item.id
|
|
411
|
+
const isValid = (!!chip.id || chip.id === 0) && String(chip.id).trim() !== "";
|
|
412
|
+
const doesNotExist = !this.chipsData.some((item) => String(item.id) === String(chip.id));
|
|
372
413
|
return isValid && doesNotExist;
|
|
373
414
|
}
|
|
374
415
|
/**
|
|
@@ -410,7 +451,7 @@ var _Chips = class _Chips extends Component {
|
|
|
410
451
|
root = "host" in root ? root.host.getRootNode() : null;
|
|
411
452
|
}
|
|
412
453
|
this._notify("chip-delete", this.options.onChipDelete, { args: [this.el, chip], detail: { chip }, current: () => !this._chips.includes(chip) });
|
|
413
|
-
if (!focus || focusPath.some(({ root: root2, element }) => root2.activeElement !== element) || this.el
|
|
454
|
+
if (!focus || focusPath.some(({ root: root2, element }) => root2.activeElement !== element) || _Chips.getInstance(this.el) !== this) return;
|
|
414
455
|
if (focus === "previous" && this._chips.length) this.selectChip(Math.max(chipIndex - 1, 0));
|
|
415
456
|
else {
|
|
416
457
|
this._setSelected(null);
|
|
@@ -435,7 +476,7 @@ var _Chips = class _Chips extends Component {
|
|
|
435
476
|
el.addEventListener("click", (e) => {
|
|
436
477
|
if (!e.target.closest(".close")) return;
|
|
437
478
|
const chip = e.target.closest(".chip");
|
|
438
|
-
if (chip && !el
|
|
479
|
+
if (chip && !_Chips.getInstance(el)?._chips.includes(chip)) chip.remove();
|
|
439
480
|
});
|
|
440
481
|
});
|
|
441
482
|
});
|
|
@@ -447,4 +488,4 @@ var Chips = _Chips;
|
|
|
447
488
|
export {
|
|
448
489
|
Chips
|
|
449
490
|
};
|
|
450
|
-
//# sourceMappingURL=chunk-
|
|
491
|
+
//# sourceMappingURL=chunk-LXRHUQAX.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/ts/components/chips.ts"],
|
|
4
|
+
"sourcesContent": ["import { Utils, restoreAttribute } from '../core/utils';\nimport { Autocomplete, AutocompleteOptions } from './autocomplete';\nimport { Component, BaseOptions } from '../core/component';\nimport { FormControl, formAssociated, wrapInControl, unwrapControl } from '../core/formControl';\n\n/** Whether a key moves between chips. Alt, Ctrl and Meta stay the browser's. */\nconst isMoveKey = (e: KeyboardEvent) => (e.key === 'ArrowLeft' || e.key === 'ArrowRight') && Utils.plainKey(e);\n\nexport interface ChipData {\n /**\n * Unique identifier.\n */\n id: number | string;\n /**\n * Chip text. If not specified, \"id\" will be used.\n */\n text?: string;\n /**\n * Chip image (URL).\n */\n image?: string;\n}\n\n/** The form control a named field submits through, wrapping its input. */\nconst CONTROL = 'expressive-chips-control';\n\n/** The values in pasted text, split by commas, tabs or lines. */\nconst pastedValues = (e: ClipboardEvent) =>\n (e.clipboardData?.getData('text') ?? '').split(/[,\\t\\n]/).map((value) => value.trim()).filter(Boolean);\n\nexport interface ChipsI18nOptions {\n /** Prefix for the delete button's accessible name. */\n remove: string;\n /** What a required field says while it has no chips. */\n required: string;\n}\n\nexport interface ChipsOptions extends BaseOptions {\n /**\n * Set the chip data.\n * @default []\n */\n data: ChipData[];\n /**\n * Set first placeholder when there are no tags.\n * @default \"\"\n */\n placeholder: string;\n /**\n * Set second placeholder when adding additional tags.\n * @default \"\"\n */\n secondaryPlaceholder: string;\n /**\n * Set autocomplete options.\n * @default {}\n */\n autocompleteOptions: Partial<AutocompleteOptions>;\n /**\n * Toggles abililty to add custom value not in autocomplete list.\n * @default false\n */\n autocompleteOnly: boolean;\n /**\n * Set chips limit.\n * @default Infinity\n */\n limit: number;\n /**\n * Specifies class to be used in \"close\" button.\n * @default 'material-symbols'\n */\n closeIconClass: string;\n /**\n * Specifies option to render user input field\n * @default false;\n */\n allowUserInput: boolean;\n /**\n * Strings the component generates. `remove` prefixes the delete button's\n * accessible name, giving \"Remove Apple\". `required` is what a required\n * field says while it has no chips.\n * @default { remove: 'Remove', required: 'Add at least one item.' }\n */\n i18n: Partial<ChipsI18nOptions>;\n /**\n * Callback for chip add.\n * @default null\n */\n onChipAdd: (element: HTMLElement, chip: HTMLElement) => void;\n /**\n * Callback for chip select.\n * @default null\n */\n onChipSelect: (element: HTMLElement, chip: HTMLElement) => void;\n /**\n * Callback for chip delete.\n * @default null\n */\n onChipDelete: (element: HTMLElement, chip: HTMLElement) => void;\n}\n\nconst _defaults: ChipsOptions = {\n data: [],\n placeholder: '',\n secondaryPlaceholder: '',\n closeIconClass: 'material-symbols',\n autocompleteOptions: {},\n autocompleteOnly: false,\n limit: Infinity,\n allowUserInput: false,\n i18n: { remove: 'Remove', required: 'Add at least one item.' },\n onChipAdd: null,\n onChipSelect: null,\n onChipDelete: null\n};\n\nexport class Chips extends Component<ChipsOptions> {\n /** Array of the current chips data. */\n chipsData: ChipData[];\n /** If the chips has autocomplete enabled. */\n hasAutocomplete: boolean;\n /** Autocomplete instance, if any. */\n autocomplete: Autocomplete;\n _input: HTMLInputElement;\n _label: HTMLLabelElement;\n _chips: HTMLElement[];\n private _selectedChip: HTMLElement;\n /** The form name the text input had, which the chips submit instead. */\n private _name = '';\n /** The chips the field started with, which a form reset puts back. */\n private _initialData: ChipData[] = [];\n /** Undoes each change setup made to the markup, newest last. */\n private _undo: (() => void)[] = [];\n /** The input's own aria-required, or null, put back on destroy. */\n private _ariaRequired: string | null = null;\n /** The form control wrapping a named input, which the form reads instead of it. */\n private _control: FormControl | null = null;\n /** The named text input, whose form, disabled state and required the chips take over. */\n private _source: HTMLInputElement | null = null;\n private _required = false;\n\n /**\n * Selection is drawn by a class now, not by `:focus`, so it does not clear\n * itself when focus moves - every path that changes the selection has to go\n * through here or the class and the field drift apart.\n *\n * Deliberately no `aria-selected`: the chip is not an option in a listbox,\n * and putting the attribute on an element with no such role is the same\n * defect the semantics standard exists to remove.\n */\n private _setSelected(chip: HTMLElement | null) {\n this._selectedChip?.classList.remove('selected');\n this._selectedChip = chip;\n chip?.classList.add('selected');\n }\n\n constructor(el: HTMLElement, options: Partial<ChipsOptions>) {\n super(el, options);\n\n this._addClass(this.el, 'chips');\n this.chipsData = [];\n this._chips = [];\n this._takeName();\n\n // Render initial chips\n this._takeInitialData(this.options.data);\n if (this.chipsData.length) this._renderChips();\n\n // Render input element, setup event handlers\n if (this.options.allowUserInput) {\n this._addClass(this.el, 'field');\n this._setupInput();\n this._setupEventHandlers();\n // move input to end, inside its control when it has one\n this.el.append(this._end);\n }\n // After _setupInput: the label points at the input's id, which is only\n // assigned there. Running this first threw on any .chips with a <label>.\n this._setupLabel();\n this._sync();\n // After autocomplete, which can turn the input's value into a chip.\n this._initialData = [...this.chipsData];\n }\n\n static get defaults() {\n return _defaults;\n }\n\n static key = 'Expressive_Chips';\n\n getData() {\n return this.chipsData;\n }\n\n destroy() {\n if (this.autocomplete && Autocomplete.getInstance(this._input) === this.autocomplete) {\n this.autocomplete.destroy();\n }\n this._events.abort();\n this._chips.forEach((c) => c.remove());\n this._chips = [];\n this._giveNameBack();\n this.el.classList.remove('focus');\n this._undo.reverse().forEach((undo) => undo());\n this._undo = [];\n super.destroy();\n }\n\n _setupEventHandlers() {\n const { signal } = this._events;\n this.el.addEventListener('click', this._handleChipClick, { signal });\n this.el.addEventListener('keydown', Chips._handleChipsKeydown, { signal });\n this.el.addEventListener('focusin', this._handleFocusIn, { signal });\n this.el.addEventListener('focusout', this._handleFocusOut, { signal });\n this._input.addEventListener('focus', this._handleInputFocus, { signal });\n this._input.addEventListener('blur', this._handleInputBlur, { signal });\n this._input.addEventListener('keydown', this._handleInputKeydown, { signal });\n this._input.addEventListener('paste', this._handleInputPaste, { signal });\n }\n\n /**\n * A text input with a `name` would submit whatever is half typed. The chips\n * submit under that name instead, one value per chip, as a multiple select\n * does, so the input gives its name up until destroy().\n */\n private _takeName() {\n const input = this._editorInput();\n this._name = input?.getAttribute('name') ?? '';\n // ponytail: without form-associated custom elements (jsdom) the input keeps its name and submits its text.\n if (this._name && formAssociated()) this._wrap(input);\n }\n\n /**\n * Wraps the input in the form control, which takes its name and required.\n * `display: contents` lays the input out as a child of the field still.\n */\n private _wrap(input: HTMLInputElement) {\n this._source = input;\n this._takeRequired(input);\n // The control follows the input's disabled state and form; a read-only input is not validated, so its required no longer counts.\n this._control = wrapInControl(CONTROL, input, () => this._validate());\n this._control.onFormReset = () => this._resetChips();\n this._validate();\n }\n\n /**\n * The editor's text field, or null. A static .chips of filter checkboxes,\n * which AutoInit also starts, keeps its own native form values.\n */\n private _editorInput() {\n return this.options.allowUserInput ? this.el.querySelector<HTMLInputElement>('input:is(:not([type]), [type=\"text\"])') : null;\n }\n\n /** Where the text field ends: chips go before it, and it goes last. */\n private get _end() {\n return this._control ?? this._input;\n }\n\n /** After the chips change: give the form one value per chip and update a required field's validity. */\n private _sync() {\n if (!this._control) return;\n const data = new FormData();\n this.chipsData.forEach((chip) => data.append(this._name, String(chip.id)));\n this._control.internals.setFormValue(data);\n this._validate();\n }\n\n /**\n * The chips are what is required, not the text, so `required` moves to the\n * control, and aria-required keeps telling assistive technology.\n */\n private _takeRequired(input: HTMLInputElement) {\n this._required = input.required;\n if (!this._required) return;\n this._ariaRequired = input.getAttribute('aria-required');\n input.required = false;\n input.setAttribute('aria-required', 'true');\n }\n\n /**\n * A required field is valid once it has a chip, whatever is half typed. The\n * control holds this validity, apart from any error the page sets on the\n * input, and anchors it at the input, which a submit then focuses.\n */\n private _validate() {\n const internals = this._control.internals;\n if (this._required && !this._source.readOnly && !this.chipsData.length) {\n internals.setValidity({ valueMissing: true }, this._requiredMessage, this._anchor);\n } else internals.setValidity({});\n }\n\n /** The input, unless page script moved it out of the control, where it cannot anchor the message. */\n private get _anchor() {\n return this._control.contains(this._source) ? this._source : undefined;\n }\n\n /** A validity flag needs a message, so an empty i18n.required falls back to the default. */\n private get _requiredMessage() {\n return this.options.i18n.required || _defaults.i18n.required;\n }\n\n private _resetChips() {\n this._setSelected(null);\n this._chips.forEach((chip) => chip.remove());\n this.chipsData = [...this._initialData];\n this._chips = this.chipsData.map((chip) => this._renderChip(chip));\n this._control.before(...this._chips);\n this._setPlaceholder();\n this._sync();\n }\n\n /** Unwraps the input, with whatever else went in the control, and gives it its name and required back. */\n private _giveNameBack() {\n if (!this._control) return;\n unwrapControl(this._control, this._source);\n this._control = null;\n if (!this._required) return;\n this._source.required = true;\n restoreAttribute(this._source, 'aria-required', this._ariaRequired);\n }\n\n /** Whether only an autocomplete suggestion can become a chip. */\n private get _suggestionsOnly() {\n return this.hasAutocomplete && this.options.autocompleteOnly;\n }\n\n /** Pasted text that lists several values, split by commas, tabs or lines, adds a chip for each. */\n _handleInputPaste = (e: ClipboardEvent) => {\n const values = pastedValues(e);\n if (values.length < 2 || this._suggestionsOnly) return;\n e.preventDefault();\n // An add callback can destroy or replace the instance; the rest of the paste is its.\n values.every((id) => (this.addChip({ id }), Chips.getInstance(this.el) === this));\n };\n\n _handleChipClick = (e: MouseEvent) => {\n const _chip = (<HTMLElement>e.target).closest('.chip');\n // closest, not classList: the close button now wraps an icon span, so a\n // click on the glyph reports the span as the target.\n const clickedClose = !!(<HTMLElement>e.target).closest('.close');\n if (_chip) {\n // Index into the chip list, not into the container's children: the\n // container also holds the label and the input, so counting children\n // gave an index that did not line up with chipsData.\n const index = this._chips.indexOf(_chip as HTMLElement);\n if (index < 0) return;\n if (clickedClose) {\n this._deleteChip(index, 'input');\n } else {\n this.selectChip(index);\n }\n // Default handle click to focus on input\n } else {\n this._input.focus();\n }\n };\n\n /** The arrow that points back towards the first chip, which in RTL is Right. */\n private static _backKey(el: Element) {\n return getComputedStyle(el).direction === 'rtl' ? 'ArrowRight' : 'ArrowLeft';\n }\n\n static _handleChipsKeydown(e: KeyboardEvent) {\n const chips = (<HTMLElement>e.target).closest('.chips');\n\n // Don't handle keydown inputs on input and textarea\n const tag = (<HTMLElement>e.target).tagName;\n if (tag === 'INPUT' || tag === 'TEXTAREA' || !chips) return;\n\n const currChips = Chips.getInstance(chips);\n if (!currChips) return; // .chips markup without an instance behind it\n\n if (e.key === 'Backspace' || e.key === 'Delete') {\n const index = currChips._chips.indexOf((e.target as HTMLElement).closest('.chip'));\n if (index < 0) return;\n e.preventDefault();\n currChips._deleteChip(index, 'previous');\n } else if (isMoveKey(e)) {\n // Move from the chip that has focus, the same one Backspace deletes.\n const current = (e.target as HTMLElement).closest<HTMLElement>('.chip') ?? currChips._selectedChip;\n const index = currChips._chips.indexOf(current);\n if (index < 0) return;\n if (e.key === Chips._backKey(chips)) {\n if (index > 0) currChips.selectChip(index - 1);\n } else {\n const selectIndex = index + 1;\n if (selectIndex >= currChips.chipsData.length) {\n // Walking off the end returns to the input, so nothing is selected\n // any more - without this the last chip kept the class.\n currChips._setSelected(null);\n currChips._input.focus();\n }\n else currChips.selectChip(selectIndex);\n }\n }\n }\n\n // Selection follows focus: a chip is selected while focus is inside it, and\n // none is once focus moves to the input or out of the field.\n _handleFocusIn = (e: FocusEvent) => {\n const chip = (e.target as HTMLElement).closest<HTMLElement>('.chip');\n this._setSelected(chip && this._chips.includes(chip) ? chip : null);\n };\n\n _handleFocusOut = (e: FocusEvent) => {\n if (!this.el.contains(e.relatedTarget as Node | null)) this._setSelected(null);\n };\n\n _handleInputFocus = () => {\n this.el.classList.add('focus');\n };\n\n _handleInputBlur = () => {\n this.el.classList.remove('focus');\n };\n\n _handleInputKeydown = (e: KeyboardEvent) => {\n // Enter that confirms an IME composition is not a request to add a chip.\n if (Utils.isComposing(e)) return;\n if (e.key === 'Enter') {\n // Override enter if autocompleting.\n if (this.hasAutocomplete && this.autocomplete?.isOpen &&\n this.autocomplete.container.querySelector('[role=\"option\"]')) {\n return;\n }\n e.preventDefault();\n if (!this.hasAutocomplete || !this.options.autocompleteOnly) {\n this.addChip({ id: this._input.value.trim() });\n }\n this._input.value = '';\n // The list answered the text Enter just used up.\n this.autocomplete?.close();\n } else if (this._leavesInput(e)) {\n e.preventDefault();\n this.selectChip(this.chipsData.length - 1);\n }\n };\n\n /** Whether a key moves from the empty input back to the last chip. */\n private _leavesInput(e: KeyboardEvent) {\n return this._input.value === '' && this.chipsData.length > 0 && Utils.plainKey(e) &&\n ['Backspace', Chips._backKey(this.el)].includes(e.key);\n }\n\n _renderChip(chip: ChipData): HTMLElement {\n if (!chip.id && chip.id !== 0) return;\n const label = chip.text || <string>chip.id;\n // <span>, not <div>: a chip is inline, and the container itself is not a\n // control. It used to be a <div tabindex=\"0\"> with no role - focusable,\n // and announcing nothing.\n const renderedChip = document.createElement('span');\n renderedChip.classList.add('chip');\n renderedChip.innerText = label;\n // attach image if needed\n if (chip.image) {\n const img = document.createElement('img');\n img.setAttribute('src', chip.image);\n renderedChip.insertBefore(img, renderedChip.firstChild);\n }\n if (this.options.allowUserInput) {\n // The delete affordance is the control, so it is the <button> and it\n // carries the name. `type` is explicit because a bare button inside a\n // form submits it.\n const closeButton = document.createElement('button');\n closeButton.type = 'button';\n closeButton.classList.add('close');\n closeButton.setAttribute('aria-label', `${this.options.i18n.remove} ${label}`);\n // The ligature is text and is read out, so the glyph is hidden and the\n // button's own label is what gets announced.\n const closeIcon = document.createElement('span');\n closeIcon.classList.add(this.options.closeIconClass);\n closeIcon.setAttribute('aria-hidden', 'true');\n closeIcon.innerText = 'close';\n closeButton.appendChild(closeIcon);\n renderedChip.appendChild(closeButton);\n }\n return renderedChip;\n }\n\n /**\n * Copies the starting chips, so adding or deleting one does not edit the\n * caller's array and a batch init does not share one list. Blank ids,\n * duplicates and chips past the limit are dropped, as addChip drops them: a\n * blank id used to render nothing and throw from the constructor.\n */\n private _takeInitialData(data: ChipData[]) {\n for (const chip of data) {\n if (this.chipsData.length < this.options.limit && this._isValidAndNotExist(chip)) this.chipsData.push(chip);\n }\n }\n\n _renderChips() {\n this._chips = []; //.remove();\n for (let i = 0; i < this.chipsData.length; i++) {\n const chipElem = this._renderChip(this.chipsData[i]);\n this.el.appendChild(chipElem);\n this._chips.push(chipElem);\n }\n }\n\n _setupAutocomplete() {\n this.options.autocompleteOptions.onAutocomplete = (items) => {\n if (Chips.getInstance(this.el) !== this) return;\n if (items.length > 0) {\n this.addChip({\n id: items[0].id,\n text: items[0].text,\n image: items[0].image\n });\n this._input.value = '';\n this._input.focus();\n }\n };\n // A new object, so a second Chips given the same options does not wrap this wrapper.\n const pageOnCreate = this.options.autocompleteOptions.onCreate;\n this.autocomplete = Autocomplete.init(this._input, {\n ...this.options.autocompleteOptions,\n onCreate: (text, autocomplete) => {\n this._addTyped(text);\n if (typeof pageOnCreate === 'function') pageOnCreate.call(autocomplete, text, autocomplete);\n }\n });\n }\n\n /** The \"Add\" row is a deliberate choice, so it adds a chip even in an autocompleteOnly field. */\n private _addTyped(text: string) {\n if (Chips.getInstance(this.el) !== this) return;\n this.addChip({ id: text.trim() });\n this._input.value = '';\n this._input.focus();\n }\n\n _setupInput() {\n this._input = this.el.querySelector('input');\n if (!this._input) {\n const input = (this._input = document.createElement('input'));\n this.el.append(input);\n this._undo.push(() => input.remove());\n }\n this._addClass(this._input, 'input');\n this._keepAttribute(this._input, 'placeholder');\n this.hasAutocomplete = Object.keys(this.options.autocompleteOptions).length > 0;\n // Setup autocomplete if needed\n if (this.hasAutocomplete) this._setupAutocomplete();\n this._setPlaceholder();\n // Set input id\n if (!this._input.getAttribute('id')) {\n this._keepAttribute(this._input, 'id');\n this._input.setAttribute('id', Utils.guid());\n }\n }\n\n _setupLabel() {\n this._label = this.el.querySelector('label');\n // No input to point at when allowUserInput is off.\n if (!this._label || !this._input) return;\n this._keepAttribute(this._label, 'for');\n this._label.setAttribute('for', this._input.getAttribute('id'));\n }\n\n /** Adds a class the markup did not have, for destroy() to take off. */\n private _addClass(el: Element, name: string) {\n if (el.classList.contains(name)) return;\n const hadClass = el.hasAttribute('class');\n el.classList.add(name);\n this._undo.push(() => {\n el.classList.remove(name);\n if (!hadClass && !el.classList.length) el.removeAttribute('class');\n });\n }\n\n /** Keeps an attribute's value for destroy() to put back. */\n private _keepAttribute(el: Element, name: string) {\n const value = el.getAttribute(name);\n this._undo.push(() => restoreAttribute(el, name, value));\n }\n\n _setPlaceholder() {\n if (!this._input) return;\n if (!this.chipsData.length && this.options.placeholder) {\n this._input.placeholder = this.options.placeholder;\n } else if (this.chipsData.length && this.options.secondaryPlaceholder) {\n this._input.placeholder = this.options.secondaryPlaceholder;\n }\n }\n\n _isValidAndNotExist(chip: ChipData) {\n // A blank or whitespace-only label is no chip.\n const isValid = (!!chip.id || chip.id === 0) && String(chip.id).trim() !== '';\n const doesNotExist = !this.chipsData.some((item) => String(item.id) === String(chip.id));\n return isValid && doesNotExist;\n }\n\n /**\n * Add chip to input.\n * @param chip Chip data object\n */\n addChip(chip: ChipData) {\n if (!this._isValidAndNotExist(chip) || this.chipsData.length >= this.options.limit) return;\n const renderedChip = this._renderChip(chip);\n this._chips.push(renderedChip);\n this.chipsData.push(chip);\n if (this._end) this._end.before(renderedChip);\n else this.el.append(renderedChip);\n this._setPlaceholder();\n this._sync();\n this._notify('chip-add', this.options.onChipAdd, { args: [this.el, renderedChip], detail: { chip: renderedChip }, current: () => this._chips.includes(renderedChip) });\n }\n\n /**\n * Delete nth chip.\n * @param chipIndex Index of chip\n */\n deleteChip(chipIndex: number) {\n const root = this.el.getRootNode() as Document | ShadowRoot;\n this._deleteChip(chipIndex, this._chips[chipIndex]?.contains(root.activeElement) ? 'input' : null);\n }\n\n private _deleteChip(chipIndex: number, focus: 'input' | 'previous' | null) {\n const chip = this._chips[chipIndex];\n if (!chip) return;\n if (this._selectedChip === chip) this._setSelected(null);\n chip.remove();\n this._chips.splice(chipIndex, 1);\n this.chipsData.splice(chipIndex, 1);\n this._setPlaceholder();\n this._sync();\n const focusPath: { root: Document | ShadowRoot; element: Element | null }[] = [];\n let root = this.el.getRootNode() as Document | ShadowRoot;\n while (root) {\n focusPath.push({ root, element: root.activeElement });\n root = 'host' in root ? root.host.getRootNode() as Document | ShadowRoot : null;\n }\n this._notify('chip-delete', this.options.onChipDelete, { args: [this.el, chip], detail: { chip }, current: () => !this._chips.includes(chip) });\n if (!focus || focusPath.some(({ root, element }) => root.activeElement !== element) || Chips.getInstance(this.el) !== this) return;\n if (focus === 'previous' && this._chips.length) this.selectChip(Math.max(chipIndex - 1, 0));\n else {\n this._setSelected(null);\n this._input?.focus();\n }\n }\n\n /**\n * Select nth chip.\n * @param chipIndex Index of chip\n */\n selectChip(chipIndex: number) {\n const chip = this._chips[chipIndex];\n if (!chip) return;\n this._setSelected(chip);\n // The chip is not a control any more, so focus goes to the one thing in it\n // that is - the delete button.\n (chip.querySelector('.close') as HTMLElement | null)?.focus();\n this._notify('chip-select', this.options.onChipSelect, { args: [this.el, chip], detail: { chip }, current: () => this._selectedChip === chip });\n }\n\n static Init() {\n // Handle removal of static chips - markup written by hand, which no Chips\n // instance tracks even when one sits on the container (AutoInit gives every\n // .chips one, usually without allowUserInput and so without a click\n // handler). A chip the instance rendered belongs to _handleChipClick:\n // removing the node here as well left chipsData holding an entry whose\n // element was gone.\n Utils.onDocumentReady(() => {\n const chips = document.querySelectorAll('.chips');\n chips.forEach((el) => {\n el.addEventListener('click', (e) => {\n // closest: the close button wraps an icon span, so a click on the\n // glyph reports the span.\n if (!(<HTMLElement>e.target).closest('.close')) return;\n const chip = (<HTMLElement>e.target).closest<HTMLElement>('.chip');\n if (chip && !Chips.getInstance(el)?._chips.includes(chip)) chip.remove();\n });\n });\n });\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["root"]
|
|
7
|
+
}
|
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import {
|
|
2
2
|
Component
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-EB2V4OKL.mjs";
|
|
4
4
|
import {
|
|
5
5
|
Utils,
|
|
6
6
|
controllerFor,
|
|
7
|
+
deepActiveElement,
|
|
7
8
|
restoreAttribute
|
|
8
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-67UNY7RH.mjs";
|
|
9
10
|
|
|
10
11
|
// src/ts/components/lightbox.ts
|
|
11
12
|
var _defaults = {
|
|
@@ -52,8 +53,12 @@ var Lightbox = class extends Component {
|
|
|
52
53
|
this._handleWindowChange = () => {
|
|
53
54
|
if (this.overlayActive) this.close();
|
|
54
55
|
};
|
|
56
|
+
// On keydown, and taken, so a dialog around the lightbox does not close on
|
|
57
|
+
// the same press.
|
|
55
58
|
this._handleWindowEscape = (e) => {
|
|
56
|
-
if (e.key
|
|
59
|
+
if (e.key !== "Escape") return;
|
|
60
|
+
e.preventDefault();
|
|
61
|
+
this.close();
|
|
57
62
|
};
|
|
58
63
|
// The image zooms in place, not in a modal, so Tab would reach the page
|
|
59
64
|
// behind the overlay. Tab closes it instead, then moves focus as usual.
|
|
@@ -115,7 +120,7 @@ var Lightbox = class extends Component {
|
|
|
115
120
|
const { signal } = this._windowEvents;
|
|
116
121
|
window.addEventListener("scroll", this._handleWindowChange, { passive: true, signal });
|
|
117
122
|
window.addEventListener("resize", this._handleWindowChange, { passive: true, signal });
|
|
118
|
-
window.addEventListener("
|
|
123
|
+
window.addEventListener("keydown", this._handleWindowEscape, { signal });
|
|
119
124
|
window.addEventListener("keydown", this._handleWindowTab, { signal });
|
|
120
125
|
this._animateImageIn();
|
|
121
126
|
};
|
|
@@ -168,8 +173,7 @@ var Lightbox = class extends Component {
|
|
|
168
173
|
// a click on the overlay, which cannot take focus, leaves it.
|
|
169
174
|
_restoreFocus() {
|
|
170
175
|
const root = this.el.getRootNode();
|
|
171
|
-
|
|
172
|
-
while (active?.shadowRoot?.activeElement) active = active.shadowRoot.activeElement;
|
|
176
|
+
const active = deepActiveElement(document);
|
|
173
177
|
if ([document.body, root.host].includes(active)) this._trigger.focus({ preventScroll: true });
|
|
174
178
|
}
|
|
175
179
|
_reset() {
|
|
@@ -313,4 +317,4 @@ Lightbox.key = "Expressive_Lightbox";
|
|
|
313
317
|
export {
|
|
314
318
|
Lightbox
|
|
315
319
|
};
|
|
316
|
-
//# sourceMappingURL=chunk-
|
|
320
|
+
//# sourceMappingURL=chunk-MA2SZZFB.mjs.map
|