ripple 0.2.46 → 0.2.48
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/package.json +1 -1
- package/src/compiler/phases/1-parse/index.js +52 -2
- package/src/compiler/phases/2-analyze/index.js +640 -667
- package/src/compiler/phases/3-transform/index.js +1878 -1879
- package/src/compiler/phases/3-transform/segments.js +2 -2
- package/src/compiler/utils.js +598 -550
- package/src/jsx-runtime.js +12 -12
- package/src/runtime/array.js +611 -609
- package/src/runtime/index.js +29 -17
- package/src/runtime/internal/client/array.js +121 -121
- package/src/runtime/internal/client/blocks.js +206 -206
- package/src/runtime/internal/client/constants.js +2 -2
- package/src/runtime/internal/client/context.js +40 -40
- package/src/runtime/internal/client/events.js +191 -191
- package/src/runtime/internal/client/for.js +355 -355
- package/src/runtime/internal/client/if.js +25 -25
- package/src/runtime/internal/client/index.js +57 -56
- package/src/runtime/internal/client/operations.js +32 -32
- package/src/runtime/internal/client/portal.js +19 -19
- package/src/runtime/internal/client/render.js +132 -132
- package/src/runtime/internal/client/runtime.js +839 -835
- package/src/runtime/internal/client/template.js +36 -36
- package/src/runtime/internal/client/try.js +113 -113
- package/src/runtime/internal/client/types.d.ts +12 -11
- package/src/runtime/internal/client/utils.js +5 -5
- package/src/runtime/map.js +139 -139
- package/src/runtime/set.js +130 -130
- package/src/utils/ast.js +189 -189
- package/src/utils/builders.js +244 -244
- package/src/utils/sanitize_template_string.js +1 -1
- package/tests/__snapshots__/composite.test.ripple.snap +1 -1
- package/tests/accessors-props.test.ripple +9 -9
- package/tests/basic.test.ripple +4 -4
- package/tests/boundaries.test.ripple +17 -17
- package/tests/compiler.test.ripple +14 -14
- package/tests/composite.test.ripple +43 -72
- package/tests/context.test.ripple +35 -12
- package/types/index.d.ts +38 -34
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
|
|
2
2
|
|
|
3
|
-
exports[`composite components > correct handles passing through component props and
|
|
3
|
+
exports[`composite components > correct handles passing through component props and children 1`] = `
|
|
4
4
|
<div>
|
|
5
5
|
<!---->
|
|
6
6
|
<div>
|
|
@@ -71,16 +71,16 @@ describe('prop accessors', () => {
|
|
|
71
71
|
|
|
72
72
|
component Child(props) {
|
|
73
73
|
effect(() => {
|
|
74
|
-
logs.push('App effect', props
|
|
74
|
+
logs.push('App effect', props.foo);
|
|
75
75
|
});
|
|
76
76
|
|
|
77
|
-
<button onClick={() => props
|
|
77
|
+
<button onClick={() => props.foo++}>{"Increment foo"}</button>
|
|
78
78
|
}
|
|
79
79
|
|
|
80
80
|
component App(props) {
|
|
81
81
|
let $foo = 0;
|
|
82
82
|
|
|
83
|
-
<Child
|
|
83
|
+
<Child foo:={() => {
|
|
84
84
|
return $foo;
|
|
85
85
|
}, v => {
|
|
86
86
|
// do not update parent
|
|
@@ -103,19 +103,19 @@ describe('prop accessors', () => {
|
|
|
103
103
|
flushSync();
|
|
104
104
|
|
|
105
105
|
expect(container.querySelectorAll('div')[0].textContent).toBe('parent foo: 0');
|
|
106
|
-
expect(logs).toEqual(['App effect', 0
|
|
106
|
+
expect(logs).toEqual(['App effect', 0]);
|
|
107
107
|
|
|
108
108
|
button2.click();
|
|
109
109
|
flushSync();
|
|
110
110
|
|
|
111
111
|
expect(container.querySelectorAll('div')[0].textContent).toBe('parent foo: 1');
|
|
112
|
-
expect(logs).toEqual(['App effect', 0, 'App effect', 1
|
|
112
|
+
expect(logs).toEqual(['App effect', 0, 'App effect', 1]);
|
|
113
113
|
|
|
114
114
|
button2.click();
|
|
115
115
|
flushSync();
|
|
116
116
|
|
|
117
117
|
expect(container.querySelectorAll('div')[0].textContent).toBe('parent foo: 2');
|
|
118
|
-
expect(logs).toEqual(['App effect', 0, 'App effect', 1, 'App effect',
|
|
118
|
+
expect(logs).toEqual(['App effect', 0, 'App effect', 1, 'App effect', 2]);
|
|
119
119
|
});
|
|
120
120
|
|
|
121
121
|
|
|
@@ -123,13 +123,13 @@ describe('prop accessors', () => {
|
|
|
123
123
|
component Parent() {
|
|
124
124
|
let $value = 123;
|
|
125
125
|
|
|
126
|
-
<Child
|
|
126
|
+
<Child value:={() => $value} />
|
|
127
127
|
|
|
128
128
|
<button onClick={() => $value++}>{"Increment value"}</button>
|
|
129
129
|
}
|
|
130
130
|
|
|
131
|
-
component Child({
|
|
132
|
-
<div>{
|
|
131
|
+
component Child({ value }) {
|
|
132
|
+
<div>{value}</div>
|
|
133
133
|
}
|
|
134
134
|
|
|
135
135
|
render(Parent);
|
package/tests/basic.test.ripple
CHANGED
|
@@ -89,15 +89,15 @@ describe('basic', () => {
|
|
|
89
89
|
});
|
|
90
90
|
|
|
91
91
|
it('render tick template literal for nested children', () => {
|
|
92
|
-
component Child({ $level,
|
|
92
|
+
component Child({ $level, children }) {
|
|
93
93
|
if($level == 1) {
|
|
94
|
-
<h1
|
|
94
|
+
<h1><children /></h1>
|
|
95
95
|
}
|
|
96
96
|
if($level == 2) {
|
|
97
|
-
<h2
|
|
97
|
+
<h2><children /></h2>
|
|
98
98
|
}
|
|
99
99
|
if($level == 3) {
|
|
100
|
-
<h3
|
|
100
|
+
<h3><children /></h3>
|
|
101
101
|
}
|
|
102
102
|
}
|
|
103
103
|
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { mount, flushSync, effect } from 'ripple';
|
|
2
|
+
import { mount, flushSync, effect, track } from 'ripple';
|
|
3
3
|
|
|
4
4
|
describe('passing reactivity between boundaries tests', () => {
|
|
5
5
|
let container;
|
|
@@ -23,23 +23,23 @@ describe('passing reactivity between boundaries tests', () => {
|
|
|
23
23
|
it('can pass reactivity between functions with simple arrays and destructuring', () => {
|
|
24
24
|
let log: string[] = [];
|
|
25
25
|
|
|
26
|
-
function createDouble([
|
|
27
|
-
const
|
|
26
|
+
function createDouble([ count ]) {
|
|
27
|
+
const double = track(() => @count * 2);
|
|
28
28
|
|
|
29
29
|
effect(() => {
|
|
30
|
-
log.push('Count:' +
|
|
30
|
+
log.push('Count:' + @count);
|
|
31
31
|
});
|
|
32
32
|
|
|
33
|
-
return [
|
|
33
|
+
return [ double ];
|
|
34
34
|
}
|
|
35
35
|
|
|
36
36
|
component App() {
|
|
37
|
-
let
|
|
37
|
+
let count = track(0);
|
|
38
38
|
|
|
39
|
-
const [
|
|
39
|
+
const [ double ] = createDouble([ count ]);
|
|
40
40
|
|
|
41
|
-
<div>{'Double: ' +
|
|
42
|
-
<button onClick={() => {
|
|
41
|
+
<div>{'Double: ' + @double}</div>
|
|
42
|
+
<button onClick={() => { @count++; }}>{'Increment'}</button>
|
|
43
43
|
}
|
|
44
44
|
|
|
45
45
|
render(App);
|
|
@@ -66,23 +66,23 @@ describe('passing reactivity between boundaries tests', () => {
|
|
|
66
66
|
it('can pass reactivity between functions with simple objects and destructuring', () => {
|
|
67
67
|
let log: string[] = [];
|
|
68
68
|
|
|
69
|
-
function createDouble({
|
|
70
|
-
const
|
|
69
|
+
function createDouble({ count }) {
|
|
70
|
+
const double = track(() => @count * 2);
|
|
71
71
|
|
|
72
72
|
effect(() => {
|
|
73
|
-
log.push('Count:' +
|
|
73
|
+
log.push('Count:' + @count);
|
|
74
74
|
});
|
|
75
75
|
|
|
76
|
-
return {
|
|
76
|
+
return { double };
|
|
77
77
|
}
|
|
78
78
|
|
|
79
79
|
component App() {
|
|
80
|
-
let
|
|
80
|
+
let count = track(0);
|
|
81
81
|
|
|
82
|
-
const {
|
|
82
|
+
const { double } = createDouble({ count });
|
|
83
83
|
|
|
84
|
-
<div>{'Double: ' +
|
|
85
|
-
<button onClick={() => {
|
|
84
|
+
<div>{'Double: ' + @double}</div>
|
|
85
|
+
<button onClick={() => { @count++; }}>{'Increment'}</button>
|
|
86
86
|
}
|
|
87
87
|
|
|
88
88
|
render(App);
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { mount, RippleArray } from 'ripple';
|
|
2
|
+
import { mount, RippleArray, track } from 'ripple';
|
|
3
3
|
import { parse } from 'ripple/compiler'
|
|
4
4
|
|
|
5
5
|
describe('compiler success tests', () => {
|
|
@@ -109,15 +109,15 @@ describe('compiler success tests', () => {
|
|
|
109
109
|
|
|
110
110
|
component App() {
|
|
111
111
|
let items = [];
|
|
112
|
-
let
|
|
112
|
+
let tracked_items = track([]);
|
|
113
113
|
let items2 = new Array();
|
|
114
114
|
let items3 = new RippleArray();
|
|
115
115
|
let i = 0;
|
|
116
116
|
|
|
117
117
|
logs.push(items[0]);
|
|
118
118
|
logs.push(items[i]);
|
|
119
|
-
logs.push(
|
|
120
|
-
logs.push(
|
|
119
|
+
logs.push(@tracked_items[0]);
|
|
120
|
+
logs.push(@tracked_items[i]);
|
|
121
121
|
logs.push(items2[0]);
|
|
122
122
|
logs.push(items2[i]);
|
|
123
123
|
logs.push(items3[0]);
|
|
@@ -125,8 +125,8 @@ describe('compiler success tests', () => {
|
|
|
125
125
|
|
|
126
126
|
items[0] = 123;
|
|
127
127
|
items[i] = 123;
|
|
128
|
-
|
|
129
|
-
|
|
128
|
+
@tracked_items[0] = 123;
|
|
129
|
+
@tracked_items[i] = 123;
|
|
130
130
|
items2[0] = 123;
|
|
131
131
|
items2[i] = 123;
|
|
132
132
|
items3[0] = 123;
|
|
@@ -134,8 +134,8 @@ describe('compiler success tests', () => {
|
|
|
134
134
|
|
|
135
135
|
logs.push(items[0]);
|
|
136
136
|
logs.push(items[i]);
|
|
137
|
-
logs.push(
|
|
138
|
-
logs.push(
|
|
137
|
+
logs.push(@tracked_items[0]);
|
|
138
|
+
logs.push(@tracked_items[i]);
|
|
139
139
|
logs.push(items2[0]);
|
|
140
140
|
logs.push(items2[i]);
|
|
141
141
|
logs.push(items3[0]);
|
|
@@ -143,8 +143,8 @@ describe('compiler success tests', () => {
|
|
|
143
143
|
|
|
144
144
|
items[0]++;
|
|
145
145
|
items[i]++;
|
|
146
|
-
|
|
147
|
-
|
|
146
|
+
@tracked_items[0]++;
|
|
147
|
+
@tracked_items[i]++;
|
|
148
148
|
items2[0]++;
|
|
149
149
|
items2[i]++;
|
|
150
150
|
items3[0]++;
|
|
@@ -152,8 +152,8 @@ describe('compiler success tests', () => {
|
|
|
152
152
|
|
|
153
153
|
logs.push(items[0]);
|
|
154
154
|
logs.push(items[i]);
|
|
155
|
-
logs.push(
|
|
156
|
-
logs.push(
|
|
155
|
+
logs.push(@tracked_items[0]);
|
|
156
|
+
logs.push(@tracked_items[i]);
|
|
157
157
|
logs.push(items2[0]);
|
|
158
158
|
logs.push(items2[i]);
|
|
159
159
|
logs.push(items3[0]);
|
|
@@ -161,8 +161,8 @@ describe('compiler success tests', () => {
|
|
|
161
161
|
|
|
162
162
|
logs.push(--items[0]);
|
|
163
163
|
logs.push(--items[i]);
|
|
164
|
-
logs.push(
|
|
165
|
-
logs.push(
|
|
164
|
+
logs.push(--@tracked_items[0]);
|
|
165
|
+
logs.push(--@tracked_items[i]);
|
|
166
166
|
logs.push(--items2[0]);
|
|
167
167
|
logs.push(--items2[i]);
|
|
168
168
|
logs.push(--items3[0]);
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { mount, flushSync } from 'ripple';
|
|
2
|
+
import { mount, flushSync, track } from 'ripple';
|
|
3
3
|
|
|
4
4
|
describe('composite components', () => {
|
|
5
5
|
let container;
|
|
@@ -21,15 +21,15 @@ describe('composite components', () => {
|
|
|
21
21
|
});
|
|
22
22
|
|
|
23
23
|
it('renders composite components', () => {
|
|
24
|
-
component Button({
|
|
25
|
-
<div>{
|
|
24
|
+
component Button({ count }) {
|
|
25
|
+
<div>{count}</div>
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
component App() {
|
|
29
|
-
let
|
|
29
|
+
let count = track(0);
|
|
30
30
|
|
|
31
|
-
<button onClick={() =>
|
|
32
|
-
<Button
|
|
31
|
+
<button onClick={() => @count++}>{'Increment'}</button>
|
|
32
|
+
<Button {@count} />
|
|
33
33
|
}
|
|
34
34
|
|
|
35
35
|
render(App);
|
|
@@ -50,48 +50,17 @@ describe('composite components', () => {
|
|
|
50
50
|
it('renders composite components with object state', () => {
|
|
51
51
|
component Button({ obj }) {
|
|
52
52
|
<button class='count2' onClick={() => {
|
|
53
|
-
obj
|
|
54
|
-
}}>{obj
|
|
53
|
+
obj.@count++;
|
|
54
|
+
}}>{obj.@count}</button>
|
|
55
55
|
}
|
|
56
56
|
|
|
57
57
|
component App() {
|
|
58
58
|
<div>
|
|
59
59
|
let obj = {
|
|
60
|
-
|
|
60
|
+
count: track(0)
|
|
61
61
|
};
|
|
62
|
-
let $button = true;
|
|
63
62
|
|
|
64
|
-
<span class='count'>{obj
|
|
65
|
-
<span>{' '}</span>
|
|
66
|
-
<Button obj={obj} />
|
|
67
|
-
</div>
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
render(App);
|
|
71
|
-
|
|
72
|
-
const button = container.querySelector('button');
|
|
73
|
-
|
|
74
|
-
button.click();
|
|
75
|
-
flushSync();
|
|
76
|
-
|
|
77
|
-
expect(container.querySelector('.count').textContent).toBe('1');
|
|
78
|
-
expect(container.querySelector('.count2').textContent).toBe('1');
|
|
79
|
-
});
|
|
80
|
-
|
|
81
|
-
it('renders composite components with object state', () => {
|
|
82
|
-
component Button({ obj }) {
|
|
83
|
-
<button class='count2' onClick={() => {
|
|
84
|
-
obj.$count++;
|
|
85
|
-
}}>{obj.$count}</button>
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
component App() {
|
|
89
|
-
<div>
|
|
90
|
-
let obj = {
|
|
91
|
-
$count: 0
|
|
92
|
-
};
|
|
93
|
-
|
|
94
|
-
<span class='count'>{obj.$count}</span>
|
|
63
|
+
<span class='count'>{obj.@count}</span>
|
|
95
64
|
<Button obj={obj} />
|
|
96
65
|
</div>
|
|
97
66
|
}
|
|
@@ -110,21 +79,21 @@ describe('composite components', () => {
|
|
|
110
79
|
it('renders composite components with object state wrapped in an if statement', () => {
|
|
111
80
|
component Button({ obj }) {
|
|
112
81
|
<button class='count2' onClick={() => {
|
|
113
|
-
obj
|
|
114
|
-
}}>{obj
|
|
82
|
+
obj.@count++;
|
|
83
|
+
}}>{obj.@count}</button>
|
|
115
84
|
}
|
|
116
85
|
|
|
117
86
|
component OtherComponent({ obj }) {
|
|
118
|
-
<div class='count3'>{obj
|
|
87
|
+
<div class='count3'>{obj.@count}</div>
|
|
119
88
|
}
|
|
120
89
|
|
|
121
90
|
component App() {
|
|
122
91
|
<div>
|
|
123
92
|
let obj = {
|
|
124
|
-
|
|
93
|
+
count: track(0)
|
|
125
94
|
};
|
|
126
95
|
|
|
127
|
-
<span class='count'>{obj
|
|
96
|
+
<span class='count'>{obj.@count}</span>
|
|
128
97
|
<span>{' '}</span>
|
|
129
98
|
if (obj) {
|
|
130
99
|
<Button obj={obj} />
|
|
@@ -148,17 +117,18 @@ describe('composite components', () => {
|
|
|
148
117
|
expect(container.querySelector('.count3').textContent).toBe('1');
|
|
149
118
|
});
|
|
150
119
|
|
|
151
|
-
it('parents and children have isolated
|
|
120
|
+
it('parents and children have isolated state', () => {
|
|
152
121
|
component Button(props) {
|
|
153
|
-
|
|
122
|
+
let count = track(() => props.count);
|
|
123
|
+
<button onClick={() => { @count++; } }>{"child: " + @count}</button>
|
|
154
124
|
}
|
|
155
125
|
|
|
156
126
|
component App() {
|
|
157
127
|
<div>
|
|
158
|
-
let
|
|
128
|
+
let count = track(0);
|
|
159
129
|
|
|
160
|
-
<button onClick={() => {
|
|
161
|
-
<Button {
|
|
130
|
+
<button onClick={() => { @count++; } }>{"parent: " + @count}</button>
|
|
131
|
+
<Button {@count} />
|
|
162
132
|
</div>
|
|
163
133
|
}
|
|
164
134
|
|
|
@@ -182,17 +152,18 @@ describe('composite components', () => {
|
|
|
182
152
|
expect(buttons[1].textContent).toBe('child: 2');
|
|
183
153
|
});
|
|
184
154
|
|
|
185
|
-
it('parents and children have isolated
|
|
186
|
-
component Button({
|
|
187
|
-
|
|
155
|
+
it('parents and children have isolated connected state (destructured props)', () => {
|
|
156
|
+
component Button({count}) {
|
|
157
|
+
let local_count = track(() => count);
|
|
158
|
+
<button onClick={() => { @local_count++; } }>{"child: " + @local_count}</button>
|
|
188
159
|
}
|
|
189
160
|
|
|
190
161
|
component App() {
|
|
191
162
|
<div>
|
|
192
|
-
let
|
|
163
|
+
let count = track(0);
|
|
193
164
|
|
|
194
|
-
<button onClick={() => {
|
|
195
|
-
<Button {
|
|
165
|
+
<button onClick={() => { @count++; } }>{"parent: " + @count}</button>
|
|
166
|
+
<Button {@count} />
|
|
196
167
|
</div>
|
|
197
168
|
}
|
|
198
169
|
|
|
@@ -216,11 +187,11 @@ describe('composite components', () => {
|
|
|
216
187
|
expect(buttons[1].textContent).toBe('child: 2');
|
|
217
188
|
});
|
|
218
189
|
|
|
219
|
-
it('correct handles passing through component props and
|
|
220
|
-
component Button({ A, B,
|
|
190
|
+
it('correct handles passing through component props and children', () => {
|
|
191
|
+
component Button({ A, B, children }) {
|
|
221
192
|
<div>
|
|
222
193
|
<A />
|
|
223
|
-
|
|
194
|
+
<children />
|
|
224
195
|
<B />
|
|
225
196
|
</div>
|
|
226
197
|
}
|
|
@@ -243,15 +214,15 @@ describe('composite components', () => {
|
|
|
243
214
|
});
|
|
244
215
|
|
|
245
216
|
it('correctly handles default prop values', () => {
|
|
246
|
-
component Child({
|
|
247
|
-
<div>{
|
|
217
|
+
component Child({ foo = 456 }) {
|
|
218
|
+
<div>{foo}</div>
|
|
248
219
|
}
|
|
249
220
|
|
|
250
221
|
component App(props) {
|
|
251
|
-
let
|
|
222
|
+
let foo = track(123);
|
|
252
223
|
|
|
253
224
|
<Child />
|
|
254
|
-
<Child {
|
|
225
|
+
<Child {@foo} />
|
|
255
226
|
}
|
|
256
227
|
|
|
257
228
|
render(App);
|
|
@@ -260,7 +231,7 @@ describe('composite components', () => {
|
|
|
260
231
|
expect(container.querySelectorAll('div')[1].textContent).toBe('123');
|
|
261
232
|
});
|
|
262
233
|
|
|
263
|
-
|
|
234
|
+
it('correctly handles default prop values #2', () => {
|
|
264
235
|
component Child({ foo = 456 }) {
|
|
265
236
|
<div>{foo}</div>
|
|
266
237
|
}
|
|
@@ -280,14 +251,14 @@ describe('composite components', () => {
|
|
|
280
251
|
|
|
281
252
|
it('correctly handles no props', () => {
|
|
282
253
|
component Child(props) {
|
|
283
|
-
<div>{props
|
|
254
|
+
<div>{props.@foo}</div>
|
|
284
255
|
}
|
|
285
256
|
|
|
286
257
|
component App(props) {
|
|
287
|
-
let
|
|
258
|
+
let foo = track(123);
|
|
288
259
|
|
|
289
260
|
<Child />
|
|
290
|
-
<Child {
|
|
261
|
+
<Child {foo} />
|
|
291
262
|
}
|
|
292
263
|
|
|
293
264
|
render(App);
|
|
@@ -297,15 +268,15 @@ describe('composite components', () => {
|
|
|
297
268
|
});
|
|
298
269
|
|
|
299
270
|
it('correctly handles no props #2', () => {
|
|
300
|
-
component Child({
|
|
301
|
-
<div>{
|
|
271
|
+
component Child({ foo }) {
|
|
272
|
+
<div>{foo}</div>
|
|
302
273
|
}
|
|
303
274
|
|
|
304
275
|
component App(props) {
|
|
305
|
-
let
|
|
276
|
+
let foo = track(123);
|
|
306
277
|
|
|
307
278
|
<Child />
|
|
308
|
-
<Child {
|
|
279
|
+
<Child {@foo} />
|
|
309
280
|
}
|
|
310
281
|
|
|
311
282
|
render(App);
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { mount, createContext } from 'ripple';
|
|
2
|
+
import { mount, createContext, flushSync, track } from 'ripple';
|
|
3
3
|
|
|
4
4
|
describe('context', () => {
|
|
5
5
|
let container;
|
|
@@ -19,25 +19,48 @@ describe('context', () => {
|
|
|
19
19
|
document.body.removeChild(container);
|
|
20
20
|
});
|
|
21
21
|
|
|
22
|
-
|
|
23
|
-
|
|
22
|
+
it('creates a reactive ref with initial value', () => {
|
|
23
|
+
const MyContext = createContext(null);
|
|
24
24
|
|
|
25
|
-
|
|
26
|
-
|
|
25
|
+
component Child() {
|
|
26
|
+
const value = MyContext.get();
|
|
27
27
|
|
|
28
|
-
|
|
29
|
-
|
|
28
|
+
<div>{value}</div>
|
|
29
|
+
}
|
|
30
30
|
|
|
31
|
-
|
|
32
|
-
|
|
31
|
+
component TestContext() {
|
|
32
|
+
const value = MyContext.get();
|
|
33
33
|
|
|
34
|
-
|
|
34
|
+
MyContext.set("Hello from context!");
|
|
35
35
|
|
|
36
|
-
|
|
37
|
-
|
|
36
|
+
<Child />
|
|
37
|
+
}
|
|
38
38
|
|
|
39
39
|
render(TestContext);
|
|
40
40
|
|
|
41
41
|
expect(container.querySelector('div').textContent).toBe('Hello from context!');
|
|
42
42
|
});
|
|
43
|
+
|
|
44
|
+
it('handles context captured inside a computed tracked', () => {
|
|
45
|
+
|
|
46
|
+
const MyContext = createContext(null)
|
|
47
|
+
|
|
48
|
+
const doubleContext = () => {
|
|
49
|
+
const value = MyContext.get()
|
|
50
|
+
return value * 2
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
component App() {
|
|
54
|
+
MyContext.set(4)
|
|
55
|
+
|
|
56
|
+
<h3>{MyContext.get()}</h3>
|
|
57
|
+
|
|
58
|
+
<h4>{'2x:'} {doubleContext()}</h4>
|
|
59
|
+
|
|
60
|
+
MyContext.set(8)
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
render(App);
|
|
64
|
+
flushSync();
|
|
65
|
+
});
|
|
43
66
|
});
|
package/types/index.d.ts
CHANGED
|
@@ -16,13 +16,13 @@ export declare class RippleArray<T> extends Array<T> {
|
|
|
16
16
|
static from<T, U>(
|
|
17
17
|
arrayLike: ArrayLike<T>,
|
|
18
18
|
mapFn: (v: T, k: number) => U,
|
|
19
|
-
thisArg?: any
|
|
19
|
+
thisArg?: any,
|
|
20
20
|
): RippleArray<U>;
|
|
21
21
|
static from<T>(iterable: Iterable<T>): RippleArray<T>;
|
|
22
22
|
static from<T, U>(
|
|
23
23
|
iterable: Iterable<T>,
|
|
24
24
|
mapFn: (v: T, k: number) => U,
|
|
25
|
-
thisArg?: any
|
|
25
|
+
thisArg?: any,
|
|
26
26
|
): RippleArray<U>;
|
|
27
27
|
|
|
28
28
|
static of<T>(...items: T[]): RippleArray<T>;
|
|
@@ -40,44 +40,48 @@ export type Context<T> = {
|
|
|
40
40
|
export declare function createContext<T>(initialValue: T): Context<T>;
|
|
41
41
|
|
|
42
42
|
export class RippleSet<T> extends Set<T> {
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
43
|
+
readonly $size: number;
|
|
44
|
+
isDisjointFrom(other: RippleSet<T> | Set<T>): boolean;
|
|
45
|
+
isSubsetOf(other: RippleSet<T> | Set<T>): boolean;
|
|
46
|
+
isSupersetOf(other: RippleSet<T> | Set<T>): boolean;
|
|
47
|
+
difference(other: RippleSet<T> | Set<T>): RippleSet<T>;
|
|
48
|
+
intersection(other: RippleSet<T> | Set<T>): RippleSet<T>;
|
|
49
|
+
symmetricDifference(other: RippleSet<T> | Set<T>): RippleSet<T>;
|
|
50
|
+
union(other: RippleSet<T> | Set<T>): RippleSet<T>;
|
|
51
|
+
toJSON(): T[];
|
|
52
52
|
}
|
|
53
53
|
|
|
54
54
|
export class RippleMap<K, V> extends Map<K, V> {
|
|
55
|
-
|
|
56
|
-
|
|
55
|
+
get $size(): number;
|
|
56
|
+
toJSON(): [K, V][];
|
|
57
57
|
}
|
|
58
58
|
|
|
59
59
|
// Compiler-injected runtime symbols (for Ripple component development)
|
|
60
60
|
declare global {
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
61
|
+
/**
|
|
62
|
+
* Runtime block context injected by the Ripple compiler.
|
|
63
|
+
* This is automatically available in component scopes and passed to runtime functions.
|
|
64
|
+
*/
|
|
65
|
+
var __block: any;
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Ripple runtime namespace - injected by the compiler
|
|
69
|
+
* These functions are available in compiled Ripple components for TypeScript analysis
|
|
70
|
+
*/
|
|
71
|
+
var $: {
|
|
72
|
+
tracked<T>(value: T, block?: any): T;
|
|
73
|
+
tracked_object<T extends Record<string, any>>(obj: T, props: string[], block?: any): T;
|
|
74
|
+
computed<T>(fn: () => T, block?: any): T;
|
|
75
|
+
scope(): any;
|
|
76
|
+
get_tracked(node: any): any;
|
|
77
|
+
get_derived(node: any): any;
|
|
78
|
+
set(node: any, value: any, block?: any): any;
|
|
79
|
+
// Add other runtime functions as needed for TypeScript analysis
|
|
80
|
+
};
|
|
81
81
|
}
|
|
82
82
|
|
|
83
|
-
export declare function createRefKey(): symbol;
|
|
83
|
+
export declare function createRefKey(): symbol;
|
|
84
|
+
|
|
85
|
+
type Tracked<V> = { '#v': V };
|
|
86
|
+
|
|
87
|
+
export declare function track<V>(value: V | (() => V)): Tracked<V>;
|