typescript - Angular - Přístup k hodnotám objektu uloženého v poli objektů uvnitř šablony
Mám jednu třídu, jak je uvedeno níže:
export class SettingsTab {
id: number;
class: string;
name: Object = {};
}
Také ji napodobím do jednoduchého pole:
export const SETTINGSTABS: SettingsTab[] = [
{ id: 1, class: 'classOne', name: [{ "pl": "Tekst po polsku" }, { "en": "Text in english" }] },
{ id: 2, class: 'classTwo', name: [{ "pl": "Tekst po polsku" }, { "en": "Text in english" }] },
{ id: 3, class: 'classThree', name: [{ "pl": "Tekst po polsku" }, { "en": "Text in english" }] }
];
Nyní bych chtěl v mé šabloně přistupovat k určité hodnotě objektu name v závislosti na tom, který jazyk právě používám. Informace o aktuálním jazyce získávám z localStorage, jak je uvedeno níže:
language = localStorage.getItem('currentLang') != null ? localStorage.getItem('currentLang').replace("'", "") : "pl";
Podařilo se mi toho dosáhnout pomocí kódu uvedeného níže:
<ng-container *ngFor="let name of settingsTab.name">
<ng-container *ngFor="let key of ObjectKeys(name)">
<span *ngIf="key == language">{{ name[key] }}</span>
</ng-container>
</ng-container>
Klíče objektu jsou v mé komponentě definovány takto:
ObjectKeys = Object.keys;
Ale moje otázka je, jestli existuje nějaký nejsnazší způsob, jak dosáhnout toho, co chci udělat? Nelíbí se mi mít dva ng-komponenty s *ngFor uvnitř. Také bych to chtěl dosáhnout co nejvíce optimalizovaným způsobem.
Odpověď č. 1
Ideálně by vlastnost name:
{ ..., name: [{ "pl": "Tekst po polsku" }, { "en": "Text in english" }] },
Mělo by to formát ne pole objektů, ale objektu:
{ ..., name: {"pl": "Tekst po polsku", "en": "Text in english"} },
Pak byste mohl(a) jednoduše použít ve svém šabloně:
<span>{{ settingsTab.name[language] }}</span>
Což je vyhledávání s konstantní časovou složitostí (jen získání vlastnosti v objektu).
Teď, pokud nemůžete změnit formát name, použil bych metodu místo těch vnořených ng-container:
export class MyComponent {
...
lang(names: [any], language: string) {
return (names.find(lang => lang[language]) || {})[language]
}
...
}
A používejte to takto:
<span>{{ lang(settingsTab.name, language) }}</span>
Samozřejmě, můžete lang pojmenovat, jak uznáte za vhodné. Jen si všimněte, že tato alternativa má složitost O(n), protože find musí procházet pole name. To pravděpodobně výkon vaší aplikace vůbec neovlivní, ale myslel jsem, že byste to měli vědět. V aktuálním formátu name zde neexistuje rychlejší způsob.
Ukázka: https://stackblitz.com/edit/angular-c5wzbk?file=src/app/app.component.ts
