ionic2 ng2-translate не работает в модальном режиме
У меня проблемы с использованием ng2-translate в сочетании с модалами в ionic2. Переводы на обычных страницах работают.
Это мой файл app.module.ts:
import ...
@NgModule({
declarations: [
MyApp,
//...
],
imports: [
TranslateModule.forRoot({
provide: TranslateLoader,
useFactory: (createTranslateLoader),
deps: [Http]
}),
IonicModule.forRoot(MyApp),
],
exports: [
TranslateModule
],
bootstrap: [IonicApp],
entryComponents: [
MyApp,
//...
],
providers: [Storage, {provide: ErrorHandler, useClass: IonicErrorHandler}]
})
export class AppModule {}
export function createTranslateLoader(http: Http) {
return new TranslateStaticLoader(http, 'assets/i18n', '.json');
}
Например, в моей панели инструментов я могу использовать следующий HTML-код и получить правильный перевод:
<h2>{{'general.tasks' | translate}}</h2>
Но когда я сейчас открываю новый модальный с ModalController от ионно-угловой, с помощью следующего кода:
let taskModal = this.modalCtrl.create(TaskCancelPage, {'task': task});
taskModal.onDidDismiss(data => {
console.log(data);
});
taskModal.present();
Наличие того же HTML-кода в этом новом TaskCancelPage
<h2>{{'general.tasks' | translate}}</h2>
Но здесь я получаю только общие задачи вместо переведенного значения.
2 ответа
Это работает для меня вот что я сделал:
В [проекте]/src//app.module.ts:
import { TranslateModule, TranslateStaticLoader, TranslateLoader } from 'ng2-translate/ng2-translate';
export function createTranslateLoader(http: Http) {
return new TranslateStaticLoader(http, './assets/i18n', '.json');
}
import { TranslationService } from '../services/translation/translation';
//custom pipe
import { CapitalizePipe } from '../custom-pipes/capitalize/capitalize';
@NgModule({
declarations: [
...,
CapitalizePipe,
....
],
imports: [
IonicModule.forRoot(MyApp),
TranslateModule.forRoot({provide: TranslateLoader,
useFactory: (createTranslateLoader),
deps: [Http]})
],
bootstrap: [IonicApp],
entryComponents: [
...
],
providers: [
TranslationService,
....
]
})
В [project]/src/app/app.component.ts
...
import { TranslationService } from '../services/translation/translation';
import { CapitalizePipe } from '../custom-pipes/capitalize/capitalize';
@Component({
templateUrl: 'app.html',
})
export class MyApp {
....
constructor(
...,
public translationService: TranslationService, ...
) {}
....
ngOnInit() {
return this.defineLang().then(
(event) => {
console.log(MyApp.CLASS_TAG + " this.defineLang() fired: ",event , " getLangs is " , this.translationService.getLangs());
this.[yourFunctionToDefineRootPage]();
}
);
}
...
private defineLang(): Promise<any> {
let appDfltLang = 'fr';
this.translationService.getBestLanguageAccordingToBrowserAvailability(appDfltLang);
let promise = this.translationService.langSettingOnInit();
return promise;
}
....
}
в [проекте]/src/custom-pipe/capitalize/capitalize.ts:
import { PipeTransform, Pipe } from '@angular/core';
@Pipe({name:'capitalize'})
export class CapitalizePipe implements PipeTransform {
transform(value?: any,args?: any): any{
return (!!value)?value.charAt(0).toUpperCase()+value.substr(1):value;
}
}
в [проект]/src/services/translation/translation.ts
import { Injectable } from '@angular/core';
import { LangChangeEvent, TranslateService } from 'ng2-translate/ng2-translate';
import { Observable } from 'rxjs/Observable';
import { CapitalizePipe } from '../../custom-pipes/capitalize/capitalize';
@Injectable()
export class TranslationService {
private static readonly CLASS_TAG = "TranslationService";
private availableLang: Array<string> = ["fr","en","nl"];
private defaultLanguage:string = "en";
constructor(
private translateService: TranslateService
) { }
setDefaultLang(lang: string) {
return this.translateService.setDefaultLang(lang);
}
use(lang: string): Observable<any> {
let brLgSubStr:string = this.getBrowserLang().substr(0,2);
let findLg:number = this.availableLang.indexOf(brLgSubStr);
if(findLg==-1){
lang = this.defaultLanguage;
}
return this.translateService.use(lang);
}
getCurrentLang(): string {
return this.translateService.currentLang;
}
getDefaultLang(): string {
return this.translateService.getDefaultLang();
}
getBestLanguageAccordingToBrowserAvailability(appDfltLang:string) {
console.log(TranslationService.CLASS_TAG + "getBestLanguageAccordingToBrowserAvailability() starts ");
let brLang = this.getBrowserLang().substr(0,2);
let brLangAmongPossibilities:boolean = false;
for(let i in this.availableLang){
if(this.availableLang[i]==brLang){
brLangAmongPossibilities=true;
}
}
if(brLangAmongPossibilities){
this.translateService.use(brLang);
} else {
this.translateService.use(appDfltLang);
}
this.translateService.setDefaultLang(appDfltLang);
}
getBrowserLang():string {
return this.translateService.getBrowserLang();
}
getLangs():Array<string> {
return this.translateService.getLangs();
}
getAvailableLangs():Array<string>{
return this.availableLang;
}
langSettingOnInit(): Promise<LangChangeEvent> {
return new Promise((resolve, reject) => {
this.translateService.onLangChange.subscribe(
(event) => {
resolve(event);
},
(error) => {
console.log(TranslationService.CLASS_TAG + "onLangChangeInit() error: " ,error);
reject(error);
}
);
});
}
instant(key: string | Array<string>, interpolateParams?: Object): string | any {
let result = key && this.translateService.instant(key, interpolateParams);
result = (result !== key) ? result : '';
if (key && !result) {
console.error(`[not translated key]::${key}`);
}
return result;
}
instantCapitalize(key: string | Array<string>, interpolateParams?: Object): string | any {
return new CapitalizePipe().transform(this.instant(key));
}
}
Затем на ваших страницах (модальных или нет), где вы хотите использовать его, импортируйте сервис:
import { TranslationService } from '[root folder]/services/translation/translation';
И объявить сервис в конструкторе страницы:
@Component({
selector:'custom',
templateUrl: 'custom.html'
})
export class CustomPage {
constructor(...,public translationService:TranslationService,...){
}
....
}
В вашем HTML-шаблоне назовите это:
<[some text tag]>{{ "[some id word from your trad file]" | translate | capitalize }}</some text tag]>
или если вы не хотите использовать заглавную букву первой буквы:
<[some text tag]>{{ "[some id word from your trad file]" | translate }}</some text tag]>
И на странице, если вы звоните AlertController
например, вы можете сделать:
this.translationService.instantCapitalize("[some id word from your trad file]");
или если вы не хотите использовать заглавную букву первой буквы:
this.translationService.instant("[some id word from your trad file]");
ПО НЕКОТОРЫМ ПРИЧИНАМ ПРОЧИТАЕТСЯ ТОЛЬКО ТОРГОВЫЕ ФАЙЛЫ ПОД [project]/wwww/assets/i18n/[2 chars language code].json
Для ionic 5 Объявите модальный компонент или страницу в текущем модуле ex: декларации: [HomePage,FilterComponent]