@microsoft/fast-element 2.10.4 → 3.0.0-rc.2

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.
Files changed (211) hide show
  1. package/CHANGELOG.md +52 -2
  2. package/README.md +244 -1
  3. package/dist/arrays/arrays.api.json +2621 -0
  4. package/dist/context/context.api.json +13 -13
  5. package/dist/declarative/declarative.api.json +8483 -0
  6. package/dist/di/di.api.json +16 -16
  7. package/dist/dts/__test__/helpers.d.ts +6 -0
  8. package/dist/dts/array-observer.d.ts +2 -0
  9. package/dist/dts/arrays.d.ts +2 -0
  10. package/dist/dts/attr.d.ts +1 -0
  11. package/dist/dts/binding/binding.d.ts +15 -5
  12. package/dist/dts/binding/one-time.d.ts +1 -1
  13. package/dist/dts/binding/one-way.d.ts +1 -1
  14. package/dist/dts/binding/signal.d.ts +6 -6
  15. package/dist/dts/binding/two-way.d.ts +2 -1
  16. package/dist/dts/binding.d.ts +7 -0
  17. package/dist/dts/components/attributes.d.ts +1 -4
  18. package/dist/dts/components/definition-schema-transforms.d.ts +9 -0
  19. package/dist/dts/components/element-controller.d.ts +80 -114
  20. package/dist/dts/components/element-hydration.d.ts +1 -1
  21. package/dist/dts/components/enable-hydration.d.ts +54 -0
  22. package/dist/dts/components/fast-definitions.d.ts +98 -46
  23. package/dist/dts/components/fast-element.d.ts +43 -16
  24. package/dist/dts/components/hydration-tracker.d.ts +83 -0
  25. package/dist/dts/components/hydration.d.ts +23 -53
  26. package/dist/dts/components/schema.d.ts +205 -0
  27. package/dist/dts/context.d.ts +13 -13
  28. package/dist/dts/css.d.ts +3 -0
  29. package/dist/dts/debug.d.ts +5 -1
  30. package/dist/dts/declarative/attribute-map.d.ts +58 -0
  31. package/dist/dts/declarative/debug.d.ts +4 -0
  32. package/dist/dts/declarative/index.d.ts +14 -0
  33. package/dist/dts/declarative/interfaces.d.ts +8 -0
  34. package/dist/dts/declarative/observer-map-utilities.d.ts +58 -0
  35. package/dist/dts/declarative/observer-map.d.ts +89 -0
  36. package/dist/dts/declarative/runtime.d.ts +5 -0
  37. package/dist/dts/declarative/syntax.d.ts +21 -0
  38. package/dist/dts/declarative/template-bridge.d.ts +33 -0
  39. package/dist/dts/declarative/template-parser.d.ts +98 -0
  40. package/dist/dts/declarative/template.d.ts +10 -0
  41. package/dist/dts/declarative/utilities.d.ts +358 -0
  42. package/dist/dts/di/di.d.ts +7 -7
  43. package/dist/dts/directives/children.d.ts +2 -0
  44. package/dist/dts/directives/node-observation.d.ts +2 -0
  45. package/dist/dts/directives/ref.d.ts +2 -0
  46. package/dist/dts/directives/repeat.d.ts +4 -0
  47. package/dist/dts/directives/slotted.d.ts +2 -0
  48. package/dist/dts/directives/when.d.ts +3 -0
  49. package/dist/dts/dom-policy.d.ts +23 -5
  50. package/dist/dts/dom.d.ts +4 -16
  51. package/dist/dts/html.d.ts +5 -0
  52. package/dist/dts/hydration/diagnostics.d.ts +93 -0
  53. package/dist/dts/hydration/hydration-debugger.d.ts +35 -0
  54. package/dist/dts/hydration/messages.d.ts +62 -0
  55. package/dist/dts/hydration/runtime.d.ts +7 -0
  56. package/dist/dts/hydration/target-builder.d.ts +40 -12
  57. package/dist/dts/hydration.d.ts +18 -0
  58. package/dist/dts/index.d.ts +42 -42
  59. package/dist/dts/index.debug.d.ts +0 -1
  60. package/dist/dts/index.rollup.debug.d.ts +0 -1
  61. package/dist/dts/interfaces.d.ts +2 -49
  62. package/dist/dts/observable.d.ts +3 -6
  63. package/dist/dts/observation/arrays.d.ts +1 -1
  64. package/dist/dts/observation/observable.d.ts +3 -3
  65. package/dist/dts/observation/update-queue.d.ts +1 -1
  66. package/dist/dts/platform.d.ts +45 -8
  67. package/dist/dts/registry.d.ts +1 -0
  68. package/dist/dts/render.d.ts +7 -0
  69. package/dist/dts/schema.d.ts +1 -0
  70. package/dist/dts/state/exports.d.ts +1 -1
  71. package/dist/dts/state/state.d.ts +2 -2
  72. package/dist/dts/styles/css-directive.d.ts +5 -12
  73. package/dist/dts/styles/css.d.ts +5 -7
  74. package/dist/dts/styles/element-styles.d.ts +0 -10
  75. package/dist/dts/styles.d.ts +6 -0
  76. package/dist/dts/templating/compiler.d.ts +1 -1
  77. package/dist/dts/templating/html-binding-directive.d.ts +10 -2
  78. package/dist/dts/templating/html-directive.d.ts +19 -1
  79. package/dist/dts/templating/hydration-view.d.ts +130 -0
  80. package/dist/dts/templating/render.d.ts +1 -1
  81. package/dist/dts/templating/repeat.d.ts +1 -1
  82. package/dist/dts/templating/template.d.ts +15 -7
  83. package/dist/dts/templating/view.d.ts +25 -102
  84. package/dist/dts/templating.d.ts +10 -0
  85. package/dist/dts/testing/exports.d.ts +2 -2
  86. package/dist/dts/testing/fakes.d.ts +4 -4
  87. package/dist/dts/updates.d.ts +1 -0
  88. package/dist/dts/volatile.d.ts +2 -0
  89. package/dist/esm/__test__/helpers.js +22 -0
  90. package/dist/esm/__test__/setup-node.js +18 -0
  91. package/dist/esm/array-observer.js +1 -0
  92. package/dist/esm/arrays.js +1 -0
  93. package/dist/esm/attr.js +1 -0
  94. package/dist/esm/binding/normalize.js +1 -1
  95. package/dist/esm/binding/signal.js +4 -4
  96. package/dist/esm/binding/two-way.js +3 -3
  97. package/dist/esm/binding.js +4 -0
  98. package/dist/esm/components/attributes.js +18 -11
  99. package/dist/esm/components/definition-schema-transforms.js +23 -0
  100. package/dist/esm/components/element-controller.js +206 -270
  101. package/dist/esm/components/element-hydration.js +1 -1
  102. package/dist/esm/components/enable-hydration.js +124 -0
  103. package/dist/esm/components/fast-definitions.js +219 -56
  104. package/dist/esm/components/fast-element.js +18 -27
  105. package/dist/esm/components/hydration-tracker.js +122 -0
  106. package/dist/esm/components/hydration.js +137 -140
  107. package/dist/esm/components/schema.js +253 -0
  108. package/dist/esm/context.js +6 -6
  109. package/dist/esm/css.js +3 -0
  110. package/dist/esm/debug.js +27 -26
  111. package/dist/esm/declarative/attribute-map.js +122 -0
  112. package/dist/esm/declarative/debug.js +4 -0
  113. package/dist/esm/declarative/index.js +4 -0
  114. package/dist/esm/declarative/interfaces.js +9 -0
  115. package/dist/esm/declarative/observer-map-utilities.js +565 -0
  116. package/dist/esm/declarative/observer-map.js +216 -0
  117. package/dist/esm/declarative/runtime.js +14 -0
  118. package/dist/esm/declarative/syntax.js +36 -0
  119. package/dist/esm/declarative/template-bridge.js +160 -0
  120. package/dist/esm/declarative/template-parser.js +306 -0
  121. package/dist/esm/declarative/template.js +143 -0
  122. package/dist/esm/declarative/utilities.js +1069 -0
  123. package/dist/esm/di/di.js +8 -9
  124. package/dist/esm/directives/children.js +1 -0
  125. package/dist/esm/directives/node-observation.js +1 -0
  126. package/dist/esm/directives/ref.js +1 -0
  127. package/dist/esm/directives/repeat.js +1 -0
  128. package/dist/esm/directives/slotted.js +1 -0
  129. package/dist/esm/directives/when.js +1 -0
  130. package/dist/esm/dom-policy.js +35 -6
  131. package/dist/esm/dom.js +1 -1
  132. package/dist/esm/html.js +2 -0
  133. package/dist/esm/hydration/diagnostics.js +50 -0
  134. package/dist/esm/hydration/hydration-debugger.js +112 -0
  135. package/dist/esm/hydration/messages.js +84 -0
  136. package/dist/esm/hydration/runtime.js +33 -0
  137. package/dist/esm/hydration/target-builder.js +144 -91
  138. package/dist/esm/hydration.js +6 -0
  139. package/dist/esm/index.debug.js +2 -1
  140. package/dist/esm/index.js +38 -29
  141. package/dist/esm/index.rollup.debug.js +3 -2
  142. package/dist/esm/index.rollup.js +1 -1
  143. package/dist/esm/interfaces.js +2 -45
  144. package/dist/esm/metadata.js +2 -8
  145. package/dist/esm/observable.js +1 -4
  146. package/dist/esm/observation/arrays.js +1 -1
  147. package/dist/esm/observation/notifier.js +2 -4
  148. package/dist/esm/observation/observable.js +5 -5
  149. package/dist/esm/observation/update-queue.js +47 -58
  150. package/dist/esm/platform.js +31 -30
  151. package/dist/esm/registry.js +1 -0
  152. package/dist/esm/render.js +1 -0
  153. package/dist/esm/schema.js +1 -0
  154. package/dist/esm/state/exports.js +1 -1
  155. package/dist/esm/styles/css-directive.js +1 -2
  156. package/dist/esm/styles/css.js +15 -56
  157. package/dist/esm/styles/element-styles.js +69 -15
  158. package/dist/esm/styles.js +2 -0
  159. package/dist/esm/templating/html-binding-directive.js +11 -9
  160. package/dist/esm/templating/hydration-view.js +228 -0
  161. package/dist/esm/templating/render.js +39 -18
  162. package/dist/esm/templating/repeat.js +69 -33
  163. package/dist/esm/templating/template.js +7 -7
  164. package/dist/esm/templating/view.js +25 -234
  165. package/dist/esm/templating.js +7 -0
  166. package/dist/esm/testing/exports.js +2 -2
  167. package/dist/esm/testing/fixture.js +2 -2
  168. package/dist/esm/testing/timeout.js +2 -2
  169. package/dist/esm/updates.js +1 -0
  170. package/dist/esm/volatile.js +1 -0
  171. package/dist/fast-element.api.json +14389 -11138
  172. package/dist/fast-element.d.ts +3651 -809
  173. package/dist/fast-element.debug.js +5666 -4722
  174. package/dist/fast-element.debug.min.js +2 -2
  175. package/dist/fast-element.js +5394 -4381
  176. package/dist/fast-element.min.js +2 -2
  177. package/dist/fast-element.untrimmed.d.ts +923 -472
  178. package/dist/hydration/hydration.api.json +6460 -0
  179. package/dist/styles/styles.api.json +2672 -0
  180. package/package.json +165 -45
  181. package/ARCHITECTURE_FASTELEMENT.md +0 -63
  182. package/ARCHITECTURE_HTML_TAGGED_TEMPLATE_LITERAL.md +0 -36
  183. package/ARCHITECTURE_INTRO.md +0 -10
  184. package/ARCHITECTURE_OVERVIEW.md +0 -52
  185. package/ARCHITECTURE_UPDATES.md +0 -11
  186. package/CHANGELOG.json +0 -2275
  187. package/DESIGN.md +0 -510
  188. package/api-extractor.context.json +0 -14
  189. package/api-extractor.di.json +0 -14
  190. package/biome.json +0 -4
  191. package/dist/dts/components/install-hydration.d.ts +0 -1
  192. package/dist/dts/pending-task.d.ts +0 -32
  193. package/dist/dts/styles/css-binding-directive.d.ts +0 -60
  194. package/dist/dts/templating/install-hydratable-view-templates.d.ts +0 -1
  195. package/dist/esm/components/install-hydration.js +0 -3
  196. package/dist/esm/pending-task.js +0 -28
  197. package/dist/esm/polyfills.js +0 -60
  198. package/dist/esm/styles/css-binding-directive.js +0 -76
  199. package/dist/esm/templating/install-hydratable-view-templates.js +0 -23
  200. package/docs/ACKNOWLEDGEMENTS.md +0 -12
  201. package/docs/api-report.api.md +0 -1122
  202. package/docs/context/api-report.api.md +0 -69
  203. package/docs/di/api-report.api.md +0 -315
  204. package/docs/fast-element-2-changes.md +0 -15
  205. package/playwright.config.ts +0 -26
  206. package/scripts/run-api-extractor.js +0 -51
  207. package/test/index.html +0 -11
  208. package/test/main.ts +0 -104
  209. package/test/vite.config.ts +0 -19
  210. package/tsconfig.api-extractor.json +0 -6
  211. /package/dist/dts/{polyfills.d.ts → __test__/setup-node.d.ts} +0 -0
