resolve merge conflicts

pull/107/head
Rich-Harris 8 years ago
commit 7654437d7b

@ -34,12 +34,12 @@ export default function generate ( parsed, source, options ) {
}, },
createMountStatement ( name ) { createMountStatement ( name ) {
if ( generator.current.useAnchor && generator.current.target === 'target' ) { if ( generator.current.target === 'target' ) {
generator.current.initStatements.push( deindent ` generator.current.mountStatements.push( deindent`
anchor.parentNode.insertBefore( ${name}, anchor ); target.insertBefore( ${name}, anchor );
` ); ` );
} else { } else {
generator.current.initStatements.push( deindent ` generator.current.initStatements.push( deindent`
${generator.current.target}.appendChild( ${name} ); ${generator.current.target}.appendChild( ${name} );
` ); ` );
} }
@ -58,10 +58,17 @@ export default function generate ( parsed, source, options ) {
} }
renderers.push( deindent` renderers.push( deindent`
function ${fragment.name} ( ${fragment.params}, component, target${fragment.useAnchor ? ', anchor' : ''} ) { function ${fragment.name} ( ${fragment.params}, component ) {
var target, anchor;
${fragment.initStatements.join( '\n\n' )} ${fragment.initStatements.join( '\n\n' )}
return { return {
mount: function ( _target, _anchor ) {
target = _target;
anchor = _anchor;
${fragment.mountStatements.join( '\n\n' )}
},
update: function ( changed, ${fragment.params} ) { update: function ( changed, ${fragment.params} ) {
${fragment.updateStatements.join( '\n\n' )} ${fragment.updateStatements.join( '\n\n' )}
}, },
@ -249,6 +256,7 @@ export default function generate ( parsed, source, options ) {
localElementDepth: 0, localElementDepth: 0,
initStatements: [], initStatements: [],
mountStatements: [],
updateStatements: [], updateStatements: [],
teardownStatements: [], teardownStatements: [],
@ -377,13 +385,17 @@ export default function generate ( parsed, source, options ) {
if ( generator.hasComplexBindings ) { if ( generator.hasComplexBindings ) {
initStatements.push( deindent` initStatements.push( deindent`
this.__bindings = []; this.__bindings = [];
var mainFragment = renderMainFragment( state, this, options.target ); var mainFragment = renderMainFragment( state, this );
if ( options.target ) this.mount( options.target );
while ( this.__bindings.length ) this.__bindings.pop()(); while ( this.__bindings.length ) this.__bindings.pop()();
` ); ` );
setStatements.push( `while ( this.__bindings.length ) this.__bindings.pop()();` ); setStatements.push( `while ( this.__bindings.length ) this.__bindings.pop()();` );
} else { } else {
initStatements.push( `var mainFragment = renderMainFragment( state, this, options.target );` ); initStatements.push( deindent`
var mainFragment = renderMainFragment( state, this );
if ( options.target ) this.mount( options.target );
` );
} }
if ( generator.hasComponents ) { if ( generator.hasComponents ) {
@ -462,6 +474,10 @@ export default function generate ( parsed, source, options ) {
${setStatements.join( '\n\n' )} ${setStatements.join( '\n\n' )}
}; };
this.mount = function mount ( target, anchor ) {
mainFragment.mount( target, anchor );
}
this.observe = function ( key, callback, options ) { this.observe = function ( key, callback, options ) {
var group = ( options && options.defer ) ? observers.deferred : observers.immediate; var group = ( options && options.defer ) ? observers.deferred : observers.immediate;

@ -5,10 +5,13 @@ export default {
enter ( generator, node ) { enter ( generator, node ) {
const i = generator.counters.each++; const i = generator.counters.each++;
const name = `eachBlock_${i}`; const name = `eachBlock_${i}`;
const iterations = `${name}_iterations`;
const renderer = `renderEachBlock_${i}`; const renderer = `renderEachBlock_${i}`;
const listName = `${name}_value`; const listName = `${name}_value`;
const isToplevel = generator.current.localElementDepth === 0;
generator.addSourcemapLocations( node.expression ); generator.addSourcemapLocations( node.expression );
const { dependencies, snippet } = generator.contextualise( node.expression ); const { dependencies, snippet } = generator.contextualise( node.expression );
@ -17,39 +20,44 @@ export default {
generator.current.initStatements.push( deindent` generator.current.initStatements.push( deindent`
var ${name}_value = ${snippet}; var ${name}_value = ${snippet};
var ${name}_fragment = document.createDocumentFragment(); var ${iterations} = [];
var ${name}_iterations = [];
for ( var i = 0; i < ${name}_value.length; i += 1 ) { for ( var i = 0; i < ${name}_value.length; i += 1 ) {
${name}_iterations[i] = ${renderer}( ${generator.current.params}, ${listName}, ${listName}[i], i, component, ${name}_fragment ); ${iterations}[i] = ${renderer}( ${generator.current.params}, ${listName}, ${listName}[i], i, component );
${!isToplevel ? `${iterations}[i].mount( ${anchor}.parentNode, ${anchor} );` : ''}
} }
${anchor}.parentNode.insertBefore( ${name}_fragment, ${anchor} );
` ); ` );
if ( isToplevel ) {
generator.current.mountStatements.push( deindent`
for ( var i = 0; i < ${iterations}.length; i += 1 ) {
${iterations}[i].mount( ${anchor}.parentNode, ${anchor} );
}
` );
}
generator.current.updateStatements.push( deindent` generator.current.updateStatements.push( deindent`
var ${name}_value = ${snippet}; var ${name}_value = ${snippet};
for ( var i = 0; i < ${name}_value.length; i += 1 ) { for ( var i = 0; i < ${name}_value.length; i += 1 ) {
if ( !${name}_iterations[i] ) { if ( !${iterations}[i] ) {
${name}_iterations[i] = ${renderer}( ${generator.current.params}, ${listName}, ${listName}[i], i, component, ${name}_fragment ); ${iterations}[i] = ${renderer}( ${generator.current.params}, ${listName}, ${listName}[i], i, component );
${iterations}[i].mount( ${anchor}.parentNode, ${anchor} );
} else { } else {
${name}_iterations[i].update( changed, ${generator.current.params}, ${listName}, ${listName}[i], i ); ${iterations}[i].update( changed, ${generator.current.params}, ${listName}, ${listName}[i], i );
} }
} }
for ( var i = ${name}_value.length; i < ${name}_iterations.length; i += 1 ) { for ( var i = ${name}_value.length; i < ${iterations}.length; i += 1 ) {
${name}_iterations[i].teardown( true ); ${iterations}[i].teardown( true );
} }
${anchor}.parentNode.insertBefore( ${name}_fragment, ${anchor} ); ${iterations}.length = ${listName}.length;
${name}_iterations.length = ${listName}.length;
` ); ` );
const isToplevel = generator.current.localElementDepth === 0;
generator.current.teardownStatements.push( deindent` generator.current.teardownStatements.push( deindent`
for ( var i = 0; i < ${name}_iterations.length; i += 1 ) { for ( var i = 0; i < ${iterations}.length; i += 1 ) {
${name}_iterations[i].teardown( ${isToplevel ? 'detach' : 'false'} ); ${iterations}[i].teardown( ${isToplevel ? 'detach' : 'false'} );
} }
` ); ` );
@ -87,6 +95,7 @@ export default {
params, params,
initStatements: [], initStatements: [],
mountStatements: [],
updateStatements: [ Object.keys( contexts ).map( contextName => { updateStatements: [ Object.keys( contexts ).map( contextName => {
const listName = listNames[ contextName ]; const listName = listNames[ contextName ];
const indexName = indexNames[ contextName ]; const indexName = indexNames[ contextName ];

@ -15,6 +15,7 @@ export default {
allUsedContexts: new Set(), allUsedContexts: new Set(),
init: [], init: [],
mount: [],
update: [], update: [],
teardown: [] teardown: []
}; };
@ -57,7 +58,7 @@ export default {
${statements.join( '\n\n' )} ${statements.join( '\n\n' )}
var ${name} = new template.components.${node.name}({ var ${name} = new template.components.${node.name}({
target: ${generator.current.target}, target: ${!isToplevel ? generator.current.target: 'null'},
root: component.root || component, root: component.root || component,
data: ${name}_initialData data: ${name}_initialData
}); });
@ -65,12 +66,16 @@ export default {
} else { } else {
local.init.unshift( deindent` local.init.unshift( deindent`
var ${name} = new template.components.${node.name}({ var ${name} = new template.components.${node.name}({
target: ${generator.current.target}, target: ${!isToplevel ? generator.current.target: 'null'},
root: component.root || component root: component.root || component
}); });
` ); ` );
} }
if ( isToplevel ) {
local.mount.unshift( `${name}.mount( target, anchor );` );
}
if ( local.dynamicAttributes.length ) { if ( local.dynamicAttributes.length ) {
const updates = local.dynamicAttributes.map( attribute => { const updates = local.dynamicAttributes.map( attribute => {
return deindent` return deindent`
@ -146,6 +151,7 @@ export default {
generator.current.initStatements.push( local.init.join( '\n' ) ); generator.current.initStatements.push( local.init.join( '\n' ) );
if ( local.update.length ) generator.current.updateStatements.push( local.update.join( '\n' ) ); if ( local.update.length ) generator.current.updateStatements.push( local.update.join( '\n' ) );
if ( local.mount.length ) generator.current.mountStatements.push( local.mount.join( '\n' ) );
generator.current.teardownStatements.push( local.teardown.join( '\n' ) ); generator.current.teardownStatements.push( local.teardown.join( '\n' ) );
generator.push({ generator.push({

@ -11,6 +11,7 @@ function generateBlock ( generator, node, name ) {
localElementDepth: 0, localElementDepth: 0,
initStatements: [], initStatements: [],
mountStatements: [],
updateStatements: [], updateStatements: [],
teardownStatements: [], teardownStatements: [],
@ -54,11 +55,12 @@ export default {
enter ( generator, node ) { enter ( generator, node ) {
const i = generator.counters.if++; const i = generator.counters.if++;
const { params, target } = generator.current; const { params } = generator.current;
const name = `ifBlock_${i}`; const name = `ifBlock_${i}`;
const getBlock = `getBlock_${i}`; const getBlock = `getBlock_${i}`;
const currentBlock = `currentBlock_${i}`; const currentBlock = `currentBlock_${i}`;
const isToplevel = generator.current.localElementDepth === 0;
const conditionsAndBlocks = getConditionsAndBlocks( generator, node, `renderIfBlock_${i}` ); const conditionsAndBlocks = getConditionsAndBlocks( generator, node, `renderIfBlock_${i}` );
const anchor = generator.createAnchor( name, `#if ${generator.source.slice( node.expression.start, node.expression.end )}` ); const anchor = generator.createAnchor( name, `#if ${generator.source.slice( node.expression.start, node.expression.end )}` );
@ -71,9 +73,16 @@ export default {
} }
var ${currentBlock} = ${getBlock}( ${params} ); var ${currentBlock} = ${getBlock}( ${params} );
var ${name} = ${currentBlock} && ${currentBlock}( ${params}, component, ${target}, ${anchor} ); var ${name} = ${currentBlock} && ${currentBlock}( ${params}, component );
` ); ` );
const mountStatement = `if ( ${name} ) ${name}.mount( ${anchor}.parentNode, ${anchor} );`;
if ( isToplevel ) {
generator.current.mountStatements.push( mountStatement );
} else {
generator.current.initStatements.push( mountStatement );
}
generator.current.updateStatements.push( deindent` generator.current.updateStatements.push( deindent`
var _${currentBlock} = ${currentBlock}; var _${currentBlock} = ${currentBlock};
${currentBlock} = ${getBlock}( ${params} ); ${currentBlock} = ${getBlock}( ${params} );
@ -81,11 +90,11 @@ export default {
${name}.update( changed, ${params} ); ${name}.update( changed, ${params} );
} else { } else {
if ( ${name} ) ${name}.teardown( true ); if ( ${name} ) ${name}.teardown( true );
${name} = ${currentBlock} && ${currentBlock}( ${params}, component, ${target}, ${anchor} ); ${name} = ${currentBlock} && ${currentBlock}( ${params}, component );
if ( ${name} ) ${name}.mount( ${anchor}.parentNode, ${anchor} );
} }
` ); ` );
const isToplevel = generator.current.localElementDepth === 0;
generator.current.teardownStatements.push( deindent` generator.current.teardownStatements.push( deindent`
if ( ${name} ) ${name}.teardown( ${isToplevel ? 'detach' : 'false'} ); if ( ${name} ) ${name}.teardown( ${isToplevel ? 'detach' : 'false'} );
` ); ` );

@ -0,0 +1,33 @@
const VALUES = Array.from( 'abcdefghijklmnopqrstuvwxyz' );
function permute () {
const values = VALUES.slice();
const number = Math.floor(Math.random() * VALUES.length);
const permuted = [];
for (let i = 0; i < number; i++) {
permuted.push( ...values.splice( Math.floor( Math.random() * ( number - i ) ), 1 ) );
}
return {
data: permuted,
expected: permuted.length ? `(${permuted.join(')(')})` : ''
};
}
let step = permute();
export default {
data: {
values: step.data
},
html: step.expected,
test ( assert, component, target ) {
for (let i = 0; i < 100; i++) {
step = permute();
component.set({ values: step.data });
assert.htmlEqual( target.innerHTML, step.expected );
}
}
};

@ -0,0 +1,3 @@
{{#each values as value}}
({{value}})
{{/each}}
Loading…
Cancel
Save