From c0115d2fd0f074b0fe0eba6d697d306c8f672402 Mon Sep 17 00:00:00 2001 From: Micah Geisel Date: Tue, 24 Sep 2024 12:20:30 +0200 Subject: [PATCH] only reload child frames during morph if the old and new frame have matching ids. --- src/core/drive/morphing_page_renderer.js | 14 ++++++-------- src/core/frames/morphing_frame_renderer.js | 13 ++++++------- src/core/renderer.js | 15 ++++++++++----- 3 files changed, 22 insertions(+), 20 deletions(-) diff --git a/src/core/drive/morphing_page_renderer.js b/src/core/drive/morphing_page_renderer.js index 489aceafe..0fff99992 100644 --- a/src/core/drive/morphing_page_renderer.js +++ b/src/core/drive/morphing_page_renderer.js @@ -6,18 +6,16 @@ export class MorphingPageRenderer extends PageRenderer { static renderElement(currentElement, newElement) { morphElements(currentElement, newElement, { callbacks: { - beforeNodeMorphed: element => { - return !super.shouldRefreshChildFrameWithMorphing(null, element) + beforeNodeMorphed: (node, newNode) => { + if (super.shouldRefreshChildFrameWithMorphing(null, node, newNode)) { + node.reload() + return false + } + return true } } }) - for (const frame of currentElement.querySelectorAll("turbo-frame")) { - if (super.shouldRefreshChildFrameWithMorphing(null, frame)) { - frame.reload() - } - } - dispatch("turbo:morph", { detail: { currentElement, newElement } }) } diff --git a/src/core/frames/morphing_frame_renderer.js b/src/core/frames/morphing_frame_renderer.js index b62f68ae6..c6c6d13b2 100644 --- a/src/core/frames/morphing_frame_renderer.js +++ b/src/core/frames/morphing_frame_renderer.js @@ -11,16 +11,15 @@ export class MorphingFrameRenderer extends FrameRenderer { morphChildren(currentElement, newElement, { callbacks: { - beforeNodeMorphed: element => { - return !super.shouldRefreshChildFrameWithMorphing(currentElement, element) + beforeNodeMorphed: (node, newNode) => { + if (super.shouldRefreshChildFrameWithMorphing(currentElement, node, newNode)) { + node.reload() + return false + } + return true } } }) - for (const frame of currentElement.querySelectorAll("turbo-frame")) { - if (super.shouldRefreshChildFrameWithMorphing(currentElement, frame)) { - frame.reload() - } - } } async preservingPermanentElements(callback) { diff --git a/src/core/renderer.js b/src/core/renderer.js index 97b97682a..aea85ac1e 100644 --- a/src/core/renderer.js +++ b/src/core/renderer.js @@ -8,11 +8,16 @@ export class Renderer { // Abstract method } - static shouldRefreshChildFrameWithMorphing(parentFrame, frame) { - return frame instanceof FrameElement && - frame.shouldReloadWithMorph && - !frame.closest("[data-turbo-permanent]") && - frame.parentElement.closest("turbo-frame[src][refresh=morph]") === parentFrame + static shouldRefreshChildFrameWithMorphing(parentFrame, currentFrame, newFrame) { + return currentFrame instanceof FrameElement && + // newFrame cannot yet be an instance of FrameElement because custom + // elements don't get initialized until they're attached to the DOM, so + // test its Element#nodeName instead + newFrame instanceof Element && newFrame.nodeName === "TURBO-FRAME" && + currentFrame.shouldReloadWithMorph && + currentFrame.id === newFrame.id && + !currentFrame.closest("[data-turbo-permanent]") && + currentFrame.parentElement.closest("turbo-frame[src][refresh=morph]") === parentFrame } constructor(currentSnapshot, newSnapshot, isPreview, willRender = true) {