diff --git a/.changeset/thick-years-invent.md b/.changeset/thick-years-invent.md new file mode 100644 index 0000000000..014da6f21c --- /dev/null +++ b/.changeset/thick-years-invent.md @@ -0,0 +1,8 @@ +--- +"@baloise/ds-testing": major +"@baloise/ds-core": major +"docs": major +"e2e": major +--- + +Removed deprecated component bal-datepicker for performance reasons diff --git a/docs/stories/components/bal-datepicker/bal-datepicker.mdx b/docs/stories/components/bal-datepicker/bal-datepicker.mdx deleted file mode 100644 index e2e4d11863..0000000000 --- a/docs/stories/components/bal-datepicker/bal-datepicker.mdx +++ /dev/null @@ -1,56 +0,0 @@ -import { Canvas, Meta, Markdown } from '@storybook/blocks' -import { Banner, Lead, PlaygroundBar, StoryHeading, WarningQuote, Footer } from '../../../.storybook/blocks' -import * as DatepickerStories from './bal-datepicker.stories' - - - - - - - - - **Datepicker** allows manual date entry as well as open the popover content with a calendar to select a date. - - - - **Deprecation Warning!** - Please use the [new component Date](?path=/docs/components-form-date--documentation), because this component is marked - as deprecated and will be removed with the next major releases. - - -## Component API - -import api from './api.md?raw' - -{api} - -## Integration - -Value must be a date string following the [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), -`1996-12-19`. The format does not have to be specific to an exact datetime. -For example, the maximum could just be the year, such as `1994`. Defaults to the end of this year. - -```typescript -import { formatDateString, now } from '@baloise/web-app-utils' - -const datepickerDisabled = document.getElementById('datepicker-disabled') -datepickerDisabled.value = formatDateString(now()) -// or -datepickerDisabled.value = formatDateString(2020, 0, 13) -// or -datepickerDisabled.value = formatDateString(new Date(2020, 0, 13)) -``` - -import integration from '../../snippets/integration.md?raw' - -{integration} - -import theming from './theming.md?raw' - -{theming} - -import testing from './testing.md?raw' - -{testing} - - diff --git a/docs/stories/components/bal-datepicker/bal-datepicker.stories.ts b/docs/stories/components/bal-datepicker/bal-datepicker.stories.ts deleted file mode 100644 index 5fc6c6d9b9..0000000000 --- a/docs/stories/components/bal-datepicker/bal-datepicker.stories.ts +++ /dev/null @@ -1,28 +0,0 @@ -import type { JSX } from '@baloise/ds-core' -import type { Meta } from '@storybook/html' -import { props, withRender, withContent, withDefaultContent, withComponentControls, StoryFactory } from '../../utils' - -type Args = JSX.BalDatepicker & { content: string } - -const meta: Meta = { - title: 'Components/Deprecated/Datepicker', - args: { - ...withDefaultContent(), - }, - argTypes: { - ...withContent(), - ...withComponentControls({ tag: 'bal-datepicker' }), - }, - ...withRender(({ content, ...args }) => `${content}`), -} - -export default meta - -/** - * STORIES - * ------------------------------------------------------ - */ - -const Story = StoryFactory(meta) - -export const Basic = Story() diff --git a/docs/stories/components/bal-datepicker/testing.md b/docs/stories/components/bal-datepicker/testing.md deleted file mode 100644 index fac5603838..0000000000 --- a/docs/stories/components/bal-datepicker/testing.md +++ /dev/null @@ -1,51 +0,0 @@ -## Testing - -The Baloise Design System provides a collection of custom cypress commands for the components. Moreover, some basic cypress commands like `should` or `click` have been overridden to work with the components. - -Go to testing guide - - - -```typescript -import { byTestId } from '@baloise/ds-testing' - -describe('Datepicker', () => { - const datepicker = byTestId('my-datepicker') // [data-testid="my-datepicker"] - - it('should open and close the datepicker', () => { - cy.get(datepicker).balDatepickerToggle().balDatepickerIsOpen().balDatepickerToggle().balDatepickerIsClosed() - }) - - it('should pick the date in datepicker', () => { - cy.get(datepicker).balDatepickerToggle().balDatepickerPick(now()) - }) - - it('should type and assert the date in the datepicker', () => { - cy.get(datepicker).type('20.02.2021').should('have.value', '20.02.2021') - cy.get(datepicker).clear().type('03.03.2021').should('not.have.value', '20.02.2021') - }) -}) -``` - - - -### Commands - -A list of the custom commands for this specific component. - -| Command | Description | Signature | -| ------------------------------- | -------------------------------------------------------------------- | ----------------------------------------------------- | -| `balDatepickerToggle` | Opens and closes the datepicker popover. | (options?: Partial\): Chainable | -| `balDatepickerIsOpen` | Assert if the datepicker popover is open. | (options?: Partial\): Chainable | -| `balDatepickerIsClosed` | Assert if the datepicker popover is closed. | (options?: Partial\): Chainable | -| `balDatepickerPick` | Picks the date in the datepicker like a human. | (date: Date, options?: Partial\): Chainable | -| `balDatepickerIsDateInRange` | Asserts if the given date is in range in the datepicker popover. | (date: Date, options?: Partial\): Chainable | -| `balDatepickerIsDateNotInRange` | Asserts if the given date is not in range in the datepicker popover. | (date: Date, options?: Partial\): Chainable | - - -### Selectors - -| Selector | Element | -| ------------------ | --------------------- | -| `datepicker.input` | Native input element. | - diff --git a/docs/stories/components/bal-datepicker/theming.md b/docs/stories/components/bal-datepicker/theming.md deleted file mode 100644 index adcbaec938..0000000000 --- a/docs/stories/components/bal-datepicker/theming.md +++ /dev/null @@ -1,22 +0,0 @@ -## Theming - -The component can be customization by changing the CSS variables. - -Go to theming guide - - - - - - - -### Variables - -| Variable | -| ------------------------------------------------- | -| `--bal-datepicker-popover-background` | -| `--bal-datepicker-cell-background` | -| `--bal-datepicker-cell-selected-background` | -| `--bal-datepicker-cell-selected-today-background` | -| `--bal-datepicker-cell-today-background` | -| `--bal-datepicker-cell-today-radius` | diff --git a/docs/stories/components/bal-form-grid/bal-form-grid.stories.ts b/docs/stories/components/bal-form-grid/bal-form-grid.stories.ts index 5a738c666e..022bd806c7 100644 --- a/docs/stories/components/bal-form-grid/bal-form-grid.stories.ts +++ b/docs/stories/components/bal-form-grid/bal-form-grid.stories.ts @@ -142,7 +142,7 @@ export const FormStructure = Story({ Datepicker - + @@ -151,7 +151,7 @@ export const FormStructure = Story({ Datepicker - + diff --git a/e2e/cypress/component/bal-datepicker.cy.ts b/e2e/cypress/component/bal-datepicker.cy.ts deleted file mode 100644 index 16a27ec2ed..0000000000 --- a/e2e/cypress/component/bal-datepicker.cy.ts +++ /dev/null @@ -1,290 +0,0 @@ -import { Components } from '../support/utils' -import { format, now } from '@baloise/web-app-utils' - -describe('bal-datepicker (DEPRECATED)', () => { - let onBalChangeSpy: Cypress.Agent - let onBalInputSpy: Cypress.Agent - let onBalFocusSpy: Cypress.Agent - let onBalBlurSpy: Cypress.Agent - - let events = { - balChange: onBalChangeSpy, - balInput: onBalInputSpy, - balFocus: onBalFocusSpy, - balBlur: onBalBlurSpy, - } - - beforeEach(() => { - onBalChangeSpy = cy.spy().as('balChange') - onBalInputSpy = cy.spy().as('balInput') - onBalFocusSpy = cy.spy().as('balFocus') - onBalBlurSpy = cy.spy().as('balBlur') - - events = { - balChange: onBalChangeSpy, - balInput: onBalInputSpy, - balFocus: onBalFocusSpy, - balBlur: onBalBlurSpy, - } - - cy.mount(``, { - events, - }) - }) - it('should open last available month if month from defaultDate is bigger that max month', () => { - cy.mount(``, { - props: { - defaultDate: '2023-04-12', - min: '2023-01-12', - max: '2024-02-28', - }, - events, - }) - cy.get('bal-datepicker') - .click() - .waitForComponents() - .find('.bal-datepicker-pagination__month-and-year__select--year select') - .select(1) - .waitForComponents() - - cy.get('bal-datepicker') - .find('.bal-datepicker-grid__row .bal-datepicker-grid__cell') - .first() - .should('not.be.disabled') - }) - it('should fire balChange when field is cleared', () => { - cy.mount(``, { - props: { - defaultDate: '2023-04-12', - min: '2023-01-12', - max: '2024-02-28', - value: '2023-02-20', - }, - events, - }) - cy.get('bal-datepicker') - .click() - .waitForComponents() - .find('input.input') - .clear({ force: true }) - .blur() - .waitForComponents() - - cy.get('@balChange').should('have.been.calledOnce') - }) - it('should change value through manual input', () => { - cy.get('bal-datepicker') - .find('input.input') - .type('{0}') - .type('{2}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{1}') - .type('{9}') - .type('{8}') - .type('{8}') - .type('{enter}') - .blur({ force: true }) - - cy.get('bal-datepicker').find('input.input').should('have.value', '02.01.1988') - - cy.get('@balChange').should('have.been.calledOnce') - cy.get('@balFocus').should('have.been.calledOnce') - cy.get('@balBlur').should('have.been.calledOnce') - cy.get('@balInput').should('have.been.callCount', 10) - }) - it('should automatically add the separators and change value through manual input', () => { - cy.get('bal-datepicker') - .find('input.input') - .type('{0}') - .type('{2}') - .type('{0}') - .type('{1}') - .type('{1}') - .type('{9}') - .type('{8}') - .type('{8}') - .type('{enter}') - cy.get('bal-datepicker').find('input.input').should('have.value', '02.01.1988') - cy.get('@balChange').should('have.been.calledOnce') - cy.get('@balFocus').should('have.been.calledOnce') - cy.get('@balInput').should('have.been.callCount', 8) - }) - it('should select the date of today', () => { - cy.get('bal-datepicker').find('input.input').click() - cy.get('bal-datepicker').find('.bal-datepicker-grid__cell--today').click() - cy.get('bal-datepicker').find('input.input').should('have.value', format('de-CH', now())) - cy.get('@balChange').should('have.been.calledOnce') - cy.get('@balInput').should('not.have.been.called') - }) - it('should fire balChange when the empty is set to nothing', () => { - cy.get('bal-datepicker').find('input.input').should('have.value', '') - cy.get('@balChange').should('not.have.been.called') - cy.get('@balInput').should('not.have.been.called') - }) - it('should be disabled', () => { - cy.mount(``, { - props: { - disabled: true, - }, - events, - }) - cy.get('bal-datepicker').find('input.input').should('be.disabled') - }) - it('should had disabled dates before min date', () => { - cy.mount(``, { - props: { - min: '2023-01-10', - }, - events, - }) - cy.get('bal-datepicker') - .find('input.input') - .type('{0}') - .type('{9}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(0).should('be.disabled') - cy.get('bal-datepicker') - .find('input.input') - .clear() - .type('{1}') - .type('{0}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(1).should('not.be.disabled') - cy.get('bal-datepicker') - .find('input.input') - .clear() - .type('{1}') - .type('{1}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(2).should('not.be.disabled') - }) - it('should not fire change event when clicking on disabled date', () => { - cy.mount(``, { - props: { - min: '2023-01-10', - }, - events, - }) - cy.get('bal-datepicker') - .find('input.input') - .clear() - .type('{0}') - .type('{9}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(0).click({ force: true }) - cy.get('@balChange').should('not.have.been.called') - }) - it('should had disabled dates after max date', () => { - cy.mount(``, { - props: { - max: '2023-01-10', - }, - events, - }) - cy.get('bal-datepicker') - .find('input.input') - .type('{9}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(0).should('not.be.disabled') - cy.get('bal-datepicker') - .find('input.input') - .clear() - .type('{1}') - .type('{0}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(1).should('not.be.disabled') - cy.get('bal-datepicker') - .find('input.input') - .clear() - .type('{1}') - .type('{1}') - .type('{.}') - .type('{0}') - .type('{1}') - .type('{.}') - .type('{2}') - .type('{0}') - .type('{2}') - .type('{3}') - .type('{enter}') - cy.get('bal-datepicker').find('.bal-datepicker-grid__row').eq(2).find('button').eq(2).should('be.disabled') - }) - it('should have set max year to the provided one', () => { - cy.mount(``, { - props: { - maxYearProp: 2023, - }, - events, - }) - cy.get('bal-datepicker') - .find('.bal-datepicker-pagination__month-and-year__select--year') - .find('select > option') - .last() - .should('have.value', '2023') - .should('not.have.value', '2024') - }) - it('should have set min year to the provided one', () => { - cy.mount(``, { - props: { - minYearProp: 2000, - }, - events, - }) - cy.get('bal-datepicker') - .find('.bal-datepicker-pagination__month-and-year__select--year') - .find('select > option') - .first() - .should('have.value', '2000') - .should('not.have.value', '1999') - }) -}) diff --git a/e2e/cypress/e2e/base/bal-datepicker.cy.ts b/e2e/cypress/e2e/base/bal-datepicker.cy.ts deleted file mode 100644 index 87da1053d4..0000000000 --- a/e2e/cypress/e2e/base/bal-datepicker.cy.ts +++ /dev/null @@ -1,63 +0,0 @@ -import { addDays, addWeeks, formatISO, subDays, subWeeks } from 'date-fns' - -const now = () => new Date() -const formatDateString = (date: Date) => formatISO(date, { representation: 'date' }) -const format = (date: Date) => { - const day = `0${date.getDate()}`.slice(-2) - const month = `0${date.getMonth() + 1}`.slice(-2) - - return `${day}.${month}.${date.getFullYear()}` -} - -describe('bal-datepicker', () => { - beforeEach(() => { - cy.visit('/components/bal-datepicker/test/bal-datepicker.cy.html') - cy.waitForDesignSystem() - }) - - describe('open & close', () => { - it('should open and close', () => { - cy.getByTestId('basic').balDatepickerToggle().balDatepickerIsOpen().balDatepickerToggle().balDatepickerIsClosed() - }) - }) - - describe('pick', () => { - it('should pick the date in datepicker', () => { - cy.getByTestId('basic') - .balDatepickerToggle() - .balDatepickerPick(now()) - .balDatepickerIsClosed() - .should('have.value', format(now())) - }) - }) - - describe('range', () => { - it('should have a min and max date', () => { - const today = new Date(2022, 3, 16) - const future = addWeeks(today, 1) - const futureDisabled = addDays(future, 1) - const past = subWeeks(today, 1) - const pastDisabled = subDays(past, 1) - - cy.getByTestId('basic') - .setProperty('min', formatDateString(past)) - .setProperty('max', formatDateString(future)) - .setProperty('value', formatDateString(today)) - .balDatepickerToggle() - .balDatepickerIsOpen() - .balDatepickerIsDateInRange(today) - .balDatepickerIsDateInRange(past) - .balDatepickerIsDateInRange(future) - .balDatepickerIsDateNotInRange(futureDisabled) - .balDatepickerIsDateNotInRange(pastDisabled) - }) - }) - - describe('reset form', () => { - it('should reset to default values', () => { - cy.getByTestId('reset').balDatepickerToggle().balDatepickerPick(now()) - cy.getByTestId('button-reset').click() - cy.getByTestId('reset').should('have.value', format(new Date(2022, 8, 16))) - }) - }) -}) diff --git a/e2e/cypress/e2e/visual/bal-datepicker.visual.cy.ts b/e2e/cypress/e2e/visual/bal-datepicker.visual.cy.ts deleted file mode 100644 index a3c4867336..0000000000 --- a/e2e/cypress/e2e/visual/bal-datepicker.visual.cy.ts +++ /dev/null @@ -1,53 +0,0 @@ -describe('bal-datepicker', () => { - beforeEach(() => cy.visit('/components/bal-datepicker/test/bal-datepicker.visual.html').waitForDesignSystem()) - - it('basic component', () => { - cy.platform('desktop') - cy.getByTestId('basic').testVisual('datepicker-basic') - - cy.getByTestId('basic-picker').balDatepickerToggle() - cy.testVisual('datepicker-basic-open') - - cy.getByTestId('basic-picker').balDatepickerPick(new Date(2022, 9, 7)) - cy.getByTestId('basic-picker').balDatepickerToggle() - cy.testVisual('datepicker-basic-open-selected') - }) - - it('basic mobile component', () => { - cy.platform('mobile') - cy.getByTestId('basic').testVisual('datepicker-basic-mobile') - - cy.getByTestId('basic-picker').balDatepickerToggle() - cy.testVisual('datepicker-basic-open-mobile') - - cy.getByTestId('basic-picker').balDatepickerPick(new Date(2022, 9, 7)) - cy.getByTestId('basic-picker').balDatepickerToggle() - cy.testVisual('datepicker-basic-open-selected-mobile') - - cy.getByTestId('basic-picker').balDatepickerToggle() - }) - - it('disabled component', () => { - cy.platform('desktop') - cy.getByTestId('disabled').testVisual('datepicker-disabled') - - cy.platform('mobile') - cy.getByTestId('disabled').testVisual('datepicker-disabled-mobile') - }) - - it('invalid component', () => { - cy.platform('desktop') - cy.getByTestId('invalid').testVisual('datepicker-invalid') - - cy.platform('mobile') - cy.getByTestId('invalid').testVisual('datepicker-invalid-mobile') - }) - - it('field component', () => { - cy.platform('desktop') - cy.getByTestId('field').testVisual('datepicker-field') - - cy.platform('mobile') - cy.getByTestId('field').testVisual('datepicker-field-mobile') - }) -}) diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-mobile.png deleted file mode 100644 index bf3e04f75a..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-mobile.png deleted file mode 100644 index 0a97883fd9..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected-mobile.png deleted file mode 100644 index f20d4c71cf..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected.png deleted file mode 100644 index af0790cff7..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open-selected.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open.png deleted file mode 100644 index 0c70d4426d..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic-open.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic.png deleted file mode 100644 index c28c8a7ce1..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-basic.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled-mobile.png deleted file mode 100644 index 1b4146af51..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled.png deleted file mode 100644 index c432f3a80f..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-disabled.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field-mobile.png deleted file mode 100644 index 3e6f02f3ae..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field.png deleted file mode 100644 index 0d8451122d..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-field.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid-mobile.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid-mobile.png deleted file mode 100644 index 843a21b8d5..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid-mobile.png and /dev/null differ diff --git a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid.png b/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid.png deleted file mode 100644 index ed0dbdea77..0000000000 Binary files a/e2e/cypress/snapshots/base/visual/bal-datepicker.visual.cy.ts/datepicker-invalid.png and /dev/null differ diff --git a/e2e/package.json b/e2e/package.json index 645f0245e0..4cc941d844 100644 --- a/e2e/package.json +++ b/e2e/package.json @@ -9,7 +9,6 @@ "dependencies": { "@baloise/ds-core": "16.8.0", "@baloise/ds-testing": "16.8.0", - "@baloise/web-app-utils": "3.15.0", "@cypress/mount-utils": "^4.1.0", "axe-core": "~4.8.4", "compression": "~1.7.4", @@ -17,7 +16,6 @@ "cypress-axe": "~1.5.0", "cypress-file-upload": "~5.0.8", "cypress-split": "~1.18.5", - "date-fns": "~2.30.0", "express": "~4.17.1", "pixelmatch": "~5.3.0", "pngjs": "~6.0.0", diff --git a/package-lock.json b/package-lock.json index c706d77371..7b266f8bc9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -177,7 +177,6 @@ "dependencies": { "@baloise/ds-core": "16.8.0", "@baloise/ds-testing": "16.8.0", - "@baloise/web-app-utils": "3.15.0", "@cypress/mount-utils": "^4.1.0", "axe-core": "~4.8.4", "compression": "~1.7.4", @@ -185,7 +184,6 @@ "cypress-axe": "~1.5.0", "cypress-file-upload": "~5.0.8", "cypress-split": "~1.18.5", - "date-fns": "~2.30.0", "express": "~4.17.1", "pixelmatch": "~5.3.0", "pngjs": "~6.0.0", @@ -48710,7 +48708,6 @@ "@stencil/core": "~4.22.2", "big.js": "~6.2.1", "contactjs": "2.1.7", - "date-fns": "~2.30.0", "filesize.js": "~2.0.0", "lodash.camelcase": "~4.3.0", "lodash.isempty": "~4.4.0", diff --git a/packages/angular/src/bundles.ts b/packages/angular/src/bundles.ts index cd4db3b932..0d004a8017 100644 --- a/packages/angular/src/bundles.ts +++ b/packages/angular/src/bundles.ts @@ -2,7 +2,6 @@ import { BalCheckbox, BalCheckboxGroup, BalDate, - BalDatepicker, BalDropdown, BalInput, BalInputDate, @@ -180,7 +179,6 @@ export const BalFormBundle = [ // Form Controls ...BalCheckboxBundle, BalDate, - BalDatepicker, ...BalDropdownBundle, BalInputDate, BalInputStepper, @@ -282,7 +280,6 @@ export const BalComponentBundle = [ BalCheckbox, BalCheckboxGroup, BalDate, - BalDatepicker, BalInput, BalInputDate, BalInputSlider, diff --git a/packages/angular/src/components/bal-datepicker.ts b/packages/angular/src/components/bal-datepicker.ts deleted file mode 100644 index d2a34be7b9..0000000000 --- a/packages/angular/src/components/bal-datepicker.ts +++ /dev/null @@ -1,75 +0,0 @@ -import { - ChangeDetectionStrategy, - ChangeDetectorRef, - Component, - ElementRef, - EventEmitter, - HostListener, - Injector, - NgZone, - forwardRef, -} from '@angular/core' -import { NG_VALUE_ACCESSOR } from '@angular/forms' - -import type { Components } from '@baloise/ds-core' -import { defineCustomElement } from '@baloise/ds-core/components/bal-datepicker' - -import { ProxyCmp, proxyOutputs } from '../generated/angular-component-lib/utils' -import { ValueAccessor } from '../generated/value-accessor' -import { BalDatepickerInputs, BalDatepickerMethods, BalDatepickerOutputs } from '../generated/meta' - -const accessorProvider = { - provide: NG_VALUE_ACCESSOR, - useExisting: /*@__PURE__*/ forwardRef(() => BalDatepicker), - multi: true, -} - -@ProxyCmp({ - defineCustomElementFn: defineCustomElement, - inputs: BalDatepickerInputs, - methods: BalDatepickerMethods, -}) -@Component({ - selector: 'bal-datepicker', - changeDetection: ChangeDetectionStrategy.OnPush, - template: '', - providers: [accessorProvider], - standalone: true, - inputs: BalDatepickerInputs, - outputs: BalDatepickerOutputs, -}) -export class BalDatepicker extends ValueAccessor { - protected el: HTMLElement - - constructor( - c: ChangeDetectorRef, - r: ElementRef, - protected z: NgZone, - injector: Injector, - ) { - super(injector, r) - c.detach() - this.el = r.nativeElement - proxyOutputs(this, this.el, BalDatepickerOutputs) - } - - @HostListener('balChange', ['$event']) - handleBalChange(event: CustomEvent): void { - this.handleValueChange(event) - } -} - -export declare interface BalDatepicker extends Components.BalDatepicker { - /** Emitted when a option got selected. */ - balChange: EventEmitter> - /** Emitted when a keyboard input occurred. */ - balInput: EventEmitter> - /** Emitted when the input loses focus. */ - balBlur: EventEmitter> - /** Emitted when the input has focus. */ - balFocus: EventEmitter> - /** Emitted when the input has clicked. */ - balInputClick: EventEmitter> - /** Emitted when the icon has clicked. */ - balIconClick: EventEmitter> -} diff --git a/packages/angular/src/components/index.ts b/packages/angular/src/components/index.ts index 1be133d4af..653271bf54 100644 --- a/packages/angular/src/components/index.ts +++ b/packages/angular/src/components/index.ts @@ -1,7 +1,6 @@ export * from './bal-checkbox' export * from './bal-checkbox-group' export * from './bal-date' -export * from './bal-datepicker' export * from './bal-file-upload' export * from './bal-input-date' export * from './bal-input-slider' diff --git a/packages/core/config/stencil.bindings.angular.ts b/packages/core/config/stencil.bindings.angular.ts index a36ba32148..1fcd10abbe 100644 --- a/packages/core/config/stencil.bindings.angular.ts +++ b/packages/core/config/stencil.bindings.angular.ts @@ -9,7 +9,6 @@ export const angularValueAccessorBindings: ValueAccessorConfig[] = [ 'bal-checkbox-group', 'bal-select', 'bal-dropdown', - 'bal-datepicker', 'bal-date', 'bal-input-date', 'bal-file-upload', @@ -51,7 +50,6 @@ export const AngularGenerator = () => 'bal-checkbox-group', 'bal-checkbox', 'bal-date', - 'bal-datepicker', 'bal-dropdown', 'bal-file-upload', 'bal-input-date', diff --git a/packages/core/config/stencil.bindings.vue.ts b/packages/core/config/stencil.bindings.vue.ts index 88e81726a5..f08e0df6ec 100644 --- a/packages/core/config/stencil.bindings.vue.ts +++ b/packages/core/config/stencil.bindings.vue.ts @@ -2,15 +2,7 @@ import { vueOutputTarget } from '@baloise/output-target-vue' export const vueComponentModels: any[] = [ { - elements: [ - 'bal-segment', - 'bal-radio-group', - 'bal-datepicker', - 'bal-select', - 'bal-tabs', - 'bal-input-stepper', - 'bal-checkbox-group', - ], + elements: ['bal-segment', 'bal-radio-group', 'bal-select', 'bal-tabs', 'bal-input-stepper', 'bal-checkbox-group'], event: 'balChange', targetAttr: 'value', }, diff --git a/packages/core/package.json b/packages/core/package.json index 69df0e186b..164039fb73 100644 --- a/packages/core/package.json +++ b/packages/core/package.json @@ -36,7 +36,6 @@ "@stencil/core": "~4.22.2", "big.js": "~6.2.1", "contactjs": "2.1.7", - "date-fns": "~2.30.0", "filesize.js": "~2.0.0", "lodash.camelcase": "~4.3.0", "lodash.isempty": "~4.4.0", diff --git a/packages/core/src/components.d.ts b/packages/core/src/components.d.ts index 7ced8d1053..486a1cbb6e 100644 --- a/packages/core/src/components.d.ts +++ b/packages/core/src/components.d.ts @@ -854,106 +854,6 @@ export namespace Components { "today": boolean; "year"?: number; } - interface BalDatepicker { - /** - * Callback to determine which date in the datepicker should be selectable. - */ - "allowedDates": BalProps.BalDatepickerCallback | undefined; - /** - * If `true`, in Angular reactive forms the control will not be set invalid - */ - "autoInvalidOff": boolean; - /** - * Closes the popover - */ - "close": () => Promise; - /** - * Closes the datepicker popover after selection - */ - "closeOnSelect": boolean; - "configChanged": (state: BalConfigState) => Promise; - /** - * Set the amount of time, in milliseconds, to wait to trigger the `ionChange` event after each keystroke. This also impacts form bindings such as `ngModel` or `v-model`. - */ - "debounce": number; - /** - * The date to defines where the datepicker popup starts. The prop accepts ISO 8601 date strings (YYYY-MM-DD). - */ - "defaultDate"?: string; - /** - * If `true`, the element is not mutable, focusable, or even submitted with the form. The user can neither edit nor focus on the control, nor its form control descendants. - */ - "disabled": boolean; - /** - * Returns the native `` element used under the hood. - */ - "getInputElement": () => Promise; - /** - * If `true` the component gets a invalid style. - */ - "invalid": boolean; - /** - * Defines if the select is in a loading state. - */ - "loading": boolean; - /** - * The maximum datetime allowed. Value must be a date string following the [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), `1996-12-19`. The format does not have to be specific to an exact datetime. For example, the maximum could just be the year, such as `1994`. Defaults to the end of this year. - */ - "max"?: string; - /** - * Latest year available for selection - */ - "maxYearProp"?: number; - /** - * The minimum datetime allowed. Value must be a date string following the [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), such as `1996-12-19`. The format does not have to be specific to an exact datetime. For example, the minimum could just be the year, such as `1994`. Defaults to the beginning of the year, 100 years ago from today. - */ - "min"?: string; - /** - * Earliest year available for selection - */ - "minYearProp"?: number; - /** - * The name of the control, which is submitted with the form data. - */ - "name": string; - /** - * Opens the popover - */ - "open": () => Promise; - /** - * The text to display when the select is empty. - */ - "placeholder"?: string; - /** - * If `true` the element can not mutated, meaning the user can not edit the control. - */ - "readonly": boolean; - /** - * If `true` the attribute required is added to the native input. - */ - "required": boolean; - /** - * Selects an option - */ - "select": (dateString: string) => Promise; - "setAriaForm": (ariaForm: BalAriaForm) => Promise; - /** - * Sets blur on the native `input`. Use this method instead of the global `input.blur()`. - */ - "setBlur": () => Promise; - /** - * Sets focus on the native `input`. Use this method instead of the global `input.focus()`. - */ - "setFocus": () => Promise; - /** - * If `true` the datepicker only open on click of the icon - */ - "triggerIcon": boolean; - /** - * The value of the form field, which accepts ISO 8601 date strings (YYYY-MM-DD). - */ - "value"?: string; - } interface BalDivider { /** * Defines the color of the separator line. @@ -3622,10 +3522,6 @@ export interface BalDateCalendarCellCustomEvent extends CustomEvent { detail: T; target: HTMLBalDateCalendarCellElement; } -export interface BalDatepickerCustomEvent extends CustomEvent { - detail: T; - target: HTMLBalDatepickerElement; -} export interface BalDropdownCustomEvent extends CustomEvent { detail: T; target: HTMLBalDropdownElement; @@ -4067,28 +3963,6 @@ declare global { prototype: HTMLBalDateCalendarCellElement; new (): HTMLBalDateCalendarCellElement; }; - interface HTMLBalDatepickerElementEventMap { - "balChange": BalEvents.BalDatepickerChangeDetail; - "balInput": BalEvents.BalDatepickerInputDetail; - "balBlur": BalEvents.BalDatepickerBlurDetail; - "balFocus": BalEvents.BalDatepickerFocusDetail; - "balInputClick": BalEvents.BalDatepickerInputClickDetail; - "balIconClick": BalEvents.BalDatepickerIconClickDetail; - } - interface HTMLBalDatepickerElement extends Components.BalDatepicker, HTMLStencilElement { - addEventListener(type: K, listener: (this: HTMLBalDatepickerElement, ev: BalDatepickerCustomEvent) => any, options?: boolean | AddEventListenerOptions): void; - addEventListener(type: K, listener: (this: Document, ev: DocumentEventMap[K]) => any, options?: boolean | AddEventListenerOptions): void; - addEventListener(type: K, listener: (this: HTMLElement, ev: HTMLElementEventMap[K]) => any, options?: boolean | AddEventListenerOptions): void; - addEventListener(type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions): void; - removeEventListener(type: K, listener: (this: HTMLBalDatepickerElement, ev: BalDatepickerCustomEvent) => any, options?: boolean | EventListenerOptions): void; - removeEventListener(type: K, listener: (this: Document, ev: DocumentEventMap[K]) => any, options?: boolean | EventListenerOptions): void; - removeEventListener(type: K, listener: (this: HTMLElement, ev: HTMLElementEventMap[K]) => any, options?: boolean | EventListenerOptions): void; - removeEventListener(type: string, listener: EventListenerOrEventListenerObject, options?: boolean | EventListenerOptions): void; - } - var HTMLBalDatepickerElement: { - prototype: HTMLBalDatepickerElement; - new (): HTMLBalDatepickerElement; - }; interface HTMLBalDividerElement extends Components.BalDivider, HTMLStencilElement { } var HTMLBalDividerElement: { @@ -5076,7 +4950,6 @@ declare global { "bal-date": HTMLBalDateElement; "bal-date-calendar": HTMLBalDateCalendarElement; "bal-date-calendar-cell": HTMLBalDateCalendarCellElement; - "bal-datepicker": HTMLBalDatepickerElement; "bal-divider": HTMLBalDividerElement; "bal-doc-app": HTMLBalDocAppElement; "bal-dropdown": HTMLBalDropdownElement; @@ -6042,104 +5915,6 @@ declare namespace LocalJSX { "today"?: boolean; "year"?: number; } - interface BalDatepicker { - /** - * Callback to determine which date in the datepicker should be selectable. - */ - "allowedDates"?: BalProps.BalDatepickerCallback | undefined; - /** - * If `true`, in Angular reactive forms the control will not be set invalid - */ - "autoInvalidOff"?: boolean; - /** - * Closes the datepicker popover after selection - */ - "closeOnSelect"?: boolean; - /** - * Set the amount of time, in milliseconds, to wait to trigger the `ionChange` event after each keystroke. This also impacts form bindings such as `ngModel` or `v-model`. - */ - "debounce"?: number; - /** - * The date to defines where the datepicker popup starts. The prop accepts ISO 8601 date strings (YYYY-MM-DD). - */ - "defaultDate"?: string; - /** - * If `true`, the element is not mutable, focusable, or even submitted with the form. The user can neither edit nor focus on the control, nor its form control descendants. - */ - "disabled"?: boolean; - /** - * If `true` the component gets a invalid style. - */ - "invalid"?: boolean; - /** - * Defines if the select is in a loading state. - */ - "loading"?: boolean; - /** - * The maximum datetime allowed. Value must be a date string following the [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), `1996-12-19`. The format does not have to be specific to an exact datetime. For example, the maximum could just be the year, such as `1994`. Defaults to the end of this year. - */ - "max"?: string; - /** - * Latest year available for selection - */ - "maxYearProp"?: number; - /** - * The minimum datetime allowed. Value must be a date string following the [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), such as `1996-12-19`. The format does not have to be specific to an exact datetime. For example, the minimum could just be the year, such as `1994`. Defaults to the beginning of the year, 100 years ago from today. - */ - "min"?: string; - /** - * Earliest year available for selection - */ - "minYearProp"?: number; - /** - * The name of the control, which is submitted with the form data. - */ - "name"?: string; - /** - * Emitted when the input loses focus. - */ - "onBalBlur"?: (event: BalDatepickerCustomEvent) => void; - /** - * Emitted when a option got selected. - */ - "onBalChange"?: (event: BalDatepickerCustomEvent) => void; - /** - * Emitted when the input has focus. - */ - "onBalFocus"?: (event: BalDatepickerCustomEvent) => void; - /** - * Emitted when the icon has clicked. - */ - "onBalIconClick"?: (event: BalDatepickerCustomEvent) => void; - /** - * Emitted when a keyboard input occurred. - */ - "onBalInput"?: (event: BalDatepickerCustomEvent) => void; - /** - * Emitted when the input has clicked. - */ - "onBalInputClick"?: (event: BalDatepickerCustomEvent) => void; - /** - * The text to display when the select is empty. - */ - "placeholder"?: string; - /** - * If `true` the element can not mutated, meaning the user can not edit the control. - */ - "readonly"?: boolean; - /** - * If `true` the attribute required is added to the native input. - */ - "required"?: boolean; - /** - * If `true` the datepicker only open on click of the icon - */ - "triggerIcon"?: boolean; - /** - * The value of the form field, which accepts ISO 8601 date strings (YYYY-MM-DD). - */ - "value"?: string; - } interface BalDivider { /** * Defines the color of the separator line. @@ -8799,7 +8574,6 @@ declare namespace LocalJSX { "bal-date": BalDate; "bal-date-calendar": BalDateCalendar; "bal-date-calendar-cell": BalDateCalendarCell; - "bal-datepicker": BalDatepicker; "bal-divider": BalDivider; "bal-doc-app": BalDocApp; "bal-dropdown": BalDropdown; @@ -8923,7 +8697,6 @@ declare module "@stencil/core" { "bal-date": LocalJSX.BalDate & JSXBase.HTMLAttributes; "bal-date-calendar": LocalJSX.BalDateCalendar & JSXBase.HTMLAttributes; "bal-date-calendar-cell": LocalJSX.BalDateCalendarCell & JSXBase.HTMLAttributes; - "bal-datepicker": LocalJSX.BalDatepicker & JSXBase.HTMLAttributes; "bal-divider": LocalJSX.BalDivider & JSXBase.HTMLAttributes; "bal-doc-app": LocalJSX.BalDocApp & JSXBase.HTMLAttributes; "bal-dropdown": LocalJSX.BalDropdown & JSXBase.HTMLAttributes; diff --git a/packages/core/src/components/bal-date/utils/calendar.ts b/packages/core/src/components/bal-date/utils/calendar.ts index 77ee08ea8e..9f75e480df 100644 --- a/packages/core/src/components/bal-date/utils/calendar.ts +++ b/packages/core/src/components/bal-date/utils/calendar.ts @@ -79,7 +79,7 @@ export function generateCalendarGrid( if (isNil(allowedDates)) { return false } - return !(allowedDates as BalProps.BalDatepickerCallback)(isoDate) + return !allowedDates(isoDate) } // Fill the grid with day numbers diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.i18n.ts b/packages/core/src/components/bal-datepicker/bal-datepicker.i18n.ts deleted file mode 100644 index 3ed2f57b29..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.i18n.ts +++ /dev/null @@ -1,87 +0,0 @@ -import { I18n } from '../../interfaces' - -interface I18nBalDatepicker { - months: string[] - monthsShort: string[] - weekdays: string[] - weekdaysShort: string[] - weekdaysMin: string[] -} - -export const i18nBalDatepicker: I18n = { - de: { - months: 'Januar_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember'.split('_'), - monthsShort: 'Jan._Feb._März_Apr._Mai_Juni_Juli_Aug._Sep._Okt._Nov._Dez.'.split('_'), - weekdays: 'Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag'.split('_'), - weekdaysShort: 'So._Mo._Di._Mi._Do._Fr._Sa.'.split('_'), - weekdaysMin: 'So_Mo_Di_Mi_Do_Fr_Sa'.split('_'), - }, - en: { - months: 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'), - monthsShort: 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'), - weekdays: 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'), - weekdaysShort: 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'), - weekdaysMin: 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'), - }, - fr: { - months: 'janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre'.split('_'), - monthsShort: 'janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.'.split('_'), - weekdays: 'dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi'.split('_'), - weekdaysShort: 'dim._lun._mar._mer._jeu._ven._sam.'.split('_'), - weekdaysMin: 'di_lu_ma_me_je_ve_sa'.split('_'), - }, - it: { - months: 'gennaio_febbraio_marzo_aprile_maggio_giugno_luglio_agosto_settembre_ottobre_novembre_dicembre'.split('_'), - monthsShort: 'gen_feb_mar_apr_mag_giu_lug_ago_set_ott_nov_dic'.split('_'), - weekdays: 'domenica_lunedì_martedì_mercoledì_giovedì_venerdì_sabato'.split('_'), - weekdaysShort: 'dom_lun_mar_mer_gio_ven_sab'.split('_'), - weekdaysMin: 'do_lu_ma_me_gi_ve_sa'.split('_'), - }, - nl: { - months: 'januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december'.split('_'), - monthsShort: 'jan_feb_mrt_apr_mei_juni_juli_aug_sept_okt_nov_dec.'.split('_'), - weekdays: 'zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag'.split('_'), - weekdaysShort: 'zo_ma_di_woe_do_vr_za'.split('_'), - weekdaysMin: 'zo_ma_di_wo_do_vr_za'.split('_'), - }, - es: { - months: 'enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre'.split('_'), - monthsShort: 'ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.'.split('_'), - weekdays: 'domingo_lunes_martes_miércoles_jueves_viernes_sábado'.split('_'), - weekdaysShort: 'dom._lun._mar._mié._jue._vie._sáb.'.split('_'), - weekdaysMin: 'do_lu_ma_mi_ju_vi_sá'.split('_'), - }, - pl: { - months: 'styczeń_luty_marzec_kwiecień_maj_czerwiec_lipiec_sierpień_wrzesień_październik_listopad_grudzień'.split( - '_', - ), - monthsShort: 'sty_lut_mar_kwi_maj_cze_lip_sie_wrz_paź_lis_gru'.split('_'), - weekdays: 'niedziela_poniedziałek_wtorek_środa_czwartek_piątek_sobota'.split('_'), - weekdaysShort: 'ndz_pon_wt_śr_czw_pt_sob'.split('_'), - weekdaysMin: 'Nd_Pn_Wt_Śr_Cz_Pt_So'.split('_'), - }, - pt: { - months: 'janeiro_fevereiro_março_abril_maio_junho_julho_agosto_setembro_outubro_novembro_dezembro'.split('_'), - monthsShort: 'jan_fev_mar_abr_mai_jun_jul_ago_set_out_nov_dez'.split('_'), - weekdays: 'Domingo_Segunda-feira_Terça-feira_Quarta-feira_Quinta-feira_Sexta-feira_Sábado'.split('_'), - weekdaysShort: 'Dom_Seg_Ter_Qua_Qui_Sex_Sáb'.split('_'), - weekdaysMin: 'Do_2ª_3ª_4ª_5ª_6ª_Sá'.split('_'), - }, - sv: { - months: 'januari_februari_mars_april_maj_juni_juli_augusti_september_oktober_november_december'.split('_'), - monthsShort: 'jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec'.split('_'), - weekdays: 'söndag_måndag_tisdag_onsdag_torsdag_fredag_lördag'.split('_'), - weekdaysShort: 'sön_mån_tis_ons_tor_fre_lör'.split('_'), - weekdaysMin: 'sö_må_ti_on_to_fr_lö'.split('_'), - }, - fi: { - months: - 'tammikuu_helmikuu_maaliskuu_huhtikuu_toukokuu_kesäkuu_heinäkuu_elokuu_syyskuu_lokakuu_marraskuu_joulukuu'.split( - '_', - ), - monthsShort: 'tammi_helmi_maalis_huhti_touko_kesä_heinä_elo_syys_loka_marras_joulu'.split('_'), - weekdays: 'sunnuntai_maanantai_tiistai_keskiviikko_torstai_perjantai_lauantai'.split('_'), - weekdaysShort: 'su_ma_ti_ke_to_pe_la'.split('_'), - weekdaysMin: 'su_ma_ti_ke_to_pe_la'.split('_'), - }, -} diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.interfaces.ts b/packages/core/src/components/bal-datepicker/bal-datepicker.interfaces.ts deleted file mode 100644 index ef63561c53..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.interfaces.ts +++ /dev/null @@ -1,33 +0,0 @@ -/* eslint-disable no-unused-vars */ -/* eslint-disable @typescript-eslint/no-unused-vars */ -// eslint-disable-next-line @typescript-eslint/triple-slash-reference -/// - -namespace BalProps { - export type BalDatepickerCallback = (dateString: string) => boolean -} - -namespace BalEvents { - export interface BalDatepickerCustomEvent extends CustomEvent { - detail: T - target: HTMLBalDatepickerElement - } - - export type BalDatepickerChangeDetail = string | undefined - export type BalDatepickerChange = BalDatepickerCustomEvent - - export type BalDatepickerInputDetail = string | undefined - export type BalDatepickerInput = BalDatepickerCustomEvent - - export type BalDatepickerBlurDetail = FocusEvent - export type BalDatepickerBlur = BalDatepickerCustomEvent - - export type BalDatepickerFocusDetail = FocusEvent - export type BalDatepickerFocus = BalDatepickerCustomEvent - - export type BalDatepickerInputClickDetail = MouseEvent - export type BalDatepickerInputClick = BalDatepickerCustomEvent - - export type BalDatepickerIconClickDetail = MouseEvent - export type BalDatepickerIconClick = BalDatepickerCustomEvent -} diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.sass b/packages/core/src/components/bal-datepicker/bal-datepicker.sass deleted file mode 100644 index 0648b2fb94..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.sass +++ /dev/null @@ -1,126 +0,0 @@ -@import '@baloise/ds-styles/sass/mixins' -@import './bal-datepicker.vars' - -+block(datepicker) - display: block - font-family: var(--bal-font-family-text) - width: 100% - - +element(native) - +hidden-input - - +element(popup) - padding: 1rem - width: 100% - +tablet - max-width: 24.5rem - user-select: none - background-color: var(--bal-datepicker-popover-background) - - +element(body) - max-width: 22.5rem - margin: 0 auto 0 auto - margin-top: 0.75rem - -+block(datepicker-pagination) - max-width: 22.5rem - margin: 0 auto 0 auto - +element(inner) - display: flex - gap: .5rem - +element(month-and-year) - display: flex - flex: 1 - gap: .5rem - +element(select) - flex: 1 - .select, - .select select - padding-top: 0 !important - padding-bottom: 0 !important - text-align: center !important - min-height: 2rem !important - height: 2rem !important - +tablet - min-height: 3rem !important - height: 3rem !important - -+block(datepicker-grid) - display: table - border-collapse: collapse - width: 100% - table-layout: fixed - - +element(body) - display: table-row-group - - +element(row) - display: table-row - .bal-datepicker-grid__cell - margin-bottom: 0.25rem - margin-right: 0.25rem - &:last-child - .bal-datepicker-grid__cell - margin-bottom: 0 - - +element(header) - display: flex - max-width: 22.5rem - margin: 0 auto 0 auto - gap: 0.25rem - .bal-datepicker-grid__cell - background: transparent - span - display: flex - justify-content: center - align-items: center - height: 100% - width: 100% - -.bal-datepicker-grid__cell - position: relative - text-align: center - vertical-align: middle - display: table-cell - width: 13% - padding: 0 !important - height: 3rem - min-height: 3rem - min-width: 2.25rem - appearance: auto !important - background: var(--bal-datepicker-cell-background) - &--selected - background: var(--bal-datepicker-cell-selected-background) !important - &--today:not(#{&}--outdated) - & > span - font-weight: var(--bal-font-weight-bold) - &--today:not(#{&}--outdated)::after - content: '' - position: absolute - display: block - width: 0.25rem - height: 0.25rem - background: var(--bal-datepicker-cell-today-background) - border-radius: var(--bal-datepicker-cell-today-radius) - margin-left: -2px - left: 50% - bottom: 0.375rem - &--today#{&}--selected:not(#{&}--outdated)::after - background: var(--bal-datepicker-cell-selected-today-background) - &:last-child - margin-right: 0 - & > span - font-family: var(--bal-font-family-text) - font-weight: var(--bal-font-weight-regular) - +tablet - min-width: 3rem !important - +modifier(disabled) - border-color: transparent !important - background: transparent !important - +modifier(header) - & > span - border: none - background: transparent - color: var(--bal-color-text-primary) - font-weight: var(--bal-font-weight-bold) - cursor: default diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.tsx b/packages/core/src/components/bal-datepicker/bal-datepicker.tsx deleted file mode 100644 index 31d4d79461..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.tsx +++ /dev/null @@ -1,1000 +0,0 @@ -import { - Component, - Host, - h, - Element, - State, - Prop, - Event, - EventEmitter, - Method, - Watch, - ComponentInterface, - Listen, -} from '@stencil/core' -import { - addDays, - subDays, - isBefore, - isAfter, - getDate, - getYear, - getMonth, - addYears, - subYears, - startOfWeek, - isSameDay, - isWithinInterval, - isSameWeek, - isSameMonth, - lastDayOfMonth, -} from 'date-fns' -import { debounceEvent, rIC } from '../../utils/helpers' -import { inheritAttributes } from '../../utils/attributes' -import { BalCalendarCell, BalPointerDate } from './bal-datepicker.type' -import { parse, format, isValidIsoString, now, formatDateString, dateSeparator } from '../../utils/date' -import { isSpaceKey, isEnterKey } from '../../utils/keyboard' -import isNil from 'lodash.isnil' -import { ACTION_KEYS, isCtrlOrCommandKey, NUMBER_KEYS } from '../../utils/constants/keys.constant' -import { i18nBalDatepicker } from './bal-datepicker.i18n' -import { - defaultConfig, - BalConfigObserver, - ListenToConfig, - useBalConfig, - defaultLocale, - BalLanguage, - BalConfigState, - BalRegion, -} from '../../utils/config' -import { - FormInput, - getInputTarget, - inputHandleFocus, - inputHandleHostClick, - inputListenOnClick, - inputSetBlur, - inputSetFocus, - stopEventBubbling, -} from '../../utils/form-input' -import { preventDefault } from '../bal-select/utils/utils' -import { BEM } from '../../utils/bem' -import { Loggable, Logger, LogInstance } from '../../utils/log' -import { BalBreakpointObserver, BalBreakpoints, ListenToBreakpoints, balBreakpoints } from '../../utils/breakpoints' -import { BalAriaForm, BalAriaFormLinking, defaultBalAriaForm } from '../../utils/form' - -@Component({ - tag: 'bal-datepicker', - styleUrl: 'bal-datepicker.sass', -}) -export class Datepicker - implements - ComponentInterface, - BalConfigObserver, - FormInput, - Loggable, - BalBreakpointObserver, - BalAriaFormLinking -{ - private inputId = `bal-dp-${datepickerIds++}` - private inheritedAttributes: { [k: string]: any } = {} - private popoverElement!: HTMLBalPopoverElement - - nativeInput!: HTMLInputElement - inputValue = this.value - initialValue?: string - - @Element() el!: HTMLElement - - @State() language: BalLanguage = defaultConfig.language - @State() region: BalRegion = defaultConfig.region - @State() isMobile = balBreakpoints.isMobile - @State() focused = false - @State() isPopoverOpen = false - @State() selectedDate?: string = '' - @State() pointerDate: BalPointerDate = { - year: getYear(now()), - month: getMonth(now()), - day: getDate(now()), - } - @State() ariaForm: BalAriaForm = defaultBalAriaForm - - log!: LogInstance - - @Logger('bal-datepicker') - createLogger(log: LogInstance) { - this.log = log - } - - /** - * The name of the control, which is submitted with the form data. - */ - @Prop() name: string = this.inputId - - /** - * If `true` the component gets a invalid style. - */ - @Prop() invalid = false - - /** - * If `true` the attribute required is added to the native input. - */ - @Prop() required = false - - /** - * If `true`, the element is not mutable, focusable, or even submitted with the form. The user can neither edit nor focus on the control, nor its form control descendants. - */ - @Prop() disabled = false - - /** - * If `true` the element can not mutated, meaning the user can not edit the control. - */ - @Prop() readonly = false - - /** - * Defines if the select is in a loading state. - */ - @Prop() loading = false - - /** - * The text to display when the select is empty. - */ - @Prop() placeholder?: string - - /** - * The minimum datetime allowed. Value must be a date string - * following the - * [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), - * such as `1996-12-19`. The format does not have to be specific to an exact - * datetime. For example, the minimum could just be the year, such as `1994`. - * Defaults to the beginning of the year, 100 years ago from today. - */ - @Prop({ mutable: true }) min?: string - - /** - * The maximum datetime allowed. Value must be a date string - * following the - * [ISO 8601 datetime format standard](https://www.w3.org/TR/NOTE-datetime), - * `1996-12-19`. The format does not have to be specific to an exact - * datetime. For example, the maximum could just be the year, such as `1994`. - * Defaults to the end of this year. - */ - @Prop({ mutable: true }) max?: string - - /** - * Closes the datepicker popover after selection - */ - @Prop() closeOnSelect = true - - /** - * If `true` the datepicker only open on click of the icon - */ - @Prop() triggerIcon = false - - /** - * Earliest year available for selection - */ - @Prop({ attribute: 'min-year' }) minYearProp?: number - - /** - * Latest year available for selection - */ - @Prop({ attribute: 'max-year' }) maxYearProp?: number - - /** - * Set the amount of time, in milliseconds, to wait to trigger the `ionChange` event after each keystroke. This also impacts form bindings such as `ngModel` or `v-model`. - */ - @Prop() debounce = 0 - - @Watch('debounce') - protected debounceChanged() { - this.balChange = debounceEvent(this.balChange, this.debounce) - } - - /** - * The date to defines where the datepicker popup starts. The prop accepts ISO 8601 date strings (YYYY-MM-DD). - */ - @Prop() defaultDate?: string - - /** - * The value of the form field, which accepts ISO 8601 date strings (YYYY-MM-DD). - */ - @Prop({ mutable: true }) value?: string - - /** - * Update the native input element when the value changes - */ - @Watch('value') - protected valueChanged() { - this.selectedDate = this.value - this.updatePointerDates() - } - - /** - * Callback to determine which date in the datepicker should be selectable. - */ - @Prop({ attribute: 'allowed-dates' }) allowedDates: BalProps.BalDatepickerCallback | undefined = undefined - - /** - * If `true`, in Angular reactive forms the control will not be set invalid - */ - @Prop({ reflect: true }) autoInvalidOff = false - - /** - * Emitted when a option got selected. - */ - @Event() balChange!: EventEmitter - - /** - * Emitted when a keyboard input occurred. - */ - @Event() balInput!: EventEmitter - - /** - * Emitted when the input loses focus. - */ - @Event() balBlur!: EventEmitter - - /** - * Emitted when the input has focus. - */ - @Event() balFocus!: EventEmitter - - /** - * Emitted when the input has clicked. - */ - @Event() balInputClick!: EventEmitter - - /** - * Emitted when the icon has clicked. - */ - @Event() balIconClick!: EventEmitter - - @Listen('click', { capture: true, target: 'document' }) - listenOnClick(ev: UIEvent) { - inputListenOnClick(this, ev) - } - - private resetHandlerTimer?: NodeJS.Timeout - - @Listen('reset', { capture: true, target: 'document' }) - resetHandler(ev: UIEvent) { - const formElement = ev.target as HTMLElement - if (formElement?.contains(this.el)) { - if (this.resetHandlerTimer) { - clearTimeout(this.resetHandlerTimer) - } - this.resetHandlerTimer = setTimeout(() => { - if (this.initialValue) { - this.nativeInput.value = format(this.getLocale(), parse(this.initialValue)) - } else { - this.nativeInput.value = '' - } - - this.selectedDate = this.initialValue - this.updateValue(this.initialValue, false) - this.updatePointerDates() - }, 0) - } - } - - @ListenToBreakpoints() - breakpointListener(breakpoints: BalBreakpoints): void { - this.isMobile = breakpoints.mobile - } - - connectedCallback() { - this.debounceChanged() - this.initialValue = this.value - } - - componentDidLoad() { - this.inputValue = this.value - } - - componentWillLoad() { - this.inheritedAttributes = inheritAttributes(this.el, ['aria-label', 'tabindex', 'title']) - - this.selectedDate = this.value - this.updatePointerDates() - this.updateValue(this.value, false) - } - - /** - * @internal define config for the component - */ - @Method() - @ListenToConfig() - async configChanged(state: BalConfigState): Promise { - this.language = state.language - this.region = state.region - } - - /** - * Opens the popover - */ - @Method() - async open(): Promise { - if (!this.disabled && this.popoverElement) { - this.popoverElement.present() - } - } - - /** - * Closes the popover - */ - @Method() - async close(): Promise { - if (!this.disabled && this.popoverElement) { - this.popoverElement.dismiss() - } - } - - /** - * Selects an option - */ - @Method() - async select(dateString: string) { - this.nativeInput.value = format(this.getLocale(), parse(dateString)) - this.updateValue(dateString) - this.updatePointerDates() - - if (this.closeOnSelect) { - await this.popoverElement?.toggle() - } - } - - /** - * Sets focus on the native `input`. Use this method instead of the global - * `input.focus()`. - */ - @Method() - async setFocus() { - inputSetFocus(this) - } - - /** - * Sets blur on the native `input`. Use this method instead of the global - * `input.blur()`. - * @internal - */ - @Method() - async setBlur() { - inputSetBlur(this) - } - - /** - * Returns the native `` element used under the hood. - */ - @Method() - getInputElement(): Promise { - return Promise.resolve(this.nativeInput) - } - - /** - * @internal - */ - @Method() - async setAriaForm(ariaForm: BalAriaForm): Promise { - this.ariaForm = { ...ariaForm } - } - - private updatePointerDates() { - let date = now() - date.setDate(1) - if (this.selectedDate) { - date = parse(this.selectedDate) as Date - } else { - if (this.defaultDate) { - date = parse(this.defaultDate) as Date - } - } - - if (this.min) { - const minDate = parse(this.min) - if (minDate && date < minDate) { - date = minDate - } - } - - if (this.max) { - const maxDate = parse(this.max) - if (maxDate && date > maxDate) { - date = maxDate - } - } - - this.pointerDate = { - year: getYear(date), - month: getMonth(date), - day: getDate(date), - } - } - - private updateValue(dateString: string | undefined, isHuman = true) { - if (!isValidIsoString(dateString)) { - this.selectedDate = undefined - this.value = undefined - if (this.nativeInput) { - this.nativeInput.value = '' - } - } - - if (this.value !== dateString) { - this.value = dateString - - if (isHuman && (this.isDateInRange(parse(this.value as string) as Date) || this.value === '')) { - this.balChange.emit(this.value) - } - } - } - - get minYear() { - if (this.min) { - return parseInt(this.min.substring(0, 4), 10) - } - return this.minYearProp ? this.minYearProp : getYear(subYears(now(), 100)) - } - - get maxYear() { - if (this.max) { - return parseInt(this.max.substring(0, 4), 10) - } - return this.maxYearProp ? this.maxYearProp : getYear(addYears(now(), 100)) - } - - get years(): number[] { - let years = Array.from({ length: this.maxYear - this.minYear + 1 }, (_, index: number) => this.minYear + index) - - if (this.min && this.pointerDate.month === getMonth(parse(this.min) as Date)) { - const minYear = getYear(parse(this.min) as Date) - years = years.filter(y => y >= minYear) - } - - if (this.max && this.pointerDate.month === getMonth(parse(this.max) as Date)) { - const maxYear = getYear(parse(this.max) as Date) - years = years.filter(y => y <= maxYear) - } - - return years - } - - get months(): { name: string; index: number }[] { - const monthNames = i18nBalDatepicker[this.language].monthsShort - let months = monthNames.map((name, index) => ({ name, index })) - - if (this.min && this.pointerDate.year === getYear(parse(this.min) as Date)) { - const minMonth = parseInt(this.min.substring(5, 7), 10) - 1 - months = months.filter(month => month.index >= minMonth) - } - - if (this.max && this.pointerDate.year === getYear(parse(this.max) as Date)) { - const maxMonth = parseInt(this.max.substring(5, 7), 10) - 1 - months = months.filter(month => month.index <= maxMonth) - } - - return months - } - - get weekDays(): string[] { - const translations = [...i18nBalDatepicker[this.language].weekdaysMin] - translations.push(translations.shift() || '') - return translations - } - - get firstDateOfBox(): Date { - const date = new Date(this.pointerDate.year, this.pointerDate.month, 1) - return startOfWeek(date, { weekStartsOn: 1 }) - } - - getLocale(): string { - const config = useBalConfig() - return (config && config.locale) || defaultLocale - } - - get calendarGrid(): BalCalendarCell[][] { - const weekDatePointer = this.firstDateOfBox - const dayDatePointer = this.firstDateOfBox - let calendar: any[] = [] // eslint-disable-line - do { - let row: any[] = [] // eslint-disable-line - do { - row = [ - ...row, - { - date: new Date(dayDatePointer), - display: format(this.getLocale(), dayDatePointer), - dateString: formatDateString(dayDatePointer), - label: getDate(dayDatePointer).toString(), - isToday: isSameDay(dayDatePointer, now()), - isSelected: - parse(this.selectedDate as string) !== undefined && - isSameDay(dayDatePointer, parse(this.selectedDate as string) as Date), - isDisabled: !this.getAllowedDates(dayDatePointer) || !this.isDateInRange(dayDatePointer), - isOutdated: this.pointerDate.month !== dayDatePointer.getMonth() || !this.isDateInRange(dayDatePointer), - } as BalCalendarCell, - ] - dayDatePointer.setDate(dayDatePointer.getDate() + 1) - } while (isSameWeek(dayDatePointer, weekDatePointer, { weekStartsOn: 1 })) - calendar = [...calendar, row] - weekDatePointer.setDate(weekDatePointer.getDate() + 7) - } while (isSameMonth(new Date(this.pointerDate.year, this.pointerDate.month, this.pointerDate.day), dayDatePointer)) - return calendar - } - - private getAllowedDates(dayDatePointer: Date): boolean { - if (isNil(this.allowedDates)) { - return true - } - - return (this.allowedDates as BalProps.BalDatepickerCallback)(formatDateString(dayDatePointer)) - } - - private onIconClick = (ev: MouseEvent) => { - if (!this.disabled && !this.readonly) { - this.popoverElement.toggle() - } - stopEventBubbling(ev) - this.balIconClick.emit(ev) - } - - private onInputClick = (ev: MouseEvent) => { - if (!this.triggerIcon && !this.disabled && !this.readonly) { - this.popoverElement.toggle() - } - stopEventBubbling(ev) - if (!this.triggerIcon) { - this.balInputClick.emit(ev) - } - } - - private onPopoverChange = (ev: CustomEvent) => { - stopEventBubbling(ev) - if (this.isPopoverOpen !== ev.detail) { - this.isPopoverOpen = ev.detail - this.fireBlur(ev) - } - } - - private formatDate(value: string): string { - const separator = dateSeparator(this.getLocale()) - const length = value.length - const currentChar = value.charAt(length - 1) - const lastChar = value.charAt(length - 2) - - if (currentChar === separator) { - if (length === 1 || lastChar === separator || value.split(separator).filter(val => val.length > 0).length >= 3) { - return value.substring(0, length - 1) - } - } - - if (length === 5) { - if (value.split(separator)[0].split('').length === 1 && lastChar !== separator && currentChar !== separator) { - return value.substring(0, length - 1) + separator + value.substring(length - 1, length) - } - } - - if (length === 3 || length === 6) { - if (currentChar !== separator && lastChar !== separator && value.split(separator).length <= 2) { - return value.substring(0, length - 1) + separator + value.substring(length - 1, length) - } - } - - return value - } - - private onInput = (ev: Event) => { - const input = getInputTarget(ev) - - if (input) { - this.inputValue = input.value - if (input.value) { - this.nativeInput.value = this.formatDate(this.inputValue) - } - if (this.inputValue && this.inputValue.length >= 6) { - const date = parse(this.inputValue, this.getLocale()) - const dateString = formatDateString(date as Date) - if (isValidIsoString(dateString)) { - this.selectedDate = dateString - this.updatePointerDates() - } - } - } - - this.balInput.emit(this.inputValue) - } - - private onInputChange = (ev: Event) => { - const inputValue = (ev.target as HTMLInputElement).value - const date = parse(inputValue, this.getLocale()) - const dateString = formatDateString(date as Date) - const formattedValue = format(this.getLocale(), date) - - this.nativeInput.value = formattedValue - this.updateValue(dateString) - this.updatePointerDates() - } - - private onClickDateCell = (cell: BalCalendarCell): void => { - if (!cell.isDisabled) { - this.select(cell.dateString) - } - } - - private onInputKeyUp = (ev: KeyboardEvent) => { - if (isSpaceKey(ev) && !this.triggerIcon) { - if (this.isPopoverOpen) { - this.close() - } else { - this.open() - } - } - - if (isEnterKey(ev) && !this.triggerIcon) { - const date = parse(this.nativeInput.value, this.getLocale()) - const dateString = formatDateString(date as Date) - - if (this.isPopoverOpen) { - if (this.value === dateString) { - this.close() - } - } - } - } - - private onInputKeyDown = (ev: KeyboardEvent) => { - const separator = dateSeparator(this.getLocale()) - const allowedKeys = [...NUMBER_KEYS, separator, ...ACTION_KEYS] - if (!isCtrlOrCommandKey(ev) && allowedKeys.indexOf(ev.key) < 0) { - ev.preventDefault() - ev.stopPropagation() - } - if (ev.key === 'Tab') { - this.close() - } - } - - private onMonthSelect = (ev: Event) => { - const inputValue = (ev.target as HTMLInputElement).value - this.pointerDate = { - ...this.pointerDate, - day: 1, - month: parseInt(inputValue, 10), - } - } - - private onYearSelect = (ev: Event) => { - const inputValue = (ev.target as HTMLInputElement).value - const yearValue = parseInt(inputValue, 10) - let month = undefined - - if (this.defaultDate) { - const defaultDate = parse(this.defaultDate) as Date - - if (this.max) { - const maxDate = parse(this.max) as Date - if (defaultDate.getMonth() > maxDate.getMonth()) { - month = maxDate.getMonth() - } - } - - if (this.min) { - const minDate = parse(this.min) as Date - if (defaultDate.getMonth() < minDate.getMonth()) { - month = minDate.getMonth() - } - } - } - - this.pointerDate = { - day: 1, - year: yearValue, - month: month !== undefined ? month : this.pointerDate.month, - } - } - - private onInputFocus = (ev: FocusEvent) => inputHandleFocus(this, ev) - - private onInputBlur = (ev: FocusEvent) => { - preventDefault(ev) - this.focused = false - this.fireBlur(ev) - } - - private fireBlur = (ev: Event) => { - if (!this.isPopoverOpen && !this.focused) { - rIC(() => this.balBlur.emit(ev as any)) - } - } - - private handleClick = (ev: MouseEvent) => inputHandleHostClick(this, ev) - - render() { - const block = BEM.block('datepicker') - const native = block.element('native') - const popup = block.element('popup') - const popupBody = popup.element('body') - const popupFooter = popup.element('footer') - - return ( - - - (this.popoverElement = el as HTMLBalPopoverElement)}> - {this.renderInput()} - - - {this.renderHeader()} - {this.renderGrid()} - - - - - - - - ) - } - - renderInput() { - return ( - - - (this.nativeInput = el as HTMLInputElement)} - id={this.ariaForm.controlId || this.inputId} - aria-labelledby={this.ariaForm.labelId} - aria-describedby={this.ariaForm.messageId} - aria-invalid={this.invalid === true ? 'true' : 'false'} - aria-disabled={this.disabled ? 'true' : null} - type="text" - maxlength="10" - autoComplete="off" - value={format(this.getLocale(), parse(this.value || ''))} - required={this.required} - disabled={this.disabled} - readonly={this.readonly} - placeholder={this.placeholder} - onKeyDown={e => this.onInputKeyDown(e)} - onKeyUp={e => this.onInputKeyUp(e)} - onInput={this.onInput} - onClick={this.onInputClick} - onChange={this.onInputChange} - onBlur={this.onInputBlur} - onFocus={this.onInputFocus} - {...this.inheritedAttributes} - /> - {!this.loading ? ( - - ) : ( - '' - )} - - - ) - } - - renderGrid() { - const block = BEM.block('datepicker-grid') - const rowEl = block.element('row') - const cellEl = block.element('cell') - - return ( - - {this.renderWeekDayHeader()} - - {this.calendarGrid.map((row, index) => ( - - {row.map(cell => ( - this.onClickDateCell(cell)} - disabled={cell.isDisabled} - class={{ - ...cellEl.class(), - 'button': true, - 'is-text': !cell.isDisabled && !cell.isSelected, - 'is-primary': cell.isSelected && cell.isSelected, - 'is-disabled': cell.isDisabled || cell.isOutdated, - ...cellEl.modifier('today').class(cell.isToday), - ...cellEl.modifier('selectable').class(!cell.isDisabled && !cell.isOutdated), - ...cellEl.modifier('disabled').class(cell.isDisabled || cell.isOutdated), - ...cellEl.modifier('outdated').class(cell.isOutdated), - ...cellEl.modifier('selected').class(cell.isSelected), - }} - > - {cell.label} - - ))} - - ))} - - - ) - } - - renderWeekDayHeader() { - const block = BEM.block('datepicker-grid') - const headerEl = block.element('header') - const cellEl = block.element('cell') - - return ( - - {this.weekDays.map(weekday => ( - - {weekday} - - ))} - - ) - } - - renderHeader() { - const block = BEM.block('datepicker-pagination') - const innerEl = block.element('inner') - const monthAndYearEl = block.element('month-and-year') - const selectEl = monthAndYearEl.element('select') - - return ( - - - this.previousMonth()} - > - - - - - {this.months.map(month => ( - - {month.name} - - ))} - - - - - - - {this.years.map(year => ( - - {year} - - ))} - - - - - this.nextMonth()} - > - - - ) - } - - private previousMonth() { - if (!this.isPreviousMonthDisabled) { - if (this.pointerDate.year === this.minYear && this.pointerDate.month === 0) { - return - } - - this.pointerDate = this.calcPreviousMonth() - } - } - - private nextMonth() { - if (!this.isNextMonthDisabled) { - if (this.pointerDate.year === this.maxYear && this.pointerDate.month === 11) { - return - } - this.pointerDate = this.calcNextMonth() - } - } - - private calcPreviousMonth(): BalPointerDate { - if (this.pointerDate.month === 0) { - return { ...this.pointerDate, year: this.pointerDate.year - 1, month: 11, day: 1 } - } else { - return { ...this.pointerDate, month: this.pointerDate.month - 1, day: 1 } - } - } - - private calcNextMonth(): BalPointerDate { - if (this.pointerDate.month === 11) { - return { ...this.pointerDate, year: this.pointerDate.year + 1, month: 0, day: 1 } - } else { - return { ...this.pointerDate, month: this.pointerDate.month + 1, day: 1 } - } - } - - private lastDayOfMonth(year: number, month: number): number { - const d = new Date(year, month + 1, 0) - return getDate(d) - } - - private get isPreviousMonthDisabled() { - if (this.min) { - const minDate = parse(this.min) as Date - const lastDayOfMonth = this.lastDayOfMonth(this.calcPreviousMonth().year, this.calcPreviousMonth().month) - const beforeDate = new Date(this.calcPreviousMonth().year, this.calcPreviousMonth().month, lastDayOfMonth) - return isBefore(beforeDate, subDays(minDate, 1)) - } - return false - } - - private get isNextMonthDisabled() { - if (this.max) { - const maxDate = parse(this.max) as Date - const beforeDate = new Date(this.calcNextMonth().year, this.calcNextMonth().month, 1) - return isAfter(beforeDate, lastDayOfMonth(maxDate) ? maxDate : addDays(maxDate, 1)) - } - return false - } - - private isDateInRange(cellDate: Date): boolean { - const parsedCellDate = parse(formatDateString(cellDate)) as Date - if (this.min && this.max && this.max > this.min) { - return isWithinInterval(parsedCellDate, { - start: parse(this.min) as Date, - end: parse(this.max) as Date, - }) - } - if (this.min) { - return isAfter(parsedCellDate, parse(this.min) as Date) || isSameDay(parsedCellDate, parse(this.min) as Date) - } - if (this.max) { - return ( - isBefore(parsedCellDate, addDays(parse(this.max) as Date, 1)) || - isSameDay(parsedCellDate, parse(this.max) as Date) - ) - } - return true - } -} - -let datepickerIds = 0 diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.type.ts b/packages/core/src/components/bal-datepicker/bal-datepicker.type.ts deleted file mode 100644 index 08448d659d..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.type.ts +++ /dev/null @@ -1,15 +0,0 @@ -export interface BalCalendarCell { - date: Date - label: string - dateString: string - isToday: boolean - isSelected: boolean - isDisabled: boolean - isOutdated: boolean -} - -export interface BalPointerDate { - year: number - month: number - day: number -} diff --git a/packages/core/src/components/bal-datepicker/bal-datepicker.vars.sass b/packages/core/src/components/bal-datepicker/bal-datepicker.vars.sass deleted file mode 100644 index aa4a1accc8..0000000000 --- a/packages/core/src/components/bal-datepicker/bal-datepicker.vars.sass +++ /dev/null @@ -1,16 +0,0 @@ -/** - * @prop --bal-datepicker-popover-background: TBD - * @prop --bal-datepicker-cell-background: TBD - * @prop --bal-datepicker-cell-selected-background: TBD - * @prop --bal-datepicker-cell-selected-today-background: TBD - * @prop --bal-datepicker-cell-today-background: TBD - * @prop --bal-datepicker-cell-today-radius: TBD - */ - -:root - --bal-datepicker-popover-background: var(--bal-color-grey-2) - --bal-datepicker-cell-background: var(--bal-color-white) - --bal-datepicker-cell-selected-background: var(--bal-color-primary) - --bal-datepicker-cell-selected-today-background: var(--bal-color-white) - --bal-datepicker-cell-today-background: var(--bal-color-primary) - --bal-datepicker-cell-today-radius: var(--bal-radius-rounded) diff --git a/packages/core/src/components/bal-datepicker/test/bal-datepicker.cy.html b/packages/core/src/components/bal-datepicker/test/bal-datepicker.cy.html deleted file mode 100644 index c5d04f307f..0000000000 --- a/packages/core/src/components/bal-datepicker/test/bal-datepicker.cy.html +++ /dev/null @@ -1,39 +0,0 @@ - - - - - - - - - - - - - - Basic - - - - Form Reset - - - - - - - - - - - - - Submit - Reset - - - - - - - diff --git a/packages/core/src/components/bal-datepicker/test/bal-datepicker.visual.html b/packages/core/src/components/bal-datepicker/test/bal-datepicker.visual.html deleted file mode 100644 index 518d544ee0..0000000000 --- a/packages/core/src/components/bal-datepicker/test/bal-datepicker.visual.html +++ /dev/null @@ -1,40 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - Label - - - - Message - - - - - - diff --git a/packages/core/src/components/bal-field/bal-field.tsx b/packages/core/src/components/bal-field/bal-field.tsx index e60ccb717e..5c405759a9 100644 --- a/packages/core/src/components/bal-field/bal-field.tsx +++ b/packages/core/src/components/bal-field/bal-field.tsx @@ -18,7 +18,6 @@ export class Field implements ComponentInterface, BalMutationObserver { 'bal-number-input', 'bal-textarea', 'bal-select', - 'bal-datepicker', 'bal-checkbox', 'bal-radio', 'bal-input-group', @@ -179,7 +178,6 @@ export class Field implements ComponentInterface, BalMutationObserver { 'bal-field-control bal-radio-group', 'bal-field-control bal-number-input', 'bal-field-control bal-time-input', - 'bal-field-control bal-datepicker', 'bal-field-control bal-input-slider', 'bal-field-control bal-input-stepper', 'bal-field-control bal-textarea', diff --git a/packages/core/src/components/bal-field/test/bal-field.cy.html b/packages/core/src/components/bal-field/test/bal-field.cy.html index f7c6afef14..c607fe2cd9 100644 --- a/packages/core/src/components/bal-field/test/bal-field.cy.html +++ b/packages/core/src/components/bal-field/test/bal-field.cy.html @@ -113,7 +113,7 @@ Form Birthdate - + @@ -180,7 +180,7 @@ Validation for all fields Birthdate - + diff --git a/packages/core/src/index.ts b/packages/core/src/index.ts index f1a8ec948b..efdc259278 100644 --- a/packages/core/src/index.ts +++ b/packages/core/src/index.ts @@ -48,7 +48,6 @@ export * from './components/bal-radio/bal-radio.type' export * from './components/bal-date/bal-date.i18n' export * from './components/bal-close/bal-close.i18n' export * from './components/bal-field/bal-field-label/bal-field-label.i18n' -export * from './components/bal-datepicker/bal-datepicker.i18n' export * from './components/bal-time-input/bal-time-input.i18n' export * from './components/bal-input-stepper/bal-input-stepper.i18n' export * from './components/bal-label/bal-label.i18n' diff --git a/packages/core/src/interfaces.d.ts b/packages/core/src/interfaces.d.ts index 4f26d018ca..95569a7bac 100644 --- a/packages/core/src/interfaces.d.ts +++ b/packages/core/src/interfaces.d.ts @@ -47,7 +47,6 @@ import './components/bal-spinner/bal-spinner.interfaces' import './components/bal-checkbox/bal-checkbox.interfaces' import './components/bal-date/bal-date.interfaces' import './components/bal-date/bal-date-calendar/bal-date-calendar.interfaces' -import './components/bal-datepicker/bal-datepicker.interfaces' import './components/bal-file-upload/bal-file-upload.interfaces' import './components/bal-field/bal-field.interfaces' import './components/bal-form-grid/bal-form-gird.interfaces' diff --git a/packages/core/src/test/all.html b/packages/core/src/test/all.html index dd600ebc56..c251134bdd 100644 --- a/packages/core/src/test/all.html +++ b/packages/core/src/test/all.html @@ -436,7 +436,7 @@ Label - + diff --git a/packages/core/src/utils/date/date.helpers.spec.ts b/packages/core/src/utils/date/date.helpers.spec.ts index d7ceea7e9e..f90af0ec7f 100644 --- a/packages/core/src/utils/date/date.helpers.spec.ts +++ b/packages/core/src/utils/date/date.helpers.spec.ts @@ -1,41 +1,12 @@ -import { formatDateString, isValidIsoString, format, parse } from './date.helpers' +import { dateSeparator } from './date.helpers' describe('date', () => { - describe('formatDateString', () => { - test('should turn a date into a iso date string', () => { - expect(formatDateString(undefined)).toBe('') - expect(formatDateString(new Date(2022, 0, 1))).toBe('2022-01-01') - expect(formatDateString(new Date(2022, 11, 31))).toBe('2022-12-31') - }) - }) - - describe('isValidIsoString', () => { - test('should verify that the given string matches the iso date string format', () => { - expect(isValidIsoString('2022-12-31')).toBe(true) - expect(isValidIsoString('2022-01-01')).toBe(true) - expect(isValidIsoString('2022-01-00')).toBe(false) - expect(isValidIsoString('2022-00-01')).toBe(false) - expect(isValidIsoString('')).toBe(false) - expect(isValidIsoString(undefined)).toBe(false) - }) - }) - - describe('format', () => { - test('should format the JS Date into the given local format to display', () => { - expect(format('de-CH', new Date(2022, 11, 31))).toBe('31.12.2022') - expect(format('fr-BE', new Date(2022, 11, 31))).toBe('31/12/2022') - expect(format('de-CH', new Date(2022, 0, 1))).toBe('01.01.2022') - expect(format('de-CH', undefined)).toBe('') - }) - }) - - describe('parse', () => { - test('should parse the iso date string into a JS Date', () => { - expect(parse('2022-12-31')).toStrictEqual(new Date('2022-12-31T00:00:00.000Z')) - expect(parse('2022-01-01')).toStrictEqual(new Date('2022-01-01T00:00:00.000Z')) - expect(parse('2022-01-00')).toBe(undefined) - expect(parse('2022-00-01')).toBe(undefined) - expect(parse('')).toBe(undefined) + describe('dateSeparator', () => { + test('should provide the correct date separator', () => { + expect(dateSeparator('de-CH')).toBe('.') + expect(dateSeparator('fr-CH')).toBe('.') + expect(dateSeparator('fr-BE')).toBe('/') + expect(dateSeparator('fr-LU')).toBe('/') }) }) }) diff --git a/packages/core/src/utils/date/date.helpers.ts b/packages/core/src/utils/date/date.helpers.ts index 73eea79acb..2a517fd83a 100644 --- a/packages/core/src/utils/date/date.helpers.ts +++ b/packages/core/src/utils/date/date.helpers.ts @@ -1,134 +1,3 @@ -import { - formatISO, - parse as dateFnsParse, - isMatch, - isValid, - parseISO, - getYear, - setYear, - getMonth, - getDate, -} from 'date-fns' -import padStart from 'lodash.padstart' - -export const ISO_PATTERN = 'yyyy-MM-dd' -export const DATE_PATTERN = 'dd-MM-yyyy' -export const TIMEZONE = 'T00:00:00.000Z' - -/** - * Returns a JS Date instance of the exact moment - * - * ```typescript - * const date = now() - * // Wed Mar 10 2021 20:30:32 GMT+0100 (Central European Standard Time) - * ``` - */ -export function now(): Date { - return new Date() -} - -/** - * Returns a JS Date instance of today with time being set to 0 - * - * ```typescript - * const date = today() - * // Wed Mar 10 2021 00:00:00 GMT+0100 (Central European Standard Time) - * ``` - */ -export function today(): Date { - return floorTime(now()) -} - -/** - * Returns a JS Date instance with time being set to 0 - * - * ```typescript - * const date = floorTime(new Date()) - * // Wed Mar 10 2021 00:00:00 GMT+0100 (Central European Standard Time) - * ``` - */ -export function floorTime(date: Date): Date { - const result = new Date(date) - result.setHours(0, 0, 0, 0) - return result -} - -// /** -// * Returns a JS Date instance with the time set to the possible end -// * -// * ```typescript -// * const date = ceilTime(new Date()) -// * // Wed Mar 10 2021 23:59:59 GMT+0100 (Central European Standard Time) -// * ``` -// */ -// export function ceilTime(date: Date): Date { -// const result = new Date(date) -// result.setHours(23, 59, 59, 999) -// return result -// } - -/** - * Return the formatted date string in ISO 8601 format. Options may be passed to control the parts and notations of the date. - * - * ```typescript - * const dateString = formatDateString(new Date()) - * // '2022-02-14' - * ``` - */ -export function formatDateString(date: Date): string { - return date && isValid(date) ? formatISO(date, { representation: 'date' }) : '' -} - -/** - * Validates if the given date string matches the iso date format. - * - * ```typescript - * isValidIsoString('2022-02-14') - * // 'true' - * ``` - */ -export function isValidIsoString(dateString: string | undefined | null) { - return !!dateString ? isMatch(dateString, ISO_PATTERN) : false -} - -/** - * Formats the dates according to the given locale. - * - * ```typescript - * format('de-CH', new Date()) - * // '14.2.2022' - * ``` - */ -export function format(locale = 'de-CH', date?: Date) { - return isValid(date) ? intlFormat(dateLocale(locale), date as Date) : '' -} - -/** - * Parses the iso date string into a javascript date object. - * - * ```typescript - * const dateString = parse('2021-03-10') - * // Wed Mar 10 2021 00:00:00 GMT+0100 (Central European Standard Time) - * ``` - */ -export function parse(dateString: string, locale = 'de-CH'): Date | undefined { - if (isMatch(dateString, ISO_PATTERN)) { - const d = parseISO(dateString + TIMEZONE) - if (d && isValid(d)) { - return validateYear(d) - } - const [year, month, day] = `${dateString}`.split('-').map(d => parseInt(d, 10)) - return generateIsoDate([year, month, day]) - } - - if (isMatch(dateString, getDatePattern(locale))) { - const d = dateFnsParse(dateString, getDatePattern(locale), now()) - return generateIsoDate([getYear(d), getMonth(d) + 1, getDate(d)]) - } - - return undefined -} - /** * Returns the char which separates day form month and year. * @@ -139,7 +8,7 @@ export function parse(dateString: string, locale = 'de-CH'): Date | undefined { */ export function dateSeparator(locale = 'de-CH'): string { return new Intl.DateTimeFormat(dateLocale(locale)) - .format(now()) + .format(new Date()) .replace(/\p{Number}/gu, '') .charAt(0) } @@ -148,36 +17,6 @@ export function dateSeparator(locale = 'de-CH'): string { * PRIVATE **************************************************************/ -function getDatePattern(locale = 'de-CH') { - return DATE_PATTERN.split('-').join(dateSeparator(locale)) -} - -function intlFormat(locale = 'de-CH', date: Date): string { - const intl = new Intl.DateTimeFormat(dateLocale(locale)) - return intl.format(date) -} - -function pad(value: number) { - return padStart(`${value}`, 2, '0') -} - -function validateYear(date: Date): Date | undefined { - if (date && isValid(date)) { - if (getYear(date) < 1000) { - return setYear(date, getYear(date) + 2000) - } - return date - } - return undefined -} - -function generateIsoDate([year, month, day]: [number, number, number]): Date | undefined { - if (year > 0 && month > 0 && day > 0) { - return parseISO(`${year < 1000 ? year + 2000 : year}-${pad(month)}-${pad(day)}` + TIMEZONE) - } - return undefined -} - function dateLocale(locale = 'de-CH'): string { const [, region] = locale.split('-') if (region === 'CH') { diff --git a/packages/core/stencil.config.ts b/packages/core/stencil.config.ts index 9fac1b2ed3..71a389f5b9 100644 --- a/packages/core/stencil.config.ts +++ b/packages/core/stencil.config.ts @@ -226,7 +226,6 @@ export const config: Config = { // // form components { components: ['bal-checkbox', 'bal-checkbox-group'] }, - { components: ['bal-datepicker'] }, { components: ['bal-dropdown'] }, { components: ['bal-field', 'bal-field-label', 'bal-field-control', 'bal-field-message', 'bal-field-hint'] }, { components: ['bal-file-upload'] }, diff --git a/packages/testing/src/add-custom-commands.ts b/packages/testing/src/add-custom-commands.ts index 9e317f17f5..b219281366 100644 --- a/packages/testing/src/add-custom-commands.ts +++ b/packages/testing/src/add-custom-commands.ts @@ -9,7 +9,6 @@ import './commands/custom/platform.command' import './commands/custom/visit.command' import './commands/custom/bal-accordion.types' -import './commands/custom/bal-datepicker.types' import './commands/custom/bal-popover.types' import './commands/custom/bal-popup.types' import './commands/custom/bal-hint.types' @@ -24,7 +23,6 @@ import './commands/custom/bal-field.types' import './commands/custom/bal-input-stepper.types' import './commands/custom/bal-accordion.command' -import './commands/custom/bal-datepicker.command' import './commands/custom/bal-popover.command' import './commands/custom/bal-popup.command' import './commands/custom/bal-hint.command' diff --git a/packages/testing/src/commands/custom/bal-datepicker.command.ts b/packages/testing/src/commands/custom/bal-datepicker.command.ts deleted file mode 100644 index 8969db0109..0000000000 --- a/packages/testing/src/commands/custom/bal-datepicker.command.ts +++ /dev/null @@ -1,114 +0,0 @@ -import { log, wrapOptions } from '../helpers' - -const getYear = (date: Date) => date.getFullYear() -const getMonth = (date: Date) => date.getMonth() - -const formatDateString = (date: Date) => { - const day = `${date.getDate()}` - const month = `${date.getMonth() + 1}` - const pad = (text: string) => (text.length === 1 ? `0${text}` : text) - - return `${date.getFullYear()}-${pad(month)}-${pad(day)}` -} - -const selectorDayBox = (date: Date) => `[data-date="${formatDateString(date)}"]` - -Cypress.Commands.add( - 'balDatepickerToggle', - { - prevSubject: true, - }, - (subject, options) => { - log('balDatepickerToggle', '', subject, options) - const o = wrapOptions(options) - return cy.wrapComponent(subject, o).find('.datepicker-trigger-icon', o).click(o).wrapComponent(subject, o) - }, -) - -Cypress.Commands.add( - 'balDatepickerIsOpen', - { - prevSubject: true, - }, - (subject, options) => { - log('balDatepickerIsOpen', '', subject, options) - const o = wrapOptions(options) - return cy - .wrapComponent(subject, o) - .find('bal-popover', o) - .should('have.attr', 'aria-presented', 'true') - .wrapComponent(subject, o) - }, -) - -Cypress.Commands.add( - 'balDatepickerIsClosed', - { - prevSubject: true, - }, - (subject, options) => { - log('balDatepickerIsClosed', '', subject, options) - const o = wrapOptions(options) - return cy - .wrapComponent(subject, o) - .find('bal-popover', o) - .should('not.have.attr', 'aria-presented') - .wrapComponent(subject, o) - }, -) - -Cypress.Commands.add( - 'balDatepickerPick', - { - prevSubject: true, - }, - (subject, date, options) => { - log('balDatepickerPick', formatDateString(date), subject, options) - const o = wrapOptions(options) - return cy - .wrapComponent(subject, o) - .balDatepickerIsOpen(o) - .within(() => { - cy.get('.bal-datepicker-pagination__month-and-year__select--month select', o) - .first(o) - .select(getMonth(date).toString(), o) - cy.get('.bal-datepicker-pagination__month-and-year__select--year select', o) - .first(o) - .select(getYear(date).toString(), o) - cy.get(selectorDayBox(date), o).click(o) - }) - .wrapComponent(subject, o) - }, -) - -Cypress.Commands.add( - 'balDatepickerIsDateInRange', - { - prevSubject: true, - }, - (subject, date, options) => { - log('balDatepickerIsDateInRange', formatDateString(date), subject, options) - const o = wrapOptions(options) - return cy - .wrapComponent(subject, o) - .find(selectorDayBox(date), { ...o, force: true }) - .should('not.have.class', 'is-disabled') - .wrapComponent(subject, o) - }, -) - -Cypress.Commands.add( - 'balDatepickerIsDateNotInRange', - { - prevSubject: true, - }, - (subject, date, options) => { - log('balDatepickerIsDateNotInRange', formatDateString(date), subject, options) - const o = wrapOptions(options) - return cy - .wrapComponent(subject, o) - .find(selectorDayBox(date), { ...o, force: true }) - .should('have.class', 'is-disabled') - .wrapComponent(subject, o) - }, -) diff --git a/packages/testing/src/commands/custom/bal-datepicker.types.ts b/packages/testing/src/commands/custom/bal-datepicker.types.ts deleted file mode 100644 index 011b32fdc7..0000000000 --- a/packages/testing/src/commands/custom/bal-datepicker.types.ts +++ /dev/null @@ -1,30 +0,0 @@ -/// - -declare namespace Cypress { - interface Chainable { - /** - * Opens and closes the datepicker popover. - */ - balDatepickerToggle(options?: Partial): Chainable - /** - * Assert if the datepicker popover is open. - */ - balDatepickerIsOpen(options?: Partial): Chainable - /** - * Assert if the datepicker popover is closed. - */ - balDatepickerIsClosed(options?: Partial): Chainable - /** - * Picks the date in the datepicker like a human. - */ - balDatepickerPick(date: Date, options?: Partial): Chainable - /** - * Asserts if the given date is in range in the datepicker popover. - */ - balDatepickerIsDateInRange(date: Date, options?: Partial): Chainable - /** - * Asserts if the given date is not in range in the datepicker popover. - */ - balDatepickerIsDateNotInRange(date: Date, options?: Partial): Chainable - } -} diff --git a/packages/testing/src/commands/helpers.ts b/packages/testing/src/commands/helpers.ts index 858d4ed3aa..618dfbd030 100644 --- a/packages/testing/src/commands/helpers.ts +++ b/packages/testing/src/commands/helpers.ts @@ -77,7 +77,6 @@ export const isLabel: isElementType = el => isElement(el, 'LABEL') export const isAccordion: isElementType = el => isElement(el, 'BAL-ACCORDION') export const isButton: isElementType = el => isElement(el, 'BAL-BUTTON') export const isCheckbox: isElementType = el => isElement(el, 'BAL-CHECKBOX') -export const isDatepicker: isElementType = el => isElement(el, 'BAL-DATEPICKER') export const isNumberInput: isElementType = el => isElement(el, 'BAL-NUMBER-INPUT') export const isModal: isElementType = el => isElement(el, 'BAL-MODAL') export const isRadioGroup: isElementType = el => isElement(el, 'BAL-RADIO-GROUP') diff --git a/packages/testing/src/commands/overrides/blur.command.ts b/packages/testing/src/commands/overrides/blur.command.ts index f77ead82c8..4abd1aeb25 100644 --- a/packages/testing/src/commands/overrides/blur.command.ts +++ b/packages/testing/src/commands/overrides/blur.command.ts @@ -3,7 +3,6 @@ import { isAccordion, isButton, isCheckbox, - isDatepicker, isInput, isRadio, isSelect, @@ -31,10 +30,6 @@ Cypress.Commands.overwrite('blur', (originalFn: any, element: Cypress. return command(selectors.checkbox.input) } - if (isDatepicker(element)) { - return command(selectors.datepicker.input) - } - if (isInput(element)) { return command(selectors.input.native) } diff --git a/packages/testing/src/commands/overrides/clear.command.ts b/packages/testing/src/commands/overrides/clear.command.ts index 0898ba35e6..3433216725 100644 --- a/packages/testing/src/commands/overrides/clear.command.ts +++ b/packages/testing/src/commands/overrides/clear.command.ts @@ -1,5 +1,4 @@ import { - isDatepicker, isCheckbox, isInput, isRadio, @@ -21,10 +20,6 @@ Cypress.Commands.overwrite('clear', (originalFn: any, element: Cypress return command(selectors.checkbox.input) } - if (isDatepicker(element)) { - return command(selectors.datepicker.input) - } - if (isInput(element)) { return command(selectors.input.native) } diff --git a/packages/testing/src/commands/overrides/click.command.ts b/packages/testing/src/commands/overrides/click.command.ts index c9e1f8e3e0..6c3445cdaa 100644 --- a/packages/testing/src/commands/overrides/click.command.ts +++ b/packages/testing/src/commands/overrides/click.command.ts @@ -2,7 +2,6 @@ import { isAccordion, isButton, isCheckbox, - isDatepicker, isRadio, isTag, hasClass, @@ -37,10 +36,6 @@ Cypress.Commands.overwrite('click', (originalFn: any, element: Cypress return command(selectors.checkbox.label) } - if (isDatepicker(element)) { - return command(selectors.datepicker.input) - } - if (isRadio(element)) { return command(selectors.radio.label) } diff --git a/packages/testing/src/commands/overrides/focus.command.ts b/packages/testing/src/commands/overrides/focus.command.ts index 143388a60e..c8f80c75d2 100644 --- a/packages/testing/src/commands/overrides/focus.command.ts +++ b/packages/testing/src/commands/overrides/focus.command.ts @@ -2,7 +2,6 @@ import { isAccordion, isButton, isCheckbox, - isDatepicker, isDropDown, isInput, isInputDate, @@ -31,10 +30,6 @@ Cypress.Commands.overwrite('focus', (originalFn: any, element: Cypress return command(selectors.checkbox.input) } - if (isDatepicker(element)) { - return command(selectors.datepicker.input) - } - if (isInput(element)) { return command(selectors.input.native) } diff --git a/packages/testing/src/commands/overrides/should.command.ts b/packages/testing/src/commands/overrides/should.command.ts index aa66a05117..70b85cd3cc 100644 --- a/packages/testing/src/commands/overrides/should.command.ts +++ b/packages/testing/src/commands/overrides/should.command.ts @@ -1,6 +1,5 @@ import { isCheckbox, - isDatepicker, isAccordion, isButton, isInput, @@ -96,18 +95,6 @@ const shouldAndAndCommand = ( } } - if (isDatepicker(element)) { - switch (condition) { - case 'have.focus': - case 'not.have.focus': - case 'have.value': - case 'not.have.value': - case 'be.disabled': - case 'not.be.disabled': - return originalFn(element.find(selectors.datepicker.input, { log: false }), condition, key, value, options) - } - } - if (isInput(element)) { if ( ['be.disabled', 'not.be.disabled', 'be.focused', 'not.be.focused', 'have.value', 'not.have.value'].includes( diff --git a/packages/testing/src/legacy/accessors/date-picker.accessor.ts b/packages/testing/src/legacy/accessors/date-picker.accessor.ts deleted file mode 100644 index 05bc9a4c64..0000000000 --- a/packages/testing/src/legacy/accessors/date-picker.accessor.ts +++ /dev/null @@ -1,93 +0,0 @@ -/// - -import { Accessor, createAccessor, Mixin, MixinContext } from './mixins/mixins' - -export interface DatePickerAccessorType { - write(date: string): DatePickerAccessorType - pick(date: Date): DatePickerAccessorType - open(): DatePickerAccessorType - shouldHaveValue(date: Date): DatePickerAccessorType - errorCheck(name: string, error: string): void - noErrorCheck(name: string): void - assertDateInRange(date: Date, shouldBeInRange?: boolean): DatePickerAccessorType -} - -export const DatePickerWriteMixin: Mixin = ({ selector, creator }: MixinContext) => ({ - write: (date: string) => { - cy.get(selector).type(date) - return creator() - }, -}) - -export const DatePickerPickableMixin: Mixin = ({ selector, creator }: MixinContext) => ({ - pick: (date: Date) => { - if (cy.get(selector).balDatepickerIsClosed()) { - cy.get(selector).balDatepickerToggle() - } - cy.get(selector).balDatepickerPick(date) - return creator() - }, -}) - -export const DatePickerOpenableMixin: Mixin = ({ selector, creator }: MixinContext) => ({ - open: () => { - if (cy.get(selector).balDatepickerIsClosed()) { - cy.get(selector).balDatepickerToggle() - } - return creator() - }, -}) - -export const DatePickerShouldHaveValueAssertableMixin: Mixin = ({ selector, creator }) => ({ - shouldHaveValue: (date: Date) => { - const day = `${date.getDate()}` - const month = `${date.getMonth() + 1}` - const pad = (text: string) => (text.length === 1 ? `0${text}` : text) - cy.get(selector).should('have.value', `${pad(day)}.${pad(month)}.${date.getFullYear()}`) - return creator() - }, -}) - -/** - * TODO: need to rework - */ -export const DatePickerErrorAssertableMixin: Mixin = ({ element, creator }: MixinContext) => ({ - errorCheck: (name: string, error: string) => { - element.clear() - const message = cy.get(`cip-error[ng-reflect-control-name=${name}]`) - message.should('contain', error) - return creator() - }, -}) - -/** - * TODO: need to rework - */ -export const DatePickerNoErrorAssertableMixin: Mixin = ({ creator }: MixinContext) => ({ - noErrorCheck: (name: string) => { - const noMessage = cy.get(`cip-error[ng-reflect-control-name=${name}]`) - noMessage.should('be.empty') - return creator() - }, -}) - -export const DatePickerMinMaxRangeAssertableMixin: Mixin = ({ selector, creator }: MixinContext) => ({ - assertDateInRange: (date: Date, shouldBeInRange = true) => { - if (shouldBeInRange) { - cy.get(selector).balDatepickerIsDateInRange(date) - } else { - cy.get(selector).balDatepickerIsDateNotInRange(date) - } - return creator() - }, -}) - -export const DatePickerAccessor: Accessor = createAccessor( - DatePickerWriteMixin, - DatePickerPickableMixin, - DatePickerShouldHaveValueAssertableMixin, - DatePickerErrorAssertableMixin, - DatePickerNoErrorAssertableMixin, - DatePickerMinMaxRangeAssertableMixin, - DatePickerOpenableMixin, -) diff --git a/packages/testing/src/legacy/index.ts b/packages/testing/src/legacy/index.ts index 6ce76b6477..0a313ef6ea 100644 --- a/packages/testing/src/legacy/index.ts +++ b/packages/testing/src/legacy/index.ts @@ -26,7 +26,6 @@ export * from './accessors/mixins/waitable' export * from './accessors/accordion.accessor' export * from './accessors/button.accessor' export * from './accessors/checkbox.accessor' -export * from './accessors/date-picker.accessor' export * from './accessors/drop-down.accessor' export * from './accessors/error.accessor' export * from './accessors/icon-accessor' diff --git a/packages/testing/src/selectors/index.ts b/packages/testing/src/selectors/index.ts index 1d282de49e..1dd79508f1 100644 --- a/packages/testing/src/selectors/index.ts +++ b/packages/testing/src/selectors/index.ts @@ -139,12 +139,6 @@ export const selectors = { */ text: byTestId('bal-checkbox-text'), }, - datepicker: { - /** - * Native input element. - */ - input: byTestId('bal-datepicker-input'), - }, field: { /** * Hint element. diff --git a/test/angular/base/app/cypress/e2e/bal-datepicker.spec.cy.ts b/test/angular/base/app/cypress/e2e/bal-datepicker.spec.cy.ts deleted file mode 100644 index b4c6b51588..0000000000 --- a/test/angular/base/app/cypress/e2e/bal-datepicker.spec.cy.ts +++ /dev/null @@ -1,40 +0,0 @@ -describe('bal-datepicker', () => { - beforeEach(() => { - cy.visit('/').platform('desktop').waitForDesignSystem() - }) - it('should change value', () => { - cy.getByLabelText('Datepicker Label') - .should('have.value', '09.09.2023') - .clear() - .click() - .blur() - .shouldBeInvalid() - .getDescribingElement() - .contains('This field is required') - - cy.getByPlaceholder('Pick a date') - .type('20.02.2024') - .blur() - .should('have.value', '20.02.2024') - .shouldBeValid() - .getDescribingElement() - .should('not.contain', 'This field is required') - - cy.get('body').type('{esc}') - - cy.getByRole('button', { name: 'Update Datepicker' }).click() - cy.getByPlaceholder('Pick a date') - .should('have.value', '21.10.2023') - .shouldBeValid() - .getDescribingElement() - .should('not.contain', 'This field is required') - - cy.getByRole('button', { name: 'Disable Datepicker' }).click() - cy.getByPlaceholder('Pick a date').should('be.disabled') - - cy.getByRole('button', { name: 'Enable Datepicker' }).click() - cy.getByPlaceholder('Pick a date').should('not.be.disabled') - - cy.getByTestId('result').contains('"datepicker": "2023-10-21"') - }) -}) diff --git a/test/angular/base/app/src/app/app.component.ts b/test/angular/base/app/src/app/app.component.ts index f58b524d01..86202f9b9b 100644 --- a/test/angular/base/app/src/app/app.component.ts +++ b/test/angular/base/app/src/app/app.component.ts @@ -5,7 +5,6 @@ import { BalModalService, balImports } from '../design-system' import { InputComponent } from './form-components/input.component' import { TextareaComponent } from './form-components/textarea.component' import { NumberInputComponent } from './form-components/number-input.component' -import { DatePickerComponent } from './form-components/datepicker.component' import { TimeComponent } from './form-components/time.component' import { InputStepperComponent } from './form-components/input-stepper.component' import { SliderComponent } from './form-components/input-slider.component' @@ -37,7 +36,6 @@ export interface UpdateControl { InputComponent, TextareaComponent, NumberInputComponent, - DatePickerComponent, TimeComponent, InputStepperComponent, SliderComponent, @@ -59,7 +57,6 @@ export interface UpdateControl { - @@ -99,7 +96,6 @@ export class AppComponent { textarea: new FormControl('Init Value', [Validators.required]), numberInput: new FormControl(null, [Validators.required]), inputDate: new FormControl('2023-09-09', [Validators.required]), - datepicker: new FormControl('2023-09-09', [Validators.required]), date: new FormControl('2023-09-09', [Validators.required]), time: new FormControl(null, [Validators.required]), inputStepper: new FormControl(0, [Validators.min(2)]), diff --git a/test/angular/base/app/src/app/form-components/datepicker.component.ts b/test/angular/base/app/src/app/form-components/datepicker.component.ts deleted file mode 100644 index c0617ea73c..0000000000 --- a/test/angular/base/app/src/app/form-components/datepicker.component.ts +++ /dev/null @@ -1,45 +0,0 @@ -import { ChangeDetectionStrategy, Component, EventEmitter, Input, Output } from '@angular/core' -import { CommonModule } from '@angular/common' -import { FormGroup, ReactiveFormsModule } from '@angular/forms' -import { balImports } from '../../design-system' -import { UpdateControl } from '../app.component' - -@Component({ - selector: 'app-datepicker', - standalone: true, - imports: [CommonModule, ReactiveFormsModule, ...balImports], - template: ` - - Datepicker - - - Datepicker Label - - - - - This field is required - - - - - Update Datepicker - - Enable Datepicker - Disable Datepicker - - - - `, - styles: [], - changeDetection: ChangeDetectionStrategy.OnPush, -}) -export class DatePickerComponent { - @Input() form!: FormGroup - - @Output() updateControl = new EventEmitter() -}