Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(locale): 🎸 add dateRange pipe #764

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
199 changes: 125 additions & 74 deletions apps/transloco-playground/src/app/locale/locale.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -7,82 +7,133 @@ <h2>Localization Support for Transloco</h2>
href="https://norbertlindenberg.com/2012/12/ecmascript-internationalization-api/index.html"
target="_blank"
>Internalization api</a
>.
</p>
>.
</p>

<h5>Select any locale from the list to see his format:</h5>
<select value="fr-FR" class="form-control" (change)="setLocale($event)">
@for (locale of localeList; track locale) {
<option [value]="locale">
{{ locale }}
</option>
}
</select>
<h5>Select any locale from the list to see his format:</h5>
<select value="fr-FR" class="form-control" (change)="setLocale($event)">
@for (locale of localeList; track locale) {
<option [value]="locale">
{{ locale }}
</option>
}
</select>

<h3 class="mtb">Date Format</h3>
<h3 class="mtb">Date Format</h3>

<ul class="list-group">
<li class="list-group-item" data-cy="date-regular">
<b>Regular date: </b>{{ date | translocoDate }}
</li>
<li class="list-group-item" data-cy="date-long">
<b>Long date: </b
>{{ date | translocoDate : { dateStyle: 'long', timeStyle: 'long' } }}
</li>
<li class="list-group-item" data-cy="date-full">
<b>Full date: </b
>{{ date | translocoDate : { dateStyle: 'full', timeStyle: 'full' } }}
</li>
<li class="list-group-item" data-cy="date-full-utc">
<b>Date in timezone UTC: </b
>{{ date | translocoDate : { timeZone: 'UTC', timeStyle: 'full' } }}
</li>
<li class="list-group-item" data-cy="date-medium-unix">
<b>Unix timestamp time date: </b
>{{ 1 | translocoDate : { dateStyle: 'medium', timeStyle: 'medium' } }}
</li>
<li class="list-group-item" data-cy="date-medium-string">
<b>String format to date: </b
>{{
'2019-02-08'
| translocoDate : { dateStyle: 'medium', timeStyle: 'medium' }
}}
</li>
</ul>
<ul class="list-group">
<li class="list-group-item" data-cy="date-regular">
<b>Regular date: </b>{{ date | translocoDate }}
</li>
<li class="list-group-item" data-cy="date-long">
<b>Long date: </b
>{{ date | translocoDate : { dateStyle: 'long', timeStyle: 'long' } }}
</li>
<li class="list-group-item" data-cy="date-full">
<b>Full date: </b
>{{ date | translocoDate : { dateStyle: 'full', timeStyle: 'full' } }}
</li>
<li class="list-group-item" data-cy="date-full-utc">
<b>Date in timezone UTC: </b
>{{ date | translocoDate : { timeZone: 'UTC', timeStyle: 'full' } }}
</li>
<li class="list-group-item" data-cy="date-medium-unix">
<b>Unix timestamp time date: </b
>{{ 1 | translocoDate : { dateStyle: 'medium', timeStyle: 'medium' } }}
</li>
<li class="list-group-item" data-cy="date-medium-string">
<b>String format to date: </b
>{{
'2019-02-08'
| translocoDate : { dateStyle: 'medium', timeStyle: 'medium' }
}}
</li>
</ul>

<h3 class="mtb">Number Format</h3>
<ul class="list-group">
<li class="list-group-item" data-cy="number-decimal">
<b>Decimal number: </b>{{ 1234567890 | translocoDecimal }}
</li>
<li class="list-group-item" data-cy="number-decimal-grouped">
<b>Decimal without grouping: </b
>{{
1234567890
| translocoDecimal
: {
useGrouping: false
}
}}
</li>
<li class="list-group-item" data-cy="number-percent">
<b>Percentage number: </b>{{ 1 | translocoPercent }}
</li>
</ul>
<h3 class="mtb">Date Range Format</h3>

