Как перебирать ключи объектов с помощью *ngFor?

Я копался и обнаружил, что могу использовать следующее, чтобы использовать *ngFor над объектом:

 <div *ngFor="#obj of objs | ObjNgFor">...</div>

где ObjNgFor труба:

@Pipe({ name: 'ObjNgFor',  pure: false })
export class ObjNgFor implements PipeTransform {
    transform(value: any, args: any[] = null): any {
        return Object.keys(value).map(key => value[key]);
    }
}

Однако, когда у меня есть такой объект:

{
"propertyA":{
    "description":"this is the propertyA",
    "default":"sth"
 },
"propertyB":{
    "description":"this is the propertyB",
    "default":"sth"
 }
}

Я не совсем уверен, как я могу извлечь «свойство A» и «свойство B», чтобы оно было доступно из директивы * ngFor. Любые идеи?

ОБНОВЛЕНИЕ

Что я хочу сделать, так это представить следующий HTML:

        <div *ngFor="#obj of objs | ObjNgFor" class="parameters-container">
            <div class="parameter-desc">
                {{SOMETHING}}:{{obj.description}}
            </div>
        </div>

Где что-то будет равно propertyA и propertyB (так устроен объект). Итак, это приведет к:

propertyA:this is the propertyA
propertyB:this is the propertyB

person uksz    schedule 05.05.2016    source источник


Ответы (5)


Обновлять

В 6.1.0-beta.1 KeyValuePipe был представлен https://github.com/angular/angular/pull/24319

<div *ngFor="let item of {'b': 1, 'a': 1} | keyvalue">
  {{ item.key }} - {{ item.value }}
</div>

Пример плункера

Предыдущая версия

Вы можете попробовать что-то вроде этого

export class ObjNgFor implements PipeTransform {
    transform(value: any, args: any[] = null): any {
        return Object.keys(value).map(key => Object.assign({ key }, value[key]));
    }
}

А потом по вашему шаблону

  <div *ngFor="let obj of objs | ObjNgFor">
   {{obj.key}} - {{obj.description}}
  </div>

Планкер

person yurzui    schedule 05.05.2016
comment
Канал значения ключа сортируется по порядку ключей и значений в angular 6. Как мы можем отключить это? - person ideeps; 31.10.2018

Или вместо того, чтобы создавать канал и передавать объект в *ngFor, просто передайте Object.keys(MyObject) в *ngFor. Возвращает так же, как труба, но без хлопот.

В файле TypeScript:

let list = Object.keys(MyObject); // good old javascript on the rescue

В шаблоне (html):

*ngFor="let item of list"
person Jorge    schedule 13.05.2017
comment
Спасибо!!! Это сделало его простым. Вы должны добавить, что положить в часть шаблона кстати =) - person Gaspa79; 09.05.2018
comment
аккуратное решение. Я получил числовые значения и строковые значения в списке, поэтому я использовал метод среза, чтобы получить правильную сторону массива: options.slice(options.length / 2). Нашел это решение здесь: strings#38554683" title="как я могу использовать ngfor для перебора перечисления машинописного текста в виде массива строк% 2338554683"> stackoverflow.com/questions/38554562/ - person Willem de Jong; 05.07.2018

Просто верните ключи из канала вместо значений, а затем используйте ключи для доступа к значениям:

(let вместо # в бета-версии 17)

@Pipe({ name: 'ObjNgFor',  pure: false })
export class ObjNgFor implements PipeTransform {
    transform(value: any, args: any[] = null): any {
        return Object.keys(value)//.map(key => value[key]);
    }
}
@Component({
    selector: 'my-app',
    pipes: [ObjNgFor],
    template: `
    <h1>Hello</h1>
 <div *ngFor="let key of objs | ObjNgFor">{{key}}:{{objs[key].description}}</div>    `,
})
export class AppComponent {
  objs = {
    "propertyA":{
      "description":"this is the propertyA",
      "default":"sth"
    },
    "propertyB":{
      "description":"this is the propertyB",
      "default":"sth"
    }
  };
}

Пример планкера

См. также Выбор на основе перечисления в Angular2

person Günter Zöchbauer    schedule 05.05.2016
comment
Гюнтер - Я хотел бы показать пользователю либо «свойство A», либо «свойство B». Так что мне нужно как-то поменять трубу - person uksz; 05.05.2016
comment
Не знаю, что вы имеете в виду. В зависимости от того, по каким критериям вы хотите показать тот или иной? - person Günter Zöchbauer; 05.05.2016
comment
Не уверен, какой именно вариант использования вы имеете в виду, но я не понимаю, почему что-то не работает с вложенными объектами. - person Günter Zöchbauer; 06.05.2016
comment
Можно ли это совместить с async pipe, если objs асинхронный? - person sabithpocker; 07.05.2017
comment
Конечно {{someObservable | async | ObjNgFor}} - person Günter Zöchbauer; 07.05.2017
comment
@GünterZöchbauer, как я могу получить доступ к значению объекта в асинхронном случае с помощью этого подхода? - person leotesta; 28.11.2017

keys.pipe.ts

import { Pipe, PipeTransform } from '@angular/core';

@Pipe({ name: 'keys' })
export class KeysPipe implements PipeTransform {
    transform(obj: Object, args: any[] = null): any {
        let array = [];
        Object.keys(obj).forEach(key => {
            array.push({
                value: obj[key],
                key: key
            });
        });
        return array;
    }
}

app.module.ts

import { KeysPipe } from './keys.pipe';

@NgModule({
  declarations: [
    ...
    KeysPipe
  ]
})

example.component.html

<elem *ngFor="let item of obj | keys" id="{{ item.key }}">
    {{ item.value }}
</elem>
person jadeallencook    schedule 01.10.2018

не используйте трубы в этом примере

*ngFor="let Value bof Values; let i = index"

{{i}}
person HaiNM    schedule 19.12.2019
comment
Полный код был бы полезен, а не его часть. - person zmag; 19.12.2019