如何使 class 可观察?
How to make class Observable?
我有 class 具有属性:
export class Model {
public id: number;
public name: string;
}
如何使这个 class 可观察,以监听 m 属性的变化。
我需要这样的东西:
let m = new Model();
m.id = 10;
监听变化:
m.pipe(map() => m.id);
let m = new Model();
m.id = 10;
const model$ = of(m);
model$.pipe(map()=> m.id);
您可以为您的 class 属性添加 getter 和 setter,在内部添加发射器,然后在 class 外部添加侦听器,这将侦听被发射的发射器
这是一个简单的例子。
https://stackblitz.com/edit/angular-ivy-kc9e4q
import { Component, OnInit, VERSION } from '@angular/core';
import {BehaviorSubject} from 'rxjs';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent implements OnInit {
model: Model;
ngOnInit() {
this.model.id$.subscribe(newid => {
// do something.
});
}
}
export class Model {
// @ts-ignore
private readonly _id = new BehaviorSubject<number>();
readonly id$ = this._id.asObservable();
// @ts-ignore
private readonly _name = new BehaviorSubject<string>();
readonly name$ = this._name.asObservable();
get id(): number {
return this._id.getValue();
}
set id(val) {
this._id.next(val);
}
get name(): number {
return this._name.getValue();
}
set name(val) {
this._name.next(val);
}
}
我的方法是将功能注入构造函数。我会避免在 class 中声明主题,因为它们很难自动整理。
您可以注入主题,但更简单的替代方法是注入回调。
在下面的测试 class 中,我允许每个 属性 注入一个回调。如果值已更改,则会在 属性 setter 中调用相关回调。
export class MyClass {
private _id: number;
private _name: string;
constructor(private callback?: {
id?: () => void,
name?: () => void
}) {}
get id(): number {
return this._id;
}
set id(value: number) {
if (value === this._id) {
return;
}
this._id = value;
if (this.callback && this.callback.id) {
this.callback.id();
}
}
get name(): string {
return this._name;
}
set name(value: string) {
if (value === this._name) {
return;
}
this._name = value;
if (this.callback && this.callback.name) {
this.callback.name();
}
}
}
然后从其他地方使用它就相当简单了。
myClass: MyClass = new MyClass({
id: () => this.onIdChange()
});
ngOnInit() {
this.myClass.id = 10;
this.myClass.name = 'Default'
}
private onIdChange() {
console.log(`id changed to ${this.myClass.id}`);
}
如果您确实需要,可以很简单地更改它以使用主题。然后调用代码将负责在适当的时候整理主题。
我有 class 具有属性:
export class Model {
public id: number;
public name: string;
}
如何使这个 class 可观察,以监听 m 属性的变化。
我需要这样的东西:
let m = new Model();
m.id = 10;
监听变化:
m.pipe(map() => m.id);
let m = new Model();
m.id = 10;
const model$ = of(m);
model$.pipe(map()=> m.id);
您可以为您的 class 属性添加 getter 和 setter,在内部添加发射器,然后在 class 外部添加侦听器,这将侦听被发射的发射器
这是一个简单的例子。
https://stackblitz.com/edit/angular-ivy-kc9e4q
import { Component, OnInit, VERSION } from '@angular/core';
import {BehaviorSubject} from 'rxjs';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent implements OnInit {
model: Model;
ngOnInit() {
this.model.id$.subscribe(newid => {
// do something.
});
}
}
export class Model {
// @ts-ignore
private readonly _id = new BehaviorSubject<number>();
readonly id$ = this._id.asObservable();
// @ts-ignore
private readonly _name = new BehaviorSubject<string>();
readonly name$ = this._name.asObservable();
get id(): number {
return this._id.getValue();
}
set id(val) {
this._id.next(val);
}
get name(): number {
return this._name.getValue();
}
set name(val) {
this._name.next(val);
}
}
我的方法是将功能注入构造函数。我会避免在 class 中声明主题,因为它们很难自动整理。
您可以注入主题,但更简单的替代方法是注入回调。
在下面的测试 class 中,我允许每个 属性 注入一个回调。如果值已更改,则会在 属性 setter 中调用相关回调。
export class MyClass {
private _id: number;
private _name: string;
constructor(private callback?: {
id?: () => void,
name?: () => void
}) {}
get id(): number {
return this._id;
}
set id(value: number) {
if (value === this._id) {
return;
}
this._id = value;
if (this.callback && this.callback.id) {
this.callback.id();
}
}
get name(): string {
return this._name;
}
set name(value: string) {
if (value === this._name) {
return;
}
this._name = value;
if (this.callback && this.callback.name) {
this.callback.name();
}
}
}
然后从其他地方使用它就相当简单了。
myClass: MyClass = new MyClass({
id: () => this.onIdChange()
});
ngOnInit() {
this.myClass.id = 10;
this.myClass.name = 'Default'
}
private onIdChange() {
console.log(`id changed to ${this.myClass.id}`);
}
如果您确实需要,可以很简单地更改它以使用主题。然后调用代码将负责在适当的时候整理主题。