template.ts 1.0 KB

12345678910111213141516171819202122232425262728293031323334
  1. import { adoptTemplate, currentHydrationNode, isHydrating } from './hydration'
  2. import { child, createElement, createTextNode } from './node'
  3. let t: HTMLTemplateElement
  4. /*! #__NO_SIDE_EFFECTS__ */
  5. export function template(html: string, root?: boolean) {
  6. let node: Node
  7. return (): Node & { $root?: true } => {
  8. if (isHydrating) {
  9. if (__DEV__ && !currentHydrationNode) {
  10. // TODO this should not happen
  11. throw new Error('No current hydration node')
  12. }
  13. // do not cache the adopted node in node because it contains child nodes
  14. // this avoids duplicate rendering of children
  15. const adopted = adoptTemplate(currentHydrationNode!, html)!
  16. if (root) (adopted as any).$root = true
  17. return adopted
  18. }
  19. // fast path for text nodes
  20. if (html[0] !== '<') {
  21. return createTextNode(html)
  22. }
  23. if (!node) {
  24. t = t || createElement('template')
  25. t.innerHTML = html
  26. node = child(t.content)
  27. }
  28. const ret = node.cloneNode(true)
  29. if (root) (ret as any).$root = true
  30. return ret
  31. }
  32. }