Skip to content

Commit

Permalink
binding callback only call when value changes internally
Browse files Browse the repository at this point in the history
  • Loading branch information
tanhauhau committed Jul 14, 2020
1 parent fc7e99e commit a7985a8
Show file tree
Hide file tree
Showing 5 changed files with 89 additions and 2 deletions.
2 changes: 2 additions & 0 deletions src/compiler/compile/render_dom/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ export default function dom(
const set = (uses_props || uses_rest || writable_props.length > 0 || component.slots.size > 0)
? x`
${$$props} => {
$$self.$$.skip_bound = true;
${uses_props && renderer.invalidate('$$props', x`$$props = @assign(@assign({}, $$props), @exclude_internal_props($$new_props))`)}
${uses_rest && !uses_props && x`$$props = @assign(@assign({}, $$props), @exclude_internal_props($$new_props))`}
${uses_rest && renderer.invalidate('$$restProps', x`$$restProps = ${compute_rest}`)}
Expand All @@ -94,6 +95,7 @@ export default function dom(
)}
${component.slots.size > 0 &&
b`if ('$$scope' in ${$$props}) ${renderer.invalidate('$$scope', x`$$scope = ${$$props}.$$scope`)};`}
$$self.$$.skip_bound = false;
}
`
: null;
Expand Down
5 changes: 3 additions & 2 deletions src/runtime/internal/Component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,8 @@ export function init(component, options, instance, create_fragment, not_equal, p

// everything else
callbacks: blank_object(),
dirty
dirty,
skip_bound: false
};

let ready = false;
Expand All @@ -129,7 +130,7 @@ export function init(component, options, instance, create_fragment, not_equal, p
? instance(component, prop_values, (i, ret, ...rest) => {
const value = rest.length ? rest[0] : ret;
if ($$.ctx && not_equal($$.ctx[i], $$.ctx[i] = value)) {
if ($$.bound[i]) $$.bound[i](value);
if (!$$.skip_bound && $$.bound[i]) $$.bound[i](value);
if (ready) make_dirty(component, i);
}
return ret;
Expand Down
5 changes: 5 additions & 0 deletions test/runtime/samples/component-binding-store/Input.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<script>
export let value = '';
</script>

<input bind:value />
61 changes: 61 additions & 0 deletions test/runtime/samples/component-binding-store/_config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
export default {
html: `
<input />
<input />
<div></div>
`,

async test({ assert, component, target, window }) {
let count = 0;
component.callback = () => {
count++;
};

const [input1, input2] = target.querySelectorAll("input");

input1.value = "1";
await input1.dispatchEvent(new window.Event("input"));

assert.htmlEqual(
target.innerHTML,
`
<input />
<input />
<div>1</div>
`
);
assert.equal(input1.value, "1");
assert.equal(input2.value, "1");
assert.equal(count, 1);

input2.value = "123";
await input2.dispatchEvent(new window.Event("input"));

assert.htmlEqual(
target.innerHTML,
`
<input />
<input />
<div>123</div>
`
);
assert.equal(input1.value, "123");
assert.equal(input2.value, "123");
assert.equal(count, 2);

input1.value = "456";
await input1.dispatchEvent(new window.Event("input"));

assert.htmlEqual(
target.innerHTML,
`
<input />
<input />
<div>456</div>
`
);
assert.equal(input1.value, "456");
assert.equal(input2.value, "456");
assert.equal(count, 3);
},
};
18 changes: 18 additions & 0 deletions test/runtime/samples/component-binding-store/main.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
<script>
import { writable } from 'svelte/store';
import Input from './Input.svelte';
let value = writable({ value: '' });
export let callback = () => {};
value.subscribe(() => {
callback();
})
</script>

<input bind:value={$value.value} />

<Input bind:value={$value.value}/>

<div>{$value.value}</div>

0 comments on commit a7985a8

Please sign in to comment.