Incremental DOM ざっと見たやつ
Introducing Incremental DOM — Google Developers — Medium
Reactやvirtual-dom、Glimmer(Ember)などVirtual DOMの実装は色々あるが、これらのVirtual DOM実装には2つの問題がある
これらを解決するためにIncremental DOMと言うものを作っている(WIP)
Incremental DOMの特徴としては
既存のVirtual DOM実装は大きく分けて2つのフェーズを行っている
この手法だと、変更点があると保持しておくVirtual DOM Treeが大きくなってメモリにはやさしくない
Incremental DOMはVirtual DOMのモデルを1つのフェーズに変更して行う
これを行うために、Incremental DOMでは実際のDOM Nodeに対してメタ情報を埋め込んでいく。 実際のDOM Treeにアクセスするわけだが、これは十分に早い。
Virtual DOM実装は一般的にタグは閉じてるものになってる。
(単純に言えばdocument.createElement()
にあたるAPIしかなく、
Virtual DOMのNodeを作る場合に必ずタグが閉じた状態になる)
一般的なテンプレートエンジンは以下の<section>
のように閉じられてなくても動作する
{template chunk1}
<h1>Hello World</h1>
<section id="body"> /* Content comes after this */
{/template}
これをIncremental DOMでもサポートしたかったので、 OpenとCloseのように組み合わせとなってる。
data.items.forEach(function(item, index) {
elementOpen('x-item', index);
text('item' + index);
elementClose('x-item');
});
つまり、既存のテンプレート言語をそのままIncremental DOM上で再現できるはずという話
詳しい例は
@ google/incremental-dom at c4b02e5aac4da34c85d0b8f7eb3df8f44d0987f3
alignWithDOM https://github.com/google/incremental-dom/blob/c4b02e5aac4da34c85d0b8f7eb3df8f44d0987f3/src/alignment.js#L53-53
メタデータ
__incrementalDOMData
プロパティにメタデータが入ってるおおまかな流れ
elementOpenStart('div', '', []);
if (obj.key) {
attr('data-expanded', obj.key);
}
// ここまででargsを貯める
elementOpenEnd();// ここで実際のNodeへ適応
elementClose('div');
感じでDOM Treeを走査していく流れ
<div>
<p>
</p>
</div>
<span></span>
というDOM Treeだと
openではdiv -> p とたどって、 closeは p -> div -> となりの要素へ(span)
elementOpen('div', null, null,
'style', {
color: 'white',
backgroundColor: 'red'
});
…
elementClose('div');
みたいな要素を組み立てるものを
一時的なバッファとしてargsBuilder
にいれている。
このバッファは、 open->close 次 open->closeとした時に同じ変数を使いまわしてる。 (tag名やattrなどの中身を置き換える)
なので、全部のTreeを走査するときに必要なメモリは 一つのopenの間にある小さなTreeの分だけで良い。
Virtual DOMの場合は、こういう情報を全体のTreeとしてメモリとかに持ってる。