NgFor ve Async Pipe Angular 2 ile Observable Object'ten bir dizi kullanma


93

Gözlemlenebilirleri Angular 2'de nasıl kullanacağımı anlamaya çalışıyorum. Bu hizmete sahibim:

import {Injectable, EventEmitter, ViewChild} from '@angular/core';
import {Observable} from "rxjs/Observable";
import {Subject} from "rxjs/Subject";
import {BehaviorSubject} from "rxjs/Rx";
import {Availabilities} from './availabilities-interface'

@Injectable()
export class AppointmentChoiceStore {
    public _appointmentChoices: BehaviorSubject<Availabilities> = new BehaviorSubject<Availabilities>({"availabilities": [''], "length": 0})

    constructor() {}

    getAppointments() {
        return this.asObservable(this._appointmentChoices)
    }
    asObservable(subject: Subject<any>) {
        return new Observable(fn => subject.subscribe(fn));
    }
}

Bu BehaviorSubject, başka bir hizmetten olduğu gibi yeni değerler itilir:

that._appointmentChoiceStore._appointmentChoices.next(parseObject)

Göstermek istediğim bileşende bir gözlemlenebilir biçiminde ona abone oluyorum:

import {Component, OnInit, AfterViewInit} from '@angular/core'
import {AppointmentChoiceStore} from '../shared/appointment-choice-service'
import {Observable} from 'rxjs/Observable'
import {Subject} from 'rxjs/Subject'
import {BehaviorSubject} from "rxjs/Rx";
import {Availabilities} from '../shared/availabilities-interface'


declare const moment: any

@Component({
    selector: 'my-appointment-choice',
    template: require('./appointmentchoice-template.html'),
    styles: [require('./appointmentchoice-style.css')],
    pipes: [CustomPipe]
})

export class AppointmentChoiceComponent implements OnInit, AfterViewInit {
    private _nextFourAppointments: Observable<string[]>

    constructor(private _appointmentChoiceStore: AppointmentChoiceStore) {
        this._appointmentChoiceStore.getAppointments().subscribe(function(value) {
            this._nextFourAppointments = value
        })
    }
}

Ve görünümde şu şekilde gösterme girişimi:

  <li *ngFor="#appointment of _nextFourAppointments.availabilities | async">
         <div class="text-left appointment-flex">{{appointment | date: 'EEE' | uppercase}}

Ancak, kullanılabilirlik henüz gözlemlenebilir nesnenin bir özelliği değildir, bu nedenle hata verir, hatta bunu kullanılabilirlik arayüzünde şu şekilde tanımladığımı düşündüm bile:

export interface Availabilities {
  "availabilities": string[],
  "length": number
}

Eşzamansız kanal ve * ngFor ile gözlemlenebilir bir nesneden eşzamansız bir dizi nasıl görüntüleyebilirim? Aldığım hata mesajı:

browser_adapter.js:77 ORIGINAL EXCEPTION: TypeError: Cannot read property 'availabilties' of undefined

Gerçek hata mesajı nedir?
Günter Zöchbauer

hata eklemek için düzenlendi
C. Kearns

son açısal-RC1 ile sözdizimi*ngFor="let appointment of _nextFourAppointments.availabilities | async">
Jagannath

bu doğrudur, ancak hataya neden olmuyor. sadece bir uyarı atar.
C. Kearns

3
Bir yerlerde bir yazım hatası olduğuna inanıyorum. Hata, ne availabiltieszaman olması gerektiğini söylüyoravailabilities
Ivan Sivak

Yanıtlar:


154

İşte bir örnek

// in the service
getVehicles(){
    return Observable.interval(2200).map(i=> [{name: 'car 1'},{name: 'car 2'}])
}

// in the controller
vehicles: Observable<Array<any>>
ngOnInit() {
    this.vehicles = this._vehicleService.getVehicles();
}

// in template
<div *ngFor='let vehicle of vehicles | async'>
    {{vehicle.name}}
</div>

get işlevim bir özneyi döndürüyor: public _appointmentChoices: Subject<any> = new Subject() getAppointments() { return this._appointmentChoices.map(object=>object.availabilities).subscribe() } denetleyicide onu eşitlediğimde şu hatayı alıyorum: browser_adapter.js:77Error: Invalid argument '[object Object]' for pipe 'AsyncPipe'özneyi nasıl gözlemlenebilir hale getirebilirim?
C. Kearns

public _appointmentChoices: Subject<any> = new Subject() getAppointments() { return (this._appointmentChoices.map(object=>object.availabilities).asObservable()) } } bu bana şu hatayı veriyor: property asObservable does not exist on type observableancak _appointmentChoices bir Subject?
C. Kearns

Zaten gözlemlenebilirdi! Sadece abone olmam gerekiyordu!
C. Kearns

Konuları bütünleştirme konusunda ek bir problemim vardı. İşte gözlenebilirleri ve konuları kullanarak StackBlitz var: stackblitz.com/edit/subject-as-observable-list-example
IceWarrior353

12

Kim de bu yazıya tökezledi.

Doğru yol olduğuna inanıyorum:

  <div *ngFor="let appointment of (_nextFourAppointments | async).availabilities;"> 
    <div>{{ appointment }}</div>
  </div>

1

Sanırım aradığın bu

<article *ngFor="let news of (news$ | async)?.articles">
<h4 class="head">{{news.title}}</h4>
<div class="desc"> {{news.description}}</div>
<footer>
    {{news.author}}
</footer>


1

Bir diziniz yoksa, ancak gözlemlenebilirinizi bir dizi gibi kullanmaya çalışıyorsanız, bu bir nesne akışı olsa bile, bu yerel olarak çalışmayacaktır. Aşağıda, yalnızca gözlemlenebilir nesneyi silmeyi değil, nesneleri eklemeyi önemsediğinizi varsayarak bunu nasıl düzelteceğimi gösteriyorum.

Kaynağı BehaviorSubject türünde olan bir gözlemlenebilir nesneyi kullanmaya çalışıyorsanız, bunu ReplaySubject olarak değiştirin ve ardından bileşeninizde şu şekilde abone olun:

Bileşen

this.messages$ = this.chatService.messages$.pipe(scan((acc, val) => [...acc, val], []));

HTML

<div class="message-list" *ngFor="let item of messages$ | async">

scanOperatör yerine kullanabilirsiniz.pipe(toArray())
MotKohn

Kendi tuzağınızı yaratırken başka bir tuzak aramak Subjectdeğil complete(). Akümülatör asla çalışmaz.
MotKohn
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.