@microsoft/webui-framework 0.0.18 → 0.0.19

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.
@@ -11,6 +11,7 @@ export declare const ATTR_KIND_ATTRIBUTE = 0;
11
11
  export declare const ATTR_KIND_COMPLEX = 1;
12
12
  export declare const ATTR_KIND_BOOLEAN = 2;
13
13
  export declare const ATTR_KIND_TEMPLATE = 3;
14
+ export declare function hasNativeLiveProperty(element: Element, name: string): boolean;
14
15
  export interface AttrBinding {
15
16
  element: Element;
16
17
  name: string;
@@ -24,9 +25,12 @@ export interface ScopeFrame {
24
25
  name: string;
25
26
  value: unknown;
26
27
  parent?: ScopeFrame;
28
+ known?: boolean;
27
29
  }
28
30
  export interface TemplateInstance {
29
31
  scope?: ScopeFrame;
32
+ parent?: TemplateInstance;
33
+ container: (ParentNode & Node) | null;
30
34
  nodes: Node[];
31
35
  texts: TextBinding[];
32
36
  attrs: AttrBinding[];
@@ -39,8 +43,17 @@ export interface CondBinding {
39
43
  blockIndex: number;
40
44
  anchor: Comment;
41
45
  scope?: ScopeFrame;
46
+ owner: TemplateInstance;
42
47
  instance: TemplateInstance | null;
43
48
  }
49
+ export type RepeatKey = string | number;
50
+ export interface RepeatKeyState {
51
+ path: string;
52
+ warned: boolean;
53
+ keys: RepeatKey[];
54
+ nextKeys: RepeatKey[];
55
+ map: Map<RepeatKey, TemplateInstance | null>;
56
+ }
44
57
  export interface RepeatBinding {
45
58
  markerId: number;
46
59
  collection: string;
@@ -51,21 +64,16 @@ export interface RepeatBinding {
51
64
  end: Comment | null;
52
65
  scope?: ScopeFrame;
53
66
  owner: TemplateInstance;
54
- instances: RepeatItemInstance[];
55
- rootTag: string | null;
56
- keyAttribute?: string;
57
- keyPath?: string;
67
+ instances: TemplateInstance[];
68
+ keyState?: RepeatKeyState;
58
69
  synced?: boolean;
59
70
  }
60
- export interface RepeatItemInstance {
61
- key: string | null;
62
- value: unknown;
63
- instance: TemplateInstance;
64
- }
65
71
  export interface RepeatHost {
66
72
  $resolveValue(path: string, scope?: ScopeFrame): unknown;
67
- $createBlockInstance(blockIndex: number, scope?: ScopeFrame): TemplateInstance | null;
73
+ $hasStateRoot(path: string, scope?: ScopeFrame): boolean;
74
+ $createBlockInstance(blockIndex: number, scope?: ScopeFrame, parent?: TemplateInstance, container?: ParentNode & Node): TemplateInstance | null;
68
75
  $updateInstance(instance: TemplateInstance): void;
69
76
  $removeInstance(instance: TemplateInstance): void;
77
+ $changeStructure(removedFrom?: TemplateInstance): void;
70
78
  $insertInstanceAfter(cursor: Node | null, container: ParentNode & Node, instance: TemplateInstance): Node | null;
71
79
  }
@@ -2,3 +2,6 @@ export const ATTR_KIND_ATTRIBUTE = 0;
2
2
  export const ATTR_KIND_COMPLEX = 1;
3
3
  export const ATTR_KIND_BOOLEAN = 2;
4
4
  export const ATTR_KIND_TEMPLATE = 3;
5
+ export function hasNativeLiveProperty(element, name) {
6
+ return element.localName.indexOf('-') === -1 && name in element;
7
+ }
package/dist/element.js CHANGED
@@ -1,11 +1,12 @@
1
1
  import { TemplateElement } from './template-element.js';
2
- import { getObservableNames, isAttributeProperty, syncAttrProperties, } from './decorators.js';
2
+ import { attributeNameForProperty, getObservableNames, syncAttrProperties, } from './decorators.js';
3
3
  export class WebUIElement extends TemplateElement {
4
4
  $observableNames() {
5
5
  return getObservableNames(this.constructor);
6
6
  }
7
7
  $shouldApplySSRState(key) {
8
- return !isAttributeProperty(this.constructor, key);
8
+ const attribute = attributeNameForProperty(this.constructor, key);
9
+ return attribute === undefined || !this.hasAttribute(attribute);
9
10
  }
10
11
  $syncAuthoredAttributes() {
11
12
  syncAttrProperties(this, this.constructor);
@@ -1,4 +1,4 @@
1
- import { ATTR_KIND_BOOLEAN, ATTR_KIND_COMPLEX, ATTR_KIND_TEMPLATE, } from './element/types.js';
1
+ import { ATTR_KIND_BOOLEAN, ATTR_KIND_COMPLEX, ATTR_KIND_TEMPLATE, hasNativeLiveProperty, } from './element/types.js';
2
2
  export function reportHydrationMismatch(tag, writes, index, ctx) {
3
3
  const mismatched = [];
4
4
  for (const path of writes) {
@@ -51,7 +51,8 @@ export function attrDiffersFromDom(b, ctx) {
51
51
  case ATTR_KIND_TEMPLATE:
52
52
  return (el.getAttribute(b.name) ?? '') !== ctx.resolveParts(b.parts, b.scope);
53
53
  default: {
54
- if (b.name === 'value' || b.name === 'checked' || b.name === 'selected')
54
+ if ((b.name === 'value' || b.name === 'checked' || b.name === 'selected')
55
+ && hasNativeLiveProperty(el, b.name))
55
56
  return false;
56
57
  const v = ctx.resolveValue(b.path, b.scope);
57
58
  return (el.getAttribute(b.name) ?? '') !== (v == null ? '' : String(v));
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { installTemplateElementRuntime } from './static-host.js';
2
- installTemplateElementRuntime();
2
+ setTimeout(installTemplateElementRuntime, 0);
3
3
  export { WebUIElement } from './element.js';
4
4
  export { observable, attr } from './decorators.js';
5
5
  export { getTemplate, registerTemplateData } from './template.js';
@@ -1,6 +1,6 @@
1
1
  import { TemplateElement } from './template-element.js';
2
2
  import { getTemplateRegistry } from './template.js';
3
- import { templateAttributeForRoot, templateNeedsStaticHost } from './template-roots.js';
3
+ import { templateNeedsStaticHost } from './template-roots.js';
4
4
  import { TEMPLATES_REGISTERED_EVENT, templateRegistrationDetail, } from './template-events.js';
5
5
  let runtimeInstalled = false;
6
6
  function defineTemplateHost(tag, meta) {
@@ -12,16 +12,25 @@ function defineTemplateHost(tag, meta) {
12
12
  if (!w.__webui.templates[tag])
13
13
  w.__webui.templates[tag] = meta;
14
14
  class StaticTemplateHost extends TemplateElement {
15
- $shouldApplyTemplateStateFromSSR(key) {
16
- const attr = templateAttributeForRoot(meta, key);
17
- return attr === undefined || !this.hasAttribute(attr);
15
+ $afterExternalStateWrite(applied) {
16
+ if (applied)
17
+ this.$activateDeferredSSR();
18
+ }
19
+ $shouldDeferSSRHydration() {
20
+ return true;
21
+ }
22
+ $shouldApplySSRBootstrapState() {
23
+ return false;
18
24
  }
19
25
  }
20
26
  StaticTemplateHost.define(tag);
21
27
  }
22
28
  function defineMissingTemplateHost(tag, meta) {
23
- if (!templateNeedsStaticHost(meta) || customElements.get(tag))
29
+ if (!templateNeedsStaticHost(meta) ||
30
+ window.__webui?.templateHostExclusions?.has(tag) ||
31
+ customElements.get(tag)) {
24
32
  return;
33
+ }
25
34
  defineTemplateHost(tag, meta);
26
35
  }
27
36
  function defineTemplateHosts(templates = getTemplateRegistry()) {
@@ -45,10 +54,9 @@ export function installTemplateElementRuntime() {
45
54
  runtimeInstalled = true;
46
55
  window.addEventListener(TEMPLATES_REGISTERED_EVENT, (event) => {
47
56
  const detail = templateRegistrationDetail(event);
48
- if (!detail)
57
+ if (!detail?.templates)
49
58
  return;
50
- if (detail.templates)
51
- defineTemplateHosts(detail.templates);
59
+ defineTemplateHosts(detail.templates);
52
60
  });
53
61
  if (document.readyState === 'loading') {
54
62
  document.addEventListener('DOMContentLoaded', () => defineTemplateHosts(), { once: true });
@@ -6,6 +6,9 @@ export declare class TemplateElement extends HTMLElement {
6
6
  private $meta?;
7
7
  private $ready;
8
8
  private $hydrated;
9
+ private $deferredSSR;
10
+ private $activatingDeferredSSR;
11
+ private $hasUnknownScopes;
9
12
  private $templateState;
10
13
  private $dirtyPaths;
11
14
  private $pendingFlush;
@@ -19,15 +22,20 @@ export declare class TemplateElement extends HTMLElement {
19
22
  private $mount;
20
23
  disconnectedCallback(): void;
21
24
  $destroy(): void;
22
- private $teardown;
23
- private $teardownInstanceCleanups;
25
+ private $clearRepeatBinding;
26
+ private $clearInstance;
24
27
  attributeChangedCallback(name: string, oldValue: string | null, newValue: string | null): void;
25
28
  setState(state: Record<string, unknown>): void;
26
29
  protected $observableNames(): Set<string>;
30
+ protected $beforeExternalStateWrite(): void;
31
+ protected $afterExternalStateWrite(_applied: boolean): void;
32
+ protected $shouldDeferSSRHydration(): boolean;
33
+ protected $activateDeferredSSR(): void;
34
+ protected $shouldApplySSRBootstrapState(): boolean;
27
35
  protected $shouldApplySSRState(_key: string): boolean;
28
36
  protected $syncAuthoredAttributes(): void;
29
37
  protected $shouldApplyTemplateStateFromSSR(_key: string): boolean;
30
- protected $setTemplateState(key: string, value: unknown): void;
38
+ protected $setTemplateState(key: string, value: unknown): boolean;
31
39
  private $writeTemplateState;
32
40
  private $templateMeta;
33
41
  private $templateRootForAttribute;
@@ -44,33 +52,36 @@ export declare class TemplateElement extends HTMLElement {
44
52
  private $parseTemplate;
45
53
  private $createStagingRoot;
46
54
  private $appendStagedChildren;
47
- private $releaseStagingRepeatContainers;
55
+ private $replaceInstanceContainer;
48
56
  private $wire;
49
57
  private $hydrate;
50
- private $collectBetween;
58
+ private $collectConditionalRange;
59
+ private $hasRootStructuralSlot;
51
60
  private $hydrateCondContent;
52
61
  private $findMarker;
53
- private $hasContentAfterMarker;
54
62
  private $findSSRText;
55
63
  private $findSSRSlotRef;
56
64
  private $rootTag;
57
65
  private $wireAttrs;
58
66
  protected $finalize(_instance: TemplateInstance, _root: Node, _meta: TemplateBlockMeta, _resolver: (root: Node, path: TemplateNodePath) => Node | null, _scope?: ScopeFrame): void;
59
67
  private $makeAttr;
60
- private $repeatMaps;
61
68
  private $buildPathIndex;
62
69
  private $updateBindings;
70
+ private $scopeIsKnown;
63
71
  $updateInstance(instance: TemplateInstance): void;
64
72
  private $patchText;
65
73
  private $patchAttr;
66
74
  private $toggleCond;
67
75
  $resolveValue(path: string, scope?: ScopeFrame): unknown;
76
+ $hasStateRoot(path: string, scope?: ScopeFrame): boolean;
68
77
  private $resolveComponentRoot;
69
78
  private $resolveParts;
70
79
  $block(blockIndex: number): TemplateBlockMeta | undefined;
71
- $createBlockInstance(blockIndex: number, scope?: ScopeFrame): TemplateInstance | null;
80
+ $createBlockInstance(blockIndex: number, scope?: ScopeFrame, parent?: TemplateInstance, container?: ParentNode & Node): TemplateInstance | null;
72
81
  $removeInstance(instance: TemplateInstance): void;
82
+ private $disposeInstance;
83
+ private $compactNodeArray;
84
+ $changeStructure(removedFrom?: TemplateInstance): void;
73
85
  $insertInstanceAfter(cursor: Node | null, container: ParentNode & Node, instance: TemplateInstance): Node | null;
74
- private $singleDynamic;
75
86
  }
76
87
  export {};