Angular 2의 DatePipe에서 로캘을 설정하는 방법은 무엇입니까?


138

유럽 ​​형식을 사용하여 날짜를 표시하고 싶지만 dd/MM/yyyyDatePipe shortDate 형식을 사용하면 미국 날짜 스타일 만 사용하여 표시됩니다 MM/dd/yyyy.
기본 로케일이 en_US라고 가정합니다. 어쩌면 문서에서 누락되었지만 Angular2 앱에서 기본 로캘 설정을 어떻게 변경할 수 있습니까? 또는 DatePipe에 사용자 지정 형식을 전달하는 방법이 있습니까?


1
이것도 알고 싶습니다. 형식 문자열에서 y의 m '및 d의 순서를 설명하는 날짜 파이프 문서가 로케일에 의해 설정되어 있으므로 무시됩니다. 그러나 로케일을 설정하거나 얻는 방법에 대한 표시는 없습니다.
Mark Farmiloe

답변:


276

Angular2 RC6부터 공급자를 추가하여 앱 모듈에서 기본 로캘을 설정할 수 있습니다.

@NgModule({
  providers: [
    { provide: LOCALE_ID, useValue: "en-US" }, //replace "en-US" with your locale
    //otherProviders...
  ]
})

Currency / Date / Number 파이프는 로캘을 선택해야합니다. LOCALE_ID는 각도 / 코어에서 가져올 OpaqueToken 입니다.

import { LOCALE_ID } from '@angular/core';

고급 사용 사례의 경우 서비스에서 로캘을 선택할 수 있습니다. 날짜 파이프를 사용하는 구성 요소를 만들면 로캘이 한 번 해결됩니다.

{
  provide: LOCALE_ID,
  deps: [SettingsService],      //some service handling global settings
  useFactory: (settingsService) => settingsService.getLanguage()  //returns locale string
}

그것이 당신을 위해 작동하기를 바랍니다.


43
나는 이것이 여전히 어디에도 문서화되지 않은 것에 놀랐다. 날짜 파이프 페이지 ( angular.io/docs/ts/latest/api/common/index/DatePipe-pipe.html )에는없고 일반 파이프 페이지 ( angular.io/docs/ts/latest/guide/pipes )에는 없습니다 .html )이 질문은 실제로 Google의 첫 번째 질문입니다 ( google.com/search?q=angular%202%20locales&rct=j ). 좋은 발견.
JP ten Berge

2
코드에서 파이프를 사용하려면 이제로 형식화해야합니다 new CurrencyPipe('en-US');. 바라건대 이것은 내 문제를 인터넷 검색 할 때 첫 번째 결과로 나타난 것처럼 뭔가 유용합니다.
Ash Blue

1
@corolla 그 서비스에 대해 알려줄 수 있습니까? 앱이 실행될 때 로케일을 변경하고 싶습니다. 해당 서비스에서 가능합니까? 그리고 어떻게 그런 서비스를 구현할 수 있습니까?
Martijn van den Bergh 2018 년

1
@MartijnvandenBergh, 서비스는 단지 로케일 문자열을 반환합니다. 앱이 실행되는 동안 로케일을 변경하려고 시도한 결과가 다양했습니다. 모든 사례를 처리하기 위해 다시로드 페이지가 종료되었습니다. YMMV.
corolla

1
나는 또한이 주제와 많은 어려움을 겪었고 이것에 대해 쓴 기사가 일부 사람들을 도울 수 있기를 바랍니다. medium.com/dailyjs/dynamic-locales-in-angular-dd9a527ebe1f
Michael Karén

72

LOCALE_ID 솔루션은 앱의 언어를 한 번 설정하려는 경우 좋습니다. 그러나 런타임 중에 언어를 변경하려는 경우 작동하지 않습니다. 이 경우 사용자 정의 날짜 파이프를 구현할 수 있습니다.

import { DatePipe } from '@angular/common';
import { Pipe, PipeTransform } from '@angular/core';
import { TranslateService } from '@ngx-translate/core';

