Skip to content

Commit ad8d618

Browse files
committed
tweaks, test
1 parent 00c1800 commit ad8d618

File tree

4 files changed

+79
-11
lines changed

4 files changed

+79
-11
lines changed

packages/svelte/src/internal/client/dom/elements/bindings/input.js

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -73,16 +73,22 @@ export function bind_group(inputs, group_index, input, get_value, update) {
7373

7474
binding_group.push(input);
7575

76-
listen_to_event_and_reset_event(input, 'change', () => {
77-
// @ts-ignore
78-
var value = input.__value;
76+
listen_to_event_and_reset_event(
77+
input,
78+
'change',
79+
() => {
80+
// @ts-ignore
81+
var value = input.__value;
7982

80-
if (is_checkbox) {
81-
value = get_binding_group_value(binding_group, value, input.checked);
82-
}
83+
if (is_checkbox) {
84+
value = get_binding_group_value(binding_group, value, input.checked);
85+
}
8386

84-
update(value);
85-
});
87+
update(value);
88+
},
89+
// TODO better default value handling
90+
() => update(is_checkbox ? [] : null)
91+
);
8692

8793
render_effect(() => {
8894
var value = get_value();

packages/svelte/src/internal/client/dom/elements/bindings/shared.js

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -34,11 +34,23 @@ let listening_to_form_reset = false;
3434
* @param {HTMLElement} element
3535
* @param {string} event
3636
* @param {() => void} handler
37+
* @param {() => void} [on_reset]
3738
*/
38-
export function listen_to_event_and_reset_event(element, event, handler) {
39+
export function listen_to_event_and_reset_event(element, event, handler, on_reset = handler) {
3940
element.addEventListener(event, handler);
4041
// @ts-expect-error
41-
element.__on_reset = handler;
42+
const prev = element.__on_r;
43+
if (prev) {
44+
// special case for checkbox that can have multiple binds (group & checked)
45+
// @ts-expect-error
46+
element.__on_r = () => {
47+
prev();
48+
on_reset();
49+
};
50+
} else {
51+
// @ts-expect-error
52+
element.__on_r = on_reset;
53+
}
4254

4355
if (!listening_to_form_reset) {
4456
listening_to_form_reset = true;
@@ -47,7 +59,7 @@ export function listen_to_event_and_reset_event(element, event, handler) {
4759
if (!evt.defaultPrevented) {
4860
for (const e of /**@type {HTMLFormElement} */ (evt.target).elements) {
4961
// @ts-expect-error
50-
e.__on_reset?.();
62+
e.__on_r?.();
5163
}
5264
}
5365
});
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
import { test } from '../../test';
2+
3+
export default test({
4+
async test({ assert, target }) {
5+
const p = target.querySelector('p');
6+
7+
assert.htmlEqual(
8+
p?.innerHTML || '',
9+
`{"text":"text","checkbox":true,"radio_group":"a","checkbox_group":["a"],"select":"b","textarea":"textarea"}`
10+
);
11+
12+
await target.querySelector('button')?.click();
13+
await new Promise((r) => requestAnimationFrame(r));
14+
assert.htmlEqual(
15+
p?.innerHTML || '',
16+
`{"text":"","checkbox":false,"radio_group":null,"checkbox_group":[],"select":"a","textarea":""}`
17+
);
18+
}
19+
});
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
<script>
2+
let text = $state('text');
3+
let checkbox = $state(true);
4+
let radio_group = $state('a');
5+
let checkbox_group = $state(['a']);
6+
let select = $state('b');
7+
let textarea = $state('textarea');
8+
</script>
9+
10+
<p>{JSON.stringify({ text, checkbox, radio_group, checkbox_group, select, textarea })}</p>
11+
12+
<form>
13+
<input bind:value={text} />
14+
15+
<input type="checkbox" bind:checked={checkbox} />
16+
17+
<input type="radio" name="radio" value="a" bind:group={radio_group} />
18+
<input type="radio" name="radio" value="b" bind:group={radio_group} />
19+
20+
<input type="checkbox" name="checkbox" value="a" bind:group={checkbox_group} />
21+
<input type="checkbox" name="checkbox" value="b" bind:group={checkbox_group} />
22+
23+
<select bind:value={select}>
24+
<option value="a">a</option>
25+
<option value="b">b</option>
26+
</select>
27+
28+
<textarea bind:value={textarea}></textarea>
29+
30+
<button type="button" onclick={(e) => e.target.form.reset()}>Reset</button>
31+
</form>

0 commit comments

Comments
 (0)