-
Notifications
You must be signed in to change notification settings - Fork 7
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
fixup! feat(date-picker): replace moment with vanilla JS
- Loading branch information
Showing
17 changed files
with
298 additions
and
235 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,5 @@ | ||
import { zeroPad } from '@lumx/react/utils/zeroPad'; | ||
|
||
/** Format date month day number padded with `0` */ | ||
export const formatDayNumber = (date: Date, locale: string) => | ||
zeroPad(date.toLocaleDateString(locale, { day: 'numeric' }), 2); |
27 changes: 27 additions & 0 deletions
27
packages/lumx-react/src/utils/date/getFirstDayOfWeek.test.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
import { getFirstDayOfWeek } from './getFirstDayOfWeek'; | ||
|
||
describe(getFirstDayOfWeek.name, () => { | ||
it('should return for a valid locales', () => { | ||
expect(getFirstDayOfWeek('fa-ir')).toBe(6); | ||
expect(getFirstDayOfWeek('ar-ma')).toBe(1); | ||
expect(getFirstDayOfWeek('ar')).toBe(6); | ||
expect(getFirstDayOfWeek('ar-eg')).toBe(0); | ||
}); | ||
|
||
it('should ignore the character case', () => { | ||
expect(getFirstDayOfWeek('zh-hk')).toBe(getFirstDayOfWeek('zh-HK')); | ||
}); | ||
|
||
it('should return for the lang locale if available', () => { | ||
// Test for a specific locale and its root locale | ||
const localeWithRoot = 'es-ES'; // Spanish (Spain) with root locale es | ||
const expectedFirstDay = getFirstDayOfWeek('es'); // First day for root locale 'es' | ||
|
||
expect(getFirstDayOfWeek(localeWithRoot)).toBe(expectedFirstDay); | ||
}); | ||
|
||
it('should return the undefined for an invalid locale', () => { | ||
// Default first day is Monday (1) | ||
expect(getFirstDayOfWeek('invalid')).toBe(undefined); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,20 +1,44 @@ | ||
import { getCurrentLocale } from '../getCurrentLocale'; | ||
import { getLocaleLang } from '@lumx/react/utils/locale/getLocaleLang'; | ||
|
||
const FIRST_DAY_FOR_LOCALES = [ | ||
{ | ||
// Locales with Sunday as the first day of the week | ||
localeRX: /^(af|ar-(dz|eg|sa)|bn|cy|en-(ca|us|za)|fr-ca|gd|he|hi|ja|km|ko|pt-br|te|th|ug|zh-hk)$/i, | ||
firstDay: 0, | ||
}, | ||
{ | ||
// Locales with Monday as the first day of the week | ||
localeRX: /^(ar-(ma|tn)|az|be|bg|bs|ca|cs|da|de|el|en-(au|gb|ie|in|nz)|eo|es|et|eu|fi|fr|fy|gl|gu|hr|ht|hu|hy|id|is|it|ka|kk|kn|lb|lt|lv|mk|mn|ms|mt|nb|nl|nn|oc|pl|pt|ro|ru|sk|sl|sq|sr|sv|ta|tr|uk|uz|vi|zh-(cn|tw))$/i, | ||
firstDay: 1, | ||
}, | ||
{ | ||
// Locales with Saturday as the first day of the week | ||
localeRX: /^(ar|fa-ir)$/i, | ||
firstDay: 6, | ||
}, | ||
]; | ||
|
||
/** Find first day of week for locale in the constant */ | ||
const getFromConstant = (locale: string) => { | ||
for (const { localeRX, firstDay } of FIRST_DAY_FOR_LOCALES) { | ||
if (localeRX.test(locale)) return firstDay; | ||
} | ||
return undefined; | ||
}; | ||
|
||
/** | ||
* Try to get the first day of a week from the `Intl` API or fallback to Monday. | ||
* @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/Locale/getWeekInfo | ||
* | ||
* @param locale (default to the browser locale) | ||
* @return number between 1 (Monday) and 7 (Sunday) | ||
* Get first day of the week for the given locale code (language + region with fallback to language only if not found). | ||
*/ | ||
export const getFirstDayOfWeek = (locale = getCurrentLocale()): number => { | ||
// Fallback to monday | ||
const FALLBACK = 1; | ||
try { | ||
const localeMetadata = new Intl.Locale(locale) as any; | ||
const weekInfo = localeMetadata.getWeekInfo?.() || localeMetadata.weekInfo; | ||
return weekInfo?.firstDay || FALLBACK; | ||
} catch (e) { | ||
return FALLBACK; | ||
export const getFirstDayOfWeek = (locale: string): number | undefined => { | ||
// Get first day of week for locale code | ||
const firstDay = getFromConstant(locale); | ||
if (firstDay !== undefined) return firstDay; | ||
|
||
// Fallback search for locale lang (local code without the region part) | ||
const localeLang = getLocaleLang(locale); | ||
if (localeLang !== locale) { | ||
return getFromConstant(localeLang); | ||
} | ||
|
||
return undefined; | ||
}; |
This file was deleted.
Oops, something went wrong.
193 changes: 103 additions & 90 deletions
193
packages/lumx-react/src/utils/date/getMonthCalendar.test.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,106 +1,119 @@ | ||
import { getFirstDayOfWeek } from '@lumx/react/utils/date/getFirstDayOfWeek'; | ||
import { getMonthCalendar } from './getMonthCalendar'; | ||
|
||
jest.mock('@lumx/react/utils/date/getFirstDayOfWeek'); | ||
|
||
describe(getMonthCalendar.name, () => { | ||
it('should generate calendar', () => { | ||
// First day of week: monday | ||
(getFirstDayOfWeek as any).mockReturnValue(1); | ||
|
||
const referenceDate = new Date('2017-02-03'); | ||
const month = getMonthCalendar('fr', referenceDate); | ||
|
||
expect(month).toEqual([ | ||
{ | ||
'3': { date: new Date('2017-02-01'), isInRange: true }, | ||
'4': { date: new Date('2017-02-02'), isInRange: true }, | ||
'5': { date: new Date('2017-02-03'), isInRange: true }, | ||
'6': { date: new Date('2017-02-04'), isInRange: true }, | ||
'7': { date: new Date('2017-02-05'), isInRange: true }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-06'), isInRange: true }, | ||
'2': { date: new Date('2017-02-07'), isInRange: true }, | ||
'3': { date: new Date('2017-02-08'), isInRange: true }, | ||
'4': { date: new Date('2017-02-09'), isInRange: true }, | ||
'5': { date: new Date('2017-02-10'), isInRange: true }, | ||
'6': { date: new Date('2017-02-11'), isInRange: true }, | ||
'7': { date: new Date('2017-02-12'), isInRange: true }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-13'), isInRange: true }, | ||
'2': { date: new Date('2017-02-14'), isInRange: true }, | ||
'3': { date: new Date('2017-02-15'), isInRange: true }, | ||
'4': { date: new Date('2017-02-16'), isInRange: true }, | ||
'5': { date: new Date('2017-02-17'), isInRange: true }, | ||
'6': { date: new Date('2017-02-18'), isInRange: true }, | ||
'7': { date: new Date('2017-02-19'), isInRange: true }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-20'), isInRange: true }, | ||
'2': { date: new Date('2017-02-21'), isInRange: true }, | ||
'3': { date: new Date('2017-02-22'), isInRange: true }, | ||
'4': { date: new Date('2017-02-23'), isInRange: true }, | ||
'5': { date: new Date('2017-02-24'), isInRange: true }, | ||
'6': { date: new Date('2017-02-25'), isInRange: true }, | ||
'7': { date: new Date('2017-02-26'), isInRange: true }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-27'), isInRange: true }, | ||
'2': { date: new Date('2017-02-28'), isInRange: true }, | ||
}, | ||
]); | ||
expect(month).toEqual({ | ||
weekDays: [ | ||
{ letter: 'L', number: 1 }, | ||
{ letter: 'M', number: 2 }, | ||
{ letter: 'M', number: 3 }, | ||
{ letter: 'J', number: 4 }, | ||
{ letter: 'V', number: 5 }, | ||
{ letter: 'S', number: 6 }, | ||
{ letter: 'D', number: 0 }, | ||
], | ||
weeks: [ | ||
{ | ||
'3': { date: new Date('2017-02-01') }, | ||
'4': { date: new Date('2017-02-02') }, | ||
'5': { date: new Date('2017-02-03') }, | ||
'6': { date: new Date('2017-02-04') }, | ||
'0': { date: new Date('2017-02-05') }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-06') }, | ||
'2': { date: new Date('2017-02-07') }, | ||
'3': { date: new Date('2017-02-08') }, | ||
'4': { date: new Date('2017-02-09') }, | ||
'5': { date: new Date('2017-02-10') }, | ||
'6': { date: new Date('2017-02-11') }, | ||
'0': { date: new Date('2017-02-12') }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-13') }, | ||
'2': { date: new Date('2017-02-14') }, | ||
'3': { date: new Date('2017-02-15') }, | ||
'4': { date: new Date('2017-02-16') }, | ||
'5': { date: new Date('2017-02-17') }, | ||
'6': { date: new Date('2017-02-18') }, | ||
'0': { date: new Date('2017-02-19') }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-20') }, | ||
'2': { date: new Date('2017-02-21') }, | ||
'3': { date: new Date('2017-02-22') }, | ||
'4': { date: new Date('2017-02-23') }, | ||
'5': { date: new Date('2017-02-24') }, | ||
'6': { date: new Date('2017-02-25') }, | ||
'0': { date: new Date('2017-02-26') }, | ||
}, | ||
{ | ||
'1': { date: new Date('2017-02-27') }, | ||
'2': { date: new Date('2017-02-28') }, | ||
}, | ||
], | ||
}); | ||
}); | ||
|
||
it('should generate calendar with sunday as start of week and mark dates in range', () => { | ||
// First day of week: sunday | ||
(getFirstDayOfWeek as any).mockReturnValue(7); | ||
|
||
const referenceDate = new Date('2017-02-03'); | ||
const minDate = new Date('2017-02-06'); | ||
const maxDate = new Date('2017-02-10'); | ||
const month = getMonthCalendar('fr', referenceDate, minDate, maxDate); | ||
const month = getMonthCalendar('en-US', referenceDate, minDate, maxDate); | ||
|
||
expect(month).toEqual([ | ||
{ | ||
'3': { date: new Date('2017-02-01'), isInRange: false }, | ||
'4': { date: new Date('2017-02-02'), isInRange: false }, | ||
'5': { date: new Date('2017-02-03'), isInRange: false }, | ||
'6': { date: new Date('2017-02-04'), isInRange: false }, | ||
}, | ||
{ | ||
'7': { date: new Date('2017-02-05'), isInRange: false }, | ||
'1': { date: new Date('2017-02-06'), isInRange: false }, | ||
'2': { date: new Date('2017-02-07'), isInRange: true }, | ||
'3': { date: new Date('2017-02-08'), isInRange: true }, | ||
'4': { date: new Date('2017-02-09'), isInRange: true }, | ||
'5': { date: new Date('2017-02-10'), isInRange: false }, | ||
'6': { date: new Date('2017-02-11'), isInRange: false }, | ||
}, | ||
{ | ||
'7': { date: new Date('2017-02-12'), isInRange: false }, | ||
'1': { date: new Date('2017-02-13'), isInRange: false }, | ||
'2': { date: new Date('2017-02-14'), isInRange: false }, | ||
'3': { date: new Date('2017-02-15'), isInRange: false }, | ||
'4': { date: new Date('2017-02-16'), isInRange: false }, | ||
'5': { date: new Date('2017-02-17'), isInRange: false }, | ||
'6': { date: new Date('2017-02-18'), isInRange: false }, | ||
}, | ||
{ | ||
'7': { date: new Date('2017-02-19'), isInRange: false }, | ||
'1': { date: new Date('2017-02-20'), isInRange: false }, | ||
'2': { date: new Date('2017-02-21'), isInRange: false }, | ||
'3': { date: new Date('2017-02-22'), isInRange: false }, | ||
'4': { date: new Date('2017-02-23'), isInRange: false }, | ||
'5': { date: new Date('2017-02-24'), isInRange: false }, | ||
'6': { date: new Date('2017-02-25'), isInRange: false }, | ||
}, | ||
{ | ||
'7': { date: new Date('2017-02-26'), isInRange: false }, | ||
'1': { date: new Date('2017-02-27'), isInRange: false }, | ||
'2': { date: new Date('2017-02-28'), isInRange: false }, | ||
}, | ||
]); | ||
expect(month).toEqual({ | ||
weekDays: [ | ||
{ letter: 'S', number: 0 }, | ||
{ letter: 'M', number: 1 }, | ||
{ letter: 'T', number: 2 }, | ||
{ letter: 'W', number: 3 }, | ||
{ letter: 'T', number: 4 }, | ||
{ letter: 'F', number: 5 }, | ||
{ letter: 'S', number: 6 }, | ||
], | ||
weeks: [ | ||
{ | ||
'3': { date: new Date('2017-02-01'), isOutOfRange: true }, | ||
'4': { date: new Date('2017-02-02'), isOutOfRange: true }, | ||
'5': { date: new Date('2017-02-03'), isOutOfRange: true }, | ||
'6': { date: new Date('2017-02-04'), isOutOfRange: true }, | ||
}, | ||
{ | ||
'0': { date: new Date('2017-02-05'), isOutOfRange: true }, | ||
'1': { date: new Date('2017-02-06'), isOutOfRange: true }, | ||
'2': { date: new Date('2017-02-07') }, | ||
'3': { date: new Date('2017-02-08') }, | ||
'4': { date: new Date('2017-02-09') }, | ||
'5': { date: new Date('2017-02-10'), isOutOfRange: true }, | ||
'6': { date: new Date('2017-02-11'), isOutOfRange: true }, | ||
}, | ||
{ | ||
'0': { date: new Date('2017-02-12'), isOutOfRange: true }, | ||
'1': { date: new Date('2017-02-13'), isOutOfRange: true }, | ||
'2': { date: new Date('2017-02-14'), isOutOfRange: true }, | ||
'3': { date: new Date('2017-02-15'), isOutOfRange: true }, | ||
'4': { date: new Date('2017-02-16'), isOutOfRange: true }, | ||
'5': { date: new Date('2017-02-17'), isOutOfRange: true }, | ||
'6': { date: new Date('2017-02-18'), isOutOfRange: true }, | ||
}, | ||
{ | ||
'0': { date: new Date('2017-02-19'), isOutOfRange: true }, | ||
'1': { date: new Date('2017-02-20'), isOutOfRange: true }, | ||
'2': { date: new Date('2017-02-21'), isOutOfRange: true }, | ||
'3': { date: new Date('2017-02-22'), isOutOfRange: true }, | ||
'4': { date: new Date('2017-02-23'), isOutOfRange: true }, | ||
'5': { date: new Date('2017-02-24'), isOutOfRange: true }, | ||
'6': { date: new Date('2017-02-25'), isOutOfRange: true }, | ||
}, | ||
{ | ||
'0': { date: new Date('2017-02-26'), isOutOfRange: true }, | ||
'1': { date: new Date('2017-02-27'), isOutOfRange: true }, | ||
'2': { date: new Date('2017-02-28'), isOutOfRange: true }, | ||
}, | ||
], | ||
}); | ||
}); | ||
}); |
Oops, something went wrong.