diff --git a/demo/components/date-picker-demo.tsx b/demo/components/date-picker-demo.tsx index 7990c16c6..87851be8e 100644 --- a/demo/components/date-picker-demo.tsx +++ b/demo/components/date-picker-demo.tsx @@ -4,12 +4,14 @@ import {DatePicker, DatePickerProps} from '../../src'; export interface DatePickerDemoState { value: Date; startingDay?: number; + locale?: string; } export class DatePickerDemo extends React.Component> { public state: DatePickerDemoState = { value: this.props.value ? this.props.value : new Date(), - startingDay: 0 + startingDay: 0, + locale: 'en-US' }; public render() { @@ -30,6 +32,17 @@ export class DatePickerDemo extends React.ComponentSaturday +

Try changing the locale!

+ + + {this.state.value!.toDateString()} @@ -37,6 +50,7 @@ export class DatePickerDemo extends React.Component): void => { + const target = event.target as HTMLSelectElement; + this.setState({locale: target.value}); + } + private onChange = (e: {value: Date}): void => { this.setState({value: e.value}); } diff --git a/src/components/date-picker/calendar.tsx b/src/components/date-picker/calendar.tsx index 070755456..4acd80198 100644 --- a/src/components/date-picker/calendar.tsx +++ b/src/components/date-picker/calendar.tsx @@ -20,12 +20,11 @@ export interface CalendarProps { startingDay?: number; highlightSelectedDate?: boolean; highlightFocusedDate?: boolean; + locale?: string; onChange(date: Date): void; updateDropdownDate(date: Date): void; } -const monthNames = getMonthNames(); - @stylable(styles) @observer export class Calendar extends React.Component { @@ -75,7 +74,7 @@ export class Calendar extends React.Component { @computed get monthName(): string { - return monthNames[this.props.value.getMonth()]; + return getMonthNames(this.props.locale)[this.props.value.getMonth()]; } @computed @@ -107,12 +106,12 @@ export class Calendar extends React.Component { @computed get dayNames(): JSX.Element[] { - return getDayNames(this.props.startingDay).map((name: string, index: number) => { + return getDayNames(this.props.startingDay, this.props.locale).map((name: string, index: number) => { return ( {name} diff --git a/src/components/date-picker/date-picker.tsx b/src/components/date-picker/date-picker.tsx index 4fc808cf0..41139de88 100644 --- a/src/components/date-picker/date-picker.tsx +++ b/src/components/date-picker/date-picker.tsx @@ -19,6 +19,7 @@ export interface DatePickerProps extends FormInputProps, properties.Props showDropdownOnInit?: boolean; startingDay?: number; calendarIcon?: React.ComponentType; + locale?: string; } export interface DatePickerState { @@ -79,6 +80,7 @@ export class DatePicker extends React.PureComponent diff --git a/src/utils/date-helpers.ts b/src/utils/date-helpers.ts index 3d5cf351d..0b67e4494 100644 --- a/src/utils/date-helpers.ts +++ b/src/utils/date-helpers.ts @@ -1,12 +1,11 @@ -const monthNames = [ - 'January', 'February', 'March', - 'April', 'May', 'June', - 'July', 'August', 'September', - 'October', 'November', 'December' -]; +export function getDayNames(startingDay: number = 0, locale: string = 'en-US', nameLength: string = 'short'): string[] { + const dayNames: string[] = []; -export function getDayNames(startingDay: number = 0): string[] { - const dayNames: string[] = ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat']; + // For each of the seven days of the week + for (let day = 0; day < 7; day++) { + const dayName = new Date(1970, 5, day).toLocaleString(locale, {weekday: nameLength}); + dayNames.push(dayName); + } // Days start from Sunday (Sunday = 0, Monday = 1, etc.) for (let i = startingDay; i > 0; i--) { @@ -16,8 +15,16 @@ export function getDayNames(startingDay: number = 0): string[] { return dayNames; } -export function getMonthNames(): string[] { - return monthNames; +export function getMonthNames(locale: string = 'en-US', nameLength: string = 'long'): string[] { + const listOfMonthNames: string[] = []; + + // For each of the twelve months of the year + for (let month = 0; month < 12; month++) { + const monthName = new Date(1970, month, 1).toLocaleString(locale, {month: nameLength}); + listOfMonthNames.push(monthName); + } + + return listOfMonthNames; } export function getMonthFromOffset(date: Date, offset: number): Date { diff --git a/test-kit/components/date-picker-driver.ts b/test-kit/components/date-picker-driver.ts index 9e5147a81..9c0195d8c 100644 --- a/test-kit/components/date-picker-driver.ts +++ b/test-kit/components/date-picker-driver.ts @@ -1,6 +1,5 @@ import {DriverBase, selectDom, simulate, trigger} from 'test-drive-react'; import {DatePicker} from '../../src'; -import {getDayNames} from '../../src/utils'; const bodySelect = selectDom(document.body); const datePickerDropdown = 'DATE_PICKER_DROPDOWN'; @@ -81,8 +80,8 @@ export class DatePickerTestDriver extends DriverBase { if (dayName < 0 || dayName > 6) { return null; } - const dayNames: string[] = getDayNames(); - return bodySelect(datePickerDropdown, `DAY_NAME_${dayNames[dayName].toUpperCase()}`); + + return bodySelect(datePickerDropdown, `DAY_NAME_${dayName}`); } public get yearLabel(): HTMLSpanElement | null { diff --git a/test/components/date-picker.spec.tsx b/test/components/date-picker.spec.tsx index f6702f372..aa6428fb2 100644 --- a/test/components/date-picker.spec.tsx +++ b/test/components/date-picker.spec.tsx @@ -7,6 +7,7 @@ import { getDayNames, getDaysInMonth, getMonthFromOffset, + getMonthNames, getNumOfFollowingDays, getNumOfPreviousDays } from '../../src/utils'; @@ -189,6 +190,27 @@ describe('The DatePicker Component', () => { }); }); + it('should support localization', async () => { + const testLocale = 'he-IL'; + const {driver: datePicker, waitForDom} = clientRenderer.render( + + ).withDriver(DatePickerTestDriver); + + const localizedDayNames = getDayNames(0, testLocale); + const monthName = getMonthNames(testLocale)[FEBRUARY_FIRST.getMonth()]; + + await waitForDom(() => { + localizedDayNames.forEach((dayName, index) => { + expect(datePicker.getDayName(index), 'day name did not have the proper text').to.have.text(dayName); + }); + expect(datePicker.monthLabel, 'Month Label did not have the proper text').to.have.text(monthName); + }); + }); + it('should show the next and previous month buttons horizontally aligned with the month and year', async () => { const {driver: datePicker, waitForDom} = clientRenderer.render(