From 98e93dce2f0491d989655fa5a1b48d4f7e099b6e Mon Sep 17 00:00:00 2001 From: geek Date: Tue, 6 Mar 2018 18:55:05 +0900 Subject: [PATCH] translations lib l10n added --- package.json | 3 +- src/app/app-routing.module.ts | 4 +- src/app/app.module.ts | 47 ++++++++++++++++++- .../component/header/header.component.html | 13 ++++- .../component/header/header.component.ts | 39 +++++++++++++-- src/app/commons/component/layouts.module.ts | 22 ++++++++- .../menu-item/menu-item.component.html | 4 +- .../menu-item/menu-item.component.ts | 3 ++ .../commons/component/sidebar/menu-element.ts | 26 +++++----- .../component/sidebar/sidebar.component.ts | 3 +- .../sub-menubar/sub-menubar.component.html | 2 +- .../sub-menubar/sub-menubar.component.ts | 4 +- .../sub-menubar/sub-menubar.module.ts | 2 +- src/app/pages/pages.module.ts | 27 ++++++++++- src/assets/translations/of-en.json | 17 +++++++ src/assets/translations/of-kr.json | 18 +++++++ src/index.html | 2 +- 17 files changed, 203 insertions(+), 33 deletions(-) create mode 100644 src/assets/translations/of-en.json create mode 100644 src/assets/translations/of-kr.json diff --git a/package.json b/package.json index b23a57a..ff512ee 100644 --- a/package.json +++ b/package.json @@ -42,7 +42,8 @@ "ngx-perfect-scrollbar": "^5.3.1", "rxjs": "^5.5.6", "url-join": "^4.0.0", - "zone.js": "^0.8.20" + "zone.js": "^0.8.20", + "angular-l10n": "^4.1.5" }, "devDependencies": { "@angular/cli": "1.6.5", diff --git a/src/app/app-routing.module.ts b/src/app/app-routing.module.ts index d5eeaeb..44f2b82 100644 --- a/src/app/app-routing.module.ts +++ b/src/app/app-routing.module.ts @@ -1,5 +1,5 @@ import { NgModule } from '@angular/core'; -import { Routes, RouterModule } from '@angular/router'; +import { Routes, RouterModule, PreloadAllModules } from '@angular/router'; const routes: Routes = [ { path: '', loadChildren: './pages/pages.module#PagesModule' }, @@ -9,7 +9,7 @@ const routes: Routes = [ ]; @NgModule({ - imports: [RouterModule.forRoot(routes, {useHash: true})], + imports: [RouterModule.forRoot(routes, {useHash: true, preloadingStrategy: PreloadAllModules})], exports: [RouterModule], }) export class AppRoutingModule { } diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 222015d..36b526b 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -1,6 +1,6 @@ -import { NgModule } from '@angular/core'; +import { NgModule, APP_INITIALIZER } from '@angular/core'; -import { BrowserModule } from '@angular/platform-browser'; +import { BrowserModule, Title } from '@angular/platform-browser'; import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; import { HttpClientModule } from '@angular/common/http'; @@ -16,6 +16,40 @@ import { environment } from '../environments/environment'; import { RESTService } from 'packages/commons/service/rest.service'; import { RPCService } from 'packages/commons/service/rpc.service'; +import { + L10nConfig, + L10nLoader, + LocalizationModule, + LocaleValidationModule, + StorageStrategy, + ProviderType +} from 'angular-l10n'; + +const l10nConfig: L10nConfig = { + locale: { + languages: [ + { code: 'en', dir: 'ltr' }, + { code: 'kr', dir: 'ltr' }, + ], + defaultLocale: { languageCode: 'en', countryCode: 'US' }, + storage: StorageStrategy.Cookie, + cookieExpiration: 30 + }, + translation: { + providers: [ + { type: ProviderType.Static, prefix: './assets/translations/of-' } + ], + caching: true, + composedKeySeparator: '.', + missingValue: 'No key', + i18nPlural: true + } +}; + +export function initL10n(l10nLoader: L10nLoader): Function { + return () => l10nLoader.load(); +} + @NgModule({ declarations: [ AppComponent, @@ -28,11 +62,20 @@ import { RPCService } from 'packages/commons/service/rpc.service'; MaterialModule, CovalentModule, HttpClientModule, + LocalizationModule.forRoot(l10nConfig), + LocaleValidationModule.forRoot() ], providers: [ {provide: 'REST_BASE_URL', useValue: environment.restBaseURL}, {provide: 'RPC_BASE_URL', useValue: environment.rpcBaseURL}, RESTService, RPCService, + Title, + { + provide: APP_INITIALIZER, + useFactory: initL10n, + deps: [L10nLoader], + multi: true + } ], bootstrap: [AppComponent] }) diff --git a/src/app/commons/component/header/header.component.html b/src/app/commons/component/header/header.component.html index 61ff353..3d6e05b 100644 --- a/src/app/commons/component/header/header.component.html +++ b/src/app/commons/component/header/header.component.html @@ -8,5 +8,16 @@ - + \ No newline at end of file diff --git a/src/app/commons/component/header/header.component.ts b/src/app/commons/component/header/header.component.ts index 9c8ed57..96c43c4 100644 --- a/src/app/commons/component/header/header.component.ts +++ b/src/app/commons/component/header/header.component.ts @@ -1,12 +1,23 @@ -import { Component, OnInit, Input } from '@angular/core'; +import { Component, OnInit, Input, OnDestroy } from '@angular/core'; import { ToolbarHelpers } from './toolbar.helpers'; +import { Title } from '@angular/platform-browser'; +import { Direction } from '@angular/cdk/bidi'; + +import { ISubscription } from 'rxjs/Subscription'; + +import { LocaleService, TranslationService } from 'angular-l10n'; @Component({ selector: 'of-header', templateUrl: './header.component.html', styleUrls: ['./header.component.scss'] }) -export class HeaderComponent implements OnInit { +export class HeaderComponent implements OnInit, OnDestroy { + + countryMenuItems: any[] = [ + { text: 'United States', language: 'en', country: 'US', currency: 'USD', numberingSystem: 'latn' }, + { text: 'Korea', language: 'kr', country: 'KR', currency: 'KRW', numberingSystem: 'latn' } +]; @Input() sidenav; @Input() sidebar; @@ -16,9 +27,31 @@ export class HeaderComponent implements OnInit { searchOpen = false; toolbarHelpers = ToolbarHelpers; - constructor() { } + dir: Direction; + + subscription: ISubscription; + + constructor(public locale: LocaleService, public translation: TranslationService, public title: Title) { } ngOnInit() { + this.subscription = this.translation.translationChanged().subscribe( + () => { this.title.setTitle(this.translation.translate('App.Title')); } + ); + + // Initializes direction. + // this.dir = this.getLanguageDirection(); } + ngOnDestroy(): void { + this.subscription.unsubscribe(); + } + + // getLanguageDirection(language?: string): Direction { + // return this.locale.getLanguageDirection(language) as Direction; + // } + + selectLocale(language: string, country: string, currency: string, numberingSystem: string): void { + this.locale.setDefaultLocale(language, country, '', numberingSystem); + this.locale.setCurrentCurrency(currency); + } } diff --git a/src/app/commons/component/layouts.module.ts b/src/app/commons/component/layouts.module.ts index 540fbb2..45bed9b 100644 --- a/src/app/commons/component/layouts.module.ts +++ b/src/app/commons/component/layouts.module.ts @@ -12,12 +12,30 @@ import { SensorItemFilterComponent } from './sensor-item-filter/sensor-item-filt import { HostSummaryCardComponent } from './host-summary-card/host-summary-card.component'; import { AppSummaryCardComponent } from './app-summary-card/app-summary-card.component'; +import { + L10nConfig, + L10nLoader, + LocalizationModule, + ProviderType, + StorageStrategy +} from 'angular-l10n'; @NgModule({ imports: [ CommonModule, - FlexLayoutModule, + FlexLayoutModule ], - declarations: [SidebarComponent, HeaderComponent, FooterComponent, MenuItemComponent, SubMenubarComponent, InfoTableComponent, SensorSummaryComponent, SensorItemFilterComponent, HostSummaryCardComponent, AppSummaryCardComponent] + declarations: [ + SidebarComponent, + HeaderComponent, + FooterComponent, + MenuItemComponent, + SubMenubarComponent, + InfoTableComponent, + SensorSummaryComponent, + SensorItemFilterComponent, + HostSummaryCardComponent, + AppSummaryCardComponent + ] }) export class LayoutsModule { } diff --git a/src/app/commons/component/menu-item/menu-item.component.html b/src/app/commons/component/menu-item/menu-item.component.html index cb6f9ed..ad0fcb5 100644 --- a/src/app/commons/component/menu-item/menu-item.component.html +++ b/src/app/commons/component/menu-item/menu-item.component.html @@ -4,7 +4,7 @@ {{menu.icon}} -

{{ menu.name }}

+

{{ menu.name }}

{{menu?.chip?.value}} @@ -13,7 +13,7 @@ {{menu.icon}} -

{{ menu.name }}

+

{{ menu.name }}

diff --git a/src/app/commons/component/menu-item/menu-item.component.ts b/src/app/commons/component/menu-item/menu-item.component.ts index bde574a..ef94f11 100644 --- a/src/app/commons/component/menu-item/menu-item.component.ts +++ b/src/app/commons/component/menu-item/menu-item.component.ts @@ -1,5 +1,7 @@ import { Component, OnInit, Input } from '@angular/core'; +import { Language } from 'angular-l10n'; + @Component({ selector: 'of-menu-item', templateUrl: './menu-item.component.html', @@ -10,6 +12,7 @@ export class MenuItemComponent implements OnInit { @Input() menu; @Input() iconOnly: boolean; @Input() secondaryMenu = false; + @Language() lang: string; constructor() { } diff --git a/src/app/commons/component/sidebar/menu-element.ts b/src/app/commons/component/sidebar/menu-element.ts index c833539..bf11e2a 100644 --- a/src/app/commons/component/sidebar/menu-element.ts +++ b/src/app/commons/component/sidebar/menu-element.ts @@ -1,39 +1,39 @@ export const menus = [ { - 'name': 'Home', + 'name': 'App.Home', 'icon': 'home', 'link': '/home', 'open': true, }, { - 'name': 'Infra', + 'name': 'App.Infra', 'icon': 'widgets', 'link': false, 'open': false, 'sub': [ { - 'name': 'Map', + 'name': 'App.Map', 'link': '/map', 'icon': 'indeterminate_check_box', 'chip': false, 'open': false, }, { - 'name': 'Sensors', + 'name': 'App.Sensors', 'link': '/sensors', 'icon': 'indeterminate_check_box', 'chip': false, 'open': false, }, { - 'name': 'SensorSetting', + 'name': 'App.SensorSetting', 'link': '/sensor-setting', 'icon': 'indeterminate_check_box', 'chip': false, 'open': false, }, { - 'name': 'Probes', + 'name': 'App.Probes', 'link': '/probes', 'icon': 'indeterminate_check_box', 'chip': false, @@ -42,20 +42,20 @@ export const menus = [ ] }, { - 'name': 'Monitor', + 'name': 'App.Monitor', 'icon': 'widgets', 'link': false, 'open': false, 'sub': [ { - 'name': 'Overview', + 'name': 'App.Overview', 'link': '/overview', 'icon': 'indeterminate_check_box', 'chip': false, 'open': false, }, { - 'name': 'Dashboards', + 'name': 'App.Dashboards', 'link': '/dashboard', 'icon': 'indeterminate_check_box', 'chip': { 'value': 3, 'color': 'accent'}, @@ -64,25 +64,25 @@ export const menus = [ ] }, { - 'name': 'Alert', + 'name': 'App.Alert', 'icon': 'warning', 'link': '', 'open': true, }, { - 'name': 'Report', + 'name': 'App.Report', 'icon': '', 'link': '', 'open': true, }, { - 'name': 'Log', + 'name': 'App.Log', 'icon': '', 'link': '', 'open': true, }, { - 'name': 'Setting', + 'name': 'App.Setting', 'icon': '', 'link': '/auth/signin', 'open': true, diff --git a/src/app/commons/component/sidebar/sidebar.component.ts b/src/app/commons/component/sidebar/sidebar.component.ts index 48c616d..0e451e1 100644 --- a/src/app/commons/component/sidebar/sidebar.component.ts +++ b/src/app/commons/component/sidebar/sidebar.component.ts @@ -1,5 +1,6 @@ import { Component, OnInit, Input } from '@angular/core'; import { menus } from './menu-element'; +import { Language } from 'angular-l10n'; @Component({ selector: 'of-sidebar', @@ -7,7 +8,7 @@ import { menus } from './menu-element'; styleUrls: ['./sidebar.component.scss'] }) export class SidebarComponent implements OnInit { - + @Language() lang: string; @Input() iconOnly = false; public menus = menus; diff --git a/src/app/commons/component/sub-menubar/sub-menubar.component.html b/src/app/commons/component/sub-menubar/sub-menubar.component.html index 26239db..e4a8449 100644 --- a/src/app/commons/component/sub-menubar/sub-menubar.component.html +++ b/src/app/commons/component/sub-menubar/sub-menubar.component.html @@ -1,6 +1,6 @@ \ No newline at end of file diff --git a/src/app/commons/component/sub-menubar/sub-menubar.component.ts b/src/app/commons/component/sub-menubar/sub-menubar.component.ts index c8a3e0e..43af6f7 100644 --- a/src/app/commons/component/sub-menubar/sub-menubar.component.ts +++ b/src/app/commons/component/sub-menubar/sub-menubar.component.ts @@ -1,13 +1,15 @@ import { Component, OnInit, Input } from '@angular/core'; import { Router } from '@angular/router'; +import { Language } from 'angular-l10n'; + @Component({ selector: 'of-sub-menubar', templateUrl: './sub-menubar.component.html', styleUrls: ['./sub-menubar.component.scss'] }) export class SubMenubarComponent implements OnInit { - + @Language() lang: string; @Input() tabs: any; constructor(public router: Router) { } diff --git a/src/app/commons/component/sub-menubar/sub-menubar.module.ts b/src/app/commons/component/sub-menubar/sub-menubar.module.ts index f99c4bc..7d706ff 100644 --- a/src/app/commons/component/sub-menubar/sub-menubar.module.ts +++ b/src/app/commons/component/sub-menubar/sub-menubar.module.ts @@ -8,7 +8,7 @@ import { RouterModule } from '@angular/router'; imports: [ CommonModule, MaterialModule, - RouterModule, + RouterModule ], declarations: [ SubMenubarComponent, diff --git a/src/app/pages/pages.module.ts b/src/app/pages/pages.module.ts index a4c3026..b0092a6 100644 --- a/src/app/pages/pages.module.ts +++ b/src/app/pages/pages.module.ts @@ -1,4 +1,5 @@ -import { NgModule } from '@angular/core'; +import { NgModule, APP_INITIALIZER} from '@angular/core'; +import { Title } from '@angular/platform-browser'; import { CommonModule } from '@angular/common'; import { PagesComponent } from './pages.component'; import { PagesRoutingModule } from './pages-routing.module'; @@ -15,6 +16,23 @@ import { } from 'ngx-perfect-scrollbar'; import { NotificationModule } from 'packages/notification/notification.module'; +import { + L10nConfig, + L10nLoader, + LocalizationModule, + ProviderType +} from 'angular-l10n'; + +const l10nConfig: L10nConfig = { + translation: { + providers: [ + { type: ProviderType.Static, prefix: './assets/translations/of-' } + ], + composedKeySeparator: '.', + missingValue: 'No key' + } +}; + const DEFAULT_PERFECT_SCROLLBAR_CONFIG: PerfectScrollbarConfigInterface = { suppressScrollX: true }; @@ -28,6 +46,7 @@ const DEFAULT_PERFECT_SCROLLBAR_CONFIG: PerfectScrollbarConfigInterface = { MaterialModule, PerfectScrollbarModule, NotificationModule, + LocalizationModule.forChild(l10nConfig) ], declarations: [ PagesComponent, @@ -43,4 +62,8 @@ const DEFAULT_PERFECT_SCROLLBAR_CONFIG: PerfectScrollbarConfigInterface = { } ], }) -export class PagesModule { } +export class PagesModule { + constructor(public l10nLoader: L10nLoader) { + this.l10nLoader.load(); + } +} diff --git a/src/assets/translations/of-en.json b/src/assets/translations/of-en.json new file mode 100644 index 0000000..5d9f183 --- /dev/null +++ b/src/assets/translations/of-en.json @@ -0,0 +1,17 @@ +{ + "App": { + "Title": "overFlow", + "Subtitle": "It's a small world", + "Home": "Home", + "Map": "Map", + "Sensors": "Sensors", + "SensorSetting": "SensorSetting", + "Probes": "Probes", + "Monitor": "Monitor", + "Overview": "Overview", + "Dashboards": "Dashboards", + "Alert": "Alert", + "Report": "Report", + "Log": "Log" + } +} diff --git a/src/assets/translations/of-kr.json b/src/assets/translations/of-kr.json new file mode 100644 index 0000000..2c426cf --- /dev/null +++ b/src/assets/translations/of-kr.json @@ -0,0 +1,18 @@ +{ + "App": { + "Title": "오버플로우", + "Subtitle": "It's a small world", + "Home": "홈", + "Infra": "인프라", + "Map": "맵", + "Sensors": "센서", + "SensorSetting": "센서설정", + "Probes": "프로브", + "Monitor": "모니터", + "Overview": "오버뷰", + "Dashboards": "대시보드", + "Alert": "알림", + "Report": "리포트", + "Log": "기록" + } +} diff --git a/src/index.html b/src/index.html index ce9b4a0..eb56078 100644 --- a/src/index.html +++ b/src/index.html @@ -17,7 +17,7 @@ - +