glass-easel 0.2.0 → 0.3.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/.eslintignore +4 -0
- package/dist/glass_easel.all.js +2 -2
- package/dist/glass_easel.all.js.map +1 -1
- package/dist/glass_easel.d.ts +2546 -0
- package/dist/glass_easel.domlike.global.js +2 -2
- package/dist/glass_easel.domlike.global.js.map +1 -1
- package/guide/zh_CN/appendix/backend_protocol.md +164 -74
- package/jest.unit.config.js +7 -4
- package/package.json +7 -5
- package/rollup.config.ts +101 -0
- package/src/backend/backend_protocol.ts +26 -345
- package/src/backend/composed_backend_protocol.ts +10 -264
- package/src/backend/current_window_backend_context.ts +478 -0
- package/src/backend/domlike_backend_protocol.ts +9 -498
- package/src/backend/empty_backend.ts +265 -0
- package/src/backend/empty_composed_backend.ts +245 -0
- package/src/backend/index.ts +18 -0
- package/src/backend/suggested_backend_protocol.ts +62 -11
- package/src/behavior.ts +131 -442
- package/src/class_list.ts +328 -222
- package/src/component.ts +349 -184
- package/src/component_params.ts +54 -25
- package/src/component_space.ts +36 -15
- package/src/data_path.ts +22 -34
- package/src/data_proxy.ts +334 -27
- package/src/devtool.ts +89 -0
- package/src/element.ts +667 -285
- package/src/element_iterator.ts +9 -4
- package/src/event.ts +39 -20
- package/src/external_shadow_tree.ts +2 -2
- package/src/func_arr.ts +55 -101
- package/src/global_options.ts +18 -42
- package/src/index.ts +72 -73
- package/src/mutation_observer.ts +10 -7
- package/src/native_node.ts +79 -35
- package/src/node.ts +23 -30
- package/src/relation.ts +101 -12
- package/src/render.ts +5 -3
- package/src/selector.ts +9 -7
- package/src/shadow_root.ts +96 -240
- package/src/template_engine.ts +10 -7
- package/src/text_node.ts +43 -19
- package/src/tmpl/index.ts +38 -30
- package/src/tmpl/native_rendering.ts +14 -21
- package/src/tmpl/proc_gen_wrapper.ts +189 -151
- package/src/tmpl/proc_gen_wrapper_dom.ts +10 -8
- package/src/tmpl/range_list_diff.ts +30 -9
- package/src/trait_behaviors.ts +1 -1
- package/src/type_symbol.ts +36 -0
- package/src/virtual_node.ts +26 -13
- package/src/warning.ts +119 -0
- package/tests/base/composed_backend.ts +143 -142
- package/tests/base/env.ts +76 -3
- package/tests/base/match.ts +24 -22
- package/tests/base/shadow_backend.ts +917 -0
- package/tests/core/backend.test.ts +53 -1
- package/tests/core/behavior.test.ts +1 -1
- package/tests/core/data_update.test.ts +135 -0
- package/tests/core/misc.test.ts +91 -21
- package/tests/core/placeholder.test.ts +66 -25
- package/tests/core/slot.test.ts +161 -23
- package/tests/legacy/component.test.js +152 -78
- package/tests/legacy/data_path.test.js +19 -19
- package/tests/legacy/data_proxy.test.js +14 -7
- package/tests/legacy/external.test.js +8 -8
- package/tests/legacy/mutation_observer.test.js +7 -5
- package/tests/legacy/slot.test.js +2 -3
- package/tests/legacy/virtual.test.js +258 -25
- package/tests/tmpl/binding_map.test.ts +201 -195
- package/tests/tmpl/event.test.ts +138 -23
- package/tests/tmpl/expression.test.ts +15 -15
- package/tests/tmpl/lvalue.test.ts +101 -0
- package/tests/tmpl/structure.test.ts +486 -43
- package/tests/types/chaining.test.ts +27 -30
- package/tests/types/createElement.test.ts +5 -4
- package/tests/types/definition.test.ts +11 -14
- package/tsconfig.json +1 -3
- package/dist/glass_easel.all.d.ts +0 -1
- package/dist/glass_easel.domlike.global.d.ts +0 -1
- package/dist/index.d.ts +0 -1
- package/dist/index.js +0 -1
- package/dist/types/src/backend/backend_protocol.d.ts +0 -141
- package/dist/types/src/backend/backend_protocol.d.ts.map +0 -1
- package/dist/types/src/backend/composed_backend_protocol.d.ts +0 -102
- package/dist/types/src/backend/composed_backend_protocol.d.ts.map +0 -1
- package/dist/types/src/backend/domlike_backend_protocol.d.ts +0 -100
- package/dist/types/src/backend/domlike_backend_protocol.d.ts.map +0 -1
- package/dist/types/src/backend/mode.d.ts +0 -65
- package/dist/types/src/backend/mode.d.ts.map +0 -1
- package/dist/types/src/backend/suggested_backend_protocol.d.ts +0 -30
- package/dist/types/src/backend/suggested_backend_protocol.d.ts.map +0 -1
- package/dist/types/src/behavior.d.ts +0 -434
- package/dist/types/src/behavior.d.ts.map +0 -1
- package/dist/types/src/class_list.d.ts +0 -83
- package/dist/types/src/class_list.d.ts.map +0 -1
- package/dist/types/src/component.d.ts +0 -325
- package/dist/types/src/component.d.ts.map +0 -1
- package/dist/types/src/component_params.d.ts +0 -236
- package/dist/types/src/component_params.d.ts.map +0 -1
- package/dist/types/src/component_space.d.ts +0 -211
- package/dist/types/src/component_space.d.ts.map +0 -1
- package/dist/types/src/data_path.d.ts +0 -5
- package/dist/types/src/data_path.d.ts.map +0 -1
- package/dist/types/src/data_proxy.d.ts +0 -107
- package/dist/types/src/data_proxy.d.ts.map +0 -1
- package/dist/types/src/data_utils.d.ts +0 -3
- package/dist/types/src/data_utils.d.ts.map +0 -1
- package/dist/types/src/element.d.ts +0 -365
- package/dist/types/src/element.d.ts.map +0 -1
- package/dist/types/src/element_iterator.d.ts +0 -43
- package/dist/types/src/element_iterator.d.ts.map +0 -1
- package/dist/types/src/event.d.ts +0 -105
- package/dist/types/src/event.d.ts.map +0 -1
- package/dist/types/src/external_shadow_tree.d.ts +0 -20
- package/dist/types/src/external_shadow_tree.d.ts.map +0 -1
- package/dist/types/src/func_arr.d.ts +0 -39
- package/dist/types/src/func_arr.d.ts.map +0 -1
- package/dist/types/src/global_options.d.ts +0 -120
- package/dist/types/src/global_options.d.ts.map +0 -1
- package/dist/types/src/index.d.ts +0 -43
- package/dist/types/src/index.d.ts.map +0 -1
- package/dist/types/src/mutation_observer.d.ts +0 -79
- package/dist/types/src/mutation_observer.d.ts.map +0 -1
- package/dist/types/src/native_node.d.ts +0 -11
- package/dist/types/src/native_node.d.ts.map +0 -1
- package/dist/types/src/node.d.ts +0 -48
- package/dist/types/src/node.d.ts.map +0 -1
- package/dist/types/src/relation.d.ts +0 -46
- package/dist/types/src/relation.d.ts.map +0 -1
- package/dist/types/src/render.d.ts +0 -3
- package/dist/types/src/render.d.ts.map +0 -1
- package/dist/types/src/selector.d.ts +0 -32
- package/dist/types/src/selector.d.ts.map +0 -1
- package/dist/types/src/shadow_root.d.ts +0 -174
- package/dist/types/src/shadow_root.d.ts.map +0 -1
- package/dist/types/src/template_engine.d.ts +0 -56
- package/dist/types/src/template_engine.d.ts.map +0 -1
- package/dist/types/src/text_node.d.ts +0 -44
- package/dist/types/src/text_node.d.ts.map +0 -1
- package/dist/types/src/tmpl/index.d.ts +0 -19
- package/dist/types/src/tmpl/index.d.ts.map +0 -1
- package/dist/types/src/tmpl/native_rendering.d.ts +0 -45
- package/dist/types/src/tmpl/native_rendering.d.ts.map +0 -1
- package/dist/types/src/tmpl/proc_gen_wrapper.d.ts +0 -89
- package/dist/types/src/tmpl/proc_gen_wrapper.d.ts.map +0 -1
- package/dist/types/src/tmpl/proc_gen_wrapper_dom.d.ts +0 -50
- package/dist/types/src/tmpl/proc_gen_wrapper_dom.d.ts.map +0 -1
- package/dist/types/src/tmpl/range_list_diff.d.ts +0 -19
- package/dist/types/src/tmpl/range_list_diff.d.ts.map +0 -1
- package/dist/types/src/trait_behaviors.d.ts +0 -38
- package/dist/types/src/trait_behaviors.d.ts.map +0 -1
- package/dist/types/src/virtual_node.d.ts +0 -10
- package/dist/types/src/virtual_node.d.ts.map +0 -1
- package/dist/types/tests/backend/domlike.test.d.ts +0 -2
- package/dist/types/tests/backend/domlike.test.d.ts.map +0 -1
- package/dist/types/tests/base/composed_backend.d.ts +0 -123
- package/dist/types/tests/base/composed_backend.d.ts.map +0 -1
- package/dist/types/tests/base/env.d.ts +0 -30
- package/dist/types/tests/base/env.d.ts.map +0 -1
- package/dist/types/tests/base/match.d.ts +0 -9
- package/dist/types/tests/base/match.d.ts.map +0 -1
- package/dist/types/tests/core/backend.test.d.ts +0 -2
- package/dist/types/tests/core/backend.test.d.ts.map +0 -1
- package/dist/types/tests/core/behavior.test.d.ts +0 -2
- package/dist/types/tests/core/behavior.test.d.ts.map +0 -1
- package/dist/types/tests/core/component_space.test.d.ts +0 -2
- package/dist/types/tests/core/component_space.test.d.ts.map +0 -1
- package/dist/types/tests/core/data_update.test.d.ts +0 -2
- package/dist/types/tests/core/data_update.test.d.ts.map +0 -1
- package/dist/types/tests/core/misc.test.d.ts +0 -2
- package/dist/types/tests/core/misc.test.d.ts.map +0 -1
- package/dist/types/tests/core/placeholder.test.d.ts +0 -2
- package/dist/types/tests/core/placeholder.test.d.ts.map +0 -1
- package/dist/types/tests/core/slot.test.d.ts +0 -2
- package/dist/types/tests/core/slot.test.d.ts.map +0 -1
- package/dist/types/tests/core/trait_behaviors.test.d.ts +0 -2
- package/dist/types/tests/core/trait_behaviors.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/binding_map.test.d.ts +0 -2
- package/dist/types/tests/tmpl/binding_map.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/event.test.d.ts +0 -2
- package/dist/types/tests/tmpl/event.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/expression.test.d.ts +0 -2
- package/dist/types/tests/tmpl/expression.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/lvalue.test.d.ts +0 -2
- package/dist/types/tests/tmpl/lvalue.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/native_rendering.test.d.ts +0 -2
- package/dist/types/tests/tmpl/native_rendering.test.d.ts.map +0 -1
- package/dist/types/tests/tmpl/structure.test.d.ts +0 -2
- package/dist/types/tests/tmpl/structure.test.d.ts.map +0 -1
- package/dist/types/tests/types/chaining.test.d.ts +0 -2
- package/dist/types/tests/types/chaining.test.d.ts.map +0 -1
- package/dist/types/tests/types/createElement.test.d.ts +0 -2
- package/dist/types/tests/types/createElement.test.d.ts.map +0 -1
- package/dist/types/tests/types/definition.test.d.ts +0 -2
- package/dist/types/tests/types/definition.test.d.ts.map +0 -1
- package/webpack.config.js +0 -275
- /package/src/backend/{mode.ts → shared.ts} +0 -0
package/src/selector.ts
CHANGED
|
@@ -1,4 +1,6 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { type ComponentSpace } from './component_space'
|
|
2
|
+
import { type Element } from './element'
|
|
3
|
+
import { isComponent, isElement, isShadowRoot, isVirtualNode } from './type_symbol'
|
|
2
4
|
|
|
3
5
|
const enum SegmentRelation {
|
|
4
6
|
Child,
|
|
@@ -106,10 +108,10 @@ export class ParsedSelector {
|
|
|
106
108
|
do {
|
|
107
109
|
if (!nextNode.parentNode) {
|
|
108
110
|
if (nextRelation === SegmentRelation.CrossShadowDescendant) {
|
|
109
|
-
nextNode = nextNode
|
|
111
|
+
nextNode = isShadowRoot(nextNode) ? nextNode.getHostNode() : null
|
|
110
112
|
} else if (relation === SegmentRelation.CrossShadowDescendant) {
|
|
111
113
|
match = false
|
|
112
|
-
nextNode = nextNode
|
|
114
|
+
nextNode = isShadowRoot(nextNode) ? nextNode.getHostNode() : null
|
|
113
115
|
} else {
|
|
114
116
|
nextNode = null
|
|
115
117
|
}
|
|
@@ -117,7 +119,7 @@ export class ParsedSelector {
|
|
|
117
119
|
nextNode = nextNode.parentNode
|
|
118
120
|
}
|
|
119
121
|
if (nextNode === root) nextNode = null
|
|
120
|
-
} while (nextNode
|
|
122
|
+
} while (isVirtualNode(nextNode))
|
|
121
123
|
if (!nextNode) return false
|
|
122
124
|
if (match) {
|
|
123
125
|
// if matches, try match ancestors
|
|
@@ -149,7 +151,7 @@ export class ParsedSelector {
|
|
|
149
151
|
* otherwise it match in the whole tree.
|
|
150
152
|
*/
|
|
151
153
|
testSelector(root: Element | null, node: Element): boolean {
|
|
152
|
-
if (node
|
|
154
|
+
if (isVirtualNode(node)) return false
|
|
153
155
|
const union = this.unions
|
|
154
156
|
let ownerSpace: ComponentSpace | undefined
|
|
155
157
|
if (root !== null) {
|
|
@@ -181,7 +183,7 @@ export class ParsedSelector {
|
|
|
181
183
|
if (findOne) return node
|
|
182
184
|
ret.push(node)
|
|
183
185
|
}
|
|
184
|
-
if (node
|
|
186
|
+
if (isComponent(node)) {
|
|
185
187
|
const shadowRoot = node.getShadowRoot()
|
|
186
188
|
if (shadowRoot) {
|
|
187
189
|
const r = rec(root, shadowRoot, findOne)
|
|
@@ -193,7 +195,7 @@ export class ParsedSelector {
|
|
|
193
195
|
const children = node.childNodes
|
|
194
196
|
for (let i = 0; i < children.length; i += 1) {
|
|
195
197
|
const child = children[i]
|
|
196
|
-
if (child
|
|
198
|
+
if (isElement(child)) {
|
|
197
199
|
const r = rec(root, child, findOne)
|
|
198
200
|
if (r && findOne) {
|
|
199
201
|
return r
|
package/src/shadow_root.ts
CHANGED
|
@@ -1,20 +1,21 @@
|
|
|
1
|
-
import
|
|
2
|
-
import {
|
|
1
|
+
import { BM, BackendMode, type backend } from './backend'
|
|
2
|
+
import { type ComponentDefinitionWithPlaceholder } from './behavior'
|
|
3
3
|
import {
|
|
4
4
|
Component,
|
|
5
|
-
GeneralComponentDefinition,
|
|
6
|
-
GeneralComponent,
|
|
7
5
|
convertGenerics,
|
|
8
6
|
resolvePlaceholder,
|
|
7
|
+
type GeneralComponent,
|
|
8
|
+
type GeneralComponentDefinition,
|
|
9
9
|
} from './component'
|
|
10
|
-
import { TextNode } from './text_node'
|
|
11
|
-
import { NativeNode } from './native_node'
|
|
12
|
-
import { DoubleLinkedList, Element } from './element'
|
|
13
|
-
import { Node } from './node'
|
|
14
|
-
import { ComponentDefinitionWithPlaceholder } from './behavior'
|
|
15
|
-
import { BM, BackendMode } from './backend/mode'
|
|
16
10
|
import { DeepCopyStrategy, getDeepCopyStrategy } from './data_proxy'
|
|
17
11
|
import { deepCopy, simpleDeepCopy } from './data_utils'
|
|
12
|
+
import { Element, type DoubleLinkedList } from './element'
|
|
13
|
+
import { NativeNode } from './native_node'
|
|
14
|
+
import { type Node } from './node'
|
|
15
|
+
import { TextNode } from './text_node'
|
|
16
|
+
import { SHADOW_ROOT_SYMBOL, isElement, isShadowRoot } from './type_symbol'
|
|
17
|
+
import { VirtualNode } from './virtual_node'
|
|
18
|
+
import { ThirdError, triggerWarning } from './warning'
|
|
18
19
|
|
|
19
20
|
export const enum SlotMode {
|
|
20
21
|
Direct = 0,
|
|
@@ -27,35 +28,32 @@ type AppliedSlotMeta = {
|
|
|
27
28
|
updatePathTree: { [key: string]: true } | undefined
|
|
28
29
|
}
|
|
29
30
|
|
|
30
|
-
const wrapPlaceholderCallback = (
|
|
31
|
-
f: (c: GeneralComponentDefinition) => void,
|
|
32
|
-
cwp: Exclude<ComponentDefinitionWithPlaceholder, string>,
|
|
33
|
-
owner: GeneralComponent,
|
|
34
|
-
) => {
|
|
35
|
-
const waiting = cwp.waiting
|
|
36
|
-
if (waiting) {
|
|
37
|
-
waiting.add(f)
|
|
38
|
-
waiting.hintUsed(owner)
|
|
39
|
-
return () => {
|
|
40
|
-
waiting.remove(f)
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
return undefined
|
|
44
|
-
}
|
|
45
|
-
|
|
46
31
|
export class ShadowRoot extends VirtualNode {
|
|
32
|
+
/* @internal */
|
|
33
|
+
[SHADOW_ROOT_SYMBOL]: true
|
|
34
|
+
/* @internal */
|
|
47
35
|
private _$host: GeneralComponent
|
|
48
36
|
/** @internal */
|
|
49
37
|
_$backendShadowRoot: backend.ShadowRootContext | null
|
|
38
|
+
/* @internal */
|
|
50
39
|
private _$slotMode: SlotMode
|
|
40
|
+
/* @internal */
|
|
51
41
|
private _$idMap: { [id: string]: Element } | null
|
|
42
|
+
/* @internal */
|
|
52
43
|
private _$singleSlot?: Element | null
|
|
44
|
+
/* @internal */
|
|
53
45
|
private _$slots?: Record<string, Element>
|
|
46
|
+
/* @internal */
|
|
54
47
|
private _$slotsList?: Record<string, DoubleLinkedList<Element>>
|
|
48
|
+
/* @internal */
|
|
55
49
|
private _$dynamicSlotsInserted?: boolean
|
|
50
|
+
/* @internal */
|
|
56
51
|
private _$dynamicSlots?: Map<Element, AppliedSlotMeta>
|
|
52
|
+
/* @internal */
|
|
57
53
|
private _$requiredSlotValueNames?: string[]
|
|
54
|
+
/* @internal */
|
|
58
55
|
private _$propertyPassingDeepCopy?: DeepCopyStrategy
|
|
56
|
+
/* @internal */
|
|
59
57
|
private _$insertDynamicSlotHandler?: (
|
|
60
58
|
slots: {
|
|
61
59
|
slot: Element
|
|
@@ -63,27 +61,33 @@ export class ShadowRoot extends VirtualNode {
|
|
|
63
61
|
slotValues: { [name: string]: unknown }
|
|
64
62
|
}[],
|
|
65
63
|
) => void
|
|
64
|
+
/* @internal */
|
|
66
65
|
private _$removeDynamicSlotHandler?: (slots: Element[]) => void
|
|
66
|
+
/* @internal */
|
|
67
67
|
private _$updateDynamicSlotHandler?: (
|
|
68
68
|
slot: Element,
|
|
69
69
|
slotValues: { [name: string]: unknown },
|
|
70
70
|
updatePathTree: { [name: string]: true },
|
|
71
71
|
) => void
|
|
72
72
|
|
|
73
|
+
/* istanbul ignore next */
|
|
73
74
|
constructor() {
|
|
74
75
|
throw new Error('Element cannot be constructed directly')
|
|
75
76
|
// eslint-disable-next-line no-unreachable
|
|
76
|
-
/* istanbul ignore next */
|
|
77
77
|
super()
|
|
78
78
|
}
|
|
79
79
|
|
|
80
|
+
static isShadowRoot = isShadowRoot
|
|
81
|
+
|
|
80
82
|
static createShadowRoot(host: GeneralComponent): ShadowRoot {
|
|
81
83
|
const node = Object.create(ShadowRoot.prototype) as ShadowRoot
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
84
|
+
|
|
85
|
+
let be: backend.ShadowRootContext | null = null
|
|
86
|
+
if (BM.SHADOW || (BM.DYNAMIC && host.getBackendMode() === BackendMode.Shadow)) {
|
|
87
|
+
be = (host._$backendElement as backend.Element).getShadowRoot()!
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
node.is = 'shadow'
|
|
87
91
|
node._$idMap = null
|
|
88
92
|
let slotMode = SlotMode.Single
|
|
89
93
|
const hostComponentOptions = host.getComponentOptions()
|
|
@@ -107,10 +111,11 @@ export class ShadowRoot extends VirtualNode {
|
|
|
107
111
|
node._$removeDynamicSlotHandler = undefined
|
|
108
112
|
node._$updateDynamicSlotHandler = undefined
|
|
109
113
|
}
|
|
110
|
-
node._$backendShadowRoot =
|
|
111
|
-
node._$initialize(true,
|
|
114
|
+
node._$backendShadowRoot = be
|
|
115
|
+
node._$initialize(true, be, node, host._$nodeTreeContext)
|
|
112
116
|
node._$host = host
|
|
113
117
|
host.shadowRoot = node
|
|
118
|
+
be?.associateValue(node)
|
|
114
119
|
return node
|
|
115
120
|
}
|
|
116
121
|
|
|
@@ -133,10 +138,10 @@ export class ShadowRoot extends VirtualNode {
|
|
|
133
138
|
createNativeNodeWithInit(
|
|
134
139
|
tagName: string,
|
|
135
140
|
stylingName: string,
|
|
136
|
-
|
|
141
|
+
placeholderHandlerRemover: (() => void) | undefined,
|
|
137
142
|
initPropValues?: (comp: NativeNode) => void,
|
|
138
143
|
): NativeNode {
|
|
139
|
-
const ret = NativeNode.create(tagName, this, stylingName,
|
|
144
|
+
const ret = NativeNode.create(tagName, this, stylingName, placeholderHandlerRemover)
|
|
140
145
|
initPropValues?.(ret)
|
|
141
146
|
return ret
|
|
142
147
|
}
|
|
@@ -160,26 +165,39 @@ export class ShadowRoot extends VirtualNode {
|
|
|
160
165
|
const space = beh.ownerSpace
|
|
161
166
|
const compName = usingKey === undefined ? tagName : usingKey
|
|
162
167
|
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
168
|
+
const possibleComponentDefinitions = [
|
|
169
|
+
// if the target is in using list, then use the one in using list
|
|
170
|
+
beh._$using[compName],
|
|
171
|
+
// if the target is in generics list, then use the one
|
|
172
|
+
hostGenericImpls && hostGenericImpls[compName],
|
|
173
|
+
]
|
|
174
|
+
|
|
175
|
+
for (let i = 0; i < possibleComponentDefinitions.length; i += 1) {
|
|
176
|
+
const cwp = possibleComponentDefinitions[i]
|
|
177
|
+
if (cwp === null || cwp === undefined) continue
|
|
178
|
+
if (typeof cwp === 'string') {
|
|
179
|
+
return this.createNativeNodeWithInit(cwp, tagName, undefined, initPropValues)
|
|
180
|
+
}
|
|
169
181
|
let usingTarget: GeneralComponentDefinition | string | undefined
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
182
|
+
let placeholderHandlerRemover: (() => void) | undefined
|
|
183
|
+
if (cwp.final) {
|
|
184
|
+
usingTarget = cwp.final
|
|
185
|
+
} else if (cwp.placeholder !== null) {
|
|
186
|
+
usingTarget = resolvePlaceholder(cwp.placeholder, space, cwp.source, hostGenericImpls)
|
|
187
|
+
const waiting = cwp.waiting
|
|
188
|
+
if (placeholderCallback && waiting) {
|
|
189
|
+
waiting.add(placeholderCallback)
|
|
190
|
+
waiting.hintUsed(host)
|
|
191
|
+
placeholderHandlerRemover = () => {
|
|
192
|
+
waiting.remove(placeholderCallback)
|
|
193
|
+
}
|
|
194
|
+
}
|
|
174
195
|
}
|
|
175
|
-
const placeholderHandler = placeholderCallback
|
|
176
|
-
? wrapPlaceholderCallback(placeholderCallback, using, host)
|
|
177
|
-
: undefined
|
|
178
196
|
if (typeof usingTarget === 'string') {
|
|
179
197
|
return this.createNativeNodeWithInit(
|
|
180
198
|
usingTarget,
|
|
181
199
|
tagName,
|
|
182
|
-
|
|
200
|
+
placeholderHandlerRemover,
|
|
183
201
|
initPropValues,
|
|
184
202
|
)
|
|
185
203
|
}
|
|
@@ -190,48 +208,24 @@ export class ShadowRoot extends VirtualNode {
|
|
|
190
208
|
this,
|
|
191
209
|
null,
|
|
192
210
|
convertGenerics(usingTarget, beh, host, genericTargets),
|
|
193
|
-
|
|
194
|
-
initPropValues,
|
|
195
|
-
)
|
|
196
|
-
}
|
|
197
|
-
}
|
|
198
|
-
|
|
199
|
-
// if the target is in generics list, then use the one
|
|
200
|
-
const g = hostGenericImpls && hostGenericImpls[compName]
|
|
201
|
-
if (typeof g === 'string') {
|
|
202
|
-
return this.createNativeNodeWithInit(g, tagName, undefined, initPropValues)
|
|
203
|
-
}
|
|
204
|
-
if (g) {
|
|
205
|
-
let genImpl: GeneralComponentDefinition | string | undefined
|
|
206
|
-
if (g.final) {
|
|
207
|
-
genImpl = g.final
|
|
208
|
-
} else if (g.placeholder !== null) {
|
|
209
|
-
genImpl = resolvePlaceholder(g.placeholder, space, g.source, hostGenericImpls)
|
|
210
|
-
}
|
|
211
|
-
const placeholderHandler = placeholderCallback
|
|
212
|
-
? wrapPlaceholderCallback(placeholderCallback, g, host)
|
|
213
|
-
: undefined
|
|
214
|
-
if (typeof genImpl === 'string') {
|
|
215
|
-
return this.createNativeNodeWithInit(genImpl, tagName, placeholderHandler, initPropValues)
|
|
216
|
-
}
|
|
217
|
-
if (genImpl) {
|
|
218
|
-
return Component._$advancedCreate(
|
|
219
|
-
tagName,
|
|
220
|
-
genImpl,
|
|
221
|
-
this,
|
|
222
|
-
null,
|
|
223
|
-
convertGenerics(genImpl, beh, host, genericTargets),
|
|
224
|
-
placeholderHandler,
|
|
211
|
+
placeholderHandlerRemover,
|
|
225
212
|
initPropValues,
|
|
226
213
|
)
|
|
227
214
|
}
|
|
228
215
|
}
|
|
229
216
|
|
|
230
217
|
// find in the space otherwise
|
|
231
|
-
|
|
232
|
-
|
|
218
|
+
let comp = space.getGlobalUsingComponent(compName)
|
|
219
|
+
if (comp === null && space._$allowUnusedNativeNode && compName !== '') {
|
|
220
|
+
comp = compName
|
|
221
|
+
}
|
|
233
222
|
if (!comp) {
|
|
234
|
-
|
|
223
|
+
comp = space.getDefaultComponent()
|
|
224
|
+
/* istanbul ignore if */
|
|
225
|
+
if (!comp) {
|
|
226
|
+
throw new ThirdError(`Cannot find component "${compName}"`, undefined, this._$host)
|
|
227
|
+
}
|
|
228
|
+
triggerWarning(`Cannot find component "${compName}", using default component.`, this._$host)
|
|
235
229
|
}
|
|
236
230
|
if (typeof comp === 'string') {
|
|
237
231
|
return this.createNativeNodeWithInit(comp, tagName, undefined, initPropValues)
|
|
@@ -247,6 +241,13 @@ export class ShadowRoot extends VirtualNode {
|
|
|
247
241
|
)
|
|
248
242
|
}
|
|
249
243
|
|
|
244
|
+
createComponentByDef(
|
|
245
|
+
tagName: string,
|
|
246
|
+
componentDef: GeneralComponentDefinition,
|
|
247
|
+
): GeneralComponent {
|
|
248
|
+
return Component._$advancedCreate(tagName, componentDef, this, null, null, undefined)
|
|
249
|
+
}
|
|
250
|
+
|
|
250
251
|
/**
|
|
251
252
|
* Create a component if the given tag name is a component in the space, or a native node if not
|
|
252
253
|
*
|
|
@@ -280,10 +281,13 @@ export class ShadowRoot extends VirtualNode {
|
|
|
280
281
|
)
|
|
281
282
|
}
|
|
282
283
|
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
284
|
+
if (space._$allowUnusedNativeNode) {
|
|
285
|
+
// use native node otherwise
|
|
286
|
+
const node = NativeNode.create(tagName, this)
|
|
287
|
+
initPropValues?.(node)
|
|
288
|
+
return node
|
|
289
|
+
}
|
|
290
|
+
throw new ThirdError(`Unknown tag name ${tagName}`, '[render]', host)
|
|
287
291
|
}
|
|
288
292
|
|
|
289
293
|
/**
|
|
@@ -372,7 +376,7 @@ export class ShadowRoot extends VirtualNode {
|
|
|
372
376
|
}
|
|
373
377
|
if (slotMode === SlotMode.Multiple) {
|
|
374
378
|
let name: string
|
|
375
|
-
if (elem
|
|
379
|
+
if (isElement(elem)) {
|
|
376
380
|
name = elem._$nodeSlot
|
|
377
381
|
} else {
|
|
378
382
|
name = ''
|
|
@@ -833,154 +837,6 @@ export class ShadowRoot extends VirtualNode {
|
|
|
833
837
|
getSlotMode(): SlotMode {
|
|
834
838
|
return this._$slotMode
|
|
835
839
|
}
|
|
836
|
-
|
|
837
|
-
/** @internal */
|
|
838
|
-
static _$updateSubtreeSlotNodes(
|
|
839
|
-
parentNode: Element,
|
|
840
|
-
elements: Node[],
|
|
841
|
-
shadowRoot: ShadowRoot | null,
|
|
842
|
-
oldShadowRoot: ShadowRoot | null,
|
|
843
|
-
posIndex: number,
|
|
844
|
-
):
|
|
845
|
-
| { updateContainingSlot: () => void; removeSlotNodes: () => void; insertSlotNodes: () => void }
|
|
846
|
-
| undefined {
|
|
847
|
-
if (!shadowRoot && !oldShadowRoot) return undefined
|
|
848
|
-
|
|
849
|
-
const slotMode = shadowRoot?.getSlotMode()
|
|
850
|
-
const oldSlotMode = oldShadowRoot?.getSlotMode()
|
|
851
|
-
|
|
852
|
-
if (
|
|
853
|
-
(slotMode === undefined || slotMode === SlotMode.Direct) &&
|
|
854
|
-
(oldSlotMode === undefined || oldSlotMode === SlotMode.Direct)
|
|
855
|
-
) {
|
|
856
|
-
return undefined
|
|
857
|
-
}
|
|
858
|
-
|
|
859
|
-
if (
|
|
860
|
-
(slotMode === undefined || slotMode === SlotMode.Single) &&
|
|
861
|
-
(oldSlotMode === undefined || oldSlotMode === SlotMode.Single)
|
|
862
|
-
) {
|
|
863
|
-
let removeStart = -1
|
|
864
|
-
let removeCount = 0
|
|
865
|
-
let insertPos = -1
|
|
866
|
-
const slotNodesToUpdate: Node[] = []
|
|
867
|
-
const oldContainingSlot = elements[0]!.containingSlot
|
|
868
|
-
const containingSlot = shadowRoot?.getContainingSlot(elements[0]!)
|
|
869
|
-
|
|
870
|
-
for (let i = 0; i < elements.length; i += 1) {
|
|
871
|
-
const elem = elements[i]!
|
|
872
|
-
// eslint-disable-next-line no-loop-func
|
|
873
|
-
Element.forEachNodeInSlot(elem, (node) => {
|
|
874
|
-
if (oldContainingSlot) {
|
|
875
|
-
if (removeCount) {
|
|
876
|
-
removeCount += 1
|
|
877
|
-
} else {
|
|
878
|
-
removeStart = node.slotIndex!
|
|
879
|
-
removeCount = 1
|
|
880
|
-
}
|
|
881
|
-
}
|
|
882
|
-
|
|
883
|
-
slotNodesToUpdate.push(node)
|
|
884
|
-
})
|
|
885
|
-
}
|
|
886
|
-
|
|
887
|
-
if (containingSlot && slotNodesToUpdate.length) {
|
|
888
|
-
const firstSlotNode = slotNodesToUpdate[0]!
|
|
889
|
-
insertPos = Element._$findSlotNodeInsertPosition(containingSlot, firstSlotNode, posIndex)
|
|
890
|
-
}
|
|
891
|
-
|
|
892
|
-
return {
|
|
893
|
-
updateContainingSlot: () => {
|
|
894
|
-
for (let i = slotNodesToUpdate.length - 1; i >= 0; i -= 1) {
|
|
895
|
-
const node = slotNodesToUpdate[i]!
|
|
896
|
-
Element._$updateContainingSlot(node, containingSlot)
|
|
897
|
-
}
|
|
898
|
-
},
|
|
899
|
-
removeSlotNodes: () => {
|
|
900
|
-
if (oldShadowRoot && oldContainingSlot && removeCount) {
|
|
901
|
-
Element._$spliceSlotNodes(oldContainingSlot, removeStart, removeCount, undefined)
|
|
902
|
-
}
|
|
903
|
-
},
|
|
904
|
-
insertSlotNodes: () => {
|
|
905
|
-
if (shadowRoot && containingSlot && slotNodesToUpdate.length) {
|
|
906
|
-
Element._$spliceSlotNodes(containingSlot, insertPos, 0, slotNodesToUpdate)
|
|
907
|
-
}
|
|
908
|
-
},
|
|
909
|
-
}
|
|
910
|
-
}
|
|
911
|
-
const slotNodesToInsertMap = new Map<Element, { nodes: Node[]; insertPos: number }>()
|
|
912
|
-
const slotNodesToRemoveMap = new Map<Element, { start: number; count: number }>()
|
|
913
|
-
|
|
914
|
-
const slotNodesWithContainingSlot: [Node, Element | undefined | null][] = []
|
|
915
|
-
|
|
916
|
-
for (let i = 0; i < elements.length; i += 1) {
|
|
917
|
-
const elem = elements[i]!
|
|
918
|
-
Element.forEachNodeInSlot(elem, (node, oldContainingSlot) => {
|
|
919
|
-
const containingSlot =
|
|
920
|
-
slotMode !== SlotMode.Direct ? shadowRoot?.getContainingSlot(node) : undefined
|
|
921
|
-
|
|
922
|
-
if (oldContainingSlot) {
|
|
923
|
-
const slotNodesToRemove = slotNodesToRemoveMap.get(oldContainingSlot)
|
|
924
|
-
if (slotNodesToRemove) {
|
|
925
|
-
slotNodesToRemove.count += 1
|
|
926
|
-
} else {
|
|
927
|
-
slotNodesToRemoveMap.set(oldContainingSlot, { start: node.slotIndex!, count: 1 })
|
|
928
|
-
}
|
|
929
|
-
}
|
|
930
|
-
|
|
931
|
-
if (containingSlot) {
|
|
932
|
-
const slotNodesToInsert = slotNodesToInsertMap.get(containingSlot)
|
|
933
|
-
if (slotNodesToInsert) {
|
|
934
|
-
slotNodesToInsert.nodes.push(node)
|
|
935
|
-
} else {
|
|
936
|
-
slotNodesToInsertMap.set(containingSlot, { nodes: [node], insertPos: -1 })
|
|
937
|
-
}
|
|
938
|
-
}
|
|
939
|
-
|
|
940
|
-
slotNodesWithContainingSlot.push([node, containingSlot])
|
|
941
|
-
})
|
|
942
|
-
}
|
|
943
|
-
|
|
944
|
-
if (shadowRoot && slotNodesToInsertMap.size) {
|
|
945
|
-
const iter = slotNodesToInsertMap.entries()
|
|
946
|
-
|
|
947
|
-
for (let it = iter.next(); !it.done; it = iter.next()) {
|
|
948
|
-
const [slot, { nodes: slotNodesToInsert }] = it.value
|
|
949
|
-
const firstSlotNodeToInsert = slotNodesToInsert[0]!
|
|
950
|
-
it.value[1].insertPos = Element._$findSlotNodeInsertPosition(
|
|
951
|
-
slot,
|
|
952
|
-
firstSlotNodeToInsert,
|
|
953
|
-
posIndex,
|
|
954
|
-
)
|
|
955
|
-
}
|
|
956
|
-
}
|
|
957
|
-
|
|
958
|
-
return {
|
|
959
|
-
updateContainingSlot: () => {
|
|
960
|
-
for (let i = slotNodesWithContainingSlot.length - 1; i >= 0; i -= 1) {
|
|
961
|
-
const [node, containingSlot] = slotNodesWithContainingSlot[i]!
|
|
962
|
-
Element._$updateContainingSlot(node, containingSlot)
|
|
963
|
-
}
|
|
964
|
-
},
|
|
965
|
-
removeSlotNodes: () => {
|
|
966
|
-
if (oldShadowRoot && slotNodesToRemoveMap.size) {
|
|
967
|
-
const iter = slotNodesToRemoveMap.entries()
|
|
968
|
-
for (let it = iter.next(); !it.done; it = iter.next()) {
|
|
969
|
-
const [slot, { start, count }] = it.value
|
|
970
|
-
Element._$spliceSlotNodes(slot, start, count, undefined)
|
|
971
|
-
}
|
|
972
|
-
}
|
|
973
|
-
},
|
|
974
|
-
insertSlotNodes: () => {
|
|
975
|
-
if (shadowRoot && slotNodesToInsertMap.size) {
|
|
976
|
-
const iter = slotNodesToInsertMap.entries()
|
|
977
|
-
|
|
978
|
-
for (let it = iter.next(); !it.done; it = iter.next()) {
|
|
979
|
-
const [slot, { nodes: slotNodesToInsert, insertPos }] = it.value
|
|
980
|
-
Element._$spliceSlotNodes(slot, insertPos, 0, slotNodesToInsert)
|
|
981
|
-
}
|
|
982
|
-
}
|
|
983
|
-
},
|
|
984
|
-
}
|
|
985
|
-
}
|
|
986
840
|
}
|
|
841
|
+
|
|
842
|
+
ShadowRoot.prototype[SHADOW_ROOT_SYMBOL] = true
|
package/src/template_engine.ts
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import { GeneralBehavior } from './behavior'
|
|
2
|
-
import { ShadowRoot } from './shadow_root'
|
|
3
|
-
import { DataChange, DataValue } from './data_proxy'
|
|
4
|
-
import { NormalizedComponentOptions } from './global_options'
|
|
5
|
-
import { ExternalShadowRoot } from './external_shadow_tree'
|
|
6
|
-
import { GeneralComponent } from './component'
|
|
1
|
+
import { type GeneralBehavior } from './behavior'
|
|
2
|
+
import { type ShadowRoot } from './shadow_root'
|
|
3
|
+
import { type DataChange, type DataValue } from './data_proxy'
|
|
4
|
+
import { type NormalizedComponentOptions } from './global_options'
|
|
5
|
+
import { type ExternalShadowRoot } from './external_shadow_tree'
|
|
6
|
+
import { type GeneralComponent } from './component'
|
|
7
7
|
|
|
8
8
|
/**
|
|
9
9
|
* A template engine that handles the template part of a component
|
|
@@ -26,7 +26,10 @@ export interface Template {
|
|
|
26
26
|
/**
|
|
27
27
|
* Create a template instance for a component instance
|
|
28
28
|
*/
|
|
29
|
-
createInstance(
|
|
29
|
+
createInstance(
|
|
30
|
+
elem: GeneralComponent,
|
|
31
|
+
createShadowRoot: (component: GeneralComponent) => ShadowRoot,
|
|
32
|
+
): TemplateInstance
|
|
30
33
|
|
|
31
34
|
/**
|
|
32
35
|
* Update the content of the template (optional)
|
package/src/text_node.ts
CHANGED
|
@@ -1,14 +1,25 @@
|
|
|
1
|
-
import
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
1
|
+
import {
|
|
2
|
+
BM,
|
|
3
|
+
BackendMode,
|
|
4
|
+
type GeneralBackendElement,
|
|
5
|
+
type backend,
|
|
6
|
+
type composedBackend,
|
|
7
|
+
type domlikeBackend,
|
|
8
|
+
} from './backend'
|
|
9
|
+
import { type Element } from './element'
|
|
10
|
+
import { ENV } from './global_options'
|
|
11
|
+
import { performanceMeasureEnd, performanceMeasureStart } from './devtool'
|
|
6
12
|
import { MutationObserverTarget } from './mutation_observer'
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
13
|
+
import { type NodeCast } from './node'
|
|
14
|
+
import { type ShadowRoot } from './shadow_root'
|
|
15
|
+
import { TEXT_NODE_SYMBOL, isTextNode } from './type_symbol'
|
|
9
16
|
|
|
10
17
|
export class TextNode implements NodeCast {
|
|
18
|
+
/* @internal */
|
|
19
|
+
[TEXT_NODE_SYMBOL]!: true
|
|
20
|
+
/* @internal */
|
|
11
21
|
_$backendElement: GeneralBackendElement | null
|
|
22
|
+
/* @internal */
|
|
12
23
|
private _$text: string
|
|
13
24
|
ownerShadowRoot: ShadowRoot
|
|
14
25
|
parentNode: Element | null
|
|
@@ -31,18 +42,21 @@ export class TextNode implements NodeCast {
|
|
|
31
42
|
|
|
32
43
|
constructor(text: string, owner: ShadowRoot) {
|
|
33
44
|
this._$text = String(text)
|
|
34
|
-
let backendElement: GeneralBackendElement | null
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
)
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
+
let backendElement: GeneralBackendElement | null = null
|
|
46
|
+
const context = owner.getBackendContext()
|
|
47
|
+
if (context) {
|
|
48
|
+
if (ENV.DEV) performanceMeasureStart('backend.createTextNode')
|
|
49
|
+
if (BM.DOMLIKE || (BM.DYNAMIC && owner.getBackendMode() === BackendMode.Domlike)) {
|
|
50
|
+
backendElement = (context as domlikeBackend.Context).document.createTextNode(text)
|
|
51
|
+
} else if (BM.SHADOW || (BM.DYNAMIC && owner.getBackendMode() === BackendMode.Shadow)) {
|
|
52
|
+
const backend = owner._$backendShadowRoot!
|
|
53
|
+
backendElement = backend.createTextNode(text)
|
|
54
|
+
} else {
|
|
55
|
+
const backend = context as composedBackend.Context
|
|
56
|
+
backendElement = backend.createTextNode(text)
|
|
57
|
+
}
|
|
45
58
|
}
|
|
59
|
+
if (ENV.DEV) performanceMeasureEnd()
|
|
46
60
|
this._$backendElement = backendElement
|
|
47
61
|
this.ownerShadowRoot = owner
|
|
48
62
|
this.parentNode = null
|
|
@@ -50,6 +64,8 @@ export class TextNode implements NodeCast {
|
|
|
50
64
|
this.containingSlot = undefined
|
|
51
65
|
}
|
|
52
66
|
|
|
67
|
+
static isTextNode = isTextNode
|
|
68
|
+
|
|
53
69
|
static create(text: string, ownerShadowRoot: ShadowRoot): TextNode {
|
|
54
70
|
return new TextNode(text, ownerShadowRoot)
|
|
55
71
|
}
|
|
@@ -87,7 +103,9 @@ export class TextNode implements NodeCast {
|
|
|
87
103
|
(BM.DYNAMIC && this.ownerShadowRoot.getBackendMode() === BackendMode.Domlike)
|
|
88
104
|
)
|
|
89
105
|
) {
|
|
106
|
+
if (ENV.DEV) performanceMeasureStart('backend.release')
|
|
90
107
|
;(this._$backendElement as backend.Element | composedBackend.Element).release()
|
|
108
|
+
if (ENV.DEV) performanceMeasureEnd()
|
|
91
109
|
}
|
|
92
110
|
this._$backendElement = null
|
|
93
111
|
}
|
|
@@ -122,8 +140,11 @@ export class TextNode implements NodeCast {
|
|
|
122
140
|
}
|
|
123
141
|
|
|
124
142
|
set textContent(text: string) {
|
|
125
|
-
|
|
143
|
+
const newText = String(text)
|
|
144
|
+
if (newText === this._$text) return
|
|
145
|
+
this._$text = newText
|
|
126
146
|
if (this._$backendElement) {
|
|
147
|
+
if (ENV.DEV) performanceMeasureStart('backend.setText')
|
|
127
148
|
if (
|
|
128
149
|
BM.DOMLIKE ||
|
|
129
150
|
(BM.DYNAMIC && this.ownerShadowRoot.getBackendMode() === BackendMode.Domlike)
|
|
@@ -132,6 +153,7 @@ export class TextNode implements NodeCast {
|
|
|
132
153
|
} else {
|
|
133
154
|
;(this._$backendElement as backend.Element | composedBackend.Element).setText(this._$text)
|
|
134
155
|
}
|
|
156
|
+
if (ENV.DEV) performanceMeasureEnd()
|
|
135
157
|
}
|
|
136
158
|
MutationObserverTarget.callTextObservers(this, {
|
|
137
159
|
type: 'characterData',
|
|
@@ -139,3 +161,5 @@ export class TextNode implements NodeCast {
|
|
|
139
161
|
})
|
|
140
162
|
}
|
|
141
163
|
}
|
|
164
|
+
|
|
165
|
+
TextNode.prototype[TEXT_NODE_SYMBOL] = true
|