From ae3a7dd36911bcdd93f23cdf7bbb1b546d270981 Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Sun, 25 Nov 2018 19:54:20 -0500 Subject: [PATCH] shuffle things around --- index.js | 4 +- src/compile/render-dom/index.ts | 29 ++--- src/internal/Component.js | 115 +++++++++--------- .../after-render-prevents-loop/main.html | 4 +- .../after-render-triggers-update/main.html | 4 +- .../samples/before-render-chain/Item.html | 4 +- .../before-render-prevents-loop/main.html | 4 +- .../component-binding-deep-b/main.html | 4 +- .../samples/flush-before-bindings/main.html | 4 +- .../samples/immutable-nested/Nested.html | 4 +- .../samples/lifecycle-render-order/_config.js | 4 +- .../samples/lifecycle-render-order/main.html | 10 +- .../Widget.html | 4 +- .../set-in-onstate-dedupes-renders/main.html | 4 +- test/runtime/samples/set-in-onstate/main.html | 4 +- test/stats/samples/hooks/_config.js | 2 +- .../samples/onstate-arrow-no-this/input.html | 4 +- .../samples/onupdate-arrow-no-this/input.html | 4 +- .../samples/onupdate-arrow-this/errors.json | 4 +- .../samples/onupdate-arrow-this/input.html | 2 +- 20 files changed, 108 insertions(+), 110 deletions(-) diff --git a/index.js b/index.js index 8eb1b4f805..6f70e663a5 100644 --- a/index.js +++ b/index.js @@ -1,7 +1,7 @@ export { onMount, onDestroy, - beforeRender, - afterRender, + beforeUpdate, + afterUpdate, createEventDispatcher } from './internal.js'; \ No newline at end of file diff --git a/src/compile/render-dom/index.ts b/src/compile/render-dom/index.ts index ea6c21462d..e2baf28267 100644 --- a/src/compile/render-dom/index.ts +++ b/src/compile/render-dom/index.ts @@ -133,6 +133,7 @@ export default function dom( const debug_name = `<${component.customElement ? component.tag : name}>`; const not_equal = component.options.immutable ? `@not_equal` : `@safe_not_equal`; + let dev_props_check; if (component.options.dev) { // TODO check no uunexpected props were passed, as well as @@ -142,17 +143,14 @@ export default function dom( .filter(name => !component.initialised_declarations.has(name)); if (expected.length) { - body.push(deindent` - $$checkProps() { - const state = this.$$.get(); - ${expected.map(name => deindent` - - if (state.${name} === undefined) { - console.warn("${debug_name} was created without expected data property '${name}'"); - } - `)} - } - `); + dev_props_check = deindent` + const state = this.$$.get(); + ${expected.map(name => deindent` + + if (state.${name} === undefined) { + console.warn("${debug_name} was created without expected data property '${name}'"); + }`)} + `; } } @@ -180,7 +178,7 @@ export default function dom( }); builder.addBlock(deindent` - function $$create_fragment(${component.alias('component')}, ctx) { + function create_fragment(${component.alias('component')}, ctx) { ${block.getContents()} } @@ -188,7 +186,7 @@ export default function dom( ${component.fully_hoisted.length > 0 && component.fully_hoisted.join('\n\n')} - function $$init($$self, $$make_dirty) { + function define($$self, $$make_dirty) { ${should_add_css && `if (!document.getElementById("${component.stylesheet.id}-style")) @add_css();`} @@ -206,7 +204,10 @@ export default function dom( class ${name} extends ${superclass} { constructor(options) { - super(options, $$init, $$create_fragment, ${not_equal}); + super(${options.dev && `options`}); + @init(this, options, define, create_fragment, ${not_equal}); + + ${dev_props_check} } ${body.join('\n\n')} diff --git a/src/internal/Component.js b/src/internal/Component.js index 5e51f78c46..08745564dc 100644 --- a/src/internal/Component.js +++ b/src/internal/Component.js @@ -9,7 +9,9 @@ export function bind(component, name, callback) { callback(component.$$.get()[name]); } -export function mount_component({ $$: { fragment }}, target, anchor, hydrate) { +export function mount_component(component, target, anchor, hydrate) { + const { fragment, refs, inject_refs, on_mount, on_destroy, after_render } = component.$$; + if (hydrate) { fragment.l(children(target)); fragment.m(target, anchor); // TODO can we avoid moving DOM? @@ -18,24 +20,24 @@ export function mount_component({ $$: { fragment }}, target, anchor, hydrate) { fragment[fragment.i ? 'i' : 'm'](target, anchor); } - component.$$.inject_refs(component.$$.refs); + inject_refs(refs); // onMount happens after the initial afterUpdate. Because // afterUpdate callbacks happen in reverse order (inner first) // we schedule onMount callbacks before afterUpdate callbacks add_render_callback(() => { - const onDestroy = component.$$.on_mount.map(run).filter(is_function); - if (component.$$.on_destroy) { - component.$$.on_destroy.push(...onDestroy); + const new_on_destroy = on_mount.map(run).filter(is_function); + if (on_destroy) { + on_destroy.push(...new_on_destroy); } else { // Edge case — component was destroyed immediately, // most likely as a result of a binding initialising - run_all(onDestroy); + run_all(new_on_destroy); } component.$$.on_mount = []; }); - component.$$.after_render.forEach(add_render_callback); + after_render.forEach(add_render_callback); } function destroy(component, detach) { @@ -58,57 +60,57 @@ function make_dirty(component, key) { component.$$.dirty[key] = true; } -export class $$Component { - constructor(options, init, create_fragment, not_equal) { - const previous_component = current_component; - set_current_component(this); - - this.$$ = { - fragment: null, - - // state - get: null, - set: noop, - inject_refs: noop, - not_equal, - bound: blankObject(), - - // lifecycle - on_mount: [], - on_destroy: [], - before_render: [], - after_render: [], - - // everything else - callbacks: blankObject(), - slotted: options.slots || {}, - refs: {}, - dirty: null, - binding_groups: [] - }; - - init(this, key => { - make_dirty(this, key); - if (this.$$.bound[key]) this.$$.bound[key](this.$$.get()[key]); - }); - - if (options.props) { - this.$$.set(options.props); - } +export function init(component, options, define, create_fragment, not_equal) { + const previous_component = current_component; + set_current_component(component); + + component.$$ = { + fragment: null, + + // state + get: null, + set: noop, + inject_refs: noop, + not_equal, + bound: blankObject(), + + // lifecycle + on_mount: [], + on_destroy: [], + before_render: [], + after_render: [], + + // everything else + callbacks: blankObject(), + slotted: options.slots || {}, + refs: {}, + dirty: null, + binding_groups: [] + }; + + define(component, key => { + make_dirty(component, key); + if (component.$$.bound[key]) component.$$.bound[key](component.$$.get()[key]); + }); - run_all(this.$$.before_render); - this.$$.fragment = create_fragment(this, this.$$.get()); + if (options.props) { + component.$$.set(options.props); + } - if (options.target) { - intro.enabled = !!options.intro; - mount_component(this, options.target, options.anchor, options.hydrate); - flush(); - intro.enabled = true; - } + run_all(component.$$.before_render); + component.$$.fragment = create_fragment(component, component.$$.get()); - set_current_component(previous_component); + if (options.target) { + intro.enabled = !!options.intro; + mount_component(component, options.target, options.anchor, options.hydrate); + flush(); + intro.enabled = true; } + set_current_component(previous_component); +} + +export class $$Component { $destroy() { destroy(this, true); this.$destroy = noop; @@ -141,8 +143,7 @@ export class $$ComponentDev extends $$Component { throw new Error(`'target' is a required option`); } - super(...arguments); - this.$$checkProps(); + super(); } $destroy() { @@ -151,8 +152,4 @@ export class $$ComponentDev extends $$Component { console.warn(`Component was already destroyed`); }; } - - $$checkProps() { - // noop by default - } } \ No newline at end of file diff --git a/test/runtime/samples/after-render-prevents-loop/main.html b/test/runtime/samples/after-render-prevents-loop/main.html index 413c8b2b2c..8733885943 100644 --- a/test/runtime/samples/after-render-prevents-loop/main.html +++ b/test/runtime/samples/after-render-prevents-loop/main.html @@ -1,10 +1,10 @@ diff --git a/test/runtime/samples/after-render-triggers-update/main.html b/test/runtime/samples/after-render-triggers-update/main.html index 310606b182..59235aef12 100644 --- a/test/runtime/samples/after-render-triggers-update/main.html +++ b/test/runtime/samples/after-render-triggers-update/main.html @@ -1,12 +1,12 @@ diff --git a/test/runtime/samples/before-render-chain/Item.html b/test/runtime/samples/before-render-chain/Item.html index 0317e153bc..be82b5f372 100644 --- a/test/runtime/samples/before-render-chain/Item.html +++ b/test/runtime/samples/before-render-chain/Item.html @@ -1,10 +1,10 @@ diff --git a/test/runtime/samples/before-render-prevents-loop/main.html b/test/runtime/samples/before-render-prevents-loop/main.html index d882ec6726..7d7a2b9a18 100644 --- a/test/runtime/samples/before-render-prevents-loop/main.html +++ b/test/runtime/samples/before-render-prevents-loop/main.html @@ -1,10 +1,10 @@ diff --git a/test/runtime/samples/component-binding-deep-b/main.html b/test/runtime/samples/component-binding-deep-b/main.html index 577aa16b2e..a2de980483 100644 --- a/test/runtime/samples/component-binding-deep-b/main.html +++ b/test/runtime/samples/component-binding-deep-b/main.html @@ -1,5 +1,5 @@ diff --git a/test/runtime/samples/lifecycle-render-order/_config.js b/test/runtime/samples/lifecycle-render-order/_config.js index addff923c1..44d7f61da6 100644 --- a/test/runtime/samples/lifecycle-render-order/_config.js +++ b/test/runtime/samples/lifecycle-render-order/_config.js @@ -5,9 +5,9 @@ export default { test({ assert, component, target }) { assert.deepEqual(order, [ - 'beforeRender', + 'beforeUpdate', 'render', - 'afterRender', + 'afterUpdate', 'onMount' ]); diff --git a/test/runtime/samples/lifecycle-render-order/main.html b/test/runtime/samples/lifecycle-render-order/main.html index 118fb053ff..719cd68327 100644 --- a/test/runtime/samples/lifecycle-render-order/main.html +++ b/test/runtime/samples/lifecycle-render-order/main.html @@ -1,5 +1,5 @@ diff --git a/test/runtime/samples/set-in-onstate/main.html b/test/runtime/samples/set-in-onstate/main.html index a166d1a11b..9009324f78 100644 --- a/test/runtime/samples/set-in-onstate/main.html +++ b/test/runtime/samples/set-in-onstate/main.html @@ -1,10 +1,10 @@ diff --git a/test/stats/samples/hooks/_config.js b/test/stats/samples/hooks/_config.js index 70830cf54d..ae9528a7fb 100644 --- a/test/stats/samples/hooks/_config.js +++ b/test/stats/samples/hooks/_config.js @@ -4,7 +4,7 @@ export default { oncreate: true, onDestroy: false, onstate: false, - afterRender: false + afterUpdate: false }); } }; \ No newline at end of file diff --git a/test/validator/samples/onstate-arrow-no-this/input.html b/test/validator/samples/onstate-arrow-no-this/input.html index 11ce6757d4..a4e3a162bd 100644 --- a/test/validator/samples/onstate-arrow-no-this/input.html +++ b/test/validator/samples/onstate-arrow-no-this/input.html @@ -1,5 +1,5 @@ diff --git a/test/validator/samples/onupdate-arrow-no-this/input.html b/test/validator/samples/onupdate-arrow-no-this/input.html index c1ea0b16ba..498b25da49 100644 --- a/test/validator/samples/onupdate-arrow-no-this/input.html +++ b/test/validator/samples/onupdate-arrow-no-this/input.html @@ -1,5 +1,5 @@ diff --git a/test/validator/samples/onupdate-arrow-this/errors.json b/test/validator/samples/onupdate-arrow-this/errors.json index aaf4b057a2..9e598f33ae 100644 --- a/test/validator/samples/onupdate-arrow-this/errors.json +++ b/test/validator/samples/onupdate-arrow-this/errors.json @@ -1,6 +1,6 @@ [{ - "code": "invalid-afterRender-property", - "message": "'afterRender' should be a function expression, not an arrow function expression", + "code": "invalid-afterUpdate-property", + "message": "'afterUpdate' should be a function expression, not an arrow function expression", "pos": 29, "start": { "line": 3, diff --git a/test/validator/samples/onupdate-arrow-this/input.html b/test/validator/samples/onupdate-arrow-this/input.html index 092e9bb9b2..2cdc2b3147 100644 --- a/test/validator/samples/onupdate-arrow-this/input.html +++ b/test/validator/samples/onupdate-arrow-this/input.html @@ -1,6 +1,6 @@