- From: Andrea Giammarchi <notifications@github.com>
- Date: Tue, 07 Feb 2023 02:33:49 -0800
- To: whatwg/dom <dom@noreply.github.com>
- Cc: Subscribed <subscribed@noreply.github.com>
- Message-ID: <whatwg/dom/issues/586/1420550548@github.com>
@chrishtr it's worth mentioning that abusing the API already allows diffing (at least per elements, not per mixed elements and text nodes (or comments) ... example:
```js
const diff = (parent, prev, curr) => {
const {length: plength} = prev;
const {length: clength} = curr;
const childs = [];
let i = 0, length = i;
// order old nodes after
while (i < plength)
prev[i++].dataset.order = (clength + i);
i = 0;
// order new nodes before
while (i < clength) {
const child = curr[i++];
child.dataset.order = i;
if (child.parentNode !== parent)
length = childs.push(child);
}
if (childs.length)
parent.append(...childs);
// reorder all by attribute
parent.reorderChildren('data-order');
// drop nodes still there
length += plength;
if (i < length) {
const {children} = parent;
const range = new Range;
range.setStartBefore(children[i]);
range.setEndAfter(children[length - 1]);
range.deleteContents();
}
return curr;
};
```
Assuming for now the polyfill would be like:
```js
Element.prototype.reorderChildren = function (attributeName) {
this.replaceChildren(
...[...this.children].sort(
(a, b) => (
parseInt(a.getAttribute(attributeName)) -
parseInt(b.getAttribute(attributeName))
)
)
);
};
```
Given the following operations would move, insert once, and drop all at once on every needed situation:
```js
document.body.innerHTML = `<ul><li>a</li><li>b</li><li>c</li></ul>`;
const ul = document.body.firstElementChild;
let children = [...ul.children];
// nothing happens
children = diff(ul, children, children);
// a swaps with c
children = diff(ul, children, [children[2], children[1], children[0]]);
let li = document.createElement('li');
li.textContent = 'd';
// result into c, b, a, d
children = diff(ul, children, children.concat(li));
// b, a remain
children = diff(ul, children, [children[1], children[2]]);
// d, b
children = diff(ul, children, [li, children[0]]);
// z
children = diff(ul, children, [document.createElement('li')]);
children[0].textContent = 'z';
```
After all this already helps diffing nodes in a *keyed* like way so maybe it's OK to have at least this helper and be creative around its full potentials.
--
Reply to this email directly or view it on GitHub:
https://github.com/whatwg/dom/issues/586#issuecomment-1420550548
You are receiving this because you are subscribed to this thread.
Message ID: <whatwg/dom/issues/586/1420550548@github.com>
Received on Tuesday, 7 February 2023 10:34:05 UTC