-
Notifications
You must be signed in to change notification settings - Fork 5
/
Copy pathsubscriptions.model.ts
109 lines (87 loc) · 2.53 KB
/
subscriptions.model.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
import { ElementRef, Inject, OnDestroy } from '@angular/core';
import { SubscriptionLike } from 'rxjs';
export function make_subscription(subscription: Function): SubscriptionLike
{
return {
closed: false,
unsubscribe()
{
if (this.closed) return;
this.closed = true;
subscription();
},
};
}
export function aux_subscribe(widget: any, name: string,
_cb: any): SubscriptionLike
{
return make_subscription(widget.subscribe(name, (...args) => _cb(...args)));
}
export abstract class AuxSubscriptions implements OnDestroy
{
private last: {[name: string]: any}|null = null;
private subscriptions = new Map<string,SubscriptionLike>();
protected remove_binding(widget: any, name: string): void
{
}
protected abstract install_binding(widget: any, name: string, b: any)
: SubscriptionLike;
protected update(bindings: {[name: string]: any}|null)
{
const element = this.el.nativeElement;
const widget = element.auxWidget;
if (!widget)
{
if (element.tagName.startsWith('AUX-'))
{
throw new Error("The AUX WebComponent has not been upgraded, yet. "+
"Are you missing and import?");
}
throw new Error("The element is not an AUX WebComponent.");
}
const last = this.last || {};
const current = bindings || {};
for (let name in last)
{
// handled by loop below
if (name in current) continue;
// remove old subscriptions
let subscriptions = this.subscriptions.get(name);
if (subscriptions)
{
this.subscriptions.delete(name);
subscriptions.unsubscribe();
}
this.remove_binding(widget, name);
}
for (let name in current)
{
const value = current[name];
if (name in last)
{
const last_value = last[name];
if (last_value === value) continue;
// remove old subscriptions
const subscriptions = this.subscriptions.get(name);
if (subscriptions)
{
this.subscriptions.delete(name);
subscriptions.unsubscribe();
}
}
const subscription = this.install_binding(widget, name, value);
if (subscription)
{
this.subscriptions.set(name, subscription);
}
}
// we create a copy to make sure that our state is not
// modified
this.last = bindings ? Object.assign({}, bindings) : null;
}
constructor(@Inject(ElementRef) private el: ElementRef) { }
public ngOnDestroy()
{
this.update(null);
}
}