@Pipe({
  name: 'localizedDate',
  pure: false
})
export class LocalizedDatePipe implements PipeTransform {

  constructor(private translateService: TranslateService) {
  }

  transform(value: any, pattern: string = 'mediumDate'): any {
    const datePipe: DatePipe = new DatePipe(this.translateService.currentLang);
    return datePipe.transform(value, pattern);
  }

}

TranslateService를 사용하여 앱 표시 언어를 변경하면 ( ngx-translate 참조 )

this.translateService.use('en');

앱 내 형식이 자동으로 업데이트되어야합니다.

사용 예 :

<p>{{ 'note.created-at' | translate:{date: note.createdAt | localizedDate} }}</p>
<p>{{ 'note.updated-at' | translate:{date: note.updatedAt | localizedDate:'fullDate'} }}</p>

또는 간단한 "메모"프로젝트를 여기에서 확인 하십시오 .

여기에 이미지 설명을 입력하십시오


템플릿 구문 분석 오류가 발생합니다. 제안 된 것과 같은 방식으로 사용한 필터 'localizedDate'를 컴파일 할 수 없습니다.
Prasad Shinde

LocalizedDatePipe를 올바르게 선언 했습니까? 예제 프로젝트 에서 pipe.module.ts를 참조하십시오 .
Milan Hlinák

예, @Milan Hlinak 이전에 해결했습니다. 당시의 의견에 대해서만 답변해야했습니다. 어쨌든 신속한 응답에 감사드립니다. 잘하고 있어요
Prasad Shinde

이것은 분명히 내가 찾던 것입니다. 런타임에 로케일을 변경하기 위해서는 커스텀 파이프가 필요하다는 것은 부끄러운 일입니다.
dendimiiii

2
작동하지만 "불순"파이프를 사용하는 것이 "순수"보다 느리다는 점에주의하십시오. 마찬가지로 각도 가이드 말한다 각도는 모든 성분 전환 검출주기 동안 불순 파이프를 행한다. 매번 키를 누르거나 마우스를 움직일 때마다 불순한 파이프가 자주 호출됩니다. 이러한 우려를 염두에두고 불순한 파이프를 신중하게 구현하십시오. 고가의 장기 배관은 사용자 경험을 파괴 할 수 있습니다.
루카 리토 사

64

angular5위의 대답은 더 이상 작동합니다!

다음 코드 :

app.module.ts

@NgModule({
  providers: [
    { provide: LOCALE_ID, useValue: "de-at" }, //replace "de-at" with your locale
    //otherProviders...
  ]
})

다음과 같은 오류가 발생합니다.

오류 : "de-at"로캘에 대한 로캘 데이터가 없습니다.

angular5로드하고 자신에 사용되는 로케일 파일을 등록해야합니다.

app.module.ts

import { NgModule, LOCALE_ID } from '@angular/core';
import { registerLocaleData } from '@angular/common';
import localeDeAt from '@angular/common/locales/de-at';

registerLocaleData(localeDeAt);

@NgModule({
  providers: [
    { provide: LOCALE_ID, useValue: "de-at" }, //replace "de-at" with your locale
    //otherProviders...
  ]
})

선적 서류 비치


실제로 en-US를 제외한 다른 로케일을 사용해야하는 경우 등록해야합니다. 답변 주셔서 감사합니다, @zgue
MikkaRin

1
나에게 또 다른 두통을 예방했다.. Thx! 문서는 조금 복잡하지만 registerLocaleData, 충분 하기는하지만 충분하지 않습니다.
danger89

1
이오니아 4에 대한 최고의 답변!
parrycima

22

TranslateServicefrom 을 사용 하는 @ngx-translate/core경우 다음은 런타임시 동적으로 전환하는 Angular 7에서 테스트하는 새 파이프를 만들지 않은 버전입니다. DatePipe의 locale매개 변수 사용 ( docs ) :

