Refactor BrowserRenderer.ts to avoid tracking unnecessary child index stack

This commit is contained in:
Steve Sanderson 2018-01-29 12:05:18 +00:00
parent 7e76490844
commit 97d575f599
1 changed files with 12 additions and 10 deletions

View File

@ -28,7 +28,8 @@ export class BrowserRenderer {
} }
applyEdits(componentId: number, parent: Element, childIndex: number, edits: System_Array, editsLength: number, referenceTree: System_Array) { applyEdits(componentId: number, parent: Element, childIndex: number, edits: System_Array, editsLength: number, referenceTree: System_Array) {
const childIndexStack: number[] = []; // TODO: This can be removed. We only (potentially) have nonzero childIndex values at the root, so we only need to track the current depth to determine whether we are at the root let currentDepth = 0;
let childIndexAtCurrentDepth = childIndex;
for (let editIndex = 0; editIndex < editsLength; editIndex++) { for (let editIndex = 0; editIndex < editsLength; editIndex++) {
const edit = getRenderTreeEditPtr(edits, editIndex); const edit = getRenderTreeEditPtr(edits, editIndex);
const editType = renderTreeEdit.type(edit); const editType = renderTreeEdit.type(edit);
@ -37,45 +38,46 @@ export class BrowserRenderer {
const nodeIndex = renderTreeEdit.newTreeIndex(edit); const nodeIndex = renderTreeEdit.newTreeIndex(edit);
const node = getTreeNodePtr(referenceTree, nodeIndex); const node = getTreeNodePtr(referenceTree, nodeIndex);
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
this.insertNode(componentId, parent, childIndex + siblingIndex, referenceTree, node, nodeIndex); this.insertNode(componentId, parent, childIndexAtCurrentDepth + siblingIndex, referenceTree, node, nodeIndex);
break; break;
} }
case EditType.removeNode: { case EditType.removeNode: {
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
removeNodeFromDOM(parent, childIndex + siblingIndex); removeNodeFromDOM(parent, childIndexAtCurrentDepth + siblingIndex);
break; break;
} }
case EditType.setAttribute: { case EditType.setAttribute: {
const nodeIndex = renderTreeEdit.newTreeIndex(edit); const nodeIndex = renderTreeEdit.newTreeIndex(edit);
const node = getTreeNodePtr(referenceTree, nodeIndex); const node = getTreeNodePtr(referenceTree, nodeIndex);
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
const element = parent.childNodes[childIndex + siblingIndex] as HTMLElement; const element = parent.childNodes[childIndexAtCurrentDepth + siblingIndex] as HTMLElement;
this.applyAttribute(componentId, element, node, nodeIndex); this.applyAttribute(componentId, element, node, nodeIndex);
break; break;
} }
case EditType.removeAttribute: { case EditType.removeAttribute: {
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
removeAttributeFromDOM(parent, childIndex + siblingIndex, renderTreeEdit.removedAttributeName(edit)!); removeAttributeFromDOM(parent, childIndexAtCurrentDepth + siblingIndex, renderTreeEdit.removedAttributeName(edit)!);
break; break;
} }
case EditType.updateText: { case EditType.updateText: {
const nodeIndex = renderTreeEdit.newTreeIndex(edit); const nodeIndex = renderTreeEdit.newTreeIndex(edit);
const node = getTreeNodePtr(referenceTree, nodeIndex); const node = getTreeNodePtr(referenceTree, nodeIndex);
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
const domTextNode = parent.childNodes[childIndex + siblingIndex] as Text; const domTextNode = parent.childNodes[childIndexAtCurrentDepth + siblingIndex] as Text;
domTextNode.textContent = renderTreeNode.textContent(node); domTextNode.textContent = renderTreeNode.textContent(node);
break; break;
} }
case EditType.stepIn: { case EditType.stepIn: {
childIndexStack.push(childIndex);
const siblingIndex = renderTreeEdit.siblingIndex(edit); const siblingIndex = renderTreeEdit.siblingIndex(edit);
parent = parent.childNodes[childIndex + siblingIndex] as HTMLElement; parent = parent.childNodes[childIndexAtCurrentDepth + siblingIndex] as HTMLElement;
childIndex = 0; currentDepth++;
childIndexAtCurrentDepth = 0;
break; break;
} }
case EditType.stepOut: { case EditType.stepOut: {
parent = parent.parentElement!; parent = parent.parentElement!;
childIndex = childIndexStack.pop()!; currentDepth--;
childIndexAtCurrentDepth = currentDepth === 0 ? childIndex : 0; // The childIndex is only ever nonzero at zero depth
break; break;
} }
default: { default: {