@microsoft/fast-element 2.9.1 → 2.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.json +58 -0
- package/CHANGELOG.md +22 -1
- package/dist/context/context.api.json +7 -7
- package/dist/di/di.api.json +12 -12
- package/dist/dts/binding/one-way.d.ts +1 -1
- package/dist/dts/binding/two-way.d.ts +3 -3
- package/dist/dts/components/attributes.d.ts +4 -4
- package/dist/dts/components/element-controller.d.ts +19 -8
- package/dist/dts/components/fast-definitions.d.ts +5 -5
- package/dist/dts/components/fast-element.d.ts +2 -2
- package/dist/dts/context.d.ts +8 -8
- package/dist/dts/di/di.d.ts +15 -15
- package/dist/dts/dom-policy.d.ts +8 -8
- package/dist/dts/dom.d.ts +2 -2
- package/dist/dts/index.d.ts +41 -28
- package/dist/dts/interfaces.d.ts +7 -7
- package/dist/dts/observable.d.ts +4 -2
- package/dist/dts/observation/arrays.d.ts +2 -2
- package/dist/dts/observation/observable.d.ts +3 -3
- package/dist/dts/observation/update-queue.d.ts +1 -1
- package/dist/dts/platform.d.ts +1 -1
- package/dist/dts/state/state.d.ts +10 -10
- package/dist/dts/state/watch.d.ts +1 -1
- package/dist/dts/styles/css-binding-directive.d.ts +2 -2
- package/dist/dts/styles/css-directive.d.ts +1 -1
- package/dist/dts/styles/css.d.ts +4 -4
- package/dist/dts/styles/element-styles.d.ts +2 -2
- package/dist/dts/templating/children.d.ts +2 -2
- package/dist/dts/templating/compiler.d.ts +3 -3
- package/dist/dts/templating/html-binding-directive.d.ts +3 -3
- package/dist/dts/templating/html-directive.d.ts +5 -5
- package/dist/dts/templating/node-observation.d.ts +2 -2
- package/dist/dts/templating/ref.d.ts +1 -1
- package/dist/dts/templating/render.d.ts +10 -10
- package/dist/dts/templating/repeat.d.ts +4 -4
- package/dist/dts/templating/slotted.d.ts +1 -1
- package/dist/dts/templating/template.d.ts +4 -4
- package/dist/dts/templating/view.d.ts +2 -2
- package/dist/esm/binding/one-way.js +1 -1
- package/dist/esm/binding/two-way.js +3 -3
- package/dist/esm/components/element-controller.js +152 -106
- package/dist/esm/components/fast-definitions.js +16 -16
- package/dist/esm/context.js +2 -2
- package/dist/esm/di/di.js +73 -63
- package/dist/esm/dom-policy.js +2 -2
- package/dist/esm/dom.js +2 -2
- package/dist/esm/index.js +21 -22
- package/dist/esm/interfaces.js +38 -0
- package/dist/esm/observable.js +1 -1
- package/dist/esm/observation/arrays.js +29 -22
- package/dist/esm/observation/observable.js +3 -3
- package/dist/esm/styles/css.js +2 -2
- package/dist/esm/styles/element-styles.js +9 -9
- package/dist/esm/templating/children.js +1 -1
- package/dist/esm/templating/compiler.js +5 -5
- package/dist/esm/templating/html-binding-directive.js +2 -2
- package/dist/esm/templating/node-observation.js +1 -1
- package/dist/esm/templating/render.js +4 -4
- package/dist/esm/templating/repeat.js +11 -11
- package/dist/esm/templating/slotted.js +1 -1
- package/dist/esm/templating/template.js +7 -7
- package/dist/esm/templating/view.js +9 -9
- package/dist/fast-element.api.json +96 -37
- package/dist/fast-element.d.ts +4 -4
- package/dist/fast-element.debug.js +2414 -2321
- package/dist/fast-element.debug.min.js +2 -2
- package/dist/fast-element.js +2414 -2321
- package/dist/fast-element.min.js +2 -2
- package/dist/fast-element.untrimmed.d.ts +17 -6
- package/docs/api-report.api.md +5 -4
- package/docs/di/api-report.api.md +4 -4
- package/karma.conf.cjs +13 -7
- package/package.json +6 -46
- package/playwright.config.ts +18 -0
- package/test/index.html +11 -0
- package/test/main.ts +10 -0
- package/test/vite.config.ts +19 -0
- package/dist/dts/observation/observable.bench.d.ts +0 -18
- package/dist/dts/templating/render.bench.d.ts +0 -3
- package/dist/dts/templating/repeat-basic-reverse.bench.d.ts +0 -3
- package/dist/dts/templating/repeat-basic-shift.bench.d.ts +0 -3
- package/dist/dts/templating/when-basic.bench.d.ts +0 -3
- package/dist/dts/templating/when-conditional.bench.d.ts +0 -3
- package/dist/dts/templating/when-switch.bench.d.ts +0 -3
- package/dist/esm/observation/observable.bench.js +0 -79
- package/dist/esm/templating/render.bench.js +0 -56
- package/dist/esm/templating/repeat-basic-reverse.bench.js +0 -43
- package/dist/esm/templating/repeat-basic-shift.bench.js +0 -43
- package/dist/esm/templating/when-basic.bench.js +0 -36
- package/dist/esm/templating/when-conditional.bench.js +0 -39
- package/dist/esm/templating/when-switch.bench.js +0 -68
- package/scripts/run-benchmarks.js +0 -46
- package/tensile.config.js +0 -12
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import "../interfaces.js";
|
|
1
|
+
import { Message } from "../interfaces.js";
|
|
2
2
|
import { PropertyChangeNotifier } from "../observation/notifier.js";
|
|
3
3
|
import { ExecutionContext, Observable, SourceLifetime, } from "../observation/observable.js";
|
|
4
4
|
import { FAST, makeSerializationNoop } from "../platform.js";
|
|
@@ -22,102 +22,33 @@ function getShadowRoot(element) {
|
|
|
22
22
|
return (_b = (_a = element.shadowRoot) !== null && _a !== void 0 ? _a : shadowRoots.get(element)) !== null && _b !== void 0 ? _b : null;
|
|
23
23
|
}
|
|
24
24
|
let elementControllerStrategy;
|
|
25
|
+
/**
|
|
26
|
+
* The various lifecycle stages of an ElementController.
|
|
27
|
+
* @public
|
|
28
|
+
*/
|
|
29
|
+
export var Stages;
|
|
30
|
+
(function (Stages) {
|
|
31
|
+
/** The element is in the process of connecting. */
|
|
32
|
+
Stages[Stages["connecting"] = 0] = "connecting";
|
|
33
|
+
/** The element is connected. */
|
|
34
|
+
Stages[Stages["connected"] = 1] = "connected";
|
|
35
|
+
/** The element is in the process of disconnecting. */
|
|
36
|
+
Stages[Stages["disconnecting"] = 2] = "disconnecting";
|
|
37
|
+
/** The element is disconnected. */
|
|
38
|
+
Stages[Stages["disconnected"] = 3] = "disconnected";
|
|
39
|
+
})(Stages || (Stages = {}));
|
|
25
40
|
/**
|
|
26
41
|
* Controls the lifecycle and rendering of a `FASTElement`.
|
|
27
42
|
* @public
|
|
28
43
|
*/
|
|
29
44
|
export class ElementController extends PropertyChangeNotifier {
|
|
30
|
-
/**
|
|
31
|
-
* Creates a Controller to control the specified element.
|
|
32
|
-
* @param element - The element to be controlled by this controller.
|
|
33
|
-
* @param definition - The element definition metadata that instructs this
|
|
34
|
-
* controller in how to handle rendering and other platform integrations.
|
|
35
|
-
* @internal
|
|
36
|
-
*/
|
|
37
|
-
constructor(element, definition) {
|
|
38
|
-
super(element);
|
|
39
|
-
/**
|
|
40
|
-
* A map of observable properties that were set on the element before upgrade.
|
|
41
|
-
*/
|
|
42
|
-
this.boundObservables = null;
|
|
43
|
-
/**
|
|
44
|
-
* Indicates whether the controller needs to perform initial rendering.
|
|
45
|
-
*/
|
|
46
|
-
this.needsInitialization = true;
|
|
47
|
-
/**
|
|
48
|
-
* Indicates whether the element has an existing shadow root (e.g. from declarative shadow DOM).
|
|
49
|
-
*/
|
|
50
|
-
this.hasExistingShadowRoot = false;
|
|
51
|
-
/**
|
|
52
|
-
* The template used to render the component.
|
|
53
|
-
*/
|
|
54
|
-
this._template = null;
|
|
55
|
-
/**
|
|
56
|
-
* The current lifecycle stage of the controller.
|
|
57
|
-
*/
|
|
58
|
-
this.stage = 3 /* Stages.disconnected */;
|
|
59
|
-
/**
|
|
60
|
-
* A guard against connecting behaviors multiple times
|
|
61
|
-
* during connect in scenarios where a behavior adds
|
|
62
|
-
* another behavior during it's connectedCallback
|
|
63
|
-
*/
|
|
64
|
-
this.guardBehaviorConnection = false;
|
|
65
|
-
/**
|
|
66
|
-
* The behaviors associated with the component.
|
|
67
|
-
*/
|
|
68
|
-
this.behaviors = null;
|
|
69
|
-
/**
|
|
70
|
-
* Tracks whether behaviors are connected so that
|
|
71
|
-
* behaviors cant be connected multiple times
|
|
72
|
-
*/
|
|
73
|
-
this.behaviorsConnected = false;
|
|
74
|
-
/**
|
|
75
|
-
* The main set of styles used for the component, independent of any
|
|
76
|
-
* dynamically added styles.
|
|
77
|
-
*/
|
|
78
|
-
this._mainStyles = null;
|
|
79
|
-
/**
|
|
80
|
-
* This allows Observable.getNotifier(...) to return the Controller
|
|
81
|
-
* when the notifier for the Controller itself is being requested. The
|
|
82
|
-
* result is that the Observable system does not need to create a separate
|
|
83
|
-
* instance of Notifier for observables on the Controller. The component and
|
|
84
|
-
* the controller will now share the same notifier, removing one-object construct
|
|
85
|
-
* per web component instance.
|
|
86
|
-
*/
|
|
87
|
-
this.$fastController = this;
|
|
88
|
-
/**
|
|
89
|
-
* The view associated with the custom element.
|
|
90
|
-
* @remarks
|
|
91
|
-
* If `null` then the element is managing its own rendering.
|
|
92
|
-
*/
|
|
93
|
-
this.view = null;
|
|
94
|
-
this.source = element;
|
|
95
|
-
this.definition = definition;
|
|
96
|
-
this.shadowOptions = definition.shadowOptions;
|
|
97
|
-
// Capture any observable values that were set by the binding engine before
|
|
98
|
-
// the browser upgraded the element. Then delete the property since it will
|
|
99
|
-
// shadow the getter/setter that is required to make the observable operate.
|
|
100
|
-
// Later, in the connect callback, we'll re-apply the values.
|
|
101
|
-
const accessors = Observable.getAccessors(element);
|
|
102
|
-
if (accessors.length > 0) {
|
|
103
|
-
const boundObservables = (this.boundObservables = Object.create(null));
|
|
104
|
-
for (let i = 0, ii = accessors.length; i < ii; ++i) {
|
|
105
|
-
const propertyName = accessors[i].name;
|
|
106
|
-
const value = element[propertyName];
|
|
107
|
-
if (value !== void 0) {
|
|
108
|
-
delete element[propertyName];
|
|
109
|
-
boundObservables[propertyName] = value;
|
|
110
|
-
}
|
|
111
|
-
}
|
|
112
|
-
}
|
|
113
|
-
}
|
|
114
45
|
/**
|
|
115
46
|
* Indicates whether or not the custom element has been
|
|
116
47
|
* connected to the document.
|
|
117
48
|
*/
|
|
118
49
|
get isConnected() {
|
|
119
50
|
Observable.track(this, isConnectedPropertyName);
|
|
120
|
-
return this.stage ===
|
|
51
|
+
return this.stage === Stages.connected;
|
|
121
52
|
}
|
|
122
53
|
/**
|
|
123
54
|
* The context the expression is evaluated against.
|
|
@@ -224,6 +155,90 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
224
155
|
this.addStyles(value);
|
|
225
156
|
}
|
|
226
157
|
}
|
|
158
|
+
/**
|
|
159
|
+
* Creates a Controller to control the specified element.
|
|
160
|
+
* @param element - The element to be controlled by this controller.
|
|
161
|
+
* @param definition - The element definition metadata that instructs this
|
|
162
|
+
* controller in how to handle rendering and other platform integrations.
|
|
163
|
+
* @internal
|
|
164
|
+
*/
|
|
165
|
+
constructor(element, definition) {
|
|
166
|
+
super(element);
|
|
167
|
+
/**
|
|
168
|
+
* A map of observable properties that were set on the element before upgrade.
|
|
169
|
+
*/
|
|
170
|
+
this.boundObservables = null;
|
|
171
|
+
/**
|
|
172
|
+
* Indicates whether the controller needs to perform initial rendering.
|
|
173
|
+
*/
|
|
174
|
+
this.needsInitialization = true;
|
|
175
|
+
/**
|
|
176
|
+
* Indicates whether the element has an existing shadow root (e.g. from declarative shadow DOM).
|
|
177
|
+
*/
|
|
178
|
+
this.hasExistingShadowRoot = false;
|
|
179
|
+
/**
|
|
180
|
+
* The template used to render the component.
|
|
181
|
+
*/
|
|
182
|
+
this._template = null;
|
|
183
|
+
/**
|
|
184
|
+
* The current lifecycle stage of the controller.
|
|
185
|
+
*/
|
|
186
|
+
this.stage = Stages.disconnected;
|
|
187
|
+
/**
|
|
188
|
+
* A guard against connecting behaviors multiple times
|
|
189
|
+
* during connect in scenarios where a behavior adds
|
|
190
|
+
* another behavior during it's connectedCallback
|
|
191
|
+
*/
|
|
192
|
+
this.guardBehaviorConnection = false;
|
|
193
|
+
/**
|
|
194
|
+
* The behaviors associated with the component.
|
|
195
|
+
*/
|
|
196
|
+
this.behaviors = null;
|
|
197
|
+
/**
|
|
198
|
+
* Tracks whether behaviors are connected so that
|
|
199
|
+
* behaviors cant be connected multiple times
|
|
200
|
+
*/
|
|
201
|
+
this.behaviorsConnected = false;
|
|
202
|
+
/**
|
|
203
|
+
* The main set of styles used for the component, independent of any
|
|
204
|
+
* dynamically added styles.
|
|
205
|
+
*/
|
|
206
|
+
this._mainStyles = null;
|
|
207
|
+
/**
|
|
208
|
+
* This allows Observable.getNotifier(...) to return the Controller
|
|
209
|
+
* when the notifier for the Controller itself is being requested. The
|
|
210
|
+
* result is that the Observable system does not need to create a separate
|
|
211
|
+
* instance of Notifier for observables on the Controller. The component and
|
|
212
|
+
* the controller will now share the same notifier, removing one-object construct
|
|
213
|
+
* per web component instance.
|
|
214
|
+
*/
|
|
215
|
+
this.$fastController = this;
|
|
216
|
+
/**
|
|
217
|
+
* The view associated with the custom element.
|
|
218
|
+
* @remarks
|
|
219
|
+
* If `null` then the element is managing its own rendering.
|
|
220
|
+
*/
|
|
221
|
+
this.view = null;
|
|
222
|
+
this.source = element;
|
|
223
|
+
this.definition = definition;
|
|
224
|
+
this.shadowOptions = definition.shadowOptions;
|
|
225
|
+
// Capture any observable values that were set by the binding engine before
|
|
226
|
+
// the browser upgraded the element. Then delete the property since it will
|
|
227
|
+
// shadow the getter/setter that is required to make the observable operate.
|
|
228
|
+
// Later, in the connect callback, we'll re-apply the values.
|
|
229
|
+
const accessors = Observable.getAccessors(element);
|
|
230
|
+
if (accessors.length > 0) {
|
|
231
|
+
const boundObservables = (this.boundObservables = Object.create(null));
|
|
232
|
+
for (let i = 0, ii = accessors.length; i < ii; ++i) {
|
|
233
|
+
const propertyName = accessors[i].name;
|
|
234
|
+
const value = element[propertyName];
|
|
235
|
+
if (value !== void 0) {
|
|
236
|
+
delete element[propertyName];
|
|
237
|
+
boundObservables[propertyName] = value;
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
}
|
|
227
242
|
/**
|
|
228
243
|
* Registers an unbind handler with the controller.
|
|
229
244
|
* @param behavior - An object to call when the controller unbinds.
|
|
@@ -245,7 +260,7 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
245
260
|
behavior.addedCallback && behavior.addedCallback(this);
|
|
246
261
|
if (behavior.connectedCallback &&
|
|
247
262
|
!this.guardBehaviorConnection &&
|
|
248
|
-
(this.stage ===
|
|
263
|
+
(this.stage === Stages.connected || this.stage === Stages.connecting)) {
|
|
249
264
|
behavior.connectedCallback(this);
|
|
250
265
|
}
|
|
251
266
|
}
|
|
@@ -269,7 +284,7 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
269
284
|
}
|
|
270
285
|
if (count === 1 || force) {
|
|
271
286
|
targetBehaviors.delete(behavior);
|
|
272
|
-
if (behavior.disconnectedCallback && this.stage !==
|
|
287
|
+
if (behavior.disconnectedCallback && this.stage !== Stages.disconnected) {
|
|
273
288
|
behavior.disconnectedCallback(this);
|
|
274
289
|
}
|
|
275
290
|
behavior.removedCallback && behavior.removedCallback(this);
|
|
@@ -330,10 +345,10 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
330
345
|
* Runs connected lifecycle behavior on the associated element.
|
|
331
346
|
*/
|
|
332
347
|
connect() {
|
|
333
|
-
if (this.stage !==
|
|
348
|
+
if (this.stage !== Stages.disconnected) {
|
|
334
349
|
return;
|
|
335
350
|
}
|
|
336
|
-
this.stage =
|
|
351
|
+
this.stage = Stages.connecting;
|
|
337
352
|
this.bindObservables();
|
|
338
353
|
this.connectBehaviors();
|
|
339
354
|
if (this.needsInitialization) {
|
|
@@ -344,7 +359,7 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
344
359
|
else if (this.view !== null) {
|
|
345
360
|
this.view.bind(this.source);
|
|
346
361
|
}
|
|
347
|
-
this.stage =
|
|
362
|
+
this.stage = Stages.connected;
|
|
348
363
|
Observable.notify(this, isConnectedPropertyName);
|
|
349
364
|
}
|
|
350
365
|
/**
|
|
@@ -396,16 +411,16 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
396
411
|
* Runs disconnected lifecycle behavior on the associated element.
|
|
397
412
|
*/
|
|
398
413
|
disconnect() {
|
|
399
|
-
if (this.stage !==
|
|
414
|
+
if (this.stage !== Stages.connected) {
|
|
400
415
|
return;
|
|
401
416
|
}
|
|
402
|
-
this.stage =
|
|
417
|
+
this.stage = Stages.disconnecting;
|
|
403
418
|
Observable.notify(this, isConnectedPropertyName);
|
|
404
419
|
if (this.view !== null) {
|
|
405
420
|
this.view.unbind();
|
|
406
421
|
}
|
|
407
422
|
this.disconnectBehaviors();
|
|
408
|
-
this.stage =
|
|
423
|
+
this.stage = Stages.disconnected;
|
|
409
424
|
}
|
|
410
425
|
/**
|
|
411
426
|
* Runs the attribute changed callback for the associated element.
|
|
@@ -428,7 +443,7 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
428
443
|
* Only emits events if connected.
|
|
429
444
|
*/
|
|
430
445
|
emit(type, detail, options) {
|
|
431
|
-
if (this.stage ===
|
|
446
|
+
if (this.stage === Stages.connected) {
|
|
432
447
|
return this.source.dispatchEvent(new CustomEvent(type, Object.assign(Object.assign({ detail }, defaultEventOptions), options)));
|
|
433
448
|
}
|
|
434
449
|
return false;
|
|
@@ -482,7 +497,7 @@ export class ElementController extends PropertyChangeNotifier {
|
|
|
482
497
|
}
|
|
483
498
|
const definition = FASTElementDefinition.getForInstance(element);
|
|
484
499
|
if (definition === void 0) {
|
|
485
|
-
throw FAST.error(
|
|
500
|
+
throw FAST.error(Message.missingElementDefinition);
|
|
486
501
|
}
|
|
487
502
|
Observable.getNotifier(definition).subscribe({
|
|
488
503
|
handleChange: () => {
|
|
@@ -698,7 +713,12 @@ export class HydratableElementController extends ElementController {
|
|
|
698
713
|
}
|
|
699
714
|
// If there are no more hydrating instances, invoke the hydrationComplete callback
|
|
700
715
|
if (((_a = HydratableElementController.hydratingInstances) === null || _a === void 0 ? void 0 : _a.size) === 0) {
|
|
701
|
-
|
|
716
|
+
try {
|
|
717
|
+
(_c = (_b = HydratableElementController.lifecycleCallbacks).hydrationComplete) === null || _c === void 0 ? void 0 : _c.call(_b);
|
|
718
|
+
}
|
|
719
|
+
catch (_d) {
|
|
720
|
+
// A lifecycle callback must never prevent post-hydration cleanup.
|
|
721
|
+
}
|
|
702
722
|
// Reset to the default strategy after hydration is complete
|
|
703
723
|
ElementController.setStrategy(ElementController);
|
|
704
724
|
}
|
|
@@ -707,7 +727,7 @@ export class HydratableElementController extends ElementController {
|
|
|
707
727
|
* Runs connected lifecycle behavior on the associated element.
|
|
708
728
|
*/
|
|
709
729
|
connect() {
|
|
710
|
-
var _a, _b, _c, _d, _e;
|
|
730
|
+
var _a, _b, _c, _d, _e, _f, _g;
|
|
711
731
|
// Initialize needsHydration on first connect
|
|
712
732
|
this.needsHydration =
|
|
713
733
|
(_a = this.needsHydration) !== null && _a !== void 0 ? _a : this.source.hasAttribute(needsHydrationAttribute);
|
|
@@ -729,17 +749,31 @@ export class HydratableElementController extends ElementController {
|
|
|
729
749
|
this.removeHydratingInstance();
|
|
730
750
|
return;
|
|
731
751
|
}
|
|
732
|
-
if (this.stage !==
|
|
752
|
+
if (this.stage !== Stages.disconnected) {
|
|
733
753
|
return;
|
|
734
754
|
}
|
|
735
|
-
|
|
736
|
-
|
|
755
|
+
if (!HydratableElementController.hydrationStarted) {
|
|
756
|
+
HydratableElementController.hydrationStarted = true;
|
|
757
|
+
try {
|
|
758
|
+
(_c = (_b = HydratableElementController.lifecycleCallbacks).hydrationStarted) === null || _c === void 0 ? void 0 : _c.call(_b);
|
|
759
|
+
}
|
|
760
|
+
catch (_h) {
|
|
761
|
+
// A lifecycle callback must never prevent hydration.
|
|
762
|
+
}
|
|
763
|
+
}
|
|
764
|
+
try {
|
|
765
|
+
(_e = (_d = HydratableElementController.lifecycleCallbacks).elementWillHydrate) === null || _e === void 0 ? void 0 : _e.call(_d, this.source);
|
|
766
|
+
}
|
|
767
|
+
catch (_j) {
|
|
768
|
+
// A lifecycle callback must never prevent hydration.
|
|
769
|
+
}
|
|
770
|
+
this.stage = Stages.connecting;
|
|
737
771
|
this.bindObservables();
|
|
738
772
|
this.connectBehaviors();
|
|
739
773
|
if (this.template) {
|
|
740
774
|
if (isHydratable(this.template)) {
|
|
741
775
|
const element = this.source;
|
|
742
|
-
const host = (
|
|
776
|
+
const host = (_f = getShadowRoot(element)) !== null && _f !== void 0 ? _f : element;
|
|
743
777
|
let firstChild = host.firstChild;
|
|
744
778
|
let lastChild = host.lastChild;
|
|
745
779
|
if (element.shadowRoot === null) {
|
|
@@ -754,14 +788,14 @@ export class HydratableElementController extends ElementController {
|
|
|
754
788
|
}
|
|
755
789
|
}
|
|
756
790
|
this.view = this.template.hydrate(firstChild, lastChild, element);
|
|
757
|
-
(
|
|
791
|
+
(_g = this.view) === null || _g === void 0 ? void 0 : _g.bind(this.source);
|
|
758
792
|
}
|
|
759
793
|
else {
|
|
760
794
|
this.renderTemplate(this.template);
|
|
761
795
|
}
|
|
762
796
|
}
|
|
763
797
|
this.addStyles(this.mainStyles);
|
|
764
|
-
this.stage =
|
|
798
|
+
this.stage = Stages.connected;
|
|
765
799
|
this.source.removeAttribute(needsHydrationAttribute);
|
|
766
800
|
this.needsInitialization = this.needsHydration = false;
|
|
767
801
|
this.removeHydratingInstance();
|
|
@@ -775,10 +809,14 @@ export class HydratableElementController extends ElementController {
|
|
|
775
809
|
if (!HydratableElementController.hydratingInstances) {
|
|
776
810
|
return;
|
|
777
811
|
}
|
|
812
|
+
try {
|
|
813
|
+
(_b = (_a = HydratableElementController.lifecycleCallbacks).elementDidHydrate) === null || _b === void 0 ? void 0 : _b.call(_a, this.source);
|
|
814
|
+
}
|
|
815
|
+
catch (_c) {
|
|
816
|
+
// A lifecycle callback must never prevent hydration.
|
|
817
|
+
}
|
|
778
818
|
const name = this.definition.name;
|
|
779
819
|
const instances = HydratableElementController.hydratingInstances.get(name);
|
|
780
|
-
// Callback: After hydration has finished
|
|
781
|
-
(_b = (_a = HydratableElementController.lifecycleCallbacks) === null || _a === void 0 ? void 0 : _a.elementDidHydrate) === null || _b === void 0 ? void 0 : _b.call(_a, this.definition.name);
|
|
782
820
|
if (instances) {
|
|
783
821
|
instances.delete(this.source);
|
|
784
822
|
if (!instances.size) {
|
|
@@ -808,6 +846,14 @@ export class HydratableElementController extends ElementController {
|
|
|
808
846
|
}
|
|
809
847
|
}
|
|
810
848
|
HydratableElementController.hydrationObserver = new UnobservableMutationObserver(HydratableElementController.hydrationObserverHandler);
|
|
849
|
+
/**
|
|
850
|
+
* Lifecycle callbacks for hydration events
|
|
851
|
+
*/
|
|
852
|
+
HydratableElementController.lifecycleCallbacks = {};
|
|
853
|
+
/**
|
|
854
|
+
* Whether the hydrationStarted callback has already been invoked.
|
|
855
|
+
*/
|
|
856
|
+
HydratableElementController.hydrationStarted = false;
|
|
811
857
|
/**
|
|
812
858
|
* An idle callback ID used to track hydration completion
|
|
813
859
|
*/
|
|
@@ -12,7 +12,7 @@ import { isString, KernelServiceId } from "../interfaces.js";
|
|
|
12
12
|
import { Observable } from "../observation/observable.js";
|
|
13
13
|
import { createTypeRegistry, FAST } from "../platform.js";
|
|
14
14
|
import { ElementStyles } from "../styles/element-styles.js";
|
|
15
|
-
import { AttributeDefinition } from "./attributes.js";
|
|
15
|
+
import { AttributeConfiguration, AttributeDefinition } from "./attributes.js";
|
|
16
16
|
const defaultShadowOptions = { mode: "open" };
|
|
17
17
|
const defaultElementOptions = {};
|
|
18
18
|
const fastElementBaseTypes = new Set();
|
|
@@ -33,6 +33,12 @@ export const TemplateOptions = {
|
|
|
33
33
|
* @public
|
|
34
34
|
*/
|
|
35
35
|
export class FASTElementDefinition {
|
|
36
|
+
/**
|
|
37
|
+
* Indicates if this element has been defined in at least one registry.
|
|
38
|
+
*/
|
|
39
|
+
get isDefined() {
|
|
40
|
+
return this.platformDefined;
|
|
41
|
+
}
|
|
36
42
|
constructor(type, nameOrConfig = type.definition) {
|
|
37
43
|
var _b;
|
|
38
44
|
this.platformDefined = false;
|
|
@@ -75,14 +81,8 @@ export class FASTElementDefinition {
|
|
|
75
81
|
: Object.assign(Object.assign({}, defaultElementOptions), nameOrConfig.elementOptions);
|
|
76
82
|
this.styles = ElementStyles.normalize(nameOrConfig.styles);
|
|
77
83
|
fastElementRegistry.register(this);
|
|
78
|
-
Observable.defineProperty(
|
|
79
|
-
|
|
80
|
-
}
|
|
81
|
-
/**
|
|
82
|
-
* Indicates if this element has been defined in at least one registry.
|
|
83
|
-
*/
|
|
84
|
-
get isDefined() {
|
|
85
|
-
return this.platformDefined;
|
|
84
|
+
Observable.defineProperty(_a.isRegistered, this.name);
|
|
85
|
+
_a.isRegistered[this.name] = this.type;
|
|
86
86
|
}
|
|
87
87
|
/**
|
|
88
88
|
* Defines a custom element based on this definition.
|
|
@@ -108,10 +108,10 @@ export class FASTElementDefinition {
|
|
|
108
108
|
*/
|
|
109
109
|
static compose(type, nameOrDef) {
|
|
110
110
|
if (fastElementBaseTypes.has(type) || fastElementRegistry.getByType(type)) {
|
|
111
|
-
return new
|
|
111
|
+
return new _a(class extends type {
|
|
112
112
|
}, nameOrDef);
|
|
113
113
|
}
|
|
114
|
-
return new
|
|
114
|
+
return new _a(type, nameOrDef);
|
|
115
115
|
}
|
|
116
116
|
/**
|
|
117
117
|
* Registers a FASTElement base type.
|
|
@@ -133,10 +133,10 @@ export class FASTElementDefinition {
|
|
|
133
133
|
static composeAsync(type, nameOrDef) {
|
|
134
134
|
return new Promise(resolve => {
|
|
135
135
|
if (fastElementBaseTypes.has(type) || fastElementRegistry.getByType(type)) {
|
|
136
|
-
resolve(new
|
|
136
|
+
resolve(new _a(class extends type {
|
|
137
137
|
}, nameOrDef));
|
|
138
138
|
}
|
|
139
|
-
const definition = new
|
|
139
|
+
const definition = new _a(type, nameOrDef);
|
|
140
140
|
Observable.getNotifier(definition).subscribe({
|
|
141
141
|
handleChange: () => {
|
|
142
142
|
var _b, _c;
|
|
@@ -169,10 +169,10 @@ FASTElementDefinition.getForInstance = fastElementRegistry.getForInstance;
|
|
|
169
169
|
*/
|
|
170
170
|
FASTElementDefinition.registerAsync = (name) => __awaiter(void 0, void 0, void 0, function* () {
|
|
171
171
|
return new Promise(resolve => {
|
|
172
|
-
if (
|
|
173
|
-
resolve(
|
|
172
|
+
if (_a.isRegistered[name]) {
|
|
173
|
+
resolve(_a.isRegistered[name]);
|
|
174
174
|
}
|
|
175
|
-
Observable.getNotifier(
|
|
175
|
+
Observable.getNotifier(_a.isRegistered).subscribe({ handleChange: () => resolve(_a.isRegistered[name]) }, name);
|
|
176
176
|
});
|
|
177
177
|
});
|
|
178
178
|
Observable.defineProperty(FASTElementDefinition.prototype, "template");
|
package/dist/esm/context.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import "./interfaces.js";
|
|
1
|
+
import { Message } from "./interfaces.js";
|
|
2
2
|
import { Metadata } from "./metadata.js";
|
|
3
3
|
import { FAST } from "./platform.js";
|
|
4
4
|
const contextsByName = new Map();
|
|
@@ -37,7 +37,7 @@ export const Context = Object.freeze({
|
|
|
37
37
|
create(name, initialValue) {
|
|
38
38
|
const Interface = function (target, property, index) {
|
|
39
39
|
if (target == null || new.target !== undefined) {
|
|
40
|
-
throw FAST.error(
|
|
40
|
+
throw FAST.error(Message.noRegistrationForContext, {
|
|
41
41
|
name: Interface.name,
|
|
42
42
|
});
|
|
43
43
|
}
|