Как браузер обрабатывает тег <template>против тега <div> - PullRequest
0 голосов
/ 25 апреля 2018

Я читал документацию по тегу <template> и не могу понять, чем он отличается от простого использования <div>, то есть display: none;

Документация: шаблон тега

<template> пример

<template id="productrow">
  <tr>
    <td class="record"></td>
    <td></td>
  </tr>
</template>

VS <div> пример

<div id="productrow" style="display: none">
  <tr>
    <td class="record"></td>
    <td></td>
  </tr>
</div>
  1. На низком уровне, какБраузер обрабатывает эти 2 примера по-разному?
  2. Некоторые методы JS или атрибуты HTML отличаются или недоступны?

PS: Мне известны различия в совместимости браузера

Ответы [ 3 ]

0 голосов
/ 25 апреля 2018

Элементы внутри <template> не могут быть найдены ни одним селектором в JS, поэтому вы не можете случайно найти их и извлечь их, вы должны использовать свойство content HTMLTemplateElement используя что-то вроде:

var clone = document.importNode(templateElement.content, true);

Также каждый <style>, <audio>/<video>/... или <script> анализируется при загрузке страницы, но не запускается, пока вы не клонируете его в основной DOM.

0 голосов
/ 25 апреля 2018

Я нашел статью, в которой подробно объясняются все различия: https://www.html5rocks.com/en/tutorials/webcomponents/template/

Теперь я понимаю, что пример <div> на самом деле был своего рода полифилом, использовавшимся в старых браузерах, и его пришлось серьезно взломать.чтобы все заработало как положено.

Спасибо всем за помощь.

0 голосов
/ 25 апреля 2018

Рассмотрим:

<template>
  <style>
    body: { background-color: black; }
  </style>
  <script>
    alert('hello');
  </script>
  <audio src="alert.wav" autoplay></audio>
</template>

И

<div style="display: none;">
  <style>
    body: { background-color: black; }
  </style>
  <script>
    alert('hello');
  </script>
  <audio src="alert.wav" autoplay></audio>
</div>

Будут ли они вести себя одинаково, когда их отображает браузер? (Спойлер: нет.)

Чтобы ответить на ваши конкретные вопросы, хотя:

  1. На низком уровне, как браузер по-разному обрабатывает эти 2 примера?

Например, HTML внутри <template> не становится элементами DOM, которые являются потомками <template>. Он становится потомком «инертного» DocumentFragment (косвенно; это упрощение), где они существуют как узлы, но ничего не «делают», как в примере выше.

Помимо «инертности», содержимое шаблона не имеет «требований соответствия». Ваш <tr> пример выше - хороший. Посмотрите, что здесь происходит:

const template = document.querySelector('template');
const div = document.querySelector('div');

console.log('template.innerHTML is', template.innerHTML);
console.log('div.innerHTML is', div.innerHTML);
<template>
  <tr>
    <td class="record"></td>
    <td></td>
  </tr>
</template>

<div style="display: none">
  <tr>
    <td class="record"></td>
    <td></td>
  </tr>
</div>

В обычном документе <tr> не может быть дочерним по отношению к <div>, поэтому браузер просто удаляет его. В <template> это требование не существует. Вы найдете то же самое с, скажем, <div style="{{myStyle}}">. В документе браузер отбрасывает атрибут style, поскольку его значение недопустимо; в <template> не было бы. Вот что делает <template> полезным для шаблонов.

Если вы хотите узнать больше о том, как визуализируются <template> s, я предлагаю прочитать раздел об этом в спецификации HTML . Это не легко читать, и части могут быть непонятны, но вы многому научитесь.

  1. Некоторые методы JS или атрибуты HTML отличаются или недоступны?

Элемент <template> имеет атрибут content, который указывает на фрагмент документа, рассмотренный выше.

...