먼저 앱에서 사용하는 로캘을 선언하십시오 (예 app.component.ts:

import localeIt from '@angular/common/locales/it';
import localeEnGb from '@angular/common/locales/en-GB';
.
.
.
ngOnInit() {
    registerLocaleData(localeIt, 'it-IT');
    registerLocaleData(localeEnGb, 'en-GB');
}

그런 다음 파이프를 동적으로 사용하십시오.

myComponent.component.html

<span>{{ dueDate | date: 'shortDate' : '' : translateService.currentLang }}</span>

myComponent.component.ts

 constructor(public translateService: TranslateService) { ... }

2
놀랍게도 좋습니다. @ ngx-translate가 필요하지 않습니다. 템플릿의 문장이 무엇을 설명 할 수 있습니까?
라마

2
@lama, dueDate (포맷하려는 날짜) | date : 'shortDate' ( '형식'에 해당하는 날짜 파이프의 첫 번째 매개 변수) : '' (2 번째 매개 변수 => timeZone, "제공되지 않으면 최종 사용자의 로컬 시스템 시간대를 사용합니다.") : trasnlateService.currentLang (3 번째 매개 변수 => local),이 DatePipe
Diego Osornio

형식을 사용자 정의한 경우 어떻게합니까? 그것도 현지화 될 것입니까?
와일드 해머

12

date_pipe.ts를 살펴 보았고 관심있는 두 비트의 정보가 있습니다. 상단 근처에는 다음 두 줄이 있습니다.

// TODO: move to a global configurable location along with other i18n components.
var defaultLocale: string = 'en-US';

하단 근처에는이 줄이 있습니다.

return DateFormatter.format(value, defaultLocale, pattern);

이것은 날짜 파이프가 현재 'en-US'로 하드 코딩되어 있음을 나타냅니다.

내가 틀렸다면 나를 깨우쳐주세요.



아래에서 코롤라의 답변을 확인하십시오. 최신 버전이며 훌륭한 솔루션을 제공합니다.
Mark Langer

9

app.module.ts에서 다음 가져 오기를 추가하십시오. LOCALE 옵션 목록이 여기에 있습니다 .

import es from '@angular/common/locales/es';
import { registerLocaleData } from '@angular/common';
registerLocaleData(es);

그런 다음 공급자를 추가하십시오.

@NgModule({
  providers: [
    { provide: LOCALE_ID, useValue: "es-ES" }, //your locale
  ]
})

html로 파이프를 사용하십시오. 이에 대한 각도 문서 는 다음과 같습니다 .

{{ dateObject | date: 'medium' }}

Justo necesitaba esto!
alexchvrches

5

당신은 이런 식으로합니다 :

{{ dateObj | date:'shortDate' }}

또는

{{ dateObj | date:'ddmmy' }}

참조 : https://angular.io/docs/ts/latest/api/common/index/DatePipe-pipe.html


내 질문에 명확하지 않은 경우 미안하지만 이것은 정확히 무엇을하고 있지만 'shortDate'패턴으로 표시되며 미국 스타일로만 표시됩니다. 시간 스타일은 괜찮습니다.
nsbm

두 번째 예는 DatePipe에 전달되는 형식을 보여줍니다.
Langley

시도했지만 작동하지 않습니다. 날짜와 독립적으로 숫자 '5'만 표시하십시오.
nsbm

3

나는 같은 문제로 어려움을 겪고 있었고 이것을 사용하여 나를 위해 일하지 않았다

{{dateObj | date:'ydM'}}

그래서 최선의 해결책은 아니지만 해결 방법을 시도했지만 효과가있었습니다.

{{dateObj | date:'d'}}/{{dateObj | date:'M'}}/{{dateObj | date:'y'}}

항상 사용자 정의 파이프를 만들 수 있습니다.


3

AOT에 문제가있는 사용자는 useFactory를 사용하여 조금 다르게해야합니다.

export function getCulture() {
    return 'fr-CA';
}

@NgModule({
  providers: [
    { provide: LOCALE_ID, useFactory: getCulture },
    //otherProviders...
  ]
})

4
angular5 기준으로, 제공자 배열에서 지방 화살표 표현을 사용할 수 있습니다
iuliust

{ provide: LOCALE_ID, useFactory: () => 'fr-CA'}나를 위해 속임수를
썼다

0

Google 파이프를 복사하여 로케일을 변경했으며 내 국가에서 작동하므로 모든 로케일에서 완료하지 못했습니다. 아래는 코드입니다.

import {
    isDate,
    isNumber,
    isPresent,
    Date,
    DateWrapper,
    CONST,
    isBlank,
    FunctionWrapper
} from 'angular2/src/facade/lang';
import {DateFormatter} from 'angular2/src/facade/intl';
import {PipeTransform, WrappedValue, Pipe, Injectable} from 'angular2/core';
import {StringMapWrapper, ListWrapper} from 'angular2/src/facade/collection';


var defaultLocale: string = 'hr';

@CONST()
@Pipe({ name: 'mydate', pure: true })
@Injectable()
export class DatetimeTempPipe implements PipeTransform {
    /** @internal */
    static _ALIASES: { [key: string]: String } = {
        'medium': 'yMMMdjms',
        'short': 'yMdjm',
        'fullDate': 'yMMMMEEEEd',
        'longDate': 'yMMMMd',
        'mediumDate': 'yMMMd',
        'shortDate': 'yMd',
        'mediumTime': 'jms',
        'shortTime': 'jm'
    };


    transform(value: any, args: any[]): string {
        if (isBlank(value)) return null;

        if (!this.supports(value)) {
            console.log("DOES NOT SUPPORT THIS DUEYE ERROR");
        }

        var pattern: string = isPresent(args) && args.length > 0 ? args[0] : 'mediumDate';
        if (isNumber(value)) {
            value = DateWrapper.fromMillis(value);
        }
        if (StringMapWrapper.contains(DatetimeTempPipe._ALIASES, pattern)) {
            pattern = <string>StringMapWrapper.get(DatetimeTempPipe._ALIASES, pattern);
        }
        return DateFormatter.format(value, defaultLocale, pattern);
    }

    supports(obj: any): boolean { return isDate(obj) || isNumber(obj); }
}

0

좋아, 나는이 솔루션을 매우 간단하게 제안한다. ngx-translate

import { DatePipe } from '@angular/common';
import { Pipe, PipeTransform } from '@angular/core';
import { TranslateService } from '@ngx-translate/core';

@Pipe({
  name: 'localizedDate',
  pure: false
})
export class LocalizedDatePipe implements PipeTransform {

  constructor(private translateService: TranslateService) {
}

  transform(value: any): any {
    const date = new Date(value);

    const options = { weekday: 'long',
                  year: 'numeric',
                  month: 'long',
                  day: 'numeric',
                  hour: '2-digit',
                  minute: '2-digit',
                  second: '2-digit'
                    };

    return date.toLocaleString(this.translateService.currentLang, options);
  }

}

-1

약간 늦을 수도 있지만 필자의 경우 (각도 6) DatePipe 위에 다음과 같은 간단한 파이프를 만들었습니다.

private _regionSub: Subscription;
private _localeId: string;

constructor(private _datePipe: DatePipe, private _store: Store<any>) {
  this._localeId = 'en-AU';
  this._regionSub = this._store.pipe(select(selectLocaleId))
    .subscribe((localeId: string) => {
      this._localeId = localeId || 'en-AU';
    });
}

ngOnDestroy() { // Unsubscribe }

transform(value: string | number, format?: string): string {
  const dateFormat = format || getLocaleDateFormat(this._localeId, FormatWidth.Short);
  return this._datePipe.transform(value, dateFormat, undefined, this._localeId);
}

최상의 솔루션은 아니지만 간단하고 작동합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.