@@ -1,67 +1,56 @@
1
- import { KernelServiceId } from "../interfaces.js";
2
- import { FAST } from "../platform.js";
3
- /**
4
- * The default UpdateQueue.
5
- * @public
6
- */
7
- export const Updates = FAST.getById(KernelServiceId.updateQueue, () => {
8
- const tasks = [];
9
- const pendingErrors = [];
10
- const rAF = globalThis.requestAnimationFrame;
11
- let updateAsync = true;
12
- function throwFirstError() {
13
- if (pendingErrors.length) {
14
- throw pendingErrors.shift();
15
- }
1
+ const tasks = [];
2
+ const pendingErrors = [];
3
+ const rAF = globalThis.requestAnimationFrame;
4
+ let updateAsync = true;
5
+ function throwFirstError() {
6
+ if (pendingErrors.length) {
7
+ throw pendingErrors.shift();
8
+ }
9
+ }
10
+ function tryRunTask(task) {
11
+ try {
12
+ task.call();
16
13
  }
17
- function tryRunTask(task) {
18
- try {
19
- task.call();
14
+ catch (error) {
15
+ if (updateAsync) {
16
+ pendingErrors.push(error);
17
+ setTimeout(throwFirstError, 0);
20
18
  }
21
- catch (error) {
22
- if (updateAsync) {
23
- pendingErrors.push(error);
24
- setTimeout(throwFirstError, 0);
25
- }
26
- else {
27
- tasks.length = 0;
28
- throw error;
29
- }
19
+ else {
20
+ tasks.length = 0;
21
+ throw error;
30
22
  }
31
23
  }
32
- function process() {
33
- const capacity = 1024;
34
- let index = 0;
35
- while (index < tasks.length) {
36
- tryRunTask(tasks[index]);
37
- index++;
38
- // Prevent leaking memory for long chains of recursive calls to `enqueue`.
39
- // If we call `enqueue` within a task scheduled by `enqueue`, the queue will
40
- // grow, but to avoid an O(n) walk for every task we execute, we don't
41
- // shift tasks off the queue after they have been executed.
42
- // Instead, we periodically shift 1024 tasks off the queue.
43
- if (index > capacity) {
44
- // Manually shift all values starting at the index back to the
45
- // beginning of the queue.
46
- for (let scan = 0, newLength = tasks.length - index; scan < newLength; scan++) {
47
- tasks[scan] = tasks[scan + index];
48
- }
49
- tasks.length -= index;
50
- index = 0;
24
+ }
25
+ function process() {
26
+ const capacity = 1024;
27
+ let index = 0;
28
+ while (index < tasks.length) {
29
+ tryRunTask(tasks[index]);
30
+ index++;
31
+ if (index > capacity) {
32
+ for (let scan = 0, newLength = tasks.length - index; scan < newLength; scan++) {
33
+ tasks[scan] = tasks[scan + index];
51
34
  }
35
+ tasks.length -= index;
36
+ index = 0;
52
37
  }
53
- tasks.length = 0;
54
38
  }
55
- function enqueue(callable) {
56
- tasks.push(callable);
57
- if (tasks.length < 2) {
58
- updateAsync ? rAF(process) : process();
59
- }
39
+ tasks.length = 0;
40
+ }
41
+ function enqueue(callable) {
42
+ tasks.push(callable);
43
+ if (tasks.length < 2) {
44
+ updateAsync ? rAF(process) : process();
60
45
  }
61
- return Object.freeze({
62
- enqueue,
63
- next: () => new Promise(enqueue),
64
- process,
65
- setMode: (isAsync) => (updateAsync = isAsync),
66
- });
46
+ }
47
+ /**
48
+ * The default UpdateQueue.
49
+ * @public
50
+ */
51
+ export const Updates = Object.freeze({
52
+ enqueue,
53
+ next: () => new Promise(enqueue),
54
+ process,
55
+ setMode: (isAsync) => (updateAsync = isAsync),
67
56
  });
@@ -1,37 +1,38 @@
1
1
  import { noop } from "./interfaces.js";
2
- import "./polyfills.js";
3
- // ensure FAST global - duplicated debug.ts
4
- const propConfig = {
5
- configurable: false,
6
- enumerable: false,
7
- writable: false,
8
- };
9
- if (globalThis.FAST === void 0) {
10
- Reflect.defineProperty(globalThis, "FAST", Object.assign({ value: Object.create(null) }, propConfig));
11
- }
2
+ const debugMessages = Object.create(null);
12
3
  /**
13
- * The FAST global.
4
+ * The FAST messaging API for warnings and errors.
14
5
  * @public
15
6
  */
16
- export const FAST = globalThis.FAST;
17
- if (FAST.getById === void 0) {
18
- const storage = Object.create(null);
19
- Reflect.defineProperty(FAST, "getById", Object.assign({ value(id, initialize) {
20
- let found = storage[id];
21
- if (found === void 0) {
22
- found = initialize ? (storage[id] = initialize()) : null;
23
- }
24
- return found;
25
- } }, propConfig));
26
- }
27
- if (FAST.error === void 0) {
28
- Object.assign(FAST, {
29
- warn() { },
30
- error(code) {
31
- return new Error(`Error ${code}`);
32
- },
33
- addMessages() { },
34
- });
7
+ export const FAST = {
8
+ /**
9
+ * Sends a warning to the developer.
10
+ * @param code - The warning code to send.
11
+ * @param values - Values relevant for the warning message.
12
+ */
13
+ warn(_code, _values) { },
14
+ /**
15
+ * Creates an error from a code.
16
+ * @param code - The error code.
17
+ * @param values - Values relevant for the error message.
18
+ */
19
+ error(code, _values) {
20
+ return new Error(`Error ${code}`);
21
+ },
22
+ /**
23
+ * Adds debug messages for errors and warnings.
24
+ * @param messages - The message dictionary to add.
25
+ */
26
+ addMessages(messages) {
27
+ Object.assign(debugMessages, messages);
28
+ },
29
+ };
30
+ /**
31
+ * Gets the shared debug message lookup.
32
+ * @internal
33
+ */
34
+ export function getDebugMessageLookup() {
35
+ return debugMessages;
35
36
  }
36
37
  /**
37
38
  * A readonly, empty array.
@@ -0,0 +1 @@
1
+ export { FASTElementDefinition, fastElementRegistry, } from "./components/fast-definitions.js";
@@ -0,0 +1 @@
1
+ export { RenderBehavior, RenderDirective, render } from "./templating/render.js";
@@ -0,0 +1 @@
1
+ export { Schema, schemaRegistry, } from "./components/schema.js";
@@ -1,3 +1,3 @@
1
1
  export { reactive } from "./reactive.js";
2
- export { watch } from "./watch.js";
3
2
  export * from "./state.js";
3
+ export { watch } from "./watch.js";
@@ -1,8 +1,7 @@
1
1
  import { createTypeRegistry } from "../platform.js";
2
2
  const registry = createTypeRegistry();
3
3
  /**
4
- * Instructs the css engine to provide dynamic styles or
5
- * associate behaviors with styles.
4
+ * Instructs the css engine to provide styles during CSS template composition.
6
5
  * @public
7
6
  */
8
7
  export const CSSDirective = Object.freeze({
@@ -1,30 +1,13 @@
1
- import { Binding } from "../binding/binding.js";
2
- import { oneWay } from "../binding/one-way.js";
3
- import { isFunction, isString } from "../interfaces.js";
4
- import { CSSBindingDirective } from "./css-binding-directive.js";
5
1
  import { CSSDirective } from "./css-directive.js";
6
2
  import { ElementStyles } from "./element-styles.js";
7
- const marker = `${Math.random().toString(36).substring(2, 8)}`;
8
- let varId = 0;
9
- const nextCSSVariable = () => `--v${marker}${++varId}`;
10
3
  function collectStyles(strings, values) {
11
4
  const styles = [];
12
5
  let cssString = "";
13
- const behaviors = [];
14
- const add = (behavior) => {
15
- behaviors.push(behavior);
16
- };
17
6
  for (let i = 0, ii = strings.length - 1; i < ii; ++i) {
18
7
  cssString += strings[i];
19
8
  let value = values[i];
20
- if (isFunction(value)) {
21
- value = new CSSBindingDirective(oneWay(value), nextCSSVariable()).createCSS(add);
22
- }
23
- else if (value instanceof Binding) {
24
- value = new CSSBindingDirective(value, nextCSSVariable()).createCSS(add);
25
- }
26
- else if (CSSDirective.getForInstance(value) !== void 0) {
27
- value = value.createCSS(add);
9
+ if (CSSDirective.getForInstance(value) !== void 0) {
10
+ value = value.createCSS();
28
11
  }
29
12
  if (value instanceof ElementStyles || value instanceof CSSStyleSheet) {
30
13
  if (cssString.trim() !== "") {
@@ -41,57 +24,33 @@ function collectStyles(strings, values) {
41
24
  if (cssString.trim() !== "") {
42
25
  styles.push(cssString);
43
26
  }
44
- return {
45
- styles,
46
- behaviors,
47
- };
27
+ return styles;
48
28
  }
49
29
  /**
50
30
  * Transforms a template literal string into styles.
51
31
  * @param strings - The string fragments that are interpolated with the values.
52
32
  * @param values - The values that are interpolated with the string fragments.
53
33
  * @remarks
54
- * The css helper supports interpolation of strings and ElementStyle instances.
34
+ * The css helper supports interpolation of static composable styles and CSS directives.
55
35
  * @public
56
36
  */
57
37
  export const css = ((strings, ...values) => {
58
- const { styles, behaviors } = collectStyles(strings, values);
59
- const elementStyles = new ElementStyles(styles);
60
- return behaviors.length ? elementStyles.withBehaviors(...behaviors) : elementStyles;
38
+ return new ElementStyles(collectStyles(strings, values));
61
39
  });
62
40
  class CSSPartial {
63
- constructor(styles, behaviors) {
64
- this.behaviors = behaviors;
65
- this.css = "";
66
- const stylesheets = styles.reduce((accumulated, current) => {
67
- if (isString(current)) {
68
- this.css += current;
69
- }
70
- else {
71
- accumulated.push(current);
72
- }
73
- return accumulated;
74
- }, []);
75
- if (stylesheets.length) {
76
- this.styles = new ElementStyles(stylesheets);
77
- }
78
- }
79
- createCSS(add) {
80
- this.behaviors.forEach(add);
81
- if (this.styles) {
82
- add(this);
83
- }
84
- return this.css;
85
- }
86
- addedCallback(controller) {
87
- controller.addStyles(this.styles);
41
+ constructor(styles) {
42
+ this.value =
43
+ styles.length === 0
44
+ ? ""
45
+ : styles.length === 1
46
+ ? styles[0]
47
+ : new ElementStyles(styles);
88
48
  }
89
- removedCallback(controller) {
90
- controller.removeStyles(this.styles);
49
+ createCSS() {
50
+ return this.value;
91
51
  }
92
52
  }
93
53
  CSSDirective.define(CSSPartial);
94
54
  css.partial = (strings, ...values) => {
95
- const { styles, behaviors } = collectStyles(strings, values);
96
- return new CSSPartial(styles, behaviors);
55
+ return new CSSPartial(collectStyles(strings, values));
97
56
  };
@@ -1,8 +1,14 @@
1
1
  let DefaultStyleStrategy;
2
2
  function reduceStyles(styles) {
3
- return styles
4
- .map((x) => x instanceof ElementStyles ? reduceStyles(x.styles) : [x])
5
- .reduce((prev, curr) => prev.concat(curr), []);
3
+ return styles.reduce((reduced, current) => {
4
+ if (current instanceof ElementStyles) {
5
+ reduced.push(...reduceStyles(current.styles));
6
+ }
7
+ else {
8
+ reduced.push(current);
9
+ }
10
+ return reduced;
11
+ }, []);
6
12
  }
7
13
  /**
8
14
  * Represents styles that can be applied to a custom element.
@@ -14,6 +20,11 @@ export class ElementStyles {
14
20
  */
15
21
  get strategy() {
16
22
  if (this._strategy === null) {
23
+ if (!DefaultStyleStrategy) {
24
+ ElementStyles.setDefaultStrategy(ElementStyles.supportsAdoptedStyleSheets
25
+ ? createAdoptedSheetsStrategy()
26
+ : createStyleElementStrategy());
27
+ }
17
28
  this.withStrategy(DefaultStyleStrategy);
18
29
  }
19
30
  return this._strategy;
@@ -26,9 +37,6 @@ export class ElementStyles {
26
37
  this.styles = styles;
27
38
  this.targets = new WeakSet();
28
39
  this._strategy = null;
29
- this.behaviors = styles
30
- .map((x) => x instanceof ElementStyles ? x.behaviors : null)
31
- .reduce((prev, curr) => (curr === null ? prev : prev === null ? curr : prev.concat(curr)), null);
32
40
  }
33
41
  /** @internal */
34
42
  addStylesTo(target) {
@@ -44,15 +52,6 @@ export class ElementStyles {
44
52
  isAttachedTo(target) {
45
53
  return this.targets.has(target);
46
54
  }
47
- /**
48
- * Associates behaviors with this set of styles.
49
- * @param behaviors - The behaviors to associate.
50
- */
51
- withBehaviors(...behaviors) {
52
- this.behaviors =
53
- this.behaviors === null ? behaviors : this.behaviors.concat(behaviors);
54
- return this;
55
- }
56
55
  /**
57
56
  * Sets the strategy that handles adding/removing these styles for an element.
58
57
  * @param strategy - The strategy to use.
@@ -88,3 +87,58 @@ export class ElementStyles {
88
87
  */
89
88
  ElementStyles.supportsAdoptedStyleSheets = Array.isArray(document.adoptedStyleSheets) &&
90
89
  "replace" in CSSStyleSheet.prototype;
90
+ // Fallback strategy factories used when no strategy has been explicitly set
91
+ // via ElementStyles.setDefaultStrategy (e.g. when importing only from the
92
+ // styles.js subpath without loading element-controller.ts).
93
+ function createAdoptedSheetsStrategy() {
94
+ const cache = new Map();
95
+ return class FallbackAdoptedSheetsStrategy {
96
+ constructor(styles) {
97
+ this.sheets = styles.map(x => {
98
+ if (x instanceof CSSStyleSheet) {
99
+ return x;
100
+ }
101
+ let sheet = cache.get(x);
102
+ if (sheet === void 0) {
103
+ sheet = new CSSStyleSheet();
104
+ sheet.replaceSync(x);
105
+ cache.set(x, sheet);
106
+ }
107
+ return sheet;
108
+ });
109
+ }
110
+ addStylesTo(target) {
111
+ const t = target;
112
+ t.adoptedStyleSheets = [...t.adoptedStyleSheets, ...this.sheets];
113
+ }
114
+ removeStylesFrom(target) {
115
+ const t = target;
116
+ t.adoptedStyleSheets = t.adoptedStyleSheets.filter((x) => this.sheets.indexOf(x) === -1);
117
+ }
118
+ };
119
+ }
120
+ let fallbackStyleId = 0;
121
+ function createStyleElementStrategy() {
122
+ return class FallbackStyleElementStrategy {
123
+ constructor(styles) {
124
+ this.styles = styles;
125
+ this.styleClass = `fast-${++fallbackStyleId}`;
126
+ }
127
+ addStylesTo(target) {
128
+ const t = target === document ? document.body : target;
129
+ for (let i = 0; i < this.styles.length; i++) {
130
+ const element = document.createElement("style");
131
+ element.innerHTML = this.styles[i];
132
+ element.className = this.styleClass;
133
+ t.append(element);
134
+ }
135
+ }
136
+ removeStylesFrom(target) {
137
+ const t = target === document ? document.body : target;
138
+ const styles = t.querySelectorAll(`.${this.styleClass}`);
139
+ for (let i = 0, ii = styles.length; i < ii; ++i) {
140
+ t.removeChild(styles[i]);
141
+ }
142
+ }
143
+ };
144
+ }
@@ -0,0 +1,2 @@
1
+ export { CSSDirective, cssDirective, } from "./styles/css-directive.js";
2
+ export { ElementStyles, } from "./styles/element-styles.js";
@@ -4,8 +4,8 @@ import { Message } from "../interfaces.js";
4
4
  import { ExecutionContext, } from "../observation/observable.js";
5
5
  import { FAST } from "../platform.js";
6
6
  import { HTMLDirective, } from "./html-directive.js";
7
+ import { HydrationStage } from "./hydration-view.js";
7
8
  import { Markup } from "./markup.js";
8
- import { HydrationStage } from "./view.js";
9
9
  function isContentTemplate(value) {
10
10
  return value.create !== undefined;
11
11
  }
@@ -158,12 +158,12 @@ export class HTMLBindingDirective {
158
158
  * @param dataBinding - The binding configuration to apply.
159
159
  */
160
160
  constructor(dataBinding) {
161
- this.dataBinding = dataBinding;
162
161
  this.updateTarget = null;
163
162
  /**
164
163
  * The type of aspect to target.
165
164
  */
166
165
  this.aspectType = DOMAspect.content;
166
+ this.dataBinding = dataBinding;
167
167
  }
168
168
  /**
169
169
  * Creates HTML to be used within a template.
@@ -203,9 +203,6 @@ export class HTMLBindingDirective {
203
203
  bind(controller) {
204
204
  var _a;
205
205
  const target = controller.targets[this.targetNodeId];
206
- const isHydrating = isHydratable(controller) &&
207
- controller.hydrationStage &&
208
- controller.hydrationStage !== HydrationStage.hydrated;
209
206
  switch (this.aspectType) {
210
207
  case DOMAspect.event:
211
208
  target[this.data] = controller;
@@ -218,14 +215,19 @@ export class HTMLBindingDirective {
218
215
  const observer = (_a = target[this.data]) !== null && _a !== void 0 ? _a : (target[this.data] = this.dataBinding.createObserver(this, this));
219
216
  observer.target = target;
220
217
  observer.controller = controller;
221
- if (isHydrating &&
218
+ // Evaluate to establish dependency tracking
219
+ const value = observer.bind(controller);
220
+ // Skip DOM update for attribute bindings when prerendered —
221
+ // the server has already rendered the correct attribute values.
222
+ // Content, property, and tokenList bindings must still run
223
+ // so structural directives, host properties, and class lists
224
+ // are properly initialized.
225
+ if (controller._skipAttrUpdates &&
222
226
  (this.aspectType === DOMAspect.attribute ||
223
227
  this.aspectType === DOMAspect.booleanAttribute)) {
224
- observer.bind(controller);
225
- // Skip updating target during bind for attributes
226
228
  break;
227
229
  }
228
- this.updateTarget(target, this.targetAspect, observer.bind(controller), controller);
230
+ this.updateTarget(target, this.targetAspect, value, controller);
229
231
  break;
230
232
  }
231
233
  }