@lightningjs/blits 1.30.0 → 1.30.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.
- package/.editorconfig +7 -7
- package/.eslintignore +1 -1
- package/.eslintrc.cjs +65 -65
- package/.github/workflows/comment-lint-results.yml +124 -124
- package/.github/workflows/comment-test-results.yml +108 -108
- package/.github/workflows/deploy-docs.yml +27 -27
- package/.github/workflows/run-blits-tests.yml +141 -141
- package/.github/workflows/run-lint.yml +127 -127
- package/.husky/pre-commit +1 -1
- package/.vscode/extensions.json +7 -7
- package/.vscode/settings.json +9 -9
- package/CHANGELOG.md +1019 -1005
- package/COPYING +1 -0
- package/LICENSE +202 -202
- package/NOTICE +12 -12
- package/README.md +33 -33
- package/bin/index.js +8 -8
- package/blits.d.ts +6 -6
- package/docs/README.md +19 -19
- package/docs/_sidebar.md +37 -37
- package/docs/built-in/directives.md +50 -50
- package/docs/built-in/for-loop.md +203 -203
- package/docs/built-in/layout.md +168 -168
- package/docs/components/component_state.md +90 -90
- package/docs/components/computed_properties.md +45 -45
- package/docs/components/lifecycle_events.md +42 -42
- package/docs/components/methods.md +45 -45
- package/docs/components/props.md +56 -56
- package/docs/components/user_input.md +186 -186
- package/docs/components/utility_methods.md +320 -320
- package/docs/components/watchers.md +34 -34
- package/docs/essentials/application_root.md +19 -19
- package/docs/essentials/components.md +68 -68
- package/docs/essentials/displaying_images.md +67 -67
- package/docs/essentials/displaying_text.md +135 -135
- package/docs/essentials/element_attributes.md +195 -195
- package/docs/essentials/settings.md +117 -117
- package/docs/essentials/template_syntax.md +83 -83
- package/docs/getting_started/file_structure.md +58 -58
- package/docs/getting_started/getting_started.md +45 -45
- package/docs/getting_started/intro.md +20 -20
- package/docs/index.html +47 -47
- package/docs/performance/lazy-loading.md +161 -161
- package/docs/plugins/global_app_state.md +98 -98
- package/docs/plugins/language.md +172 -172
- package/docs/plugins/text-to-speech-announcer.md +119 -119
- package/docs/plugins/theme.md +176 -176
- package/docs/router/basics.md +175 -175
- package/docs/router/hooks.md +70 -70
- package/docs/router/transitions.md +146 -146
- package/docs/sidebar.json +171 -171
- package/docs/transitions_animations/transitions.md +150 -150
- package/index.d.ts +1099 -1099
- package/index.js +28 -28
- package/jsconfig.json +12 -12
- package/package.json +56 -56
- package/public/assets/fps_sprite.base64.js +1 -1
- package/scripts/postpublish.js +59 -59
- package/scripts/prepublishOnly.js +84 -84
- package/scripts/prepush.js +78 -78
- package/src/announcer/announcer.js +162 -162
- package/src/announcer/speechSynthesis.js +107 -107
- package/src/application.js +100 -100
- package/src/component/base/announcer.js +27 -27
- package/src/component/base/events.js +69 -69
- package/src/component/base/index.js +33 -33
- package/src/component/base/methods.js +244 -244
- package/src/component/base/router.js +41 -41
- package/src/component/base/timeouts_intervals.js +99 -99
- package/src/component/base/utils.js +72 -72
- package/src/component/setup/computed.js +48 -48
- package/src/component/setup/index.js +62 -62
- package/src/component/setup/input.js +30 -30
- package/src/component/setup/methods.js +37 -37
- package/src/component/setup/props.js +62 -62
- package/src/component/setup/props.test.js +238 -238
- package/src/component/setup/routes.js +42 -42
- package/src/component/setup/state.js +59 -59
- package/src/component/setup/watch.js +35 -35
- package/src/component.js +437 -437
- package/src/component.test.js +388 -388
- package/src/components/Circle.js +73 -73
- package/src/components/Circle.orig.js +31 -31
- package/src/components/FPScounter.js +1510 -1510
- package/src/components/FPScounter.orig.js +121 -121
- package/src/components/RouterView.js +81 -81
- package/src/components/RouterView.orig.js +54 -54
- package/src/components/Sprite.js +94 -94
- package/src/components/Sprite.orig.js +58 -58
- package/src/components/index.js +28 -28
- package/src/components/index.orig.js +28 -28
- package/src/constants.js +21 -21
- package/src/engine.js +1 -1
- package/src/engines/L3/element.js +744 -744
- package/src/engines/L3/element.test.js +579 -579
- package/src/engines/L3/fontLoader.js +38 -38
- package/src/engines/L3/index.js +7 -7
- package/src/engines/L3/launch.js +123 -123
- package/src/engines/L3/shaderLoader.js +12 -12
- package/src/engines/index.js +1 -1
- package/src/focus.js +90 -90
- package/src/helpers/deepEqualArray.js +50 -50
- package/src/helpers/deepEqualArray.test.js +127 -127
- package/src/helpers/fetchJson.js +34 -34
- package/src/helpers/sequence.js +26 -26
- package/src/launch.js +123 -123
- package/src/lib/blitsfileconverter/blitsfileconverter.js +52 -52
- package/src/lib/codegenerator/generator.js +788 -788
- package/src/lib/codegenerator/generator.test.js +3801 -3801
- package/src/lib/colors/colors.js +92 -92
- package/src/lib/colors/colors.test.js +290 -290
- package/src/lib/colors/htmlColors.js +168 -168
- package/src/lib/componentId.js +49 -49
- package/src/lib/componentId.test.js +84 -84
- package/src/lib/eventListeners.js +123 -123
- package/src/lib/eventListeners.test.js +236 -236
- package/src/lib/hooks.js +59 -59
- package/src/lib/lifecycle.js +85 -85
- package/src/lib/log.js +117 -117
- package/src/lib/precompiler/precompiler.js +73 -73
- package/src/lib/reactivity/effect.js +93 -93
- package/src/lib/reactivity/effect.test.js +35 -35
- package/src/lib/reactivity/reactive.js +208 -208
- package/src/lib/reactivity/reactive.test.js +27 -27
- package/src/lib/reactivityguard/computedprops.js +218 -218
- package/src/lib/symbols.js +108 -108
- package/src/lib/templateparser/parser.js +386 -386
- package/src/lib/templateparser/parser.test.js +1411 -1411
- package/src/lib/utils.js +27 -27
- package/src/plugin.js +27 -27
- package/src/plugins/appstate.js +26 -26
- package/src/plugins/index.js +20 -20
- package/src/plugins/language.js +152 -152
- package/src/plugins/log.js +25 -25
- package/src/plugins/theme.js +94 -94
- package/src/router/router.js +514 -514
- package/src/router/router.test.js +473 -473
- package/src/router/transitions/fadeIn.js +27 -27
- package/src/router/transitions/fadeInOut.js +33 -33
- package/src/router/transitions/index.js +21 -21
- package/src/router/transitions/slideIn.js +28 -28
- package/src/router/transitions/slideInOut.js +33 -33
- package/src/settings.js +40 -40
- package/vite/blitsFileConverter.js +67 -67
- package/vite/index.js +28 -28
- package/vite/msdfGenerator.js +269 -269
- package/vite/preCompiler.js +42 -42
- package/vite/reactivityGuard.js +45 -45
- package/vscode/data/template-attributes.json +589 -589
|
@@ -1,93 +1,93 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
-
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
* you may not use this file except in compliance with the License.
|
|
5
|
-
* You may obtain a copy of the License at
|
|
6
|
-
*
|
|
7
|
-
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
*
|
|
9
|
-
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
* See the License for the specific language governing permissions and
|
|
13
|
-
* limitations under the License.
|
|
14
|
-
*
|
|
15
|
-
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
-
*/
|
|
17
|
-
|
|
18
|
-
let currentEffect = null
|
|
19
|
-
let currentKey = null
|
|
20
|
-
|
|
21
|
-
let paused = false
|
|
22
|
-
|
|
23
|
-
export const pauseTracking = () => {
|
|
24
|
-
paused = true
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
export const resumeTracking = () => {
|
|
28
|
-
paused = false
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
const objectMap = new WeakMap()
|
|
32
|
-
const globalEffectsMap = new Map()
|
|
33
|
-
|
|
34
|
-
export const removeGlobalEffects = (effectsToRemove) => {
|
|
35
|
-
if (globalEffectsMap.size === 0) return
|
|
36
|
-
for (const [effect, target] of globalEffectsMap) {
|
|
37
|
-
if (effectsToRemove.indexOf(effect) === -1) continue
|
|
38
|
-
const effectsSet = objectMap.get(target)
|
|
39
|
-
if (effectsSet === undefined) continue
|
|
40
|
-
for (const set of effectsSet.values()) {
|
|
41
|
-
set.delete(effect)
|
|
42
|
-
globalEffectsMap.delete(effect)
|
|
43
|
-
}
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
export const track = (target, key, global = false) => {
|
|
48
|
-
if (currentEffect !== null) {
|
|
49
|
-
if (paused) {
|
|
50
|
-
return
|
|
51
|
-
}
|
|
52
|
-
// note: nesting the conditions like this seems to perform better ¯\_(ツ)_/¯
|
|
53
|
-
if (Array.isArray(currentKey) === true) {
|
|
54
|
-
if (currentKey.includes(key) === false) return
|
|
55
|
-
} else if (currentKey !== null && key !== currentKey) return
|
|
56
|
-
|
|
57
|
-
let effectsMap = objectMap.get(target)
|
|
58
|
-
if (effectsMap === undefined) {
|
|
59
|
-
effectsMap = new Map()
|
|
60
|
-
objectMap.set(target, effectsMap)
|
|
61
|
-
}
|
|
62
|
-
let effects = effectsMap.get(key)
|
|
63
|
-
if (effects === undefined) {
|
|
64
|
-
effects = new Set()
|
|
65
|
-
effectsMap.set(key, effects)
|
|
66
|
-
}
|
|
67
|
-
effects.add(currentEffect)
|
|
68
|
-
|
|
69
|
-
if (global === true) globalEffectsMap.set(currentEffect, target)
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
export const trigger = (target, key, force = false) => {
|
|
74
|
-
if (paused === true) return
|
|
75
|
-
const effectsMap = objectMap.get(target)
|
|
76
|
-
if (effectsMap === undefined) {
|
|
77
|
-
return
|
|
78
|
-
}
|
|
79
|
-
const effects = effectsMap.get(key)
|
|
80
|
-
if (effects !== undefined) {
|
|
81
|
-
for (let effect of effects) {
|
|
82
|
-
effect(force)
|
|
83
|
-
}
|
|
84
|
-
}
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
export const effect = (effect, key = null) => {
|
|
88
|
-
currentEffect = effect
|
|
89
|
-
currentKey = key
|
|
90
|
-
currentEffect()
|
|
91
|
-
currentEffect = null
|
|
92
|
-
currentKey = null
|
|
93
|
-
}
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
* you may not use this file except in compliance with the License.
|
|
5
|
+
* You may obtain a copy of the License at
|
|
6
|
+
*
|
|
7
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
*
|
|
9
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
* See the License for the specific language governing permissions and
|
|
13
|
+
* limitations under the License.
|
|
14
|
+
*
|
|
15
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
let currentEffect = null
|
|
19
|
+
let currentKey = null
|
|
20
|
+
|
|
21
|
+
let paused = false
|
|
22
|
+
|
|
23
|
+
export const pauseTracking = () => {
|
|
24
|
+
paused = true
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
export const resumeTracking = () => {
|
|
28
|
+
paused = false
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
const objectMap = new WeakMap()
|
|
32
|
+
const globalEffectsMap = new Map()
|
|
33
|
+
|
|
34
|
+
export const removeGlobalEffects = (effectsToRemove) => {
|
|
35
|
+
if (globalEffectsMap.size === 0) return
|
|
36
|
+
for (const [effect, target] of globalEffectsMap) {
|
|
37
|
+
if (effectsToRemove.indexOf(effect) === -1) continue
|
|
38
|
+
const effectsSet = objectMap.get(target)
|
|
39
|
+
if (effectsSet === undefined) continue
|
|
40
|
+
for (const set of effectsSet.values()) {
|
|
41
|
+
set.delete(effect)
|
|
42
|
+
globalEffectsMap.delete(effect)
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export const track = (target, key, global = false) => {
|
|
48
|
+
if (currentEffect !== null) {
|
|
49
|
+
if (paused) {
|
|
50
|
+
return
|
|
51
|
+
}
|
|
52
|
+
// note: nesting the conditions like this seems to perform better ¯\_(ツ)_/¯
|
|
53
|
+
if (Array.isArray(currentKey) === true) {
|
|
54
|
+
if (currentKey.includes(key) === false) return
|
|
55
|
+
} else if (currentKey !== null && key !== currentKey) return
|
|
56
|
+
|
|
57
|
+
let effectsMap = objectMap.get(target)
|
|
58
|
+
if (effectsMap === undefined) {
|
|
59
|
+
effectsMap = new Map()
|
|
60
|
+
objectMap.set(target, effectsMap)
|
|
61
|
+
}
|
|
62
|
+
let effects = effectsMap.get(key)
|
|
63
|
+
if (effects === undefined) {
|
|
64
|
+
effects = new Set()
|
|
65
|
+
effectsMap.set(key, effects)
|
|
66
|
+
}
|
|
67
|
+
effects.add(currentEffect)
|
|
68
|
+
|
|
69
|
+
if (global === true) globalEffectsMap.set(currentEffect, target)
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
export const trigger = (target, key, force = false) => {
|
|
74
|
+
if (paused === true) return
|
|
75
|
+
const effectsMap = objectMap.get(target)
|
|
76
|
+
if (effectsMap === undefined) {
|
|
77
|
+
return
|
|
78
|
+
}
|
|
79
|
+
const effects = effectsMap.get(key)
|
|
80
|
+
if (effects !== undefined) {
|
|
81
|
+
for (let effect of effects) {
|
|
82
|
+
effect(force)
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
export const effect = (effect, key = null) => {
|
|
88
|
+
currentEffect = effect
|
|
89
|
+
currentKey = key
|
|
90
|
+
currentEffect()
|
|
91
|
+
currentEffect = null
|
|
92
|
+
currentKey = null
|
|
93
|
+
}
|
|
@@ -1,35 +1,35 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
-
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
* you may not use this file except in compliance with the License.
|
|
5
|
-
* You may obtain a copy of the License at
|
|
6
|
-
*
|
|
7
|
-
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
*
|
|
9
|
-
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
* See the License for the specific language governing permissions and
|
|
13
|
-
* limitations under the License.
|
|
14
|
-
*
|
|
15
|
-
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
-
*/
|
|
17
|
-
|
|
18
|
-
import test from 'tape'
|
|
19
|
-
import { trigger, track } from './effect.js'
|
|
20
|
-
|
|
21
|
-
test('Trigger - type', (assert) => {
|
|
22
|
-
const expected = 'function'
|
|
23
|
-
const actual = typeof trigger
|
|
24
|
-
|
|
25
|
-
assert.equal(actual, expected, 'Trigger should be a function')
|
|
26
|
-
assert.end()
|
|
27
|
-
})
|
|
28
|
-
|
|
29
|
-
test('Track type', (assert) => {
|
|
30
|
-
const expected = 'function'
|
|
31
|
-
const actual = typeof track
|
|
32
|
-
|
|
33
|
-
assert.equal(actual, expected, 'Track should be a function')
|
|
34
|
-
assert.end()
|
|
35
|
-
})
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
* you may not use this file except in compliance with the License.
|
|
5
|
+
* You may obtain a copy of the License at
|
|
6
|
+
*
|
|
7
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
*
|
|
9
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
* See the License for the specific language governing permissions and
|
|
13
|
+
* limitations under the License.
|
|
14
|
+
*
|
|
15
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
import test from 'tape'
|
|
19
|
+
import { trigger, track } from './effect.js'
|
|
20
|
+
|
|
21
|
+
test('Trigger - type', (assert) => {
|
|
22
|
+
const expected = 'function'
|
|
23
|
+
const actual = typeof trigger
|
|
24
|
+
|
|
25
|
+
assert.equal(actual, expected, 'Trigger should be a function')
|
|
26
|
+
assert.end()
|
|
27
|
+
})
|
|
28
|
+
|
|
29
|
+
test('Track type', (assert) => {
|
|
30
|
+
const expected = 'function'
|
|
31
|
+
const actual = typeof track
|
|
32
|
+
|
|
33
|
+
assert.equal(actual, expected, 'Track should be a function')
|
|
34
|
+
assert.end()
|
|
35
|
+
})
|
|
@@ -1,208 +1,208 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
-
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
* you may not use this file except in compliance with the License.
|
|
5
|
-
* You may obtain a copy of the License at
|
|
6
|
-
*
|
|
7
|
-
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
*
|
|
9
|
-
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
* See the License for the specific language governing permissions and
|
|
13
|
-
* limitations under the License.
|
|
14
|
-
*
|
|
15
|
-
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
-
*/
|
|
17
|
-
|
|
18
|
-
import { track, trigger, pauseTracking, resumeTracking } from './effect.js'
|
|
19
|
-
import symbols from '../symbols.js'
|
|
20
|
-
import deepEqualArray from '../../helpers/deepEqualArray.js'
|
|
21
|
-
|
|
22
|
-
const arrayPatchMethods = ['push', 'pop', 'shift', 'unshift', 'splice', 'sort']
|
|
23
|
-
|
|
24
|
-
const proxyMap = new WeakMap()
|
|
25
|
-
|
|
26
|
-
export const getRaw = (value) => {
|
|
27
|
-
const raw = value && value[symbols.raw]
|
|
28
|
-
return raw ? getRaw(raw) : value
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
const reactiveProxy = (original, _parent = null, _key, global) => {
|
|
32
|
-
// only create a proxy for plain objects. Other classes, Blits components, renderer textures etc
|
|
33
|
-
// are returned unmodified and will not become reactive
|
|
34
|
-
if (
|
|
35
|
-
typeof original === 'object' &&
|
|
36
|
-
Array.isArray(original) === false &&
|
|
37
|
-
Object.getPrototypeOf(original) !== Object.prototype
|
|
38
|
-
) {
|
|
39
|
-
return original
|
|
40
|
-
}
|
|
41
|
-
// if original object is already a proxy, don't create a new one but return the existing one instead
|
|
42
|
-
const existingProxy = proxyMap.get(original)
|
|
43
|
-
if (existingProxy !== undefined) {
|
|
44
|
-
return existingProxy
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
const handler = {
|
|
48
|
-
get(target, key, receiver) {
|
|
49
|
-
// return the original object instead of the proxied
|
|
50
|
-
if (key === symbols.raw) {
|
|
51
|
-
return original
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
// handling arrays
|
|
55
|
-
if (Array.isArray(target) === true) {
|
|
56
|
-
if (typeof target[key] === 'object' && target[key] !== null) {
|
|
57
|
-
if (Array.isArray(target[key]) === true) {
|
|
58
|
-
track(target, key, global)
|
|
59
|
-
}
|
|
60
|
-
// create a new reactive proxy
|
|
61
|
-
return reactiveProxy(getRaw(target[key]), target, key)
|
|
62
|
-
}
|
|
63
|
-
// augment array path methods (that change the length of the array)
|
|
64
|
-
if (arrayPatchMethods.indexOf(key) !== -1) {
|
|
65
|
-
return function (...args) {
|
|
66
|
-
pauseTracking()
|
|
67
|
-
const result = target[key].apply(this, args)
|
|
68
|
-
resumeTracking()
|
|
69
|
-
// trigger a change on the parent object and the key
|
|
70
|
-
// i.e. when pushing a new item to `obj.data`, _parent will equal `obj`
|
|
71
|
-
// and _key will equal `data`
|
|
72
|
-
trigger(_parent, _key)
|
|
73
|
-
return result
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
if (key === 'length') {
|
|
77
|
-
return original.length
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
return Reflect.get(target, key, receiver)
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
// handling objects (but not null values, which have object type in JS)
|
|
84
|
-
if (typeof target[key] === 'object' && target[key] !== null) {
|
|
85
|
-
if (Array.isArray(target[key]) === true) {
|
|
86
|
-
track(target, key, global)
|
|
87
|
-
}
|
|
88
|
-
// create a new reactive proxy
|
|
89
|
-
return reactiveProxy(getRaw(target[key]), target, key)
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
// handling all other types
|
|
93
|
-
// track the key on the target
|
|
94
|
-
track(target, key, global)
|
|
95
|
-
// return the reflected value
|
|
96
|
-
return Reflect.get(target, key, receiver)
|
|
97
|
-
},
|
|
98
|
-
set(target, key, value, receiver) {
|
|
99
|
-
// get the raw values (without proxy wrapper) so we can compare them
|
|
100
|
-
const oldRawValue = getRaw(target[key])
|
|
101
|
-
const rawValue = getRaw(value)
|
|
102
|
-
|
|
103
|
-
let result = true
|
|
104
|
-
let isEqual = false
|
|
105
|
-
|
|
106
|
-
// We need to check that the oldRawValue is also an array before we do the deep equal check
|
|
107
|
-
if (Array.isArray(rawValue) === true && Array.isArray(oldRawValue) === true) {
|
|
108
|
-
isEqual = deepEqualArray(oldRawValue, rawValue)
|
|
109
|
-
} else if (oldRawValue === rawValue) {
|
|
110
|
-
isEqual = true
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
if (isEqual === false) {
|
|
114
|
-
if (typeof value === 'object') {
|
|
115
|
-
if (Array.isArray(value) === true) {
|
|
116
|
-
value = getRaw(value).slice(0)
|
|
117
|
-
} else if (
|
|
118
|
-
value !== null &&
|
|
119
|
-
target[key] !== null &&
|
|
120
|
-
target[key] !== undefined &&
|
|
121
|
-
Array.isArray(target) === false &&
|
|
122
|
-
Object.getPrototypeOf(value) === Object.prototype
|
|
123
|
-
) {
|
|
124
|
-
value = Object.assign(receiver[key], value)
|
|
125
|
-
}
|
|
126
|
-
}
|
|
127
|
-
result = Reflect.set(target, key, value, receiver)
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
if (result === true && isEqual === false) {
|
|
131
|
-
// if we're assigning an array key directly trigger reactivity on the parent key as well
|
|
132
|
-
if (Array.isArray(target) === true && key in target === true) {
|
|
133
|
-
trigger(_parent, _key, true)
|
|
134
|
-
}
|
|
135
|
-
trigger(target, key, true)
|
|
136
|
-
}
|
|
137
|
-
return result
|
|
138
|
-
},
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
const proxy = new Proxy(original, handler)
|
|
142
|
-
proxyMap.set(original, proxy)
|
|
143
|
-
return proxy
|
|
144
|
-
}
|
|
145
|
-
|
|
146
|
-
const reactiveDefineProperty = (target, global) => {
|
|
147
|
-
Object.keys(target).forEach((key) => {
|
|
148
|
-
let internalValue = target[key]
|
|
149
|
-
|
|
150
|
-
if (target[key] !== null && typeof target[key] === 'object') {
|
|
151
|
-
if (Object.getPrototypeOf(target[key]) === Object.prototype) {
|
|
152
|
-
return reactiveDefineProperty(target[key])
|
|
153
|
-
} else if (Array.isArray(target[key]) === true) {
|
|
154
|
-
for (let i = 0; i < arrayPatchMethods.length - 1; i++) {
|
|
155
|
-
target[key][arrayPatchMethods[i]] = function (v) {
|
|
156
|
-
Array.prototype[arrayPatchMethods[i]].call(this, v)
|
|
157
|
-
trigger(target, key)
|
|
158
|
-
}
|
|
159
|
-
}
|
|
160
|
-
}
|
|
161
|
-
}
|
|
162
|
-
|
|
163
|
-
Object.defineProperty(target, key, {
|
|
164
|
-
enumerable: true,
|
|
165
|
-
configurable: true,
|
|
166
|
-
get() {
|
|
167
|
-
track(target, key, global)
|
|
168
|
-
return internalValue
|
|
169
|
-
},
|
|
170
|
-
set(newValue) {
|
|
171
|
-
// todo: support assigning array (as we do with proxies)
|
|
172
|
-
let oldValue = internalValue
|
|
173
|
-
if (oldValue !== newValue) {
|
|
174
|
-
internalValue = newValue
|
|
175
|
-
trigger(target, key)
|
|
176
|
-
}
|
|
177
|
-
},
|
|
178
|
-
})
|
|
179
|
-
})
|
|
180
|
-
|
|
181
|
-
return target
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
const hasProxySupport = typeof Proxy !== 'undefined'
|
|
185
|
-
|
|
186
|
-
export const reactive = (target, mode = 'Proxy', global = false) => {
|
|
187
|
-
// force defineProperty reactivity mode when no proxy support
|
|
188
|
-
if (hasProxySupport === false) {
|
|
189
|
-
mode = 'defineProperty'
|
|
190
|
-
}
|
|
191
|
-
return mode === 'defineProperty'
|
|
192
|
-
? reactiveDefineProperty(target, global)
|
|
193
|
-
: reactiveProxy(target, undefined, undefined, global)
|
|
194
|
-
}
|
|
195
|
-
|
|
196
|
-
export const memo = (raw) => {
|
|
197
|
-
const r = {
|
|
198
|
-
get value() {
|
|
199
|
-
track(r, 'value')
|
|
200
|
-
return raw
|
|
201
|
-
},
|
|
202
|
-
set value(v) {
|
|
203
|
-
raw = v
|
|
204
|
-
trigger(r, 'value')
|
|
205
|
-
},
|
|
206
|
-
}
|
|
207
|
-
return r
|
|
208
|
-
}
|
|
1
|
+
/*
|
|
2
|
+
* Copyright 2023 Comcast Cable Communications Management, LLC
|
|
3
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
* you may not use this file except in compliance with the License.
|
|
5
|
+
* You may obtain a copy of the License at
|
|
6
|
+
*
|
|
7
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
*
|
|
9
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
* See the License for the specific language governing permissions and
|
|
13
|
+
* limitations under the License.
|
|
14
|
+
*
|
|
15
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
import { track, trigger, pauseTracking, resumeTracking } from './effect.js'
|
|
19
|
+
import symbols from '../symbols.js'
|
|
20
|
+
import deepEqualArray from '../../helpers/deepEqualArray.js'
|
|
21
|
+
|
|
22
|
+
const arrayPatchMethods = ['push', 'pop', 'shift', 'unshift', 'splice', 'sort']
|
|
23
|
+
|
|
24
|
+
const proxyMap = new WeakMap()
|
|
25
|
+
|
|
26
|
+
export const getRaw = (value) => {
|
|
27
|
+
const raw = value && value[symbols.raw]
|
|
28
|
+
return raw ? getRaw(raw) : value
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
const reactiveProxy = (original, _parent = null, _key, global) => {
|
|
32
|
+
// only create a proxy for plain objects. Other classes, Blits components, renderer textures etc
|
|
33
|
+
// are returned unmodified and will not become reactive
|
|
34
|
+
if (
|
|
35
|
+
typeof original === 'object' &&
|
|
36
|
+
Array.isArray(original) === false &&
|
|
37
|
+
Object.getPrototypeOf(original) !== Object.prototype
|
|
38
|
+
) {
|
|
39
|
+
return original
|
|
40
|
+
}
|
|
41
|
+
// if original object is already a proxy, don't create a new one but return the existing one instead
|
|
42
|
+
const existingProxy = proxyMap.get(original)
|
|
43
|
+
if (existingProxy !== undefined) {
|
|
44
|
+
return existingProxy
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
const handler = {
|
|
48
|
+
get(target, key, receiver) {
|
|
49
|
+
// return the original object instead of the proxied
|
|
50
|
+
if (key === symbols.raw) {
|
|
51
|
+
return original
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
// handling arrays
|
|
55
|
+
if (Array.isArray(target) === true) {
|
|
56
|
+
if (typeof target[key] === 'object' && target[key] !== null) {
|
|
57
|
+
if (Array.isArray(target[key]) === true) {
|
|
58
|
+
track(target, key, global)
|
|
59
|
+
}
|
|
60
|
+
// create a new reactive proxy
|
|
61
|
+
return reactiveProxy(getRaw(target[key]), target, key)
|
|
62
|
+
}
|
|
63
|
+
// augment array path methods (that change the length of the array)
|
|
64
|
+
if (arrayPatchMethods.indexOf(key) !== -1) {
|
|
65
|
+
return function (...args) {
|
|
66
|
+
pauseTracking()
|
|
67
|
+
const result = target[key].apply(this, args)
|
|
68
|
+
resumeTracking()
|
|
69
|
+
// trigger a change on the parent object and the key
|
|
70
|
+
// i.e. when pushing a new item to `obj.data`, _parent will equal `obj`
|
|
71
|
+
// and _key will equal `data`
|
|
72
|
+
trigger(_parent, _key)
|
|
73
|
+
return result
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
if (key === 'length') {
|
|
77
|
+
return original.length
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
return Reflect.get(target, key, receiver)
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
// handling objects (but not null values, which have object type in JS)
|
|
84
|
+
if (typeof target[key] === 'object' && target[key] !== null) {
|
|
85
|
+
if (Array.isArray(target[key]) === true) {
|
|
86
|
+
track(target, key, global)
|
|
87
|
+
}
|
|
88
|
+
// create a new reactive proxy
|
|
89
|
+
return reactiveProxy(getRaw(target[key]), target, key)
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
// handling all other types
|
|
93
|
+
// track the key on the target
|
|
94
|
+
track(target, key, global)
|
|
95
|
+
// return the reflected value
|
|
96
|
+
return Reflect.get(target, key, receiver)
|
|
97
|
+
},
|
|
98
|
+
set(target, key, value, receiver) {
|
|
99
|
+
// get the raw values (without proxy wrapper) so we can compare them
|
|
100
|
+
const oldRawValue = getRaw(target[key])
|
|
101
|
+
const rawValue = getRaw(value)
|
|
102
|
+
|
|
103
|
+
let result = true
|
|
104
|
+
let isEqual = false
|
|
105
|
+
|
|
106
|
+
// We need to check that the oldRawValue is also an array before we do the deep equal check
|
|
107
|
+
if (Array.isArray(rawValue) === true && Array.isArray(oldRawValue) === true) {
|
|
108
|
+
isEqual = deepEqualArray(oldRawValue, rawValue)
|
|
109
|
+
} else if (oldRawValue === rawValue) {
|
|
110
|
+
isEqual = true
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
if (isEqual === false) {
|
|
114
|
+
if (typeof value === 'object') {
|
|
115
|
+
if (Array.isArray(value) === true) {
|
|
116
|
+
value = getRaw(value).slice(0)
|
|
117
|
+
} else if (
|
|
118
|
+
value !== null &&
|
|
119
|
+
target[key] !== null &&
|
|
120
|
+
target[key] !== undefined &&
|
|
121
|
+
Array.isArray(target) === false &&
|
|
122
|
+
Object.getPrototypeOf(value) === Object.prototype
|
|
123
|
+
) {
|
|
124
|
+
value = Object.assign(receiver[key], value)
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
result = Reflect.set(target, key, value, receiver)
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
if (result === true && isEqual === false) {
|
|
131
|
+
// if we're assigning an array key directly trigger reactivity on the parent key as well
|
|
132
|
+
if (Array.isArray(target) === true && key in target === true) {
|
|
133
|
+
trigger(_parent, _key, true)
|
|
134
|
+
}
|
|
135
|
+
trigger(target, key, true)
|
|
136
|
+
}
|
|
137
|
+
return result
|
|
138
|
+
},
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
const proxy = new Proxy(original, handler)
|
|
142
|
+
proxyMap.set(original, proxy)
|
|
143
|
+
return proxy
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
const reactiveDefineProperty = (target, global) => {
|
|
147
|
+
Object.keys(target).forEach((key) => {
|
|
148
|
+
let internalValue = target[key]
|
|
149
|
+
|
|
150
|
+
if (target[key] !== null && typeof target[key] === 'object') {
|
|
151
|
+
if (Object.getPrototypeOf(target[key]) === Object.prototype) {
|
|
152
|
+
return reactiveDefineProperty(target[key])
|
|
153
|
+
} else if (Array.isArray(target[key]) === true) {
|
|
154
|
+
for (let i = 0; i < arrayPatchMethods.length - 1; i++) {
|
|
155
|
+
target[key][arrayPatchMethods[i]] = function (v) {
|
|
156
|
+
Array.prototype[arrayPatchMethods[i]].call(this, v)
|
|
157
|
+
trigger(target, key)
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
Object.defineProperty(target, key, {
|
|
164
|
+
enumerable: true,
|
|
165
|
+
configurable: true,
|
|
166
|
+
get() {
|
|
167
|
+
track(target, key, global)
|
|
168
|
+
return internalValue
|
|
169
|
+
},
|
|
170
|
+
set(newValue) {
|
|
171
|
+
// todo: support assigning array (as we do with proxies)
|
|
172
|
+
let oldValue = internalValue
|
|
173
|
+
if (oldValue !== newValue) {
|
|
174
|
+
internalValue = newValue
|
|
175
|
+
trigger(target, key)
|
|
176
|
+
}
|
|
177
|
+
},
|
|
178
|
+
})
|
|
179
|
+
})
|
|
180
|
+
|
|
181
|
+
return target
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
const hasProxySupport = typeof Proxy !== 'undefined'
|
|
185
|
+
|
|
186
|
+
export const reactive = (target, mode = 'Proxy', global = false) => {
|
|
187
|
+
// force defineProperty reactivity mode when no proxy support
|
|
188
|
+
if (hasProxySupport === false) {
|
|
189
|
+
mode = 'defineProperty'
|
|
190
|
+
}
|
|
191
|
+
return mode === 'defineProperty'
|
|
192
|
+
? reactiveDefineProperty(target, global)
|
|
193
|
+
: reactiveProxy(target, undefined, undefined, global)
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
export const memo = (raw) => {
|
|
197
|
+
const r = {
|
|
198
|
+
get value() {
|
|
199
|
+
track(r, 'value')
|
|
200
|
+
return raw
|
|
201
|
+
},
|
|
202
|
+
set value(v) {
|
|
203
|
+
raw = v
|
|
204
|
+
trigger(r, 'value')
|
|
205
|
+
},
|
|
206
|
+
}
|
|
207
|
+
return r
|
|
208
|
+
}
|