]> git.ipfire.org Git - thirdparty/vuejs/core.git/commitdiff
wip: hmr updating
authordaiwei <daiwei521@126.com>
Tue, 25 Mar 2025 03:10:50 +0000 (11:10 +0800)
committerdaiwei <daiwei521@126.com>
Tue, 25 Mar 2025 03:10:50 +0000 (11:10 +0800)
packages/runtime-vapor/src/component.ts
packages/runtime-vapor/src/components/Teleport.ts

index 2855fa9ce9658093ae22aa27e7cdb0634bc857b7..4d5c6d0b78232ae4ea54591ceebe2db01b94bd30 100644 (file)
@@ -172,11 +172,12 @@ export function createComponent(
       frag.hydrate()
     }
 
+    // remove the teleport content from the parent tree for HMR updates
     if (__DEV__) {
       const instance = currentInstance as VaporComponentInstance
-      ;(instance!.hmrEffects || (instance!.hmrEffects = [])).push(() =>
-        frag.remove(frag.anchor.parentNode!),
-      )
+      ;(instance!.hmrEffects || (instance!.hmrEffects = [])).push(() => {
+        frag.remove(frag.anchor.parentNode!)
+      })
     }
 
     return frag as any
index ba47442500ed908bca629bfb0c33f7c297c30037..8a036578204adb9a48b21eda4f8f4240310d6ef4 100644 (file)
@@ -19,6 +19,7 @@ import type { LooseRawProps, LooseRawSlots } from '../component'
 import { rawPropsProxyHandlers } from '../componentProps'
 import { renderEffect } from '../renderEffect'
 import { extend } from '@vue/shared'
+import { EffectScope, pauseTracking, resetTracking } from '@vue/reactivity'
 
 export const VaporTeleportImpl = {
   name: 'VaporTeleport',
@@ -30,23 +31,28 @@ export const VaporTeleportImpl = {
       ? new TeleportFragment('teleport')
       : new TeleportFragment()
 
-    let children: Block
-    renderEffect(() => {
-      frag.updateChildren(
-        (children = slots.default && (slots.default as BlockFn)()),
-      )
-    })
-
-    renderEffect(() => {
-      frag.update(
-        // access the props to trigger tracking
-        extend(
-          {},
-          new Proxy(props, rawPropsProxyHandlers) as any as TeleportProps,
-        ),
-        children!,
-      )
+    pauseTracking()
+    const scope = (frag.scope = new EffectScope())
+    scope!.run(() => {
+      let children: Block
+      renderEffect(() => {
+        frag.updateChildren(
+          (children = slots.default && (slots.default as BlockFn)()),
+        )
+      })
+
+      renderEffect(() => {
+        frag.update(
+          // access the props to trigger tracking
+          extend(
+            {},
+            new Proxy(props, rawPropsProxyHandlers) as any as TeleportProps,
+          ),
+          children!,
+        )
+      })
     })
+    resetTracking()
 
     return frag
   },
@@ -54,6 +60,7 @@ export const VaporTeleportImpl = {
 
 class TeleportFragment extends VaporFragment {
   anchor: Node
+  scope: EffectScope | undefined
 
   private targetStart?: Node
   private mainAnchor?: Node
@@ -155,17 +162,31 @@ class TeleportFragment extends VaporFragment {
   }
 
   remove = (parent: ParentNode | undefined): void => {
+    // stop effect scope
+    if (this.scope) {
+      this.scope.stop()
+      this.scope = undefined
+    }
+
     // remove nodes
-    remove(this.nodes, this.currentParent)
+    if (this.nodes) {
+      remove(this.nodes, this.currentParent)
+      this.nodes = []
+    }
 
     // remove anchors
     if (this.targetStart) {
       remove(this.targetStart!, this.target!)
+      this.targetStart = undefined
       remove(this.targetAnchor!, this.target!)
+      this.targetAnchor = undefined
     }
+
     if (this.placeholder) {
       remove(this.placeholder!, parent)
+      this.placeholder = undefined
       remove(this.mainAnchor!, parent)
+      this.mainAnchor = undefined
     }
   }