fix(runtime-core): handle dynamicChildren when portal is used as a block

This commit is contained in:
Evan You 2019-10-16 17:43:33 -04:00
parent 4b2b29efa1
commit 1722dc05c5

View File

@ -495,25 +495,14 @@ export function createRenderer<
} }
if (dynamicChildren != null) { if (dynamicChildren != null) {
// children fast path patchBlockChildren(
const oldDynamicChildren = n1.dynamicChildren! n1.dynamicChildren!,
for (let i = 0; i < dynamicChildren.length; i++) { dynamicChildren,
const oldVNode = oldDynamicChildren[i] el,
patch( parentComponent,
oldVNode, parentSuspense,
dynamicChildren[i], isSVG
// in the case of a Fragment, we need to provide the actual parent )
// of the Fragment itself so it can move its children. In other cases,
// the parent container is not actually used so we just pass the
// block element here to avoid a DOM parentNode call.
oldVNode.type === Fragment ? hostParentNode(oldVNode.el!)! : el,
null,
parentComponent,
parentSuspense,
isSVG,
true
)
}
} else if (!optimized) { } else if (!optimized) {
// full diff // full diff
patchChildren(n1, n2, el, null, parentComponent, parentSuspense, isSVG) patchChildren(n1, n2, el, null, parentComponent, parentSuspense, isSVG)
@ -526,6 +515,36 @@ export function createRenderer<
} }
} }
// The fast path for blocks.
function patchBlockChildren(
oldChildren: HostVNode[],
newChildren: HostVNode[],
fallbackContainer: HostElement,
parentComponent: ComponentInternalInstance | null,
parentSuspense: HostSuspenseBoundary | null,
isSVG: boolean
) {
for (let i = 0; i < newChildren.length; i++) {
const oldVNode = oldChildren[i]
patch(
oldVNode,
newChildren[i],
// in the case of a Fragment, we need to provide the actual parent
// of the Fragment itself so it can move its children. In other cases,
// the parent container is not actually used so we just pass the
// block element here to avoid a DOM parentNode call.
oldVNode.type === Fragment
? hostParentNode(oldVNode.el!)!
: fallbackContainer,
null,
parentComponent,
parentSuspense,
isSVG,
true
)
}
}
function patchProps( function patchProps(
el: HostElement, el: HostElement,
vnode: HostVNode, vnode: HostVNode,
@ -654,6 +673,16 @@ export function createRenderer<
const target = (n2.target = n1.target)! const target = (n2.target = n1.target)!
if (patchFlag === PatchFlags.TEXT) { if (patchFlag === PatchFlags.TEXT) {
hostSetElementText(target, children as string) hostSetElementText(target, children as string)
} else if (n2.dynamicChildren) {
// fast path when the portal happens to be a block root
patchBlockChildren(
n1.dynamicChildren!,
n2.dynamicChildren,
container,
parentComponent,
parentSuspense,
isSVG
)
} else if (!optimized) { } else if (!optimized) {
patchChildren( patchChildren(
n1, n1,