diff --git a/src/generators/Generator.ts b/src/generators/Generator.ts index eea74c3173..2b921f812e 100644 --- a/src/generators/Generator.ts +++ b/src/generators/Generator.ts @@ -727,9 +727,9 @@ export default class Generator { } else if (node.name === ':Window') { // TODO do this in parse? node.type = 'Window'; node.__proto__ = nodes.Window.prototype; - } else if (node.name === ':Document') { // TODO do this in parse? - node.type = 'Document'; - node.__proto__ = nodes.Document.prototype; + } else if (node.name === ':Head') { // TODO do this in parse? + node.type = 'Head'; + node.__proto__ = nodes.Head.prototype; } else if (node.type === 'Element' && node.name === 'slot' && !generator.customElement) { node.type = 'Slot'; node.__proto__ = nodes.Slot.prototype; diff --git a/src/generators/dom/Block.ts b/src/generators/dom/Block.ts index adf410f9ef..ad452b930e 100644 --- a/src/generators/dom/Block.ts +++ b/src/generators/dom/Block.ts @@ -132,9 +132,9 @@ export default class Block { ) { this.addVariable(name); this.builders.create.addLine(`${name} = ${renderStatement};`); - this.builders.claim.addLine(`${name} = ${claimStatement};`); + this.builders.claim.addLine(`${name} = ${claimStatement || renderStatement};`); - if (parentNode) { + if (parentNode && parentNode !== 'document.head') { this.builders.mount.addLine(`@appendNode(${name}, ${parentNode});`); } else { this.builders.mount.addLine(`@insertNode(${name}, #target, anchor);`); diff --git a/src/generators/nodes/AwaitBlock.ts b/src/generators/nodes/AwaitBlock.ts index f47f5de61b..8dccd62e83 100644 --- a/src/generators/nodes/AwaitBlock.ts +++ b/src/generators/nodes/AwaitBlock.ts @@ -68,7 +68,7 @@ export default class AwaitBlock extends Node { ) { const name = this.var; - const anchor = this.getOrCreateAnchor(block, parentNode); + const anchor = this.getOrCreateAnchor(block, parentNode, parentNodes); const updateMountNode = this.getUpdateMountNode(anchor); const params = block.params.join(', '); @@ -143,9 +143,11 @@ export default class AwaitBlock extends Node { ${await_block}.c(); `); - block.builders.claim.addBlock(deindent` - ${await_block}.l(${parentNodes}); - `); + if (parentNodes) { + block.builders.claim.addBlock(deindent` + ${await_block}.l(${parentNodes}); + `); + } const initialMountNode = parentNode || '#target'; const anchorNode = parentNode ? 'null' : 'anchor'; diff --git a/src/generators/nodes/Component.ts b/src/generators/nodes/Component.ts index 95b29fcbd3..e52c41e9f8 100644 --- a/src/generators/nodes/Component.ts +++ b/src/generators/nodes/Component.ts @@ -248,7 +248,7 @@ export default class Component extends Node { block.contextualise(this.expression); const { dependencies, snippet } = this.metadata; - const anchor = this.getOrCreateAnchor(block, parentNode); + const anchor = this.getOrCreateAnchor(block, parentNode, parentNodes); const params = block.params.join(', '); @@ -281,9 +281,11 @@ export default class Component extends Node { `if (${name}) ${name}._fragment.c();` ); - block.builders.claim.addLine( - `if (${name}) ${name}._fragment.l(${parentNodes});` - ); + if (parentNodes) { + block.builders.claim.addLine( + `if (${name}) ${name}._fragment.l(${parentNodes});` + ); + } block.builders.mount.addLine( `if (${name}) ${name}._mount(${parentNode || '#target'}, ${parentNode ? 'null' : 'anchor'});` @@ -350,9 +352,11 @@ export default class Component extends Node { block.builders.create.addLine(`${name}._fragment.c();`); - block.builders.claim.addLine( - `${name}._fragment.l(${parentNodes});` - ); + if (parentNodes) { + block.builders.claim.addLine( + `${name}._fragment.l(${parentNodes});` + ); + } block.builders.mount.addLine( `${name}._mount(${parentNode || '#target'}, ${parentNode ? 'null' : 'anchor'});` diff --git a/src/generators/nodes/EachBlock.ts b/src/generators/nodes/EachBlock.ts index 809eaf9397..688c964fac 100644 --- a/src/generators/nodes/EachBlock.ts +++ b/src/generators/nodes/EachBlock.ts @@ -154,7 +154,7 @@ export default class EachBlock extends Node { block.addElement( anchor, `@createComment()`, - `@createComment()`, + parentNodes && `@createComment()`, parentNode ); } @@ -263,7 +263,7 @@ export default class EachBlock extends Node { this.block.addElement( this.block.first, `@createComment()`, - `@createComment()`, + parentNodes && `@createComment()`, null ); } @@ -293,13 +293,15 @@ export default class EachBlock extends Node { } `); - block.builders.claim.addBlock(deindent` - var ${iteration} = ${head}; - while (${iteration}) { - ${iteration}.l(${parentNodes}); - ${iteration} = ${iteration}.next; - } - `); + if (parentNodes) { + block.builders.claim.addBlock(deindent` + var ${iteration} = ${head}; + while (${iteration}) { + ${iteration}.l(${parentNodes}); + ${iteration} = ${iteration}.next; + } + `); + } block.builders.mount.addBlock(deindent` var ${iteration} = ${head}; @@ -481,11 +483,13 @@ export default class EachBlock extends Node { } `); - block.builders.claim.addBlock(deindent` - for (var #i = 0; #i < ${iterations}.length; #i += 1) { - ${iterations}[#i].l(${parentNodes}); - } - `); + if (parentNodes) { + block.builders.claim.addBlock(deindent` + for (var #i = 0; #i < ${iterations}.length; #i += 1) { + ${iterations}[#i].l(${parentNodes}); + } + `); + } block.builders.mount.addBlock(deindent` for (var #i = 0; #i < ${iterations}.length; #i += 1) { diff --git a/src/generators/nodes/Element.ts b/src/generators/nodes/Element.ts index 9a11cbde25..fdd09d676f 100644 --- a/src/generators/nodes/Element.ts +++ b/src/generators/nodes/Element.ts @@ -163,7 +163,7 @@ export default class Element extends Node { const childState = { parentNode: this.var, - parentNodes: block.getUniqueName(`${this.var}_nodes`) + parentNodes: parentNodes && block.getUniqueName(`${this.var}_nodes`) // if we're in unclaimable territory, i.e.
, parentNodes is null }; const name = this.var; @@ -175,22 +175,25 @@ export default class Element extends Node { parentNode; block.addVariable(name); + const renderStatement = getRenderStatement(this.generator, this.namespace, this.name); block.builders.create.addLine( - `${name} = ${getRenderStatement( - this.generator, - this.namespace, - this.name - )};` + `${name} = ${renderStatement};` ); if (this.generator.hydratable) { - block.builders.claim.addBlock(deindent` - ${name} = ${getClaimStatement(generator, this.namespace, parentNodes, this)}; - var ${childState.parentNodes} = @children(${name}); - `); + if (parentNodes) { + block.builders.claim.addBlock(deindent` + ${name} = ${getClaimStatement(generator, this.namespace, parentNodes, this)}; + var ${childState.parentNodes} = @children(${name}); + `); + } else { + block.builders.claim.addLine( + `${name} = ${renderStatement};` + ); + } } - if (initialMountNode) { + if (initialMountNode && initialMountNode !== 'document.head') { block.builders.mount.addLine( `@appendNode(${name}, ${initialMountNode});` ); @@ -394,9 +397,11 @@ export default class Element extends Node { block.builders.mount.addBlock(this.initialUpdate); } - block.builders.claim.addLine( - `${childState.parentNodes}.forEach(@detachNode);` - ); + if (childState.parentNodes) { + block.builders.claim.addLine( + `${childState.parentNodes}.forEach(@detachNode);` + ); + } function toHTML(node: Element | Text) { if (node.type === 'Text') return node.data; diff --git a/src/generators/nodes/Document.ts b/src/generators/nodes/Head.ts similarity index 53% rename from src/generators/nodes/Document.ts rename to src/generators/nodes/Head.ts index c481b15299..be72087aca 100644 --- a/src/generators/nodes/Document.ts +++ b/src/generators/nodes/Head.ts @@ -4,10 +4,18 @@ import Node from './shared/Node'; import Block from '../dom/Block'; import Attribute from './Attribute'; -export default class Document extends Node { - type: 'Document'; +export default class Head extends Node { + type: 'Head'; attributes: Attribute[]; + init( + block: Block, + stripWhitespace: boolean, + nextSibling: Node + ) { + this.initChildren(block, true, null); + } + build( block: Block, parentNode: string, @@ -15,12 +23,10 @@ export default class Document extends Node { ) { const { generator } = this; - this.var = 'document'; + this.var = 'document.head'; - this.attributes.forEach((attribute: Attribute) => { - if (attribute.name === 'title') { - attribute.render(block); - } + this.children.forEach((child: Node) => { + child.build(block, 'document.head', null); }); } } diff --git a/src/generators/nodes/IfBlock.ts b/src/generators/nodes/IfBlock.ts index b3978e5356..3cec2245d9 100644 --- a/src/generators/nodes/IfBlock.ts +++ b/src/generators/nodes/IfBlock.ts @@ -133,15 +133,17 @@ export default class IfBlock extends Node { block.builders.create.addLine(`${if_name}${name}.c();`); - block.builders.claim.addLine( - `${if_name}${name}.l(${parentNodes});` - ); + if (parentNodes) { + block.builders.claim.addLine( + `${if_name}${name}.l(${parentNodes});` + ); + } if (needsAnchor) { block.addElement( anchor, `@createComment()`, - `@createComment()`, + parentNodes && `@createComment()`, parentNode ); } diff --git a/src/generators/nodes/MustacheTag.ts b/src/generators/nodes/MustacheTag.ts index 35baccdc2b..21b3b30df2 100644 --- a/src/generators/nodes/MustacheTag.ts +++ b/src/generators/nodes/MustacheTag.ts @@ -22,7 +22,7 @@ export default class MustacheTag extends Tag { block.addElement( this.var, `@createText(${init})`, - `@claimText(${parentNodes}, ${init})`, + parentNodes && `@claimText(${parentNodes}, ${init})`, parentNode ); } diff --git a/src/generators/nodes/RawMustacheTag.ts b/src/generators/nodes/RawMustacheTag.ts index 8b81453033..6e9e5e664e 100644 --- a/src/generators/nodes/RawMustacheTag.ts +++ b/src/generators/nodes/RawMustacheTag.ts @@ -61,7 +61,7 @@ export default class RawMustacheTag extends Tag { block.addElement( anchorBefore, `@createElement('noscript')`, - `@createElement('noscript')`, + parentNodes && `@createElement('noscript')`, parentNode ); } @@ -70,7 +70,7 @@ export default class RawMustacheTag extends Tag { block.addElement( anchorAfter, `@createElement('noscript')`, - `@createElement('noscript')`, + parentNodes && `@createElement('noscript')`, parentNode ); } diff --git a/src/generators/nodes/Text.ts b/src/generators/nodes/Text.ts index 28d56f14c4..c00b00f4fe 100644 --- a/src/generators/nodes/Text.ts +++ b/src/generators/nodes/Text.ts @@ -53,7 +53,7 @@ export default class Text extends Node { block.addElement( this.var, `@createText(${stringify(this.data)})`, - `@claimText(${parentNodes}, ${stringify(this.data)})`, + parentNodes && `@claimText(${parentNodes}, ${stringify(this.data)})`, parentNode ); } diff --git a/src/generators/nodes/index.ts b/src/generators/nodes/index.ts index b41c676967..274735043d 100644 --- a/src/generators/nodes/index.ts +++ b/src/generators/nodes/index.ts @@ -5,12 +5,12 @@ import Binding from './Binding'; import CatchBlock from './CatchBlock'; import Comment from './Comment'; import Component from './Component'; -import Document from './Document'; import EachBlock from './EachBlock'; import Element from './Element'; import ElseBlock from './ElseBlock'; import EventHandler from './EventHandler'; import Fragment from './Fragment'; +import Head from './Head'; import IfBlock from './IfBlock'; import MustacheTag from './MustacheTag'; import PendingBlock from './PendingBlock'; @@ -29,12 +29,12 @@ const nodes: Record