Skip to content

Commit

Permalink
Use counter per boundary for id generation
Browse files Browse the repository at this point in the history
  • Loading branch information
marvinhagemeister committed Oct 25, 2022
1 parent f6f4bee commit 8c04d9a
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 25 deletions.
21 changes: 5 additions & 16 deletions hooks/src/index.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Fragment, options } from 'preact';
import { options } from 'preact';

/** @type {number} */
let currentIndex;
Expand Down Expand Up @@ -374,26 +374,15 @@ export function useId() {
// the root node.
/** @type {import('./internal.d').VNode} */
let root = currentComponent._vnode;
let parent = root._parent;
let i = 0;
while (parent !== null) {
if (parent.type !== Fragment && typeof parent.type === 'function') {
i++;
}

root = parent;
parent = parent._parent;
while (root !== null && root._parent !== null) {
root = root._parent;
}

// Attach the id usage array to the root node and resize it to fit
let ids = root._mask || (root._mask = [0]);
while (ids.length < i) {
ids.push(0);
}
let mask = root._mask || (root._mask = [0, 0]);

// Increase the current component depth pointer
ids[i - 1]++;
state._value = 'P' + ids.join('') + currentIndex;
state._value = 'P' + mask[0] + mask[1]++ + currentIndex;
}

return state._value;
Expand Down
2 changes: 1 addition & 1 deletion hooks/src/internal.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ export interface Component extends PreactComponent<any, any> {
}

export interface VNode extends PreactVNode {
_mask?: number[];
_mask?: [number, number];
}

export type HookState =
Expand Down
19 changes: 11 additions & 8 deletions hooks/test/browser/useId.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -55,12 +55,12 @@ describe('useId', () => {

render(<Comp />, scratch);
expect(scratch.innerHTML).to.equal(
'<div id="P01"><div id="P11"><span id="P22">h</span></div></div>'
'<div id="P001"><div id="P011"><span id="P022">h</span></div></div>'
);

render(<Comp />, scratch);
expect(scratch.innerHTML).to.equal(
'<div id="P01"><div id="P11"><span id="P22">h</span></div></div>'
'<div id="P001"><div id="P011"><span id="P022">h</span></div></div>'
);
});

Expand All @@ -83,12 +83,12 @@ describe('useId', () => {

render(<Comp />, scratch);
expect(scratch.innerHTML).to.equal(
'<div id="P01"><span id="P11">h</span><span id="P21">h</span><span id="P31">h</span></div>'
'<div id="P001"><span id="P011">h</span><span id="P021">h</span><span id="P031">h</span></div>'
);

render(<Comp />, scratch);
expect(scratch.innerHTML).to.equal(
'<div id="P01"><span id="P11">h</span><span id="P21">h</span><span id="P31">h</span></div>'
'<div id="P001"><span id="P011">h</span><span id="P021">h</span><span id="P031">h</span></div>'
);
});

Expand Down Expand Up @@ -121,13 +121,13 @@ describe('useId', () => {

render(<Comp />, scratch);
expect(scratch.innerHTML).to.equal(
'<div id="P01"><div><span id="P011">h</span></div></div>'
'<div id="P001"><div><span id="P011">h</span></div></div>'
);

set(true);
rerender();
expect(scratch.innerHTML).to.equal(
'<div id="P01"><div><span id="P011">h</span><span id="P021">h</span></div></div>'
'<div id="P001"><div><span id="P011">h</span><span id="P021">h</span></div></div>'
);
});

Expand Down Expand Up @@ -332,13 +332,16 @@ describe('useId', () => {
return <Fragment>{children}</Fragment>;
};

const ids = [];
function Foo() {
const id = useId();
ids.push(id);
return <p>{id}</p>;
}

function App() {
const id = useId();
ids.push(id);
return (
<div>
<p>{id}</p>
Expand All @@ -350,7 +353,7 @@ describe('useId', () => {
}

render(<App />, scratch);
expect(scratch.innerHTML).to.equal('<div><p>P01</p><p>P011</p></div>');
expect(ids[0]).not.to.equal(ids[1]);
});

it('should skip over HTML', () => {
Expand All @@ -376,7 +379,7 @@ describe('useId', () => {
}

render(<App />, scratch);
expect(ids).to.deep.equal(['P11', 'P21']);
expect(ids[0]).not.to.equal(ids[1]);
});

it('should reset for each renderToString roots', () => {
Expand Down

0 comments on commit 8c04d9a

Please sign in to comment.