<h3 class="mtb">Currency Format</h3>
<ul class="list-group">
<li class="list-group-item" data-cy="currency-symbol-only">
<b>Symbol: </b>{{ currencySymbol }}
</li>
<li class="list-group-item" data-cy="currency-symbol">
<b>Symbol currency: </b>{{ 1000000 | translocoCurrency }}
</li>
<li class="list-group-item" data-cy="currency-name">
<b>Name currency: </b>{{ 1000000 | translocoCurrency : 'name' }}
</li>
<li class="list-group-item" data-cy="currency-custom-digit">
<b>Custom digit formatted currency: </b>
{{ 1000000 | translocoCurrency : 'symbol' : { minimumFractionDigits: 0 } }}
</li>
</ul>
<ul class="list-group">
<li class="list-group-item" data-cy="date-regular">
<b>Regular date: </b>{{ date | translocoDateRange : endDate }}
</li>
<li class="list-group-item" data-cy="date-long">
<b>Long date: </b
>{{
date
| translocoDateRange
: endDate
: { dateStyle: 'long', timeStyle: 'long' }
}}
</li>
<li class="list-group-item" data-cy="date-full">
<b>Full date: </b
>{{
date
| translocoDateRange
: endDate
: { dateStyle: 'full', timeStyle: 'full' }
}}
</li>
<li class="list-group-item" data-cy="date-full-utc">
<b>Date in timezone UTC: </b
>{{
date
| translocoDateRange : endDate : { timeZone: 'UTC', timeStyle: 'full' }
}}
</li>
<li class="list-group-item" data-cy="date-medium-unix">
<b>Unix timestamp time date: </b
>{{
1
| translocoDateRange
: endDate
: { dateStyle: 'medium', timeStyle: 'medium' }
}}
</li>
<li class="list-group-item" data-cy="date-medium-string">
<b>String format to date: </b
>{{
'2019-02-08'
| translocoDateRange
: endDate
: { dateStyle: 'medium', timeStyle: 'medium' }
}}
</li>
</ul>

<h3 class="mtb">Number Format</h3>
<ul class="list-group">
<li class="list-group-item" data-cy="number-decimal">
<b>Decimal number: </b>{{ 1234567890 | translocoDecimal }}
</li>
<li class="list-group-item" data-cy="number-decimal-grouped">
<b>Decimal without grouping: </b
>{{
1234567890
| translocoDecimal
: {
useGrouping: false
}
}}
</li>
<li class="list-group-item" data-cy="number-percent">
<b>Percentage number: </b>{{ 1 | translocoPercent }}
</li>
</ul>

