This is a plugin for NativeScript that implements internationalization (i18n) using the native capabilities of each platform. It is a direct fork of nativescript-localize.
This plugin was created to have a different behavior from nativescript-localize:
- the default
localize
method was renamed tol
- the default
l
method tries to load from a local JSON object - you can load such a JSON object with
loadLocalJSON
passing either the JSON or the path to it - if no local JSON,
l
load natively - keys are not encoded anymore, meaning keys are the same in native/js worlds.
- the locale JSON must now be a trully nested object (no
.
in keys names) - special characters support has been dropped in keys names.
A lot of thanks goes out to Eddy Verbruggen and Ludovic Fabrèges (@lfabreges) for developing and maintaining nativescript-localize.
tns plugin add @nativescript-community/l
Create a folder i18n
in the app
folder with the following structure:
app
| i18n
| en.json <-- english language
| fr.default.json <-- french language (default)
| es.js
You need to set the default langage and make sure it contains the application name to avoid any error.
import { NgModule, NO_ERRORS_SCHEMA } from "@angular/core";
import { NativeScriptLocalizeModule } from "@nativescript-community/l/angular";
import { NativeScriptModule } from "nativescript-angular/nativescript.module";
import { AppComponent } from "./app.component";
@NgModule({
declarations: [AppComponent],
bootstrap: [AppComponent],
imports: [
NativeScriptModule,
NativeScriptLocalizeModule
],
schemas: [NO_ERRORS_SCHEMA]
})
export class AppModule { }
<Label text="{{ 'Hello world !' | L }}"/>
<Label text="{{ 'I am %s' | L:'user name' }}"/>
import { localize } from "@nativescript-community/l";
console.log(localize("Hello world !"));
const application = require("application");
const localize = require("@nativescript-community/l");
application.setResources({ L: localize.l });
<Label text="{{ L('Hello world !') }}"/>
<Label text="{{ L('I am %s', 'user name') }}"/>
const localize = require("@nativescript-community/l");
console.log(localize("Hello world !"));
const page = args.object;
page.bindingContext = new Observable();
import { l } from "@nativescript-community/l";
Vue.filter("L", l);
<Label :text="'Hello world !'|L"></Label>
<Label :text="'I am %s'|L('user name')"></Label>
Each file is imported using require
, use the file format of your choice:
{
"app.name": "My app",
"ios.info.plist": {
"NSLocationWhenInUseUsageDescription": "This will be added to InfoPlist.strings"
},
"user": {
"name": "user.name",
"email": "user.email"
},
"array": [
"split the translation into ",
"multiples lines"
],
"sprintf": "format me %s",
"sprintf with numbered placeholders": "format me %2$s one more time %1$s"
}
const i18n = {
"app.name": "My app"
};
module.exports = i18n;
Add the .default
extension to the default language file to set it as the fallback language:
fr.default.json
The app.name
key is used to localize the application name:
{
"app.name": "My app"
}
Keys starting with ios.info.plist.
are used to localize iOS properties:
{
"ios.info.plist.NSLocationWhenInUseUsageDescription": "This will be added to InfoPlist.strings"
}
Seeing this module now uses JSON objects. Overriding consist of 3 steps:
- overriding native language, done with
overrideLocaleNative
- overriding json language, done with
loadLocalJSON
- updating all labels, buttons.... your job!
import { overrideLocaleNative } from "@nativescript-community/l/localize";
const localeOverriddenSuccessfully = overrideLocaleNative("en-GB"); // or "nl-NL", etc (or even just the part before the hyphen)
Important: In case you are using Android app bundle to release your android app, add this to App_Resources/Android/app.gradle to make sure all lanugages are bundled in the split apks
android {
// there maybe other code here //
bundle {
language {
enableSplit = false
}
}
}
Tip: you can get the default language on user's phone by using this
import { device } from '@nativescript/core/platform';
console.log("user's language is", device.language.split('-')[0]);
Tip: overrideLocaleNative method stores the language in a special key in app-settings, you can access it like this,
import { getString } from '@nativescript/core/application-settings';
console.log(getString('__app__language__')); // only available after the first time you use overrideLocaleNative(langName);
As a workaround, you can trigger a change detection from within your component constructor:
constructor(
private readonly params: ModalDialogParams,
private readonly changeDetectorRef: ChangeDetectorRef,
) {
setTimeout(() => this.changeDetectorRef.detectChanges(), 0);
}