@nova-design-system/nova-webcomponents 3.0.0 → 3.2.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/{constants-bcd6b2e2.js → constants-8fb8ccc0.js} +14 -1
- package/dist/cjs/constants-8fb8ccc0.js.map +1 -0
- package/dist/cjs/{index-9bda5507.js → index-108ddff0.js} +22 -6
- package/dist/cjs/index-108ddff0.js.map +1 -0
- package/dist/cjs/index.cjs.js +5 -471
- package/dist/cjs/index.cjs.js.map +1 -1
- package/dist/cjs/loader.cjs.js +2 -2
- package/dist/cjs/native.cjs.js +2 -2
- package/dist/cjs/nv-alert.cjs.entry.js +6 -6
- package/dist/cjs/nv-alert.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-avatar.cjs.entry.js +2 -2
- package/dist/cjs/nv-badge_2.cjs.entry.js +18 -9
- package/dist/cjs/nv-badge_2.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-breadcrumb.cjs.entry.js +1 -1
- package/dist/cjs/nv-breadcrumbs.cjs.entry.js +1 -1
- package/dist/cjs/nv-button.cjs.entry.js +2 -2
- package/dist/cjs/nv-calendar.cjs.entry.js +821 -843
- package/dist/cjs/nv-calendar.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-col.cjs.entry.js +1 -1
- package/dist/cjs/nv-datagrid.cjs.entry.js +423 -94
- package/dist/cjs/nv-datagrid.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-datagridcolumn.cjs.entry.js +2 -2
- package/dist/cjs/nv-datagridcolumn.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-dialog.cjs.entry.js +19 -13
- package/dist/cjs/nv-dialog.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-dialogfooter_2.cjs.entry.js +2 -2
- package/dist/cjs/nv-fieldcheckbox.cjs.entry.js +1 -1
- package/dist/cjs/nv-fielddate.cjs.entry.js +9 -18
- package/dist/cjs/nv-fielddate.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fielddaterange.cjs.entry.js +85 -32
- package/dist/cjs/nv-fielddaterange.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fielddropdown.cjs.entry.js +88 -57
- package/dist/cjs/nv-fielddropdown.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fielddropdownitem.cjs.entry.js +2 -2
- package/dist/cjs/nv-fieldmultiselect.cjs.entry.js +122 -104
- package/dist/cjs/nv-fieldmultiselect.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldnumber.cjs.entry.js +9 -5
- package/dist/cjs/nv-fieldnumber.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldpassword.cjs.entry.js +9 -5
- package/dist/cjs/nv-fieldpassword.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldradio.cjs.entry.js +4 -4
- package/dist/cjs/nv-fieldselect.cjs.entry.js +11 -7
- package/dist/cjs/nv-fieldselect.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldslider.cjs.entry.js +663 -0
- package/dist/cjs/nv-fieldslider.cjs.entry.js.map +1 -0
- package/dist/cjs/nv-fieldtext.cjs.entry.js +9 -5
- package/dist/cjs/nv-fieldtext.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldtextarea.cjs.entry.js +9 -5
- package/dist/cjs/nv-fieldtextarea.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-fieldtime.cjs.entry.js +16 -13
- package/dist/cjs/nv-fieldtime.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-icon.cjs.entry.js +4 -4
- package/dist/cjs/nv-icon.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-iconbutton_2.cjs.entry.js +3 -3
- package/dist/cjs/nv-menu.cjs.entry.js +4 -2
- package/dist/cjs/nv-menu.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-menuitem.cjs.entry.js +2 -2
- package/dist/cjs/nv-popover.cjs.entry.js +2 -2
- package/dist/cjs/nv-row.cjs.entry.js +2 -2
- package/dist/cjs/nv-stack.cjs.entry.js +2 -2
- package/dist/cjs/nv-table.cjs.entry.js +3 -3
- package/dist/cjs/nv-table.cjs.entry.js.map +1 -1
- package/dist/cjs/nv-tablecolumn.cjs.entry.js +1 -1
- package/dist/cjs/nv-toggle.cjs.entry.js +3 -3
- package/dist/cjs/nv-tooltip.cjs.entry.js +3 -3
- package/dist/cjs/nv-tooltip.cjs.entry.js.map +1 -1
- package/dist/collection/collection-manifest.json +1 -0
- package/dist/collection/components/nv-alert/nv-alert.css +3 -0
- package/dist/collection/components/nv-alert/nv-alert.js +6 -11
- package/dist/collection/components/nv-alert/nv-alert.js.map +1 -1
- package/dist/collection/components/nv-badge/nv-badge.css +181 -1
- package/dist/collection/components/nv-badge/nv-badge.docs.js +20 -1
- package/dist/collection/components/nv-badge/nv-badge.docs.js.map +1 -1
- package/dist/collection/components/nv-badge/nv-badge.js +39 -15
- package/dist/collection/components/nv-badge/nv-badge.js.map +1 -1
- package/dist/collection/components/nv-breadcrumbs/nv-breadcrumbs.docs.js +0 -1
- package/dist/collection/components/nv-breadcrumbs/nv-breadcrumbs.docs.js.map +1 -1
- package/dist/collection/components/nv-calendar/nv-calendar.css +25 -2
- package/dist/collection/components/nv-calendar/nv-calendar.docs.js +33 -38
- package/dist/collection/components/nv-calendar/nv-calendar.docs.js.map +1 -1
- package/dist/collection/components/nv-calendar/nv-calendar.js +659 -897
- package/dist/collection/components/nv-calendar/nv-calendar.js.map +1 -1
- package/dist/collection/components/nv-calendar/nv-calendar.utils.js +202 -0
- package/dist/collection/components/nv-calendar/nv-calendar.utils.js.map +1 -0
- package/dist/collection/components/nv-calendar/test/nv-calendar.utils.test.js +667 -0
- package/dist/collection/components/nv-calendar/test/nv-calendar.utils.test.js.map +1 -0
- package/dist/collection/components/nv-datagrid/nv-datagrid.css +98 -0
- package/dist/collection/components/nv-datagrid/nv-datagrid.docs.js +232 -51
- package/dist/collection/components/nv-datagrid/nv-datagrid.docs.js.map +1 -1
- package/dist/collection/components/nv-datagrid/nv-datagrid.js +437 -160
- package/dist/collection/components/nv-datagrid/nv-datagrid.js.map +1 -1
- package/dist/collection/components/nv-datagridcolumn/nv-datagridcolumn.js +20 -1
- package/dist/collection/components/nv-datagridcolumn/nv-datagridcolumn.js.map +1 -1
- package/dist/collection/components/nv-dialog/nv-dialog.css +29 -5
- package/dist/collection/components/nv-dialog/nv-dialog.docs.js +0 -1
- package/dist/collection/components/nv-dialog/nv-dialog.docs.js.map +1 -1
- package/dist/collection/components/nv-dialog/nv-dialog.js +16 -10
- package/dist/collection/components/nv-dialog/nv-dialog.js.map +1 -1
- package/dist/collection/components/nv-fielddate/nv-fielddate.docs.js +16 -8
- package/dist/collection/components/nv-fielddate/nv-fielddate.docs.js.map +1 -1
- package/dist/collection/components/nv-fielddate/nv-fielddate.js +48 -39
- package/dist/collection/components/nv-fielddate/nv-fielddate.js.map +1 -1
- package/dist/collection/components/nv-fielddate/styles/nv-fielddate.css +14 -1
- package/dist/collection/components/nv-fielddaterange/nv-fielddaterange.docs.js +12 -15
- package/dist/collection/components/nv-fielddaterange/nv-fielddaterange.docs.js.map +1 -1
- package/dist/collection/components/nv-fielddaterange/nv-fielddaterange.js +147 -68
- package/dist/collection/components/nv-fielddaterange/nv-fielddaterange.js.map +1 -1
- package/dist/collection/components/nv-fielddaterange/styles/nv-fielddaterange.css +20 -12
- package/dist/collection/components/nv-fielddropdown/nv-fielddropdown.docs.js +16 -0
- package/dist/collection/components/nv-fielddropdown/nv-fielddropdown.docs.js.map +1 -1
- package/dist/collection/components/nv-fielddropdown/nv-fielddropdown.js +197 -103
- package/dist/collection/components/nv-fielddropdown/nv-fielddropdown.js.map +1 -1
- package/dist/collection/components/nv-fielddropdown/styles/nv-fielddropdown.css +36 -1
- package/dist/collection/components/nv-fielddropdownitem/nv-fielddropdownitem.js +1 -1
- package/dist/collection/components/nv-fielddropdownitemcheck/nv-fielddropdownitemcheck.js +1 -1
- package/dist/collection/components/nv-fieldmultiselect/nv-fieldmultiselect.docs.js +8 -1
- package/dist/collection/components/nv-fieldmultiselect/nv-fieldmultiselect.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldmultiselect/nv-fieldmultiselect.js +228 -190
- package/dist/collection/components/nv-fieldmultiselect/nv-fieldmultiselect.js.map +1 -1
- package/dist/collection/components/nv-fieldmultiselect/{nv-fieldmultiselect.css → styles/nv-fieldmultiselect.css} +36 -1
- package/dist/collection/components/nv-fieldnumber/nv-fieldnumber.css +12 -1
- package/dist/collection/components/nv-fieldnumber/nv-fieldnumber.docs.js +8 -0
- package/dist/collection/components/nv-fieldnumber/nv-fieldnumber.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldnumber/nv-fieldnumber.js +27 -3
- package/dist/collection/components/nv-fieldnumber/nv-fieldnumber.js.map +1 -1
- package/dist/collection/components/nv-fieldpassword/nv-fieldpassword.css +12 -1
- package/dist/collection/components/nv-fieldpassword/nv-fieldpassword.docs.js +8 -0
- package/dist/collection/components/nv-fieldpassword/nv-fieldpassword.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldpassword/nv-fieldpassword.js +27 -3
- package/dist/collection/components/nv-fieldpassword/nv-fieldpassword.js.map +1 -1
- package/dist/collection/components/nv-fieldradio/nv-fieldradio.js +3 -3
- package/dist/collection/components/nv-fieldselect/nv-fieldselect.css +12 -1
- package/dist/collection/components/nv-fieldselect/nv-fieldselect.docs.js +8 -0
- package/dist/collection/components/nv-fieldselect/nv-fieldselect.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldselect/nv-fieldselect.js +29 -5
- package/dist/collection/components/nv-fieldselect/nv-fieldselect.js.map +1 -1
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.docs.js +264 -0
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.docs.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.js +1035 -0
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.utils.js +77 -0
- package/dist/collection/components/nv-fieldslider/nv-fieldslider.utils.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/partials/field-input.js +33 -0
- package/dist/collection/components/nv-fieldslider/partials/field-input.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/partials/range-thumb.js +34 -0
- package/dist/collection/components/nv-fieldslider/partials/range-thumb.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/partials/single-thumb.js +18 -0
- package/dist/collection/components/nv-fieldslider/partials/single-thumb.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/partials/tick-marks.js +18 -0
- package/dist/collection/components/nv-fieldslider/partials/tick-marks.js.map +1 -0
- package/dist/collection/components/nv-fieldslider/styles/nv-fieldslider.css +267 -0
- package/dist/collection/components/nv-fieldslider/test/nv-fieldslider.utils.test.js +159 -0
- package/dist/collection/components/nv-fieldslider/test/nv-fieldslider.utils.test.js.map +1 -0
- package/dist/collection/components/nv-fieldtext/nv-fieldtext.css +20 -1
- package/dist/collection/components/nv-fieldtext/nv-fieldtext.docs.js +17 -1
- package/dist/collection/components/nv-fieldtext/nv-fieldtext.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldtext/nv-fieldtext.js +28 -3
- package/dist/collection/components/nv-fieldtext/nv-fieldtext.js.map +1 -1
- package/dist/collection/components/nv-fieldtextarea/nv-fieldtextarea.css +30 -1
- package/dist/collection/components/nv-fieldtextarea/nv-fieldtextarea.docs.js +8 -0
- package/dist/collection/components/nv-fieldtextarea/nv-fieldtextarea.docs.js.map +1 -1
- package/dist/collection/components/nv-fieldtextarea/nv-fieldtextarea.js +27 -3
- package/dist/collection/components/nv-fieldtextarea/nv-fieldtextarea.js.map +1 -1
- package/dist/collection/components/nv-fieldtime/nv-fieldtime.js +13 -10
- package/dist/collection/components/nv-fieldtime/nv-fieldtime.js.map +1 -1
- package/dist/collection/components/nv-fieldtime/styles/nv-fieldtime.css +26 -3
- package/dist/collection/components/nv-icon/nv-icon.js +1 -1
- package/dist/collection/components/nv-icon/nv-icons.js +4 -470
- package/dist/collection/components/nv-icon/nv-icons.js.map +1 -1
- package/dist/collection/components/nv-iconbutton/nv-iconbutton.js +1 -1
- package/dist/collection/components/nv-loader/nv-loader.js +1 -1
- package/dist/collection/components/nv-menu/nv-menu.js +3 -1
- package/dist/collection/components/nv-menu/nv-menu.js.map +1 -1
- package/dist/collection/components/nv-menuitem/nv-menuitem.js +2 -2
- package/dist/collection/components/nv-popover/nv-popover.js +1 -1
- package/dist/collection/components/nv-row/nv-row.js +1 -1
- package/dist/collection/components/nv-stack/nv-stack.js +1 -1
- package/dist/collection/components/nv-table/nv-table.js +8 -11
- package/dist/collection/components/nv-table/nv-table.js.map +1 -1
- package/dist/collection/components/nv-toggle/nv-toggle.js +2 -2
- package/dist/collection/components/nv-tooltip/nv-tooltip.css +1 -0
- package/dist/collection/components/nv-tooltip/nv-tooltip.js +1 -1
- package/dist/collection/index.js.map +1 -1
- package/dist/collection/interfaces/Column.js.map +1 -1
- package/dist/collection/templates/navigation.docs.js +0 -1
- package/dist/collection/templates/navigation.docs.js.map +1 -1
- package/dist/collection/utils/constants.js +11 -0
- package/dist/collection/utils/constants.js.map +1 -1
- package/dist/components/index.js +6 -472
- package/dist/components/index.js.map +1 -1
- package/dist/components/nv-alert.js +7 -7
- package/dist/components/nv-alert.js.map +1 -1
- package/dist/components/nv-avatar.js +3 -3
- package/dist/components/nv-badge.js +1 -1
- package/dist/components/nv-breadcrumb.js +3 -3
- package/dist/components/nv-breadcrumbs.js +1 -1
- package/dist/components/nv-button.js +1 -1
- package/dist/components/nv-calendar.js +1 -1
- package/dist/components/nv-col.js +1 -1
- package/dist/components/nv-datagrid.js +447 -102
- package/dist/components/nv-datagrid.js.map +1 -1
- package/dist/components/nv-datagridcolumn.js +4 -3
- package/dist/components/nv-datagridcolumn.js.map +1 -1
- package/dist/components/nv-dialog.js +24 -18
- package/dist/components/nv-dialog.js.map +1 -1
- package/dist/components/nv-dialogfooter.js +1 -1
- package/dist/components/nv-dialogheader.js +1 -1
- package/dist/components/nv-fieldcheckbox.js +1 -1
- package/dist/components/nv-fielddate.js +19 -27
- package/dist/components/nv-fielddate.js.map +1 -1
- package/dist/components/nv-fielddaterange.js +99 -44
- package/dist/components/nv-fielddaterange.js.map +1 -1
- package/dist/components/nv-fielddropdown.js +103 -69
- package/dist/components/nv-fielddropdown.js.map +1 -1
- package/dist/components/nv-fielddropdownitem.js +1 -1
- package/dist/components/nv-fielddropdownitemcheck.js +1 -1
- package/dist/components/nv-fieldmultiselect.js +139 -120
- package/dist/components/nv-fieldmultiselect.js.map +1 -1
- package/dist/components/nv-fieldnumber.js +14 -9
- package/dist/components/nv-fieldnumber.js.map +1 -1
- package/dist/components/nv-fieldpassword.js +13 -8
- package/dist/components/nv-fieldpassword.js.map +1 -1
- package/dist/components/nv-fieldradio.js +4 -4
- package/dist/components/nv-fieldselect.js +15 -10
- package/dist/components/nv-fieldselect.js.map +1 -1
- package/dist/components/nv-fieldslider.d.ts +11 -0
- package/dist/components/nv-fieldslider.js +726 -0
- package/dist/components/nv-fieldslider.js.map +1 -0
- package/dist/components/nv-fieldtext.js +1 -158
- package/dist/components/nv-fieldtext.js.map +1 -1
- package/dist/components/nv-fieldtextarea.js +11 -6
- package/dist/components/nv-fieldtextarea.js.map +1 -1
- package/dist/components/nv-fieldtime.js +20 -17
- package/dist/components/nv-fieldtime.js.map +1 -1
- package/dist/components/nv-icon.js +1 -1
- package/dist/components/nv-iconbutton.js +1 -1
- package/dist/components/nv-loader.js +1 -1
- package/dist/components/nv-menu.js +7 -5
- package/dist/components/nv-menu.js.map +1 -1
- package/dist/components/nv-menuitem.js +1 -1
- package/dist/components/nv-popover.js +1 -1
- package/dist/components/nv-row.js +2 -2
- package/dist/components/nv-stack.js +2 -2
- package/dist/components/nv-table.js +3 -3
- package/dist/components/nv-table.js.map +1 -1
- package/dist/components/nv-tablecolumn.js +1 -1
- package/dist/components/nv-toggle.js +3 -3
- package/dist/components/nv-tooltip.js +1 -1
- package/dist/components/{p-dc3faba3.js → p-04cb3a6f.js} +5 -5
- package/dist/components/{p-dc3faba3.js.map → p-04cb3a6f.js.map} +1 -1
- package/dist/components/p-07a89754.js +187 -0
- package/dist/components/p-07a89754.js.map +1 -0
- package/dist/components/{p-b7b78e64.js → p-0ab80d95.js} +3 -3
- package/dist/components/{p-b7b78e64.js.map → p-0ab80d95.js.map} +1 -1
- package/dist/components/{p-8348db09.js → p-1f505531.js} +15 -2
- package/dist/components/p-1f505531.js.map +1 -0
- package/dist/components/{p-02752770.js → p-33e231f4.js} +2 -2
- package/dist/components/{p-02752770.js.map → p-33e231f4.js.map} +1 -1
- package/dist/components/p-4656efae.js +1111 -0
- package/dist/components/p-4656efae.js.map +1 -0
- package/dist/components/{p-2012b8ba.js → p-581e67cc.js} +4 -4
- package/dist/components/{p-2012b8ba.js.map → p-581e67cc.js.map} +1 -1
- package/dist/components/{p-1c45c0f2.js → p-679e0fa9.js} +16 -4
- package/dist/components/p-679e0fa9.js.map +1 -0
- package/dist/components/p-76a30bf1.js +88 -0
- package/dist/components/p-76a30bf1.js.map +1 -0
- package/dist/components/{p-150daf68.js → p-83c8873a.js} +3 -3
- package/dist/components/{p-150daf68.js.map → p-83c8873a.js.map} +1 -1
- package/dist/components/{p-c14f6b8e.js → p-c0a91091.js} +5 -5
- package/dist/components/p-c0a91091.js.map +1 -0
- package/dist/components/{p-6c364a23.js → p-cbdc2c8b.js} +6 -6
- package/dist/components/{p-6c364a23.js.map → p-cbdc2c8b.js.map} +1 -1
- package/dist/components/{p-2d9ba7d3.js → p-cbe9521f.js} +4 -4
- package/dist/components/{p-2d9ba7d3.js.map → p-cbe9521f.js.map} +1 -1
- package/dist/components/{p-a30b55fc.js → p-d19b41d2.js} +2 -2
- package/dist/components/{p-a30b55fc.js.map → p-d19b41d2.js.map} +1 -1
- package/dist/components/{p-4d3ec142.js → p-d63f1cbe.js} +4 -4
- package/dist/components/{p-4d3ec142.js.map → p-d63f1cbe.js.map} +1 -1
- package/dist/components/{p-e00cbb8a.js → p-dd2273a3.js} +2 -2
- package/dist/components/{p-e00cbb8a.js.map → p-dd2273a3.js.map} +1 -1
- package/dist/components/p-f0a5e7e4.js +167 -0
- package/dist/components/p-f0a5e7e4.js.map +1 -0
- package/dist/components/{p-f4d86795.js → p-f1859ddc.js} +4 -4
- package/dist/components/{p-f4d86795.js.map → p-f1859ddc.js.map} +1 -1
- package/dist/esm/{constants-98e2dcc2.js → constants-b97e736d.js} +15 -2
- package/dist/esm/constants-b97e736d.js.map +1 -0
- package/dist/esm/{index-1fb7a9a6.js → index-8f0e5f19.js} +22 -6
- package/dist/esm/index-8f0e5f19.js.map +1 -0
- package/dist/esm/index.js +5 -471
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/loader.js +3 -3
- package/dist/esm/native.js +3 -3
- package/dist/esm/nv-alert.entry.js +6 -6
- package/dist/esm/nv-alert.entry.js.map +1 -1
- package/dist/esm/nv-avatar.entry.js +2 -2
- package/dist/esm/nv-badge_2.entry.js +18 -9
- package/dist/esm/nv-badge_2.entry.js.map +1 -1
- package/dist/esm/nv-breadcrumb.entry.js +1 -1
- package/dist/esm/nv-breadcrumbs.entry.js +1 -1
- package/dist/esm/nv-button.entry.js +2 -2
- package/dist/esm/nv-calendar.entry.js +821 -843
- package/dist/esm/nv-calendar.entry.js.map +1 -1
- package/dist/esm/nv-col.entry.js +1 -1
- package/dist/esm/nv-datagrid.entry.js +423 -94
- package/dist/esm/nv-datagrid.entry.js.map +1 -1
- package/dist/esm/nv-datagridcolumn.entry.js +2 -2
- package/dist/esm/nv-datagridcolumn.entry.js.map +1 -1
- package/dist/esm/nv-dialog.entry.js +19 -13
- package/dist/esm/nv-dialog.entry.js.map +1 -1
- package/dist/esm/nv-dialogfooter_2.entry.js +2 -2
- package/dist/esm/nv-fieldcheckbox.entry.js +1 -1
- package/dist/esm/nv-fielddate.entry.js +9 -18
- package/dist/esm/nv-fielddate.entry.js.map +1 -1
- package/dist/esm/nv-fielddaterange.entry.js +85 -32
- package/dist/esm/nv-fielddaterange.entry.js.map +1 -1
- package/dist/esm/nv-fielddropdown.entry.js +88 -57
- package/dist/esm/nv-fielddropdown.entry.js.map +1 -1
- package/dist/esm/nv-fielddropdownitem.entry.js +2 -2
- package/dist/esm/nv-fieldmultiselect.entry.js +122 -104
- package/dist/esm/nv-fieldmultiselect.entry.js.map +1 -1
- package/dist/esm/nv-fieldnumber.entry.js +9 -5
- package/dist/esm/nv-fieldnumber.entry.js.map +1 -1
- package/dist/esm/nv-fieldpassword.entry.js +9 -5
- package/dist/esm/nv-fieldpassword.entry.js.map +1 -1
- package/dist/esm/nv-fieldradio.entry.js +4 -4
- package/dist/esm/nv-fieldselect.entry.js +11 -7
- package/dist/esm/nv-fieldselect.entry.js.map +1 -1
- package/dist/esm/nv-fieldslider.entry.js +659 -0
- package/dist/esm/nv-fieldslider.entry.js.map +1 -0
- package/dist/esm/nv-fieldtext.entry.js +9 -5
- package/dist/esm/nv-fieldtext.entry.js.map +1 -1
- package/dist/esm/nv-fieldtextarea.entry.js +9 -5
- package/dist/esm/nv-fieldtextarea.entry.js.map +1 -1
- package/dist/esm/nv-fieldtime.entry.js +16 -13
- package/dist/esm/nv-fieldtime.entry.js.map +1 -1
- package/dist/esm/nv-icon.entry.js +4 -4
- package/dist/esm/nv-icon.entry.js.map +1 -1
- package/dist/esm/nv-iconbutton_2.entry.js +3 -3
- package/dist/esm/nv-menu.entry.js +4 -2
- package/dist/esm/nv-menu.entry.js.map +1 -1
- package/dist/esm/nv-menuitem.entry.js +2 -2
- package/dist/esm/nv-popover.entry.js +2 -2
- package/dist/esm/nv-row.entry.js +2 -2
- package/dist/esm/nv-stack.entry.js +2 -2
- package/dist/esm/nv-table.entry.js +3 -3
- package/dist/esm/nv-table.entry.js.map +1 -1
- package/dist/esm/nv-tablecolumn.entry.js +1 -1
- package/dist/esm/nv-toggle.entry.js +3 -3
- package/dist/esm/nv-tooltip.entry.js +3 -3
- package/dist/esm/nv-tooltip.entry.js.map +1 -1
- package/dist/native/index.esm.js +1 -1
- package/dist/native/index.esm.js.map +1 -1
- package/dist/native/native.css +1 -1
- package/dist/native/native.esm.js +1 -1
- package/dist/native/native.esm.js.map +1 -1
- package/dist/native/{p-6b348684.entry.js → p-0323daf6.entry.js} +2 -2
- package/dist/native/{p-d5cbf5c8.entry.js → p-05d95d4d.entry.js} +2 -2
- package/dist/native/{p-fb5bddba.entry.js → p-0ec1e2e3.entry.js} +2 -2
- package/dist/native/{p-c7b201cd.entry.js → p-16a4cdf3.entry.js} +2 -2
- package/dist/native/p-19fb0fd0.entry.js +2 -0
- package/dist/native/p-19fb0fd0.entry.js.map +1 -0
- package/dist/native/p-1e3d3374.entry.js +2 -0
- package/dist/native/{p-9135fdf5.entry.js.map → p-1e3d3374.entry.js.map} +1 -1
- package/dist/native/p-21e7132f.entry.js +2 -0
- package/dist/native/p-21e7132f.entry.js.map +1 -0
- package/dist/native/p-221b8f72.entry.js +2 -0
- package/dist/native/p-221b8f72.entry.js.map +1 -0
- package/dist/native/p-2805f9f2.entry.js +2 -0
- package/dist/native/p-2805f9f2.entry.js.map +1 -0
- package/dist/native/p-3f2b6a22.entry.js +2 -0
- package/dist/native/p-3f2b6a22.entry.js.map +1 -0
- package/dist/native/{p-0245863d.entry.js → p-407fc32d.entry.js} +2 -2
- package/dist/native/{p-63e6aed3.entry.js → p-4c0d81b0.entry.js} +2 -2
- package/dist/native/p-4c0d81b0.entry.js.map +1 -0
- package/dist/native/{p-39bb95ff.entry.js → p-519b4819.entry.js} +2 -2
- package/dist/native/{p-fa77a591.entry.js → p-5382eab2.entry.js} +2 -2
- package/dist/native/p-5ba3fc3c.entry.js +2 -0
- package/dist/native/p-5ba3fc3c.entry.js.map +1 -0
- package/dist/native/{p-bad11367.entry.js → p-60b204ac.entry.js} +2 -2
- package/dist/native/p-60b204ac.entry.js.map +1 -0
- package/dist/native/p-7092a675.entry.js +2 -0
- package/dist/native/p-711a7778.js +3 -0
- package/dist/native/p-711a7778.js.map +1 -0
- package/dist/native/p-759c9ce4.entry.js +2 -0
- package/dist/native/p-759c9ce4.entry.js.map +1 -0
- package/dist/native/{p-d7a76400.entry.js → p-7c676f2c.entry.js} +2 -2
- package/dist/native/p-7c6edd1c.entry.js +2 -0
- package/dist/native/p-7c6edd1c.entry.js.map +1 -0
- package/dist/native/p-987c79d8.entry.js +2 -0
- package/dist/native/p-987c79d8.entry.js.map +1 -0
- package/dist/native/{p-f85aca27.entry.js → p-9fba8663.entry.js} +2 -2
- package/dist/native/{p-b094296d.entry.js → p-a2c0f1a7.entry.js} +2 -2
- package/dist/native/p-aa86af25.entry.js +2 -0
- package/dist/native/p-aa86af25.entry.js.map +1 -0
- package/dist/native/p-adc96c3a.entry.js +2 -0
- package/dist/native/p-adc96c3a.entry.js.map +1 -0
- package/dist/native/p-b0fc08e7.entry.js +2 -0
- package/dist/native/p-b0fc08e7.entry.js.map +1 -0
- package/dist/native/{p-6ff228da.entry.js → p-c930adb7.entry.js} +2 -2
- package/dist/native/{p-701b5557.entry.js → p-cfe0a6c6.entry.js} +2 -2
- package/dist/native/p-d07ab618.entry.js +2 -0
- package/dist/native/p-dac0089b.entry.js +2 -0
- package/dist/native/p-dac0089b.entry.js.map +1 -0
- package/dist/native/p-de2c07a6.entry.js +13 -0
- package/dist/native/p-de2c07a6.entry.js.map +1 -0
- package/dist/native/p-ed488498.entry.js +7 -0
- package/dist/native/p-ed488498.entry.js.map +1 -0
- package/dist/native/p-ef76178b.entry.js +2 -0
- package/dist/native/p-ef76178b.entry.js.map +1 -0
- package/dist/native/{p-e5de64d5.entry.js → p-f0ddf60b.entry.js} +2 -2
- package/dist/native/p-f39803d9.entry.js +2 -0
- package/dist/native/p-f39803d9.entry.js.map +1 -0
- package/dist/native/{p-59768ee5.js → p-f85c08f1.js} +2 -2
- package/dist/native/p-f85c08f1.js.map +1 -0
- package/dist/native/p-fb897f7d.entry.js +2 -0
- package/dist/native/p-fb897f7d.entry.js.map +1 -0
- package/dist/native/{p-244f56ac.entry.js → p-fc3bea07.entry.js} +2 -2
- package/dist/types/components/nv-alert/nv-alert.d.ts +1 -1
- package/dist/types/components/nv-badge/nv-badge.d.ts +11 -3
- package/dist/types/components/nv-calendar/nv-calendar.d.ts +70 -112
- package/dist/types/components/nv-calendar/nv-calendar.utils.d.ts +60 -0
- package/dist/types/components/nv-calendar/test/nv-calendar.utils.test.d.ts +1 -0
- package/dist/types/components/nv-datagrid/nv-datagrid.d.ts +47 -26
- package/dist/types/components/nv-datagridcolumn/nv-datagridcolumn.d.ts +4 -0
- package/dist/types/components/nv-dialog/nv-dialog.d.ts +4 -0
- package/dist/types/components/nv-fielddate/nv-fielddate.d.ts +6 -7
- package/dist/types/components/nv-fielddaterange/nv-fielddaterange.d.ts +23 -12
- package/dist/types/components/nv-fielddropdown/nv-fielddropdown.d.ts +51 -26
- package/dist/types/components/nv-fieldmultiselect/nv-fieldmultiselect.d.ts +65 -55
- package/dist/types/components/nv-fieldnumber/nv-fieldnumber.d.ts +4 -0
- package/dist/types/components/nv-fieldpassword/nv-fieldpassword.d.ts +4 -0
- package/dist/types/components/nv-fieldselect/nv-fieldselect.d.ts +4 -0
- package/dist/types/components/nv-fieldslider/nv-fieldslider.d.ts +230 -0
- package/dist/types/components/nv-fieldslider/nv-fieldslider.docs.d.ts +4 -0
- package/dist/types/components/nv-fieldslider/nv-fieldslider.utils.d.ts +46 -0
- package/dist/types/components/nv-fieldslider/partials/field-input.d.ts +45 -0
- package/dist/types/components/nv-fieldslider/partials/range-thumb.d.ts +37 -0
- package/dist/types/components/nv-fieldslider/partials/single-thumb.d.ts +35 -0
- package/dist/types/components/nv-fieldslider/partials/tick-marks.d.ts +28 -0
- package/dist/types/components/nv-fieldslider/test/nv-fieldslider.utils.test.d.ts +1 -0
- package/dist/types/components/nv-fieldtext/nv-fieldtext.d.ts +5 -0
- package/dist/types/components/nv-fieldtextarea/nv-fieldtextarea.d.ts +4 -0
- package/dist/types/components/nv-icon/nv-icons.d.ts +1 -1
- package/dist/types/components/nv-table/nv-table.d.ts +13 -2
- package/dist/types/components.d.ts +656 -154
- package/dist/types/index.d.ts +0 -2
- package/dist/types/interfaces/Column.d.ts +5 -1
- package/dist/types/utils/constants.d.ts +9 -0
- package/dist/vscode-data.json +292 -1546
- package/hydrate/index.js +2715 -1533
- package/hydrate/index.mjs +2715 -1533
- package/package.json +6 -2
- package/dist/cjs/constants-bcd6b2e2.js.map +0 -1
- package/dist/cjs/index-9bda5507.js.map +0 -1
- package/dist/collection/interfaces/actionEvent.js +0 -2
- package/dist/collection/interfaces/actionEvent.js.map +0 -1
- package/dist/collection/interfaces/calendarShortcut.js +0 -2
- package/dist/collection/interfaces/calendarShortcut.js.map +0 -1
- package/dist/collection/interfaces/dateRange.js +0 -2
- package/dist/collection/interfaces/dateRange.js.map +0 -1
- package/dist/components/p-1c45c0f2.js.map +0 -1
- package/dist/components/p-373926aa.js +0 -177
- package/dist/components/p-373926aa.js.map +0 -1
- package/dist/components/p-591730e7.js +0 -88
- package/dist/components/p-591730e7.js.map +0 -1
- package/dist/components/p-8348db09.js.map +0 -1
- package/dist/components/p-c14f6b8e.js.map +0 -1
- package/dist/components/p-f331117c.js +0 -1133
- package/dist/components/p-f331117c.js.map +0 -1
- package/dist/esm/constants-98e2dcc2.js.map +0 -1
- package/dist/esm/index-1fb7a9a6.js.map +0 -1
- package/dist/native/p-0ee428d5.entry.js +0 -2
- package/dist/native/p-0ee428d5.entry.js.map +0 -1
- package/dist/native/p-2691e02d.entry.js +0 -2
- package/dist/native/p-37f0210e.entry.js +0 -2
- package/dist/native/p-37f0210e.entry.js.map +0 -1
- package/dist/native/p-4a440970.entry.js +0 -2
- package/dist/native/p-4a440970.entry.js.map +0 -1
- package/dist/native/p-4ae26462.entry.js +0 -7
- package/dist/native/p-4ae26462.entry.js.map +0 -1
- package/dist/native/p-4d9c4618.entry.js +0 -2
- package/dist/native/p-4d9c4618.entry.js.map +0 -1
- package/dist/native/p-4dc1d036.entry.js +0 -2
- package/dist/native/p-59768ee5.js.map +0 -1
- package/dist/native/p-59e0bd2b.entry.js +0 -2
- package/dist/native/p-59e0bd2b.entry.js.map +0 -1
- package/dist/native/p-5c00f092.entry.js +0 -2
- package/dist/native/p-5c00f092.entry.js.map +0 -1
- package/dist/native/p-63e6aed3.entry.js.map +0 -1
- package/dist/native/p-7f5eb2ac.entry.js +0 -2
- package/dist/native/p-7f5eb2ac.entry.js.map +0 -1
- package/dist/native/p-84a73e2a.entry.js +0 -2
- package/dist/native/p-84a73e2a.entry.js.map +0 -1
- package/dist/native/p-9135fdf5.entry.js +0 -2
- package/dist/native/p-93dc2f47.entry.js +0 -2
- package/dist/native/p-93dc2f47.entry.js.map +0 -1
- package/dist/native/p-9a267f16.entry.js +0 -13
- package/dist/native/p-9a267f16.entry.js.map +0 -1
- package/dist/native/p-9d6431c7.entry.js +0 -2
- package/dist/native/p-9d6431c7.entry.js.map +0 -1
- package/dist/native/p-ab002252.js +0 -3
- package/dist/native/p-ab002252.js.map +0 -1
- package/dist/native/p-b2ce83ad.entry.js +0 -2
- package/dist/native/p-b2ce83ad.entry.js.map +0 -1
- package/dist/native/p-bad11367.entry.js.map +0 -1
- package/dist/native/p-e1a4f776.entry.js +0 -2
- package/dist/native/p-e1a4f776.entry.js.map +0 -1
- package/dist/native/p-e49bbd02.entry.js +0 -2
- package/dist/native/p-e49bbd02.entry.js.map +0 -1
- package/dist/native/p-eee01062.entry.js +0 -2
- package/dist/native/p-eee01062.entry.js.map +0 -1
- package/dist/native/p-f6bdc270.entry.js +0 -2
- package/dist/native/p-f6bdc270.entry.js.map +0 -1
- package/dist/types/interfaces/actionEvent.d.ts +0 -13
- package/dist/types/interfaces/calendarShortcut.d.ts +0 -17
- package/dist/types/interfaces/dateRange.d.ts +0 -13
- /package/dist/native/{p-6b348684.entry.js.map → p-0323daf6.entry.js.map} +0 -0
- /package/dist/native/{p-d5cbf5c8.entry.js.map → p-05d95d4d.entry.js.map} +0 -0
- /package/dist/native/{p-fb5bddba.entry.js.map → p-0ec1e2e3.entry.js.map} +0 -0
- /package/dist/native/{p-c7b201cd.entry.js.map → p-16a4cdf3.entry.js.map} +0 -0
- /package/dist/native/{p-0245863d.entry.js.map → p-407fc32d.entry.js.map} +0 -0
- /package/dist/native/{p-39bb95ff.entry.js.map → p-519b4819.entry.js.map} +0 -0
- /package/dist/native/{p-fa77a591.entry.js.map → p-5382eab2.entry.js.map} +0 -0
- /package/dist/native/{p-2691e02d.entry.js.map → p-7092a675.entry.js.map} +0 -0
- /package/dist/native/{p-d7a76400.entry.js.map → p-7c676f2c.entry.js.map} +0 -0
- /package/dist/native/{p-f85aca27.entry.js.map → p-9fba8663.entry.js.map} +0 -0
- /package/dist/native/{p-b094296d.entry.js.map → p-a2c0f1a7.entry.js.map} +0 -0
- /package/dist/native/{p-6ff228da.entry.js.map → p-c930adb7.entry.js.map} +0 -0
- /package/dist/native/{p-701b5557.entry.js.map → p-cfe0a6c6.entry.js.map} +0 -0
- /package/dist/native/{p-4dc1d036.entry.js.map → p-d07ab618.entry.js.map} +0 -0
- /package/dist/native/{p-e5de64d5.entry.js.map → p-f0ddf60b.entry.js.map} +0 -0
- /package/dist/native/{p-244f56ac.entry.js.map → p-fc3bea07.entry.js.map} +0 -0
|
@@ -1,13 +1,6 @@
|
|
|
1
1
|
import { Host, h, } from "@stencil/core";
|
|
2
|
-
import dayjs from "dayjs";
|
|
3
|
-
import customParseFormat from "dayjs/plugin/customParseFormat";
|
|
4
|
-
import utc from "dayjs/plugin/utc";
|
|
5
|
-
import weekOfYear from "dayjs/plugin/weekOfYear";
|
|
6
2
|
import { WEEK_ABBREVIATIONS, CUSTOM_DAY_NAMES, CUSTOM_MONTH_NAMES, } from "../../utils/constants";
|
|
7
|
-
|
|
8
|
-
dayjs.extend(customParseFormat);
|
|
9
|
-
dayjs.extend(utc);
|
|
10
|
-
dayjs.extend(weekOfYear);
|
|
3
|
+
import { getWeekNumber, parseDate, isSameDate, formatDate, isSameOrAfter, isSameOrBefore, } from "./nv-calendar.utils";
|
|
11
4
|
/**
|
|
12
5
|
* @slot default - Child content of the component.
|
|
13
6
|
* @slot actions - Child content of the component.
|
|
@@ -27,33 +20,12 @@ export class NvCalendar {
|
|
|
27
20
|
*/
|
|
28
21
|
this.numberOfCalendars = 1;
|
|
29
22
|
/**
|
|
30
|
-
*
|
|
31
|
-
* ex: "2025-03-15"
|
|
32
|
-
*/
|
|
33
|
-
this.singleValue = '';
|
|
34
|
-
/**
|
|
35
|
-
* Selected date range
|
|
36
|
-
* format: { start: ISO string, end: ISO string }
|
|
37
|
-
* ex: { start: "2025-03-15", end: "2025-03-20" }
|
|
38
|
-
*/
|
|
39
|
-
this.rangeValue = '';
|
|
40
|
-
/**
|
|
41
|
-
* Minimum date for selection (ISO string format, ex: "2025-01-01")
|
|
42
|
-
*/
|
|
43
|
-
this.min = '';
|
|
44
|
-
/**
|
|
45
|
-
* Maximum date for selection (ISO string format, ex: "2025-12-31")
|
|
46
|
-
*/
|
|
47
|
-
this.max = '';
|
|
48
|
-
/** Disabled dates (ISO string array)
|
|
49
|
-
* @default '[]'
|
|
50
|
-
*/
|
|
51
|
-
this.disabledDates = '';
|
|
52
|
-
/** Locale for date formatting
|
|
23
|
+
* Locale for date formatting
|
|
53
24
|
* @default 'en-BE'
|
|
54
25
|
*/
|
|
55
26
|
this.locale = 'en-BE';
|
|
56
|
-
/**
|
|
27
|
+
/**
|
|
28
|
+
* Date format (ex: 'YYYY-MM-DD', 'DD-MM-YYYY', etc.)
|
|
57
29
|
* @default 'YYYY-MM-DD'
|
|
58
30
|
* @note If the date format is in UTC mode, the date will be displayed in UTC time.
|
|
59
31
|
* @note If the date format is not in UTC mode, the date will be displayed in the local time.
|
|
@@ -71,40 +43,454 @@ export class NvCalendar {
|
|
|
71
43
|
this.selectionType = 'single';
|
|
72
44
|
/**
|
|
73
45
|
* Show action buttons
|
|
74
|
-
* @default false
|
|
75
46
|
*/
|
|
76
47
|
this.showActions = false;
|
|
77
|
-
/**
|
|
78
|
-
* Custom actions to display in the footer
|
|
79
|
-
* JSON array of objects with the following properties:
|
|
80
|
-
* - label: string
|
|
81
|
-
* - onClick: function
|
|
82
|
-
* @default '[]'
|
|
83
|
-
*/
|
|
84
|
-
this.shortcuts = '[]';
|
|
85
48
|
/** Cache for parsed disabled dates */
|
|
86
49
|
this.parsedDisabledDates = [];
|
|
87
|
-
|
|
50
|
+
//#endregion PROPERTIES
|
|
51
|
+
/****************************************************************************/
|
|
52
|
+
//#region STATE
|
|
53
|
+
this.currentDate = null;
|
|
88
54
|
this.selectedDate = null;
|
|
89
|
-
/** Start date */
|
|
90
55
|
this.startDate = null;
|
|
91
|
-
/** End date */
|
|
92
56
|
this.endDate = null;
|
|
93
57
|
/** List of formatted months for the selector */
|
|
94
58
|
this.months = [];
|
|
59
|
+
/**
|
|
60
|
+
* Change the displayed month
|
|
61
|
+
* @param {number} offset - Month offset (-1 for previous, 1 for next)
|
|
62
|
+
*/
|
|
63
|
+
this.changeMonth = (offset) => {
|
|
64
|
+
const newDate = new Date(this.currentDate);
|
|
65
|
+
// Ensure we only move by one month at a time
|
|
66
|
+
newDate.setUTCMonth(newDate.getUTCMonth() + offset);
|
|
67
|
+
// Add the appropriate animation class
|
|
68
|
+
const containers = this.el.querySelectorAll('.calendar-grid');
|
|
69
|
+
containers.forEach(container => {
|
|
70
|
+
// Remove existing animation classes
|
|
71
|
+
container.classList.remove('slide-left', 'slide-right');
|
|
72
|
+
// Add the new animation class
|
|
73
|
+
const animationClass = offset > 0 ? 'slide-left' : 'slide-right';
|
|
74
|
+
container.classList.add(animationClass);
|
|
75
|
+
// Remove the class after the animation
|
|
76
|
+
setTimeout(() => {
|
|
77
|
+
container.classList.remove(animationClass);
|
|
78
|
+
}, 300); // 300ms corresponds to $slide-duration in the SCSS
|
|
79
|
+
});
|
|
80
|
+
this.currentDate = newDate;
|
|
81
|
+
};
|
|
82
|
+
/**
|
|
83
|
+
* Handles date selection based on the mode
|
|
84
|
+
* @param {Date} date - Selected date
|
|
85
|
+
*/
|
|
86
|
+
this.handleDateSelection = (date) => {
|
|
87
|
+
if (this.isDateDisabled(date)) {
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
if (this.selectionType === 'single') {
|
|
91
|
+
this.handleSingleSelection(date);
|
|
92
|
+
}
|
|
93
|
+
else {
|
|
94
|
+
this.handleRangeSelection(date);
|
|
95
|
+
}
|
|
96
|
+
};
|
|
97
|
+
/**
|
|
98
|
+
* Handles single date selection
|
|
99
|
+
* @param {Date} date - Selected date
|
|
100
|
+
*/
|
|
101
|
+
this.handleSingleSelection = (date) => {
|
|
102
|
+
if (!date)
|
|
103
|
+
return;
|
|
104
|
+
const formattedDate = formatDate(date, { dateFormat: this.dateFormat });
|
|
105
|
+
this.selectedDate = date;
|
|
106
|
+
this.singleDateChange.emit(formattedDate);
|
|
107
|
+
};
|
|
108
|
+
/**
|
|
109
|
+
* Handles range date selection
|
|
110
|
+
* @param {Date} date - Selected date
|
|
111
|
+
*/
|
|
112
|
+
this.handleRangeSelection = (date) => {
|
|
113
|
+
if (!this.startDate || (this.startDate && this.endDate)) {
|
|
114
|
+
this.startDate = date;
|
|
115
|
+
this.endDate = null;
|
|
116
|
+
}
|
|
117
|
+
else {
|
|
118
|
+
this.endDate = date;
|
|
119
|
+
if (this.startDate > this.endDate) {
|
|
120
|
+
[this.startDate, this.endDate] = [this.endDate, this.startDate];
|
|
121
|
+
}
|
|
122
|
+
this.rangeDateChange.emit({
|
|
123
|
+
start: formatDate(this.startDate, { dateFormat: this.dateFormat }),
|
|
124
|
+
end: formatDate(this.endDate, { dateFormat: this.dateFormat }),
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
};
|
|
128
|
+
/**
|
|
129
|
+
* Checks if a date is disabled.
|
|
130
|
+
* Disabled if:
|
|
131
|
+
* - The date is before min (if defined)
|
|
132
|
+
* - The date is after max (if defined)
|
|
133
|
+
* - The date is in the disabledDates array
|
|
134
|
+
* @param {Date} date - Date to check
|
|
135
|
+
* @returns {boolean} true if the date is disabled
|
|
136
|
+
*/
|
|
137
|
+
this.isDateDisabled = (date) => {
|
|
138
|
+
if (!date)
|
|
139
|
+
return true;
|
|
140
|
+
// Minimum bound check
|
|
141
|
+
if (this.min) {
|
|
142
|
+
const minDate = parseDate(this.min, this.dateFormat);
|
|
143
|
+
if (minDate && date < minDate) {
|
|
144
|
+
return true;
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
// Maximum bound check
|
|
148
|
+
if (this.max) {
|
|
149
|
+
const maxDate = parseDate(this.max, this.dateFormat);
|
|
150
|
+
if (maxDate && date > maxDate) {
|
|
151
|
+
return true;
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
// Check disabled dates
|
|
155
|
+
return this.parsedDisabledDates.some(disabledDate => isSameDate(date, disabledDate, { isUTCMode: this.isUTCMode }));
|
|
156
|
+
};
|
|
157
|
+
/**
|
|
158
|
+
* Checks if a date is in the selected range
|
|
159
|
+
* @param {Date} date - Date to check
|
|
160
|
+
* @returns {boolean} true if the date is in the range
|
|
161
|
+
*/
|
|
162
|
+
this.isDateInRange = (date) => {
|
|
163
|
+
if (!date || !this.startDate || !this.endDate)
|
|
164
|
+
return false;
|
|
165
|
+
const checkDate = parseDate(date, this.dateFormat);
|
|
166
|
+
const startDate = parseDate(this.startDate, this.dateFormat);
|
|
167
|
+
const endDate = parseDate(this.endDate, this.dateFormat);
|
|
168
|
+
// Verify if startDate and endDate are valid
|
|
169
|
+
if (isNaN(startDate.getTime()) || isNaN(endDate.getTime())) {
|
|
170
|
+
return false;
|
|
171
|
+
}
|
|
172
|
+
// Verify that startDate is before endDate (additional security)
|
|
173
|
+
if (startDate > endDate)
|
|
174
|
+
return false;
|
|
175
|
+
// Comparison based only on the date (year, month, day)
|
|
176
|
+
return (isSameOrAfter(checkDate, startDate, { isUTCMode: this.isUTCMode }) &&
|
|
177
|
+
isSameOrBefore(checkDate, endDate, { isUTCMode: this.isUTCMode }));
|
|
178
|
+
};
|
|
179
|
+
/**
|
|
180
|
+
* Retrieves the localized day names
|
|
181
|
+
* @returns {string[]} Array of short day names
|
|
182
|
+
*/
|
|
183
|
+
this.getDayNames = () => {
|
|
184
|
+
// If we have custom day names for this locale
|
|
185
|
+
if (CUSTOM_DAY_NAMES[this.locale]) {
|
|
186
|
+
const days = [...CUSTOM_DAY_NAMES[this.locale]];
|
|
187
|
+
// Reorganize the days based on the first day of the week
|
|
188
|
+
const firstDays = days.slice(0, this.firstDayOfWeek);
|
|
189
|
+
const remainingDays = days.slice(this.firstDayOfWeek);
|
|
190
|
+
return [...remainingDays, ...firstDays];
|
|
191
|
+
}
|
|
192
|
+
// Otherwise, use the default behavior
|
|
193
|
+
const formatter = new Intl.DateTimeFormat(this.locale, {
|
|
194
|
+
weekday: 'short',
|
|
195
|
+
});
|
|
196
|
+
const days = [...Array(7)].map((_, i) => formatter.format(new Date(2023, 0, i + 1)).toUpperCase());
|
|
197
|
+
// Reorganize the days based on the first day of the week
|
|
198
|
+
const firstDays = days.slice(0, this.firstDayOfWeek);
|
|
199
|
+
const remainingDays = days.slice(this.firstDayOfWeek);
|
|
200
|
+
return [...remainingDays, ...firstDays];
|
|
201
|
+
};
|
|
202
|
+
/**
|
|
203
|
+
* Generates the days of the current month
|
|
204
|
+
* @param {number} offset - Month offset (0 by default)
|
|
205
|
+
* @param {number} totalCalendars - Number of calendars to display (1 by default)
|
|
206
|
+
* @returns {Array<{ dayOfMonth: number | null, date: Date | null, isSelected: boolean, isDisabled: boolean }>} Array of formatted days
|
|
207
|
+
*/
|
|
208
|
+
this.getDaysInMonth = (offset = 0, totalCalendars = 1) => {
|
|
209
|
+
const year = this.currentDate.getUTCFullYear();
|
|
210
|
+
const month = this.currentDate.getUTCMonth() + offset;
|
|
211
|
+
const firstDay = new Date(Date.UTC(year, month, 1));
|
|
212
|
+
const lastDay = new Date(Date.UTC(year, month + 1, 0));
|
|
213
|
+
const days = [];
|
|
214
|
+
// Correct calculation of offset for previous month days
|
|
215
|
+
// Use getUTCDay to stay consistent with UTC timezone
|
|
216
|
+
const dayOfWeekIndex = firstDay.getUTCDay(); // 0 = Sunday, 1 = Monday, etc.
|
|
217
|
+
// Adjust based on firstDayOfWeek (if week starts on Monday, offset is different)
|
|
218
|
+
const offsetDays = (dayOfWeekIndex - this.firstDayOfWeek + 7) % 7;
|
|
219
|
+
// Add the days of the previous month for the first calendar
|
|
220
|
+
if (offset === 0 && offsetDays > 0) {
|
|
221
|
+
const prevMonthLastDay = new Date(Date.UTC(year, month, 0)).getUTCDate();
|
|
222
|
+
for (let i = offsetDays; i > 0; i--) {
|
|
223
|
+
const date = new Date(Date.UTC(year, month - 1, prevMonthLastDay - i + 1));
|
|
224
|
+
days.push({
|
|
225
|
+
dayOfMonth: date.getUTCDate(),
|
|
226
|
+
date,
|
|
227
|
+
isCurrentMonth: false,
|
|
228
|
+
isDisabled: this.isDateDisabled(date),
|
|
229
|
+
});
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
// Add the days of the current month
|
|
233
|
+
for (let i = 1; i <= lastDay.getUTCDate(); i++) {
|
|
234
|
+
const date = new Date(Date.UTC(year, month, i));
|
|
235
|
+
days.push({
|
|
236
|
+
dayOfMonth: i,
|
|
237
|
+
date,
|
|
238
|
+
isCurrentMonth: true,
|
|
239
|
+
isDisabled: this.isDateDisabled(date),
|
|
240
|
+
});
|
|
241
|
+
}
|
|
242
|
+
// Add the days of the next month only for the last calendar
|
|
243
|
+
if (offset === totalCalendars - 1) {
|
|
244
|
+
const nextMonthDaysNeeded = 7 - (days.length % 7 || 7);
|
|
245
|
+
for (let i = 1; i <= nextMonthDaysNeeded; i++) {
|
|
246
|
+
const date = new Date(Date.UTC(year, month + 1, i));
|
|
247
|
+
days.push({
|
|
248
|
+
dayOfMonth: i,
|
|
249
|
+
date,
|
|
250
|
+
isCurrentMonth: false,
|
|
251
|
+
isDisabled: this.isDateDisabled(date),
|
|
252
|
+
});
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
return days;
|
|
256
|
+
};
|
|
257
|
+
/** Initializes the list of formatted months according to the locale */
|
|
258
|
+
this.initializeMonths = () => {
|
|
259
|
+
// If we have custom month names for this locale
|
|
260
|
+
if (CUSTOM_MONTH_NAMES[this.locale]) {
|
|
261
|
+
this.months = CUSTOM_MONTH_NAMES[this.locale].map((label, value) => ({
|
|
262
|
+
value,
|
|
263
|
+
label,
|
|
264
|
+
}));
|
|
265
|
+
return;
|
|
266
|
+
}
|
|
267
|
+
// Otherwise, use the default behavior
|
|
268
|
+
const formatter = new Intl.DateTimeFormat(this.locale, { month: 'short' });
|
|
269
|
+
this.months = Array.from({ length: 12 }, (_, i) => ({
|
|
270
|
+
value: i,
|
|
271
|
+
label: formatter.format(new Date(2000, i, 1)).toUpperCase(),
|
|
272
|
+
}));
|
|
273
|
+
};
|
|
274
|
+
/**
|
|
275
|
+
* Retrieves the localized abbreviation for "week"
|
|
276
|
+
* @returns {string} Localized abbreviation for "week"
|
|
277
|
+
*/
|
|
278
|
+
this.getLocalizedWeekText = () => {
|
|
279
|
+
return WEEK_ABBREVIATIONS[this.locale] || 'W';
|
|
280
|
+
};
|
|
281
|
+
/**
|
|
282
|
+
* Handles month change in the selector
|
|
283
|
+
* @param {Event} event - Month change event
|
|
284
|
+
* @param {number} calendarOffset - Calendar offset (0 by default)
|
|
285
|
+
*/
|
|
286
|
+
this.handleMonthChange = (event, calendarOffset = 0) => {
|
|
287
|
+
const select = event.target;
|
|
288
|
+
const selectedMonth = parseInt(select.value, 10);
|
|
289
|
+
const currentMonth = this.currentDate.getUTCMonth();
|
|
290
|
+
// Calculate the difference considering the calendar offset
|
|
291
|
+
const monthDiff = selectedMonth - ((currentMonth + calendarOffset) % 12);
|
|
292
|
+
const newDate = new Date(this.currentDate);
|
|
293
|
+
newDate.setUTCMonth(newDate.getUTCMonth() + monthDiff);
|
|
294
|
+
this.currentDate = newDate;
|
|
295
|
+
};
|
|
296
|
+
/**
|
|
297
|
+
* Handles year change in the numeric entry
|
|
298
|
+
* @param {Event} event - Year change event
|
|
299
|
+
* @param {number} calendarOffset - Calendar offset (0 by default)
|
|
300
|
+
*/
|
|
301
|
+
this.handleYearChange = (event, calendarOffset = 0) => {
|
|
302
|
+
const input = event.target;
|
|
303
|
+
const year = parseInt(input.value, 10);
|
|
304
|
+
if (!isNaN(year) && year >= 1900 && year <= 2100) {
|
|
305
|
+
const newDate = new Date(this.currentDate);
|
|
306
|
+
newDate.setUTCFullYear(year);
|
|
307
|
+
newDate.setUTCMonth(newDate.getUTCMonth() + calendarOffset);
|
|
308
|
+
this.currentDate = newDate;
|
|
309
|
+
}
|
|
310
|
+
};
|
|
311
|
+
/**
|
|
312
|
+
* Handles week selection
|
|
313
|
+
* @param {Date[]} weekDays - Selected week days
|
|
314
|
+
* @param {number} calendarIndex - Calendar index from which the selection is made
|
|
315
|
+
*/
|
|
316
|
+
this.handleWeekSelection = (weekDays, calendarIndex) => {
|
|
317
|
+
if (this.selectionType !== 'range')
|
|
318
|
+
return;
|
|
319
|
+
const allDays = this.getDaysInMonth(calendarIndex, this.numberOfCalendars);
|
|
320
|
+
const weekStart = weekDays[0];
|
|
321
|
+
const weekEnd = weekDays[weekDays.length - 1];
|
|
322
|
+
if (!weekStart || !weekEnd)
|
|
323
|
+
return;
|
|
324
|
+
const selectedWeekDays = allDays.filter(day => day.date && day.date >= weekStart && day.date <= weekEnd);
|
|
325
|
+
const validDays = selectedWeekDays.filter(day => !this.isDateDisabled(day.date));
|
|
326
|
+
if (validDays.length > 0) {
|
|
327
|
+
this.startDate = validDays[0].date;
|
|
328
|
+
this.endDate = validDays[validDays.length - 1].date;
|
|
329
|
+
this.rangeDateChange.emit({
|
|
330
|
+
start: formatDate(this.startDate, { dateFormat: this.dateFormat }),
|
|
331
|
+
end: formatDate(this.endDate, { dateFormat: this.dateFormat }),
|
|
332
|
+
});
|
|
333
|
+
}
|
|
334
|
+
};
|
|
335
|
+
/**
|
|
336
|
+
* Checks if a date corresponds to today
|
|
337
|
+
* @param {Date} date - Date to check
|
|
338
|
+
* @returns {boolean} true if the date is today
|
|
339
|
+
*/
|
|
340
|
+
this.isToday = (date) => {
|
|
341
|
+
const today = new Date();
|
|
342
|
+
return (date.getDate() === today.getDate() &&
|
|
343
|
+
date.getMonth() === today.getMonth() &&
|
|
344
|
+
date.getFullYear() === today.getFullYear());
|
|
345
|
+
};
|
|
346
|
+
/**
|
|
347
|
+
* Parse and cache the disabled dates
|
|
348
|
+
* @description Parse and cache the disabled dates
|
|
349
|
+
*/
|
|
350
|
+
this.parseDisabledDates = () => {
|
|
351
|
+
if (!this.disabledDates) {
|
|
352
|
+
this.parsedDisabledDates = [];
|
|
353
|
+
return;
|
|
354
|
+
}
|
|
355
|
+
try {
|
|
356
|
+
this.parsedDisabledDates = this.disabledDates
|
|
357
|
+
.map(date => parseDate(date, this.dateFormat))
|
|
358
|
+
.filter(date => date !== null);
|
|
359
|
+
}
|
|
360
|
+
catch (error) {
|
|
361
|
+
console.error('Error parsing disabled dates:', error);
|
|
362
|
+
this.parsedDisabledDates = [];
|
|
363
|
+
}
|
|
364
|
+
};
|
|
365
|
+
/**
|
|
366
|
+
* Applies a shortcut selection
|
|
367
|
+
* @param {Object} shortcut - Shortcut to apply
|
|
368
|
+
* @param {string | Date} shortcut.singleValue - Selected date value
|
|
369
|
+
* @param {Object} shortcut.rangeValue - Start and end date values
|
|
370
|
+
* @param {string | Date} shortcut.rangeValue.start - Start date value
|
|
371
|
+
* @param {string | Date} shortcut.rangeValue.end - End date value
|
|
372
|
+
* @param {string} shortcut.label - Label
|
|
373
|
+
*/
|
|
374
|
+
this.applyShortcut = (shortcut) => {
|
|
375
|
+
this.selectedDate = null;
|
|
376
|
+
this.startDate = null;
|
|
377
|
+
this.endDate = null;
|
|
378
|
+
if (shortcut.singleValue) {
|
|
379
|
+
const newDate = parseDate(shortcut.singleValue, this.dateFormat);
|
|
380
|
+
this.selectedDate = newDate;
|
|
381
|
+
this.singleDateChange.emit(formatDate(newDate, { dateFormat: this.dateFormat }));
|
|
382
|
+
this.singleValue = formatDate(newDate, { dateFormat: this.dateFormat });
|
|
383
|
+
if (!this.showActions) {
|
|
384
|
+
const event = new CustomEvent('closePopover', {
|
|
385
|
+
bubbles: true,
|
|
386
|
+
composed: true,
|
|
387
|
+
});
|
|
388
|
+
this.el.dispatchEvent(event);
|
|
389
|
+
}
|
|
390
|
+
this.forceCalendarUpdate(newDate);
|
|
391
|
+
}
|
|
392
|
+
else {
|
|
393
|
+
const start = parseDate(shortcut.rangeValue.start, this.dateFormat);
|
|
394
|
+
const end = parseDate(shortcut.rangeValue.end, this.dateFormat);
|
|
395
|
+
this.startDate = start;
|
|
396
|
+
this.endDate = end;
|
|
397
|
+
this.rangeDateChange.emit({
|
|
398
|
+
start: formatDate(start, { dateFormat: this.dateFormat }),
|
|
399
|
+
end: formatDate(end, { dateFormat: this.dateFormat }),
|
|
400
|
+
});
|
|
401
|
+
this.rangeValue = {
|
|
402
|
+
start: formatDate(start, { dateFormat: this.dateFormat }),
|
|
403
|
+
end: formatDate(end, { dateFormat: this.dateFormat }),
|
|
404
|
+
};
|
|
405
|
+
if (!this.showActions) {
|
|
406
|
+
const event = new CustomEvent('closePopover', {
|
|
407
|
+
bubbles: true,
|
|
408
|
+
composed: true,
|
|
409
|
+
});
|
|
410
|
+
this.el.dispatchEvent(event);
|
|
411
|
+
}
|
|
412
|
+
this.currentDate = start;
|
|
413
|
+
}
|
|
414
|
+
};
|
|
415
|
+
/**
|
|
416
|
+
* Method to force the complete calendar update
|
|
417
|
+
* @param {Date} newDate - Date to force
|
|
418
|
+
*/
|
|
419
|
+
this.forceCalendarUpdate = newDate => {
|
|
420
|
+
this.currentDate = new Date(newDate);
|
|
421
|
+
};
|
|
422
|
+
/**
|
|
423
|
+
* Handles month change with an offset
|
|
424
|
+
* @param {number} direction - Direction (-1 for previous, 1 for next)
|
|
425
|
+
* @returns {Function} Change month handler
|
|
426
|
+
*/
|
|
427
|
+
this.getChangeMonthHandler = (direction) => {
|
|
428
|
+
return () => this.changeMonth(direction);
|
|
429
|
+
};
|
|
430
|
+
/**
|
|
431
|
+
* Handles month change from an event (ex: dropdown)
|
|
432
|
+
* @param {number} offset - Month offset (0 by default)
|
|
433
|
+
* @returns {Function} Change month handler
|
|
434
|
+
*/
|
|
435
|
+
this.getHandleMonthChange = (offset) => {
|
|
436
|
+
return (event) => this.handleMonthChange(event, offset);
|
|
437
|
+
};
|
|
438
|
+
/**
|
|
439
|
+
* Handles year change from an event (ex: dropdown)
|
|
440
|
+
* @param {number} offset - Year offset (0 by default)
|
|
441
|
+
* @returns {Function} Change year handler
|
|
442
|
+
*/
|
|
443
|
+
this.getHandleYearChange = (offset) => {
|
|
444
|
+
return (event) => this.handleYearChange(event, offset);
|
|
445
|
+
};
|
|
446
|
+
/**
|
|
447
|
+
* Handles day click
|
|
448
|
+
* @param {Date} date - Date to handle
|
|
449
|
+
* @param {boolean} isDisabled - Whether the date is disabled
|
|
450
|
+
* @returns {Function} Day click handler
|
|
451
|
+
*/
|
|
452
|
+
this.getDayClickHandler = (date, isDisabled) => {
|
|
453
|
+
return isDisabled ? undefined : () => this.handleDateSelection(date);
|
|
454
|
+
};
|
|
455
|
+
/**
|
|
456
|
+
* Handles shortcut selection
|
|
457
|
+
* @param {Object} shortcut - Shortcut to handle
|
|
458
|
+
* @param {string | Date} shortcut.singleValue - Selected date value
|
|
459
|
+
* @param {Object} shortcut.rangeValue - Start and end date values
|
|
460
|
+
* @param {string | Date} shortcut.rangeValue.start - Start date value
|
|
461
|
+
* @param {string | Date} shortcut.rangeValue.end - End date value
|
|
462
|
+
* @param {string} shortcut.label - Label
|
|
463
|
+
* @returns {Function} Shortcut selection handler
|
|
464
|
+
*/
|
|
465
|
+
this.getShortcutHandler = (shortcut) => {
|
|
466
|
+
return () => this.applyShortcut(shortcut);
|
|
467
|
+
};
|
|
468
|
+
/**
|
|
469
|
+
* Handles week selection
|
|
470
|
+
* @param {Date[]} dates - Dates to handle
|
|
471
|
+
* @param {number} index - Calendar index
|
|
472
|
+
* @returns {Function} Week selection handler
|
|
473
|
+
*/
|
|
474
|
+
this.getWeekSelectionHandler = (dates, index) => {
|
|
475
|
+
return () => {
|
|
476
|
+
if (this.selectionType === 'range') {
|
|
477
|
+
this.handleWeekSelection(dates, index);
|
|
478
|
+
}
|
|
479
|
+
};
|
|
480
|
+
};
|
|
95
481
|
/**
|
|
96
482
|
* Resets the current selection
|
|
97
483
|
*/
|
|
98
484
|
this.resetSelection = () => {
|
|
99
485
|
if (this.selectionType === 'single') {
|
|
100
486
|
this.selectedDate = null;
|
|
101
|
-
this.singleValue =
|
|
487
|
+
this.singleValue = null;
|
|
102
488
|
this.singleDateChange.emit('');
|
|
103
489
|
}
|
|
104
490
|
else {
|
|
105
491
|
this.startDate = null;
|
|
106
492
|
this.endDate = null;
|
|
107
|
-
this.rangeValue =
|
|
493
|
+
this.rangeValue = null;
|
|
108
494
|
this.rangeDateChange.emit({ start: '', end: '' });
|
|
109
495
|
}
|
|
110
496
|
};
|
|
@@ -113,7 +499,9 @@ export class NvCalendar {
|
|
|
113
499
|
*/
|
|
114
500
|
this.confirmSelection = () => {
|
|
115
501
|
if (this.selectionType === 'single' && this.selectedDate) {
|
|
116
|
-
const dateStr =
|
|
502
|
+
const dateStr = formatDate(this.selectedDate, {
|
|
503
|
+
dateFormat: this.dateFormat,
|
|
504
|
+
});
|
|
117
505
|
this.singleDateChange.emit(dateStr);
|
|
118
506
|
this.singleValue = dateStr;
|
|
119
507
|
const event = new CustomEvent('closePopover', {
|
|
@@ -126,13 +514,13 @@ export class NvCalendar {
|
|
|
126
514
|
this.startDate &&
|
|
127
515
|
this.endDate) {
|
|
128
516
|
this.rangeDateChange.emit({
|
|
129
|
-
start:
|
|
130
|
-
end:
|
|
131
|
-
});
|
|
132
|
-
this.rangeValue = JSON.stringify({
|
|
133
|
-
start: this.formatDate(this.startDate),
|
|
134
|
-
end: this.formatDate(this.endDate),
|
|
517
|
+
start: formatDate(this.startDate, { dateFormat: this.dateFormat }),
|
|
518
|
+
end: formatDate(this.endDate, { dateFormat: this.dateFormat }),
|
|
135
519
|
});
|
|
520
|
+
this.rangeValue = {
|
|
521
|
+
start: formatDate(this.startDate, { dateFormat: this.dateFormat }),
|
|
522
|
+
end: formatDate(this.endDate, { dateFormat: this.dateFormat }),
|
|
523
|
+
};
|
|
136
524
|
const event = new CustomEvent('closePopover', {
|
|
137
525
|
bubbles: true,
|
|
138
526
|
composed: true,
|
|
@@ -140,353 +528,114 @@ export class NvCalendar {
|
|
|
140
528
|
this.el.dispatchEvent(event);
|
|
141
529
|
}
|
|
142
530
|
};
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
//#endregion LIFECYCLE
|
|
188
|
-
/****************************************************************************/
|
|
189
|
-
//#region METHODS
|
|
190
|
-
/**
|
|
191
|
-
* Change the displayed month
|
|
192
|
-
* @param {number} offset - Month offset (-1 for previous, 1 for next)
|
|
193
|
-
*/
|
|
194
|
-
changeMonth(offset) {
|
|
195
|
-
const newDate = new Date(this.currentDate);
|
|
196
|
-
// Ensure we only move by one month at a time
|
|
197
|
-
newDate.setUTCMonth(newDate.getUTCMonth() + offset);
|
|
198
|
-
// Add the appropriate animation class
|
|
199
|
-
const containers = this.el.querySelectorAll('.calendar-grid');
|
|
200
|
-
containers.forEach(container => {
|
|
201
|
-
// Remove existing animation classes
|
|
202
|
-
container.classList.remove('slide-left', 'slide-right');
|
|
203
|
-
// Add the new animation class
|
|
204
|
-
const animationClass = offset > 0 ? 'slide-left' : 'slide-right';
|
|
205
|
-
container.classList.add(animationClass);
|
|
206
|
-
// Remove the class after the animation
|
|
207
|
-
setTimeout(() => {
|
|
208
|
-
container.classList.remove(animationClass);
|
|
209
|
-
}, 300); // 300ms corresponds to $slide-duration in the SCSS
|
|
210
|
-
});
|
|
211
|
-
this.currentDate = newDate;
|
|
212
|
-
}
|
|
213
|
-
/**
|
|
214
|
-
* Handles date selection based on the mode
|
|
215
|
-
* @param {Date} date - Selected date
|
|
216
|
-
*/
|
|
217
|
-
handleDateSelection(date) {
|
|
218
|
-
if (this.isDateDisabled(date)) {
|
|
219
|
-
return;
|
|
220
|
-
}
|
|
221
|
-
if (this.selectionType === 'single') {
|
|
222
|
-
this.handleSingleSelection(date);
|
|
223
|
-
}
|
|
224
|
-
else {
|
|
225
|
-
this.handleRangeSelection(date);
|
|
226
|
-
}
|
|
227
|
-
}
|
|
228
|
-
/**
|
|
229
|
-
* Handles single date selection
|
|
230
|
-
* @param {Date} date - Selected date
|
|
231
|
-
*/
|
|
232
|
-
handleSingleSelection(date) {
|
|
233
|
-
if (!date)
|
|
234
|
-
return;
|
|
235
|
-
const formattedDate = this.formatDate(date);
|
|
236
|
-
this.selectedDate = date;
|
|
237
|
-
this.singleDateChange.emit(formattedDate);
|
|
238
|
-
}
|
|
239
|
-
/**
|
|
240
|
-
* Handles range date selection
|
|
241
|
-
* @param {Date} date - Selected date
|
|
242
|
-
*/
|
|
243
|
-
handleRangeSelection(date) {
|
|
244
|
-
if (!this.startDate || (this.startDate && this.endDate)) {
|
|
245
|
-
this.startDate = date;
|
|
246
|
-
this.endDate = null;
|
|
247
|
-
}
|
|
248
|
-
else {
|
|
249
|
-
this.endDate = date;
|
|
250
|
-
if (this.startDate > this.endDate) {
|
|
251
|
-
[this.startDate, this.endDate] = [this.endDate, this.startDate];
|
|
252
|
-
}
|
|
253
|
-
this.rangeDateChange.emit({
|
|
254
|
-
start: this.formatDate(this.startDate),
|
|
255
|
-
end: this.formatDate(this.endDate),
|
|
256
|
-
});
|
|
257
|
-
}
|
|
258
|
-
}
|
|
259
|
-
/**
|
|
260
|
-
* Calculates the ISO week number
|
|
261
|
-
* @param {Date} date - Date to calculate
|
|
262
|
-
* @returns {number} Week number
|
|
263
|
-
*/
|
|
264
|
-
getWeekNumber(date) {
|
|
265
|
-
const startOfYear = new Date(date.getFullYear(), 0, 1);
|
|
266
|
-
const pastDaysOfYear = (date.getTime() - startOfYear.getTime()) / 86400000;
|
|
267
|
-
return Math.ceil((pastDaysOfYear + startOfYear.getDay() + 1) / 7);
|
|
268
|
-
}
|
|
269
|
-
/**
|
|
270
|
-
* Checks if a date is disabled.
|
|
271
|
-
* Disabled if:
|
|
272
|
-
* - The date is before min (if defined)
|
|
273
|
-
* - The date is after max (if defined)
|
|
274
|
-
* - The date is in the disabledDates array
|
|
275
|
-
* @param {Date} date - Date to check
|
|
276
|
-
* @returns {boolean} true if the date is disabled
|
|
277
|
-
*/
|
|
278
|
-
isDateDisabled(date) {
|
|
279
|
-
if (!date)
|
|
280
|
-
return true;
|
|
281
|
-
// Minimum bound check
|
|
282
|
-
if (this.min) {
|
|
283
|
-
const minDate = this.parseDate(this.min);
|
|
284
|
-
if (minDate && date < minDate) {
|
|
285
|
-
return true;
|
|
286
|
-
}
|
|
287
|
-
}
|
|
288
|
-
// Maximum bound check
|
|
289
|
-
if (this.max) {
|
|
290
|
-
const maxDate = this.parseDate(this.max);
|
|
291
|
-
if (maxDate && date > maxDate) {
|
|
292
|
-
return true;
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
// Check disabled dates
|
|
296
|
-
return this.parsedDisabledDates.some(disabledDate => this.isSameDate(date, disabledDate));
|
|
297
|
-
}
|
|
298
|
-
/**
|
|
299
|
-
* Checks if a date is in the selected range
|
|
300
|
-
* @param {Date} date - Date to check
|
|
301
|
-
* @returns {boolean} true if the date is in the range
|
|
302
|
-
*/
|
|
303
|
-
isDateInRange(date) {
|
|
304
|
-
if (!date || !this.startDate || !this.endDate)
|
|
305
|
-
return false;
|
|
306
|
-
const checkDate = this.parseDate(date);
|
|
307
|
-
const startDate = this.parseDate(this.startDate);
|
|
308
|
-
const endDate = this.parseDate(this.endDate);
|
|
309
|
-
// Verify if startDate and endDate are valid
|
|
310
|
-
if (isNaN(startDate.getTime()) || isNaN(endDate.getTime())) {
|
|
311
|
-
return false;
|
|
312
|
-
}
|
|
313
|
-
// Verify that startDate is before endDate (additional security)
|
|
314
|
-
if (startDate > endDate)
|
|
315
|
-
return false;
|
|
316
|
-
// Comparison based only on the date (year, month, day)
|
|
317
|
-
return (this.isSameOrAfter(checkDate, startDate) &&
|
|
318
|
-
this.isSameOrBefore(checkDate, endDate));
|
|
319
|
-
}
|
|
320
|
-
/**
|
|
321
|
-
* Retrieves the localized day names
|
|
322
|
-
* @returns {string[]} Array of short day names
|
|
323
|
-
*/
|
|
324
|
-
getDayNames() {
|
|
325
|
-
// If we have custom day names for this locale
|
|
326
|
-
if (CUSTOM_DAY_NAMES[this.locale]) {
|
|
327
|
-
const days = [...CUSTOM_DAY_NAMES[this.locale]];
|
|
328
|
-
// Reorganize the days based on the first day of the week
|
|
329
|
-
const firstDays = days.slice(0, this.firstDayOfWeek);
|
|
330
|
-
const remainingDays = days.slice(this.firstDayOfWeek);
|
|
331
|
-
return [...remainingDays, ...firstDays];
|
|
332
|
-
}
|
|
333
|
-
// Otherwise, use the default behavior
|
|
334
|
-
const formatter = new Intl.DateTimeFormat(this.locale, {
|
|
335
|
-
weekday: 'short',
|
|
336
|
-
});
|
|
337
|
-
const days = [...Array(7)].map((_, i) => formatter.format(new Date(2023, 0, i + 1)).toUpperCase());
|
|
338
|
-
// Reorganize the days based on the first day of the week
|
|
339
|
-
const firstDays = days.slice(0, this.firstDayOfWeek);
|
|
340
|
-
const remainingDays = days.slice(this.firstDayOfWeek);
|
|
341
|
-
return [...remainingDays, ...firstDays];
|
|
342
|
-
}
|
|
343
|
-
/**
|
|
344
|
-
* Generates the days of the current month
|
|
345
|
-
* @param {number} offset - Month offset (0 by default)
|
|
346
|
-
* @param {number} totalCalendars - Number of calendars to display (1 by default)
|
|
347
|
-
* @returns {Array<{ dayOfMonth: number | null, date: Date | null, isSelected: boolean, isDisabled: boolean }>} Array of formatted days
|
|
348
|
-
*/
|
|
349
|
-
getDaysInMonth(offset = 0, totalCalendars = 1) {
|
|
350
|
-
const year = this.currentDate.getUTCFullYear();
|
|
351
|
-
const month = this.currentDate.getUTCMonth() + offset;
|
|
352
|
-
const firstDay = new Date(Date.UTC(year, month, 1));
|
|
353
|
-
const lastDay = new Date(Date.UTC(year, month + 1, 0));
|
|
354
|
-
const days = [];
|
|
355
|
-
// Correct calculation of offset for previous month days
|
|
356
|
-
// Use getUTCDay to stay consistent with UTC timezone
|
|
357
|
-
const dayOfWeekIndex = firstDay.getUTCDay(); // 0 = Sunday, 1 = Monday, etc.
|
|
358
|
-
// Adjust based on firstDayOfWeek (if week starts on Monday, offset is different)
|
|
359
|
-
const offsetDays = (dayOfWeekIndex - this.firstDayOfWeek + 7) % 7;
|
|
360
|
-
// Add the days of the previous month for the first calendar
|
|
361
|
-
if (offset === 0 && offsetDays > 0) {
|
|
362
|
-
const prevMonthLastDay = new Date(Date.UTC(year, month, 0)).getUTCDate();
|
|
363
|
-
for (let i = offsetDays; i > 0; i--) {
|
|
364
|
-
const date = new Date(Date.UTC(year, month - 1, prevMonthLastDay - i + 1));
|
|
365
|
-
days.push({
|
|
366
|
-
dayOfMonth: date.getUTCDate(),
|
|
367
|
-
date,
|
|
368
|
-
isCurrentMonth: false,
|
|
369
|
-
isDisabled: this.isDateDisabled(date),
|
|
531
|
+
//#endregion METHODS
|
|
532
|
+
/****************************************************************************/
|
|
533
|
+
//#region RENDER
|
|
534
|
+
/**
|
|
535
|
+
* Renders the header
|
|
536
|
+
* @param {number} offset - Month offset
|
|
537
|
+
* @param {number} index - Calendar index
|
|
538
|
+
* @returns {JSX.Element} Header
|
|
539
|
+
* @description Renders the header of the calendar
|
|
540
|
+
*/
|
|
541
|
+
this.renderHeader = (offset, index) => {
|
|
542
|
+
return (h("div", { class: "header" }, this.numberOfCalendars > 1 && index === 0 && (h("nv-iconbutton", { class: "nav-left", emphasis: "lower", name: "chevron-left", onClick: this.getChangeMonthHandler(-1) })), h("div", { class: "date-controls" }, h("select", { class: "month-select mr-4", onChange: this.getHandleMonthChange(offset) }, this.months.map(month => (h("option", { key: month.value, value: month.value, selected: month.value === (this.currentDate.getUTCMonth() + offset) % 12 }, month.label)))), h("input", { type: "number", class: "year-input", min: "1950", max: "2100", value: this.currentDate.getUTCFullYear() +
|
|
543
|
+
Math.floor((this.currentDate.getUTCMonth() + offset) / 12), onChange: this.getHandleYearChange(offset) })), this.numberOfCalendars === 1 && (h("div", { class: "nav-buttons" }, h("nv-iconbutton", { emphasis: "lower", name: "chevron-left", onClick: this.getChangeMonthHandler(-1) }), h("nv-iconbutton", { emphasis: "lower", name: "chevron-right", onClick: this.getChangeMonthHandler(1) }))), this.numberOfCalendars > 1 && index === this.numberOfCalendars - 1 && (h("nv-iconbutton", { emphasis: "lower", name: "chevron-right", onClick: this.getChangeMonthHandler(1), class: "nav-right" }))));
|
|
544
|
+
};
|
|
545
|
+
/**
|
|
546
|
+
* Renders the week numbers
|
|
547
|
+
* @param {Array<{date: Date}>} weeks - Weeks to render
|
|
548
|
+
* @param {number} index - Calendar index
|
|
549
|
+
* @returns {JSX.Element} Week numbers
|
|
550
|
+
* @description Renders the week numbers of the calendar
|
|
551
|
+
*/
|
|
552
|
+
this.renderWeekNumbers = (
|
|
553
|
+
/** Weeks to render */
|
|
554
|
+
weeks,
|
|
555
|
+
/** Calendar index */
|
|
556
|
+
index) => {
|
|
557
|
+
return (h("div", { class: "week-numbers" }, h("div", { class: "week-header" }, this.getLocalizedWeekText()), weeks.map((week, weekIndex) => {
|
|
558
|
+
var _a;
|
|
559
|
+
const dates = week.map(d => d.date);
|
|
560
|
+
return (h("div", { class: `week-number ${this.selectionType === 'range' ? 'clickable' : ''}`, onClick: this.getWeekSelectionHandler(dates, index), key: `week-${weekIndex}` }, getWeekNumber(((_a = week.find(d => d.date)) === null || _a === void 0 ? void 0 : _a.date) || new Date())));
|
|
561
|
+
})));
|
|
562
|
+
};
|
|
563
|
+
this.renderDaysGrid = (
|
|
564
|
+
/** Days to render */
|
|
565
|
+
days) => {
|
|
566
|
+
return (h("div", { class: "days-grid" }, days.map(day => {
|
|
567
|
+
const date = day.date;
|
|
568
|
+
if (!date)
|
|
569
|
+
return null;
|
|
570
|
+
const isSelected = this.selectionType === 'single' &&
|
|
571
|
+
isSameDate(date, this.selectedDate, { isUTCMode: this.isUTCMode });
|
|
572
|
+
const isInRange = this.isDateInRange(date);
|
|
573
|
+
const isStart = isSameDate(date, this.startDate, {
|
|
574
|
+
isUTCMode: this.isUTCMode,
|
|
370
575
|
});
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
// Add the days of the current month
|
|
374
|
-
for (let i = 1; i <= lastDay.getUTCDate(); i++) {
|
|
375
|
-
const date = new Date(Date.UTC(year, month, i));
|
|
376
|
-
days.push({
|
|
377
|
-
dayOfMonth: i,
|
|
378
|
-
date,
|
|
379
|
-
isCurrentMonth: true,
|
|
380
|
-
isDisabled: this.isDateDisabled(date),
|
|
381
|
-
});
|
|
382
|
-
}
|
|
383
|
-
// Add the days of the next month only for the last calendar
|
|
384
|
-
if (offset === totalCalendars - 1) {
|
|
385
|
-
const nextMonthDaysNeeded = 7 - (days.length % 7 || 7);
|
|
386
|
-
for (let i = 1; i <= nextMonthDaysNeeded; i++) {
|
|
387
|
-
const date = new Date(Date.UTC(year, month + 1, i));
|
|
388
|
-
days.push({
|
|
389
|
-
dayOfMonth: i,
|
|
390
|
-
date,
|
|
391
|
-
isCurrentMonth: false,
|
|
392
|
-
isDisabled: this.isDateDisabled(date),
|
|
576
|
+
const isEnd = isSameDate(date, this.endDate, {
|
|
577
|
+
isUTCMode: this.isUTCMode,
|
|
393
578
|
});
|
|
579
|
+
const isToday = this.isToday(date);
|
|
580
|
+
const isOutsideMonth = !day.isCurrentMonth;
|
|
581
|
+
const dayClasses = [
|
|
582
|
+
'day',
|
|
583
|
+
isSelected ? 'selected' : '',
|
|
584
|
+
isStart ? 'range-start' : '',
|
|
585
|
+
isEnd ? 'range-end' : '',
|
|
586
|
+
isInRange ? 'in-range' : '',
|
|
587
|
+
day.isDisabled ? 'disabled' : '',
|
|
588
|
+
isOutsideMonth ? 'outside-month' : '',
|
|
589
|
+
isToday ? 'is-today' : '',
|
|
590
|
+
];
|
|
591
|
+
return (h("div", { class: dayClasses.filter(Boolean).join(' '), onClick: this.getDayClickHandler(date, day.isDisabled), "aria-disabled": day.isDisabled, key: `day-${date.toISOString()}` }, day.dayOfMonth));
|
|
592
|
+
})));
|
|
593
|
+
};
|
|
594
|
+
/**
|
|
595
|
+
* Renders the calendar
|
|
596
|
+
* @param {number} index - Calendar index
|
|
597
|
+
* @param {number} offset - Month offset
|
|
598
|
+
* @returns {JSX.Element} Calendar
|
|
599
|
+
* @description Renders the calendar of the calendar
|
|
600
|
+
*/
|
|
601
|
+
this.renderCalendar = (
|
|
602
|
+
/** Calendar index */
|
|
603
|
+
index,
|
|
604
|
+
/** Month offset */
|
|
605
|
+
offset) => {
|
|
606
|
+
const days = this.getDaysInMonth(offset, this.numberOfCalendars);
|
|
607
|
+
const weeks = [];
|
|
608
|
+
for (let i = 0; i < days.length; i += 7) {
|
|
609
|
+
weeks.push(days.slice(i, i + 7));
|
|
394
610
|
}
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
}
|
|
406
|
-
return;
|
|
407
|
-
}
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
* @returns {string} Localized abbreviation for "week"
|
|
418
|
-
*/
|
|
419
|
-
getLocalizedWeekText() {
|
|
420
|
-
return WEEK_ABBREVIATIONS[this.locale] || 'W';
|
|
421
|
-
}
|
|
422
|
-
/**
|
|
423
|
-
* Handles month change in the selector
|
|
424
|
-
* @param {Event} event - Month change event
|
|
425
|
-
* @param {number} calendarOffset - Calendar offset (0 by default)
|
|
426
|
-
*/
|
|
427
|
-
handleMonthChange(event, calendarOffset = 0) {
|
|
428
|
-
const select = event.target;
|
|
429
|
-
const selectedMonth = parseInt(select.value, 10);
|
|
430
|
-
const currentMonth = this.currentDate.getUTCMonth();
|
|
431
|
-
// Calculate the difference considering the calendar offset
|
|
432
|
-
const monthDiff = selectedMonth - ((currentMonth + calendarOffset) % 12);
|
|
433
|
-
const newDate = new Date(this.currentDate);
|
|
434
|
-
newDate.setUTCMonth(newDate.getUTCMonth() + monthDiff);
|
|
435
|
-
this.currentDate = newDate;
|
|
436
|
-
}
|
|
437
|
-
/**
|
|
438
|
-
* Handles year change in the numeric entry
|
|
439
|
-
* @param {Event} event - Year change event
|
|
440
|
-
* @param {number} calendarOffset - Calendar offset (0 by default)
|
|
441
|
-
*/
|
|
442
|
-
handleYearChange(event, calendarOffset = 0) {
|
|
443
|
-
const input = event.target;
|
|
444
|
-
const year = parseInt(input.value, 10);
|
|
445
|
-
if (!isNaN(year) && year >= 1900 && year <= 2100) {
|
|
446
|
-
const newDate = new Date(this.currentDate);
|
|
447
|
-
newDate.setUTCFullYear(year);
|
|
448
|
-
newDate.setUTCMonth(newDate.getUTCMonth() + calendarOffset);
|
|
449
|
-
this.currentDate = newDate;
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
/**
|
|
453
|
-
* Handles week selection
|
|
454
|
-
* @param {Date[]} weekDays - Selected week days
|
|
455
|
-
* @param {number} calendarIndex - Calendar index from which the selection is made
|
|
456
|
-
*/
|
|
457
|
-
handleWeekSelection(weekDays, calendarIndex) {
|
|
458
|
-
if (this.selectionType !== 'range')
|
|
459
|
-
return;
|
|
460
|
-
const allDays = this.getDaysInMonth(calendarIndex, this.numberOfCalendars);
|
|
461
|
-
const weekStart = weekDays[0];
|
|
462
|
-
const weekEnd = weekDays[weekDays.length - 1];
|
|
463
|
-
if (!weekStart || !weekEnd)
|
|
464
|
-
return;
|
|
465
|
-
const selectedWeekDays = allDays.filter(day => day.date && day.date >= weekStart && day.date <= weekEnd);
|
|
466
|
-
const validDays = selectedWeekDays.filter(day => !this.isDateDisabled(day.date));
|
|
467
|
-
if (validDays.length > 0) {
|
|
468
|
-
this.startDate = validDays[0].date;
|
|
469
|
-
this.endDate = validDays[validDays.length - 1].date;
|
|
470
|
-
this.rangeDateChange.emit({
|
|
471
|
-
start: this.formatDate(this.startDate),
|
|
472
|
-
end: this.formatDate(this.endDate),
|
|
473
|
-
});
|
|
474
|
-
}
|
|
475
|
-
}
|
|
476
|
-
/**
|
|
477
|
-
* Checks if a date corresponds to today
|
|
478
|
-
* @param {Date} date - Date to check
|
|
479
|
-
* @returns {boolean} true if the date is today
|
|
480
|
-
*/
|
|
481
|
-
isToday(date) {
|
|
482
|
-
const today = new Date();
|
|
483
|
-
return (date.getDate() === today.getDate() &&
|
|
484
|
-
date.getMonth() === today.getMonth() &&
|
|
485
|
-
date.getFullYear() === today.getFullYear());
|
|
611
|
+
return (h("div", { class: "calendar-wrapper" }, h("div", { class: "calendar-container", key: `calendar-${index}` }, this.renderHeader(offset, index), h("div", { class: "calendar-grid" }, this.showWeekNumbers && this.renderWeekNumbers(weeks, index), h("div", { class: "days-container" }, h("div", { class: "days-header" }, this.getDayNames().map(day => (h("div", { class: "day-header" }, day)))), this.renderDaysGrid(days)))), index < this.numberOfCalendars - 1 && (h("div", { class: "calendar-separator" }))));
|
|
612
|
+
};
|
|
613
|
+
/**
|
|
614
|
+
* Renders the shortcuts
|
|
615
|
+
* @returns {JSX.Element} Shortcuts
|
|
616
|
+
* @description Renders the shortcuts of the calendar
|
|
617
|
+
*/
|
|
618
|
+
this.renderShortcuts = () => {
|
|
619
|
+
if (!this.hasShortcuts) {
|
|
620
|
+
return null;
|
|
621
|
+
}
|
|
622
|
+
return (h("div", { class: `shortcuts-container shortcuts-placement-${this.shortcutsPlacement}` }, this.shortcuts.map(shortcut => (h("nv-button", { emphasis: "lower", size: "xs", "aria-label": shortcut.label, onClick: this.getShortcutHandler(shortcut) }, shortcut.label)))));
|
|
623
|
+
};
|
|
624
|
+
/**
|
|
625
|
+
* Renders the actions
|
|
626
|
+
* @returns {JSX.Element} Actions
|
|
627
|
+
* @description Renders the actions of the calendar
|
|
628
|
+
* @slot actions - Child content of the component.
|
|
629
|
+
*/
|
|
630
|
+
this.renderActions = () => {
|
|
631
|
+
return (h("div", { class: "datepicker-actions" }, h("slot", { name: "actions" }, h("nv-button", { emphasis: "low", size: "xs", onClick: this.resetSelection }, "Cancel"), h("nv-button", { size: "xs", onClick: this.confirmSelection }, "OK"))));
|
|
632
|
+
};
|
|
486
633
|
}
|
|
634
|
+
//#endregion EVENTS
|
|
635
|
+
/****************************************************************************/
|
|
636
|
+
//#region WATCHERS
|
|
487
637
|
/**
|
|
488
638
|
* Watches the changes of the number of calendars
|
|
489
|
-
* @watch numberOfCalendars
|
|
490
639
|
* @param {number} newValue - New number of calendars
|
|
491
640
|
*/
|
|
492
641
|
validateNumberOfCalendars(newValue) {
|
|
@@ -497,29 +646,29 @@ export class NvCalendar {
|
|
|
497
646
|
}
|
|
498
647
|
/**
|
|
499
648
|
* Watches the changes of the selected date range
|
|
500
|
-
* @watch rangeValue
|
|
501
649
|
* @param {Object} newValue - New rangeValue value
|
|
502
650
|
* @param {string} newValue.start - Start date
|
|
503
651
|
* @param {string} newValue.end - End date
|
|
504
652
|
*/
|
|
505
653
|
onRangeValueChange(newValue) {
|
|
506
|
-
if (newValue) {
|
|
654
|
+
if (newValue && newValue.start && newValue.end) {
|
|
507
655
|
try {
|
|
508
|
-
const
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
656
|
+
const { startDate, endDate } = this.validateDateRange(newValue.start, newValue.end);
|
|
657
|
+
this.startDate = startDate;
|
|
658
|
+
this.endDate = endDate;
|
|
659
|
+
// Do not navigate to the start date if data-prevent-navigation attribute is present
|
|
660
|
+
const preventNavigation = this.el.getAttribute('data-prevent-navigation') === 'true';
|
|
661
|
+
if (!preventNavigation) {
|
|
662
|
+
this.currentDate = startDate;
|
|
513
663
|
}
|
|
514
664
|
}
|
|
515
665
|
catch (error) {
|
|
516
|
-
console.error('Invalid
|
|
666
|
+
console.error('Invalid rangeValue:', error);
|
|
517
667
|
}
|
|
518
668
|
}
|
|
519
669
|
}
|
|
520
670
|
/**
|
|
521
671
|
* Watches the changes of the disabled dates
|
|
522
|
-
* @watch disabledDates
|
|
523
672
|
* @description Watches the changes of the disabled dates
|
|
524
673
|
*/
|
|
525
674
|
handleDisabledDatesChange() {
|
|
@@ -527,381 +676,65 @@ export class NvCalendar {
|
|
|
527
676
|
}
|
|
528
677
|
/**
|
|
529
678
|
* Watches the changes of the single value
|
|
530
|
-
* @watch singleValue
|
|
531
679
|
* @param {string} newValue - New single value
|
|
532
680
|
* @param {string} oldValue - Old single value
|
|
533
681
|
*/
|
|
534
682
|
onSingleValueChange(newValue, oldValue) {
|
|
535
683
|
if (this.selectionType === 'single' && newValue !== oldValue && newValue) {
|
|
536
|
-
const parsedDate =
|
|
684
|
+
const parsedDate = parseDate(newValue, this.dateFormat);
|
|
537
685
|
if (parsedDate) {
|
|
538
686
|
this.selectedDate = parsedDate;
|
|
539
|
-
|
|
687
|
+
// Do not navigate to the selected date if data-prevent-navigation attribute is present
|
|
688
|
+
const preventNavigation = this.el.getAttribute('data-prevent-navigation') === 'true';
|
|
689
|
+
if (!preventNavigation) {
|
|
690
|
+
this.currentDate = parsedDate;
|
|
691
|
+
}
|
|
540
692
|
}
|
|
541
693
|
}
|
|
542
694
|
}
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
if (typeof dateInput === 'string' &&
|
|
554
|
-
/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}.\d{3}Z$/.test(dateInput)) {
|
|
695
|
+
//#endregion WATCHERS
|
|
696
|
+
/****************************************************************************/
|
|
697
|
+
//#region LIFECYCLE
|
|
698
|
+
componentWillLoad() {
|
|
699
|
+
this.parseDisabledDates();
|
|
700
|
+
if (this.selectionType === 'single' && this.singleValue) {
|
|
701
|
+
this.selectedDate = parseDate(this.singleValue, this.dateFormat);
|
|
702
|
+
this.currentDate = this.selectedDate;
|
|
703
|
+
}
|
|
704
|
+
else if (this.selectionType === 'range' && this.rangeValue) {
|
|
555
705
|
try {
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
706
|
+
if (this.rangeValue.start && this.rangeValue.end) {
|
|
707
|
+
const { startDate, endDate, swapped } = this.validateDateRange(this.rangeValue.start, this.rangeValue.end);
|
|
708
|
+
this.startDate = startDate;
|
|
709
|
+
this.endDate = endDate;
|
|
710
|
+
this.currentDate = startDate;
|
|
711
|
+
if (swapped) {
|
|
712
|
+
// If dates were swapped, update the rangeValue property
|
|
713
|
+
this.rangeValue = {
|
|
714
|
+
start: formatDate(startDate, { dateFormat: this.dateFormat }),
|
|
715
|
+
end: formatDate(endDate, { dateFormat: this.dateFormat }),
|
|
716
|
+
};
|
|
717
|
+
}
|
|
559
718
|
}
|
|
560
719
|
}
|
|
561
720
|
catch (error) {
|
|
562
|
-
|
|
563
|
-
console.error('Error parsing ISO date:', error);
|
|
564
|
-
}
|
|
565
|
-
}
|
|
566
|
-
// Handling Unix Seconds ("X") formats
|
|
567
|
-
if (this.dateFormat === 'X') {
|
|
568
|
-
const unixSeconds = Number(dateInput);
|
|
569
|
-
if (isNaN(unixSeconds))
|
|
570
|
-
return null;
|
|
571
|
-
return this.isUTCMode
|
|
572
|
-
? dayjs.unix(unixSeconds).utc().toDate()
|
|
573
|
-
: dayjs.unix(unixSeconds).toDate();
|
|
574
|
-
}
|
|
575
|
-
// Handling Unix Milliseconds ("x") formats
|
|
576
|
-
if (this.dateFormat === 'x') {
|
|
577
|
-
const unixMilliseconds = Number(dateInput);
|
|
578
|
-
if (isNaN(unixMilliseconds))
|
|
579
|
-
return null;
|
|
580
|
-
return this.isUTCMode
|
|
581
|
-
? dayjs(unixMilliseconds).utc().toDate()
|
|
582
|
-
: dayjs(unixMilliseconds).toDate();
|
|
583
|
-
}
|
|
584
|
-
// Handling C# Ticks format
|
|
585
|
-
if (this.dateFormat === 'Ticks') {
|
|
586
|
-
const ticks = Number(dateInput);
|
|
587
|
-
if (isNaN(ticks))
|
|
588
|
-
return null;
|
|
589
|
-
// Conversion of .NET ticks to milliseconds since Unix epoch
|
|
590
|
-
const unixMilliseconds = (ticks - 621355968000000000) / 10000;
|
|
591
|
-
return this.isUTCMode
|
|
592
|
-
? dayjs(unixMilliseconds).utc().toDate()
|
|
593
|
-
: dayjs(unixMilliseconds).toDate();
|
|
594
|
-
}
|
|
595
|
-
// For all other formats, use customParseFormat in strict mode
|
|
596
|
-
let parsed;
|
|
597
|
-
if (this.isUTCMode) {
|
|
598
|
-
parsed = dayjs.utc(dateInput, this.dateFormat, true);
|
|
599
|
-
}
|
|
600
|
-
else {
|
|
601
|
-
parsed = dayjs(dateInput, this.dateFormat, true);
|
|
602
|
-
}
|
|
603
|
-
if (!parsed.isValid()) {
|
|
604
|
-
console.error(`Parsing error:`, {
|
|
605
|
-
dateInput,
|
|
606
|
-
dateFormat: this.dateFormat,
|
|
607
|
-
});
|
|
608
|
-
return null;
|
|
609
|
-
}
|
|
610
|
-
return parsed.toDate();
|
|
611
|
-
}
|
|
612
|
-
/**
|
|
613
|
-
* Checks if the date format is in UTC mode
|
|
614
|
-
* @returns {boolean} true if the date format is in UTC mode
|
|
615
|
-
*/
|
|
616
|
-
get isUTCMode() {
|
|
617
|
-
return this.dateFormat.includes('Z');
|
|
618
|
-
}
|
|
619
|
-
/**
|
|
620
|
-
* Checks if the date format is ISO 8601
|
|
621
|
-
* @returns {boolean} true if the format is ISO 8601
|
|
622
|
-
*/
|
|
623
|
-
get isISO8601Format() {
|
|
624
|
-
return this.dateFormat === 'YYYY-MM-DD[T]HH:mm:ss[Z]';
|
|
625
|
-
}
|
|
626
|
-
/**
|
|
627
|
-
* Formats a date to a string according to the format
|
|
628
|
-
* @param {Date} date - Date to format
|
|
629
|
-
* @returns {string} Formatted date
|
|
630
|
-
*/
|
|
631
|
-
formatDate(date) {
|
|
632
|
-
if (!date)
|
|
633
|
-
return '';
|
|
634
|
-
// Special case for ISO 8601
|
|
635
|
-
if (this.isISO8601Format) {
|
|
636
|
-
// For the ISO 8601 format, use directly toISOString() which is standard
|
|
637
|
-
return date.toISOString();
|
|
638
|
-
}
|
|
639
|
-
// If the format is "Ticks", convert the time to C# ticks
|
|
640
|
-
if (this.dateFormat === 'Ticks') {
|
|
641
|
-
const ticks = date.getTime() * 10000 + 621355968000000000;
|
|
642
|
-
return ticks.toString();
|
|
643
|
-
}
|
|
644
|
-
// If the format is "X" (Unix Seconds)
|
|
645
|
-
if (this.dateFormat === 'X') {
|
|
646
|
-
return dayjs(date).unix().toString();
|
|
647
|
-
}
|
|
648
|
-
// If the format is "x" (Unix Milliseconds)
|
|
649
|
-
if (this.dateFormat === 'x') {
|
|
650
|
-
return date.getTime().toString();
|
|
651
|
-
}
|
|
652
|
-
// Otherwise, format according to the mode (UTC or local)
|
|
653
|
-
return this.isUTCMode
|
|
654
|
-
? dayjs(date).utc().format(this.dateFormat)
|
|
655
|
-
: dayjs(date).format(this.dateFormat);
|
|
656
|
-
}
|
|
657
|
-
/**
|
|
658
|
-
* Parse and cache the disabled dates
|
|
659
|
-
* @description Parse and cache the disabled dates
|
|
660
|
-
*/
|
|
661
|
-
parseDisabledDates() {
|
|
662
|
-
if (!this.disabledDates) {
|
|
663
|
-
this.parsedDisabledDates = [];
|
|
664
|
-
return;
|
|
665
|
-
}
|
|
666
|
-
try {
|
|
667
|
-
const disabledDatesArray = JSON.parse(this.disabledDates);
|
|
668
|
-
this.parsedDisabledDates = disabledDatesArray
|
|
669
|
-
.map(date => this.parseDate(date))
|
|
670
|
-
.filter(date => date !== null);
|
|
671
|
-
}
|
|
672
|
-
catch (error) {
|
|
673
|
-
console.error('Error parsing disabled dates:', error);
|
|
674
|
-
this.parsedDisabledDates = [];
|
|
675
|
-
}
|
|
676
|
-
}
|
|
677
|
-
/**
|
|
678
|
-
* Checks if two dates are identical
|
|
679
|
-
* @param {Date | null} date1 - First date
|
|
680
|
-
* @param {Date | null} date2 - Second date
|
|
681
|
-
* @returns {boolean} true if the dates are identical
|
|
682
|
-
*/
|
|
683
|
-
isSameDate(date1, date2) {
|
|
684
|
-
if (!date1 || !date2)
|
|
685
|
-
return false;
|
|
686
|
-
if (this.isUTCMode) {
|
|
687
|
-
return (date1.getUTCFullYear() === date2.getUTCFullYear() &&
|
|
688
|
-
date1.getUTCMonth() === date2.getUTCMonth() &&
|
|
689
|
-
date1.getUTCDate() === date2.getUTCDate());
|
|
690
|
-
}
|
|
691
|
-
else {
|
|
692
|
-
return (date1.getFullYear() === date2.getFullYear() &&
|
|
693
|
-
date1.getMonth() === date2.getMonth() &&
|
|
694
|
-
date1.getDate() === date2.getDate());
|
|
695
|
-
}
|
|
696
|
-
}
|
|
697
|
-
/**
|
|
698
|
-
* Checks if a date is identical or after another date
|
|
699
|
-
* @param {Date} date - Date to check
|
|
700
|
-
* @param {Date} compareDate - Reference date
|
|
701
|
-
* @returns {boolean} true if `date` >= `compareDate`
|
|
702
|
-
*/
|
|
703
|
-
isSameOrAfter(date, compareDate) {
|
|
704
|
-
if (this.isUTCMode) {
|
|
705
|
-
return (date.getUTCFullYear() > compareDate.getUTCFullYear() ||
|
|
706
|
-
(date.getUTCFullYear() === compareDate.getUTCFullYear() &&
|
|
707
|
-
date.getUTCMonth() > compareDate.getUTCMonth()) ||
|
|
708
|
-
(date.getUTCFullYear() === compareDate.getUTCFullYear() &&
|
|
709
|
-
date.getUTCMonth() === compareDate.getUTCMonth() &&
|
|
710
|
-
date.getUTCDate() >= compareDate.getUTCDate()));
|
|
711
|
-
}
|
|
712
|
-
else {
|
|
713
|
-
return (date.getFullYear() > compareDate.getFullYear() ||
|
|
714
|
-
(date.getFullYear() === compareDate.getFullYear() &&
|
|
715
|
-
date.getMonth() > compareDate.getMonth()) ||
|
|
716
|
-
(date.getFullYear() === compareDate.getFullYear() &&
|
|
717
|
-
date.getMonth() === compareDate.getMonth() &&
|
|
718
|
-
date.getDate() >= compareDate.getDate()));
|
|
719
|
-
}
|
|
720
|
-
}
|
|
721
|
-
/**
|
|
722
|
-
* Checks if a date is identical or before another date
|
|
723
|
-
* @param {Date} date - Date to check
|
|
724
|
-
* @param {Date} compareDate - Reference date
|
|
725
|
-
* @returns {boolean} true if `date` <= `compareDate`
|
|
726
|
-
*/
|
|
727
|
-
isSameOrBefore(date, compareDate) {
|
|
728
|
-
if (this.isUTCMode) {
|
|
729
|
-
return (date.getUTCFullYear() < compareDate.getUTCFullYear() ||
|
|
730
|
-
(date.getUTCFullYear() === compareDate.getUTCFullYear() &&
|
|
731
|
-
date.getUTCMonth() < compareDate.getUTCMonth()) ||
|
|
732
|
-
(date.getUTCFullYear() === compareDate.getUTCFullYear() &&
|
|
733
|
-
date.getUTCMonth() === compareDate.getUTCMonth() &&
|
|
734
|
-
date.getUTCDate() <= compareDate.getUTCDate()));
|
|
735
|
-
}
|
|
736
|
-
else {
|
|
737
|
-
return (date.getFullYear() < compareDate.getFullYear() ||
|
|
738
|
-
(date.getFullYear() === compareDate.getFullYear() &&
|
|
739
|
-
date.getMonth() < compareDate.getMonth()) ||
|
|
740
|
-
(date.getFullYear() === compareDate.getFullYear() &&
|
|
741
|
-
date.getMonth() === compareDate.getMonth() &&
|
|
742
|
-
date.getDate() <= compareDate.getDate()));
|
|
743
|
-
}
|
|
744
|
-
}
|
|
745
|
-
/**
|
|
746
|
-
* Applies a shortcut selection
|
|
747
|
-
* @param {Object} shortcut - Shortcut to apply
|
|
748
|
-
* @param {string | Date} shortcut.singleValue - Selected date value
|
|
749
|
-
* @param {Object} shortcut.rangeValue - Start and end date values
|
|
750
|
-
* @param {string | Date} shortcut.rangeValue.start - Start date value
|
|
751
|
-
* @param {string | Date} shortcut.rangeValue.end - End date value
|
|
752
|
-
* @param {string} shortcut.label - Label
|
|
753
|
-
*/
|
|
754
|
-
applyShortcut(shortcut) {
|
|
755
|
-
this.selectedDate = null;
|
|
756
|
-
this.startDate = null;
|
|
757
|
-
this.endDate = null;
|
|
758
|
-
if (shortcut.singleValue) {
|
|
759
|
-
const newDate = this.parseDate(shortcut.singleValue);
|
|
760
|
-
this.selectedDate = newDate;
|
|
761
|
-
this.singleDateChange.emit(this.formatDate(newDate));
|
|
762
|
-
this.singleValue = this.formatDate(newDate);
|
|
763
|
-
if (!this.showActions) {
|
|
764
|
-
const event = new CustomEvent('closePopover', {
|
|
765
|
-
bubbles: true,
|
|
766
|
-
composed: true,
|
|
767
|
-
});
|
|
768
|
-
this.el.dispatchEvent(event);
|
|
721
|
+
console.error('Invalid rangeValue:', error);
|
|
769
722
|
}
|
|
770
|
-
this.forceCalendarUpdate(newDate);
|
|
771
723
|
}
|
|
772
724
|
else {
|
|
773
|
-
|
|
774
|
-
const end = this.parseDate(shortcut.rangeValue.end);
|
|
775
|
-
this.startDate = start;
|
|
776
|
-
this.endDate = end;
|
|
777
|
-
this.rangeDateChange.emit({
|
|
778
|
-
start: this.formatDate(start),
|
|
779
|
-
end: this.formatDate(end),
|
|
780
|
-
});
|
|
781
|
-
this.rangeValue = JSON.stringify({
|
|
782
|
-
start: this.formatDate(start),
|
|
783
|
-
end: this.formatDate(end),
|
|
784
|
-
});
|
|
785
|
-
if (!this.showActions) {
|
|
786
|
-
const event = new CustomEvent('closePopover', {
|
|
787
|
-
bubbles: true,
|
|
788
|
-
composed: true,
|
|
789
|
-
});
|
|
790
|
-
this.el.dispatchEvent(event);
|
|
791
|
-
}
|
|
792
|
-
this.forceCalendarUpdate(end);
|
|
793
|
-
}
|
|
794
|
-
}
|
|
795
|
-
/**
|
|
796
|
-
* Method to force the complete calendar update (and fix the persistent hover problem)
|
|
797
|
-
* @param {Date} newDate - Date to force
|
|
798
|
-
*/
|
|
799
|
-
forceCalendarUpdate(newDate) {
|
|
800
|
-
this.currentDate = new Date(newDate);
|
|
801
|
-
this.currentDate = new Date(this.currentDate); // Force a re-render
|
|
802
|
-
// Reset visually the hover/touch effect
|
|
803
|
-
requestAnimationFrame(() => {
|
|
804
|
-
const days = document.querySelectorAll('.day');
|
|
805
|
-
days.forEach(el => {
|
|
806
|
-
el.classList.remove('hover', 'active', 'touched');
|
|
807
|
-
el.style.pointerEvents = 'none';
|
|
808
|
-
});
|
|
809
|
-
// Add specific touch handling (for mobile)
|
|
810
|
-
document.body.addEventListener('touchstart', this.clearTouchState, {
|
|
811
|
-
passive: true,
|
|
812
|
-
});
|
|
813
|
-
// Reset the touch state after 50ms
|
|
814
|
-
setTimeout(() => {
|
|
815
|
-
days.forEach(el => {
|
|
816
|
-
el.style.pointerEvents = '';
|
|
817
|
-
});
|
|
818
|
-
}, 50);
|
|
819
|
-
});
|
|
820
|
-
}
|
|
821
|
-
/**
|
|
822
|
-
* Function to reset the touch effect (Mobile fix)
|
|
823
|
-
*/
|
|
824
|
-
clearTouchState() {
|
|
825
|
-
document.querySelectorAll('.day').forEach(el => {
|
|
826
|
-
el.classList.remove('touched');
|
|
827
|
-
});
|
|
828
|
-
// Remove the listener after the first interaction
|
|
829
|
-
document.body.removeEventListener('touchstart', this.clearTouchState);
|
|
830
|
-
}
|
|
831
|
-
/**
|
|
832
|
-
* Handles month change with an offset
|
|
833
|
-
* @param {number} direction - Direction (-1 for previous, 1 for next)
|
|
834
|
-
* @returns {Function} Change month handler
|
|
835
|
-
*/
|
|
836
|
-
getChangeMonthHandler(direction) {
|
|
837
|
-
return () => this.changeMonth(direction);
|
|
838
|
-
}
|
|
839
|
-
/**
|
|
840
|
-
* Handles month change from an event (ex: dropdown)
|
|
841
|
-
* @param {number} offset - Month offset (0 by default)
|
|
842
|
-
* @returns {Function} Change month handler
|
|
843
|
-
*/
|
|
844
|
-
getHandleMonthChange(offset) {
|
|
845
|
-
return (event) => this.handleMonthChange(event, offset);
|
|
846
|
-
}
|
|
847
|
-
/**
|
|
848
|
-
* Handles year change from an event (ex: dropdown)
|
|
849
|
-
* @param {number} offset - Year offset (0 by default)
|
|
850
|
-
* @returns {Function} Change year handler
|
|
851
|
-
*/
|
|
852
|
-
getHandleYearChange(offset) {
|
|
853
|
-
return (event) => this.handleYearChange(event, offset);
|
|
854
|
-
}
|
|
855
|
-
/**
|
|
856
|
-
* Handles day click
|
|
857
|
-
* @param {Date} date - Date to handle
|
|
858
|
-
* @param {boolean} isDisabled - Whether the date is disabled
|
|
859
|
-
* @returns {Function} Day click handler
|
|
860
|
-
*/
|
|
861
|
-
getDayClickHandler(date, isDisabled) {
|
|
862
|
-
return isDisabled ? undefined : () => this.handleDateSelection(date);
|
|
863
|
-
}
|
|
864
|
-
/**
|
|
865
|
-
* Handles shortcut selection
|
|
866
|
-
* @param {Object} shortcut - Shortcut to handle
|
|
867
|
-
* @param {string | Date} shortcut.singleValue - Selected date value
|
|
868
|
-
* @param {Object} shortcut.rangeValue - Start and end date values
|
|
869
|
-
* @param {string | Date} shortcut.rangeValue.start - Start date value
|
|
870
|
-
* @param {string | Date} shortcut.rangeValue.end - End date value
|
|
871
|
-
* @param {string} shortcut.label - Label
|
|
872
|
-
* @returns {Function} Shortcut selection handler
|
|
873
|
-
*/
|
|
874
|
-
getShortcutHandler(shortcut) {
|
|
875
|
-
return () => this.applyShortcut(shortcut);
|
|
876
|
-
}
|
|
877
|
-
/**
|
|
878
|
-
* Handles week selection
|
|
879
|
-
* @param {Date[]} dates - Dates to handle
|
|
880
|
-
* @param {number} index - Calendar index
|
|
881
|
-
* @returns {Function} Week selection handler
|
|
882
|
-
*/
|
|
883
|
-
getWeekSelectionHandler(dates, index) {
|
|
884
|
-
return () => {
|
|
885
|
-
if (this.selectionType === 'range') {
|
|
886
|
-
this.handleWeekSelection(dates, index);
|
|
887
|
-
}
|
|
888
|
-
};
|
|
889
|
-
}
|
|
890
|
-
parsedShortcuts() {
|
|
891
|
-
try {
|
|
892
|
-
return this.shortcuts ? JSON.parse(this.shortcuts) : [];
|
|
893
|
-
}
|
|
894
|
-
catch (error) {
|
|
895
|
-
console.error('Invalid JSON for shortcuts:', error);
|
|
896
|
-
return [];
|
|
725
|
+
this.currentDate = new Date();
|
|
897
726
|
}
|
|
727
|
+
this.initializeMonths();
|
|
898
728
|
}
|
|
729
|
+
//#endregion LIFECYCLE
|
|
730
|
+
/****************************************************************************/
|
|
731
|
+
//#region METHODS
|
|
899
732
|
/**
|
|
900
733
|
* Checks if shortcuts are visible
|
|
901
734
|
* @returns {boolean} true if shortcuts are visible
|
|
902
735
|
*/
|
|
903
736
|
get hasShortcuts() {
|
|
904
|
-
return (this.shortcutsPlacement
|
|
737
|
+
return Boolean(this.shortcutsPlacement && this.shortcuts);
|
|
905
738
|
}
|
|
906
739
|
/**
|
|
907
740
|
* Checks if actions are visible
|
|
@@ -910,103 +743,46 @@ export class NvCalendar {
|
|
|
910
743
|
get hasActions() {
|
|
911
744
|
return this.showActions;
|
|
912
745
|
}
|
|
913
|
-
//#endregion METHODS
|
|
914
|
-
/****************************************************************************/
|
|
915
|
-
//#region RENDER
|
|
916
|
-
/**
|
|
917
|
-
* Renders the header
|
|
918
|
-
* @param {number} offset - Month offset
|
|
919
|
-
* @param {number} index - Calendar index
|
|
920
|
-
* @returns {JSX.Element} Header
|
|
921
|
-
* @description Renders the header of the calendar
|
|
922
|
-
*/
|
|
923
|
-
renderHeader(offset, index) {
|
|
924
|
-
return (h("div", { class: "header" }, this.numberOfCalendars > 1 && index === 0 && (h("nv-iconbutton", { class: "nav-left", emphasis: "lower", name: "chevron-left", onClick: this.getChangeMonthHandler(-1) })), h("div", { class: "date-controls" }, h("select", { class: "month-select mr-4", onChange: this.getHandleMonthChange(offset) }, this.months.map(month => (h("option", { key: month.value, value: month.value, selected: month.value === (this.currentDate.getUTCMonth() + offset) % 12 }, month.label)))), h("input", { type: "number", class: "year-input", min: "1950", max: "2100", value: this.currentDate.getUTCFullYear() +
|
|
925
|
-
Math.floor((this.currentDate.getUTCMonth() + offset) / 12), onChange: this.getHandleYearChange(offset) })), this.numberOfCalendars === 1 && (h("div", { class: "nav-buttons" }, h("nv-iconbutton", { emphasis: "lower", name: "chevron-left", onClick: this.getChangeMonthHandler(-1) }), h("nv-iconbutton", { emphasis: "lower", name: "chevron-right", onClick: this.getChangeMonthHandler(1) }))), this.numberOfCalendars > 1 && index === this.numberOfCalendars - 1 && (h("nv-iconbutton", { emphasis: "lower", name: "chevron-right", onClick: this.getChangeMonthHandler(1), class: "nav-right" }))));
|
|
926
|
-
}
|
|
927
746
|
/**
|
|
928
|
-
*
|
|
929
|
-
* @
|
|
930
|
-
* @param {number} index - Calendar index
|
|
931
|
-
* @returns {JSX.Element} Week numbers
|
|
932
|
-
* @description Renders the week numbers of the calendar
|
|
747
|
+
* Checks if the date format is in UTC mode
|
|
748
|
+
* @returns {boolean} true if the date format is in UTC mode
|
|
933
749
|
*/
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
weeks,
|
|
937
|
-
/** Calendar index */
|
|
938
|
-
index) {
|
|
939
|
-
return (h("div", { class: "week-numbers" }, h("div", { class: "week-header" }, this.getLocalizedWeekText()), weeks.map((week, weekIndex) => {
|
|
940
|
-
var _a;
|
|
941
|
-
const dates = week.map(d => d.date);
|
|
942
|
-
return (h("div", { class: `week-number ${this.selectionType === 'range' ? 'clickable' : ''}`, onClick: this.getWeekSelectionHandler(dates, index), key: `week-${weekIndex}` }, this.getWeekNumber(((_a = week.find(d => d.date)) === null || _a === void 0 ? void 0 : _a.date) || new Date())));
|
|
943
|
-
})));
|
|
944
|
-
}
|
|
945
|
-
renderDaysGrid(
|
|
946
|
-
/** Days to render */
|
|
947
|
-
days) {
|
|
948
|
-
return (h("div", { class: "days-grid" }, days.map(day => {
|
|
949
|
-
const date = day.date;
|
|
950
|
-
if (!date)
|
|
951
|
-
return null;
|
|
952
|
-
const isSelected = this.selectionType === 'single' &&
|
|
953
|
-
this.isSameDate(date, this.selectedDate);
|
|
954
|
-
const isInRange = this.isDateInRange(date);
|
|
955
|
-
const isStart = this.isSameDate(date, this.startDate);
|
|
956
|
-
const isEnd = this.isSameDate(date, this.endDate);
|
|
957
|
-
const isToday = this.isToday(date);
|
|
958
|
-
const isOutsideMonth = !day.isCurrentMonth;
|
|
959
|
-
const dayClasses = [
|
|
960
|
-
'day',
|
|
961
|
-
isSelected ? 'selected' : '',
|
|
962
|
-
isStart ? 'range-start' : '',
|
|
963
|
-
isEnd ? 'range-end' : '',
|
|
964
|
-
isInRange ? 'in-range' : '',
|
|
965
|
-
day.isDisabled ? 'disabled' : '',
|
|
966
|
-
isOutsideMonth ? 'outside-month' : '',
|
|
967
|
-
isToday ? 'is-today' : '',
|
|
968
|
-
];
|
|
969
|
-
return (h("div", { class: dayClasses.filter(Boolean).join(' '), onClick: this.getDayClickHandler(date, day.isDisabled), "aria-disabled": day.isDisabled, key: `day-${date.toISOString()}` }, day.dayOfMonth));
|
|
970
|
-
})));
|
|
750
|
+
get isUTCMode() {
|
|
751
|
+
return this.dateFormat.includes('Z');
|
|
971
752
|
}
|
|
972
753
|
/**
|
|
973
|
-
*
|
|
974
|
-
* @param {
|
|
975
|
-
* @param {
|
|
976
|
-
* @returns {
|
|
977
|
-
* @description Renders the calendar of the calendar
|
|
754
|
+
* Validates and processes a date range, warning if start is after end
|
|
755
|
+
* @param {string} startDateStr - Start date in ISO string format
|
|
756
|
+
* @param {string} endDateStr - End date in ISO string format
|
|
757
|
+
* @returns {object} Object containing the validated start and end dates
|
|
978
758
|
*/
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
759
|
+
validateDateRange(startDateStr, endDateStr) {
|
|
760
|
+
try {
|
|
761
|
+
const startDate = parseDate(startDateStr, this.dateFormat);
|
|
762
|
+
const endDate = parseDate(endDateStr, this.dateFormat);
|
|
763
|
+
if (startDate && endDate && startDate > endDate) {
|
|
764
|
+
console.warn(`Warning: startDate (${formatDate(startDate, {
|
|
765
|
+
dateFormat: this.dateFormat,
|
|
766
|
+
})}) is after endDate (${formatDate(endDate, {
|
|
767
|
+
dateFormat: this.dateFormat,
|
|
768
|
+
})})`);
|
|
769
|
+
// Return dates in correct order, with swapped flag
|
|
770
|
+
return {
|
|
771
|
+
startDate: endDate,
|
|
772
|
+
endDate: startDate,
|
|
773
|
+
swapped: true,
|
|
774
|
+
};
|
|
775
|
+
}
|
|
776
|
+
return {
|
|
777
|
+
startDate,
|
|
778
|
+
endDate,
|
|
779
|
+
swapped: false,
|
|
780
|
+
};
|
|
988
781
|
}
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
* Renders the shortcuts
|
|
993
|
-
* @returns {JSX.Element} Shortcuts
|
|
994
|
-
* @description Renders the shortcuts of the calendar
|
|
995
|
-
*/
|
|
996
|
-
renderShortcuts() {
|
|
997
|
-
if (!this.parsedShortcuts().length) {
|
|
998
|
-
return null;
|
|
782
|
+
catch (error) {
|
|
783
|
+
console.error('Invalid date range:', error);
|
|
784
|
+
throw error; // Re-throw to let the caller handle it
|
|
999
785
|
}
|
|
1000
|
-
return (h("div", { class: `shortcuts-container shortcuts-placement-${this.shortcutsPlacement}` }, this.parsedShortcuts().map(shortcut => (h("nv-button", { emphasis: "lower", size: "xs", "aria-label": shortcut.label, onClick: this.getShortcutHandler(shortcut) }, shortcut.label)))));
|
|
1001
|
-
}
|
|
1002
|
-
/**
|
|
1003
|
-
* Renders the actions
|
|
1004
|
-
* @returns {JSX.Element} Actions
|
|
1005
|
-
* @description Renders the actions of the calendar
|
|
1006
|
-
* @slot actions - Child content of the component.
|
|
1007
|
-
*/
|
|
1008
|
-
renderActions() {
|
|
1009
|
-
return (h("div", { class: "datepicker-actions" }, h("slot", { name: "actions" }, h("nv-button", { emphasis: "low", size: "xs", onClick: this.resetSelection }, "Cancel"), h("nv-button", { size: "xs", onClick: this.confirmSelection }, "OK"))));
|
|
1010
786
|
}
|
|
1011
787
|
/**
|
|
1012
788
|
* Renders the datepicker
|
|
@@ -1015,7 +791,8 @@ export class NvCalendar {
|
|
|
1015
791
|
* @slot default - Child content of the component.
|
|
1016
792
|
*/
|
|
1017
793
|
render() {
|
|
1018
|
-
return (h(Host, { key: '
|
|
794
|
+
return (h(Host, { key: '9804c486acf32e12f2d88f932a54ca6260365887' }, h("div", { key: '8503f585401191b904f2de248ed0c24b1fed1505', class: "datepicker-root" }, h("div", { key: '9da71618bd2031b44f5a3fd889d40b2580fcca58', class: `datepicker-container ${this.numberOfCalendars === 1 ? 'datepicker-container-single' : ''}` }, h("div", { key: 'fbf71a34b520ca48f1440d8caeec442773b1e57a', class: `datepicker-wrapper ${this.numberOfCalendars === 1 ? 'single' : ''}` }, this.shortcutsPlacement === 'left' && this.renderShortcuts(), Array.from({ length: this.numberOfCalendars }, (_, index) => this.renderCalendar(index, index)), this.shortcutsPlacement === 'right' && this.renderShortcuts()), ((this.hasShortcuts && this.shortcutsPlacement === 'bottom') ||
|
|
795
|
+
this.hasActions) && (h("div", { key: '4431e3f1221e9d47807d58af380dcaa91bf05c48', class: "datepicker-controls" }, this.shortcutsPlacement === 'bottom' && this.renderShortcuts(), this.hasActions && this.renderActions())))), h("slot", { key: '30386356bda72f4f12a28351084ab498ec95f5b9' })));
|
|
1019
796
|
}
|
|
1020
797
|
static get is() { return "nv-calendar"; }
|
|
1021
798
|
static get originalStyleUrls() {
|
|
@@ -1093,15 +870,14 @@ export class NvCalendar {
|
|
|
1093
870
|
"getter": false,
|
|
1094
871
|
"setter": false,
|
|
1095
872
|
"attribute": "single-value",
|
|
1096
|
-
"reflect": true
|
|
1097
|
-
"defaultValue": "''"
|
|
873
|
+
"reflect": true
|
|
1098
874
|
},
|
|
1099
875
|
"rangeValue": {
|
|
1100
|
-
"type": "
|
|
876
|
+
"type": "unknown",
|
|
1101
877
|
"mutable": true,
|
|
1102
878
|
"complexType": {
|
|
1103
|
-
"original": "string",
|
|
1104
|
-
"resolved": "string",
|
|
879
|
+
"original": "{\n /** ISO string for start date */\n start: string;\n /** ISO string for end date */\n end: string;\n }",
|
|
880
|
+
"resolved": "{ start: string; end: string; }",
|
|
1105
881
|
"references": {}
|
|
1106
882
|
},
|
|
1107
883
|
"required": false,
|
|
@@ -1111,10 +887,7 @@ export class NvCalendar {
|
|
|
1111
887
|
"text": "Selected date range\nformat: { start: ISO string, end: ISO string }\nex: { start: \"2025-03-15\", end: \"2025-03-20\" }"
|
|
1112
888
|
},
|
|
1113
889
|
"getter": false,
|
|
1114
|
-
"setter": false
|
|
1115
|
-
"attribute": "range-value",
|
|
1116
|
-
"reflect": true,
|
|
1117
|
-
"defaultValue": "''"
|
|
890
|
+
"setter": false
|
|
1118
891
|
},
|
|
1119
892
|
"min": {
|
|
1120
893
|
"type": "string",
|
|
@@ -1133,8 +906,7 @@ export class NvCalendar {
|
|
|
1133
906
|
"getter": false,
|
|
1134
907
|
"setter": false,
|
|
1135
908
|
"attribute": "min",
|
|
1136
|
-
"reflect": true
|
|
1137
|
-
"defaultValue": "''"
|
|
909
|
+
"reflect": true
|
|
1138
910
|
},
|
|
1139
911
|
"max": {
|
|
1140
912
|
"type": "string",
|
|
@@ -1153,31 +925,29 @@ export class NvCalendar {
|
|
|
1153
925
|
"getter": false,
|
|
1154
926
|
"setter": false,
|
|
1155
927
|
"attribute": "max",
|
|
1156
|
-
"reflect": true
|
|
1157
|
-
"defaultValue": "''"
|
|
928
|
+
"reflect": true
|
|
1158
929
|
},
|
|
1159
930
|
"disabledDates": {
|
|
1160
|
-
"type": "
|
|
931
|
+
"type": "unknown",
|
|
1161
932
|
"mutable": false,
|
|
1162
933
|
"complexType": {
|
|
1163
|
-
"original": "string",
|
|
1164
|
-
"resolved": "string",
|
|
1165
|
-
"references": {
|
|
934
|
+
"original": "Array<string>",
|
|
935
|
+
"resolved": "string[]",
|
|
936
|
+
"references": {
|
|
937
|
+
"Array": {
|
|
938
|
+
"location": "global",
|
|
939
|
+
"id": "global::Array"
|
|
940
|
+
}
|
|
941
|
+
}
|
|
1166
942
|
},
|
|
1167
943
|
"required": false,
|
|
1168
944
|
"optional": false,
|
|
1169
945
|
"docs": {
|
|
1170
|
-
"tags": [
|
|
1171
|
-
"name": "default",
|
|
1172
|
-
"text": "'[]'"
|
|
1173
|
-
}],
|
|
946
|
+
"tags": [],
|
|
1174
947
|
"text": "Disabled dates (ISO string array)"
|
|
1175
948
|
},
|
|
1176
949
|
"getter": false,
|
|
1177
|
-
"setter": false
|
|
1178
|
-
"attribute": "disabled-dates",
|
|
1179
|
-
"reflect": true,
|
|
1180
|
-
"defaultValue": "''"
|
|
950
|
+
"setter": false
|
|
1181
951
|
},
|
|
1182
952
|
"locale": {
|
|
1183
953
|
"type": "string",
|
|
@@ -1288,10 +1058,7 @@ export class NvCalendar {
|
|
|
1288
1058
|
"required": false,
|
|
1289
1059
|
"optional": false,
|
|
1290
1060
|
"docs": {
|
|
1291
|
-
"tags": [
|
|
1292
|
-
"name": "default",
|
|
1293
|
-
"text": "false"
|
|
1294
|
-
}],
|
|
1061
|
+
"tags": [],
|
|
1295
1062
|
"text": "Show action buttons"
|
|
1296
1063
|
},
|
|
1297
1064
|
"getter": false,
|
|
@@ -1301,27 +1068,26 @@ export class NvCalendar {
|
|
|
1301
1068
|
"defaultValue": "false"
|
|
1302
1069
|
},
|
|
1303
1070
|
"shortcuts": {
|
|
1304
|
-
"type": "
|
|
1071
|
+
"type": "unknown",
|
|
1305
1072
|
"mutable": false,
|
|
1306
1073
|
"complexType": {
|
|
1307
|
-
"original": "string",
|
|
1308
|
-
"resolved": "string",
|
|
1309
|
-
"references": {
|
|
1074
|
+
"original": "{\n /** Label of the shortcut */\n label: string;\n /** Selected date value for single selection mode */\n singleValue?: string;\n /** Date range values for range selection mode */\n rangeValue?: HTMLNvCalendarElement['rangeValue'];\n }[]",
|
|
1075
|
+
"resolved": "{ label: string; singleValue?: string; rangeValue?: { start: string; end: string; }; }[]",
|
|
1076
|
+
"references": {
|
|
1077
|
+
"HTMLNvCalendarElement": {
|
|
1078
|
+
"location": "global",
|
|
1079
|
+
"id": "global::HTMLNvCalendarElement"
|
|
1080
|
+
}
|
|
1081
|
+
}
|
|
1310
1082
|
},
|
|
1311
1083
|
"required": false,
|
|
1312
1084
|
"optional": false,
|
|
1313
1085
|
"docs": {
|
|
1314
|
-
"tags": [
|
|
1315
|
-
|
|
1316
|
-
"text": "'[]'"
|
|
1317
|
-
}],
|
|
1318
|
-
"text": "Custom actions to display in the footer\nJSON array of objects with the following properties:\n- label: string\n- onClick: function"
|
|
1086
|
+
"tags": [],
|
|
1087
|
+
"text": "Custom actions to display in the footer"
|
|
1319
1088
|
},
|
|
1320
1089
|
"getter": false,
|
|
1321
|
-
"setter": false
|
|
1322
|
-
"attribute": "shortcuts",
|
|
1323
|
-
"reflect": true,
|
|
1324
|
-
"defaultValue": "'[]'"
|
|
1090
|
+
"setter": false
|
|
1325
1091
|
},
|
|
1326
1092
|
"showWeekNumbers": {
|
|
1327
1093
|
"type": "boolean",
|
|
@@ -1334,10 +1100,7 @@ export class NvCalendar {
|
|
|
1334
1100
|
"required": false,
|
|
1335
1101
|
"optional": false,
|
|
1336
1102
|
"docs": {
|
|
1337
|
-
"tags": [
|
|
1338
|
-
"name": "default",
|
|
1339
|
-
"text": "true"
|
|
1340
|
-
}],
|
|
1103
|
+
"tags": [],
|
|
1341
1104
|
"text": "Show week numbers"
|
|
1342
1105
|
},
|
|
1343
1106
|
"getter": false,
|
|
@@ -1383,13 +1146,12 @@ export class NvCalendar {
|
|
|
1383
1146
|
"text": "Emitted when a date range is selected"
|
|
1384
1147
|
},
|
|
1385
1148
|
"complexType": {
|
|
1386
|
-
"original": "
|
|
1387
|
-
"resolved": "
|
|
1149
|
+
"original": "HTMLNvCalendarElement['rangeValue']",
|
|
1150
|
+
"resolved": "{ start: string; end: string; }",
|
|
1388
1151
|
"references": {
|
|
1389
|
-
"
|
|
1390
|
-
"location": "
|
|
1391
|
-
"
|
|
1392
|
-
"id": "src/interfaces/dateRange.tsx::DateRange"
|
|
1152
|
+
"HTMLNvCalendarElement": {
|
|
1153
|
+
"location": "global",
|
|
1154
|
+
"id": "global::HTMLNvCalendarElement"
|
|
1393
1155
|
}
|
|
1394
1156
|
}
|
|
1395
1157
|
}
|