<h3 class="mtb">Currency Format</h3>
<ul class="list-group">
<li class="list-group-item" data-cy="currency-symbol-only">
<b>Symbol: </b>{{ currencySymbol }}
</li>
<li class="list-group-item" data-cy="currency-symbol">
<b>Symbol currency: </b>{{ 1000000 | translocoCurrency }}
</li>
<li class="list-group-item" data-cy="currency-name">
<b>Name currency: </b>{{ 1000000 | translocoCurrency : 'name' }}
</li>
<li class="list-group-item" data-cy="currency-custom-digit">
<b>Custom digit formatted currency: </b>
{{ 1000000 | translocoCurrency : 'symbol' : { minimumFractionDigits: 0 } }}
</li>
</ul>
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import {
})
export default class LocaleComponent {
date = new Date(2019, 7, 14, 0, 0, 0, 0);
endDate = new Date(2019, 8, 5, 0, 0, 0, 0);
localeList: string[];

constructor(
Expand Down
4 changes: 2 additions & 2 deletions apps/transloco-playground/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,11 @@
"strict": true,
"noImplicitReturns": true,
"noFallthroughCasesInSwitch": true,
"target": "es2020"
"target": "es2021"
},
"angularCompilerOptions": {
"strictInjectionParameters": true,
"strictInputAccessModifiers": true,
"strictTemplates": true
}
}
}
4 changes: 4 additions & 0 deletions libs/transloco-locale/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,10 @@ export {
export { TranslocoLocaleModule } from './lib/transloco-locale.module';
export {
TRANSLOCO_DATE_TRANSFORMER,
TRANSLOCO_DATE_RANGE_TRANSFORMER,
TRANSLOCO_NUMBER_TRANSFORMER,
TranslocoDateTransformer,
TranslocoDateRangeTransformer,
TranslocoNumberTransformer,
DefaultDateTransformer,
DefaultNumberTransformer,
Expand All @@ -19,6 +21,7 @@ export {
provideTranslocoLocaleLangMapping,
provideTranslocoLocaleCurrencyMapping,
provideTranslocoDateTransformer,
provideTranslocoDateRangeTransformer,
provideTranslocoDefaultCurrency,
provideTranslocoLocale,
provideTranslocoNumberTransformer,
Expand All @@ -29,6 +32,7 @@ export * from './lib/transloco-locale.types';
export {
TranslocoCurrencyPipe,
TranslocoDatePipe,
TranslocoDateRangePipe,
TranslocoDecimalPipe,
TranslocoPercentPipe,
BaseLocalePipe,
Expand Down
15 changes: 15 additions & 0 deletions libs/transloco-locale/src/lib/helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,21 @@ export function localizeDate(
return '';
}

export function localizeDateRange(
startDate: Date,
endDate: Date,
locale: Locale,
options: DateFormatOptions,
): string {
if (isDate(startDate) && isDate(endDate)) {
return new Intl.DateTimeFormat(locale, options as any).formatRange(
startDate,
endDate,
);
}
return '';
}

export function isDate(value: any): boolean {
return value instanceof Date && !isNaN(<any>value);
}
Expand Down
1 change: 1 addition & 0 deletions libs/transloco-locale/src/lib/pipes/index.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
export { TranslocoCurrencyPipe } from './transloco-currency.pipe';
export { TranslocoDatePipe } from './transloco-date.pipe';
export { TranslocoDateRangePipe } from './transloco-date-range.pipe';
export { TranslocoDecimalPipe } from './transloco-decimal.pipe';
export { BaseLocalePipe } from './base-locale.pipe';
export { TranslocoPercentPipe } from './transloco-percent.pipe';
57 changes: 57 additions & 0 deletions libs/transloco-locale/src/lib/pipes/transloco-date-range.pipe.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
import { inject, Pipe, PipeTransform } from '@angular/core';
import { isNil } from '@jsverse/transloco';

import { getDefaultOptions } from '../shared';
import { TRANSLOCO_LOCALE_CONFIG } from '../transloco-locale.config';
import {
Locale,
DateFormatOptions,
LocaleConfig,
ValidDate,
} from '../transloco-locale.types';

import { BaseLocalePipe } from './base-locale.pipe';
import { TranslocoDatePipe } from './transloco-date.pipe';

@Pipe({
name: 'translocoDateRange',
pure: false,
standalone: true,
})
export class TranslocoDateRangePipe
extends BaseLocalePipe
implements PipeTransform
{
private localeConfig: LocaleConfig = inject(TRANSLOCO_LOCALE_CONFIG);

/**
* Transform two dates into the locale's date range format.
*
* The date expression: a `Date` object, a number
* (milliseconds since UTC epoch), or an ISO string (https://www.w3.org/TR/NOTE-datetime).
*
* @example
*
* startDate | translocoDateRange: endDate : {} : en-US // 9/10–10/10/2019
* startDate | translocoDate: endDate : { dateStyle: 'medium', timeStyle: 'medium' } : en-US // Sep 10, 2019, 10:46:12 PM – Oct 10, 2019, 10:46:12 PM
* '2019-02-08' | translocoDate: '2020-03-10' : { dateStyle: 'medium' } // Feb 8 2019 – Mar 10 2020
*/
transform(
startDate: ValidDate,
endDate: ValidDate,
options: DateFormatOptions = {},
locale?: Locale,
) {
if (isNil(startDate)) return '';
if (isNil(endDate)) {
return inject(TranslocoDatePipe).transform(startDate, options, locale);
}

locale = this.getLocale(locale);

return this.localeService.localizeDateRange(startDate, endDate, locale, {
...getDefaultOptions(locale, 'date', this.localeConfig),
...options,
});
}
}
Loading