vue3学习记录-Teleport和KeepAlive
vue3学习记录-Teleport和KeepAlive
1.Teleport
Teleport组件在遮罩框很实用。
<template>
<div class="hello">
</div>
</template>
<style scoped lang="scss">
.hello {
height: 200px;
width: 90px;
border: 1px solid #000;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
</style>
<script setup>
import InfiniteScroll from './components/HelloWorld.vue'
import { ref } from 'vue';
let page = 0
const fetchMoreItems = async () => {
// 模拟API调用
await new Promise(resolve => setTimeout(resolve, 1000))
page++
return Array.from({ length: 10 }, (_, i) => ({
id: page * 10 + i,
content: `Item ${page * 10 + i}`
}))
}
</script>
<template>
<div class="content">
<Teleport :disabled="true" to="body">
<InfiniteScroll>
</InfiniteScroll>
</Teleport>
</div>
</template>
<style>
.content {
position: relative;
height: 50vh;
width: 100%;
background-color: aqua;
}
</style>
2.KeepAlive
<script setup>
import { ref } from 'vue';
import A from './components/A.vue';
import B from './components/B.vue';
const activeTab = ref('a'); // 用于控制选中的 tab
</script>
<template>
<el-tabs v-model="activeTab">
<el-tab-pane label="A" name="a">
<component :is="A"></component>
</el-tab-pane>
<el-tab-pane label="Infinite Scroll" name="second">
<component :is="B"></component>
</el-tab-pane>
</el-tabs>
</template>
//A.vue
<template>
<!-- elementui数字加减器 -->
<el-input-number v-model="count" :min="1" :max="10" label="描述文字"></el-input-number>
</template>
<script setup>
import { ref } from 'vue' ;
const count = ref(1) ;
</script>
//B.vue
<template>
<!-- elementui数字加减器 -->
<el-radio-group v-model="radio1">
<el-radio value="1" size="large">Option 1</el-radio>
<el-radio value="2" size="large">Option 2</el-radio>
</el-radio-group>
</template>
<script setup>
import { ref } from 'vue' ;
const radio1 = ref('1') ;
</script>
本来以为这样的组件不是keepalive的,结果它竟然是keepalive的,但是我没有在代码里加入keepalive呢!!!应该是el-tabs处理过了的。用官方的例子吧那就
<script setup>
import { ref, shallowRef } from "vue";
import A from "./components/A.vue";
import B from "./components/B.vue";
const activeTab = ref("a");
const current = shallowRef(A);
</script>
<template>
<div class="demo">
<label><input type="radio" v-model="current" :value="A" /> A</label>
<label><input type="radio" v-model="current" :value="B" /> B</label>
<component :is="current"></component>
</div>
</template>
这下就不是keppalive了。keepalive在vue2里也有,缓存组件状态的。
2.1 包含/排除
默认会缓存内部的所有组件实例,但我们可以通过 include 和 exclude prop 来定制该行为。这两个 prop 的值都可以是一个以英文逗号分隔的字符串、一个正则表达式,或是包含这两种类型的一个数组:
<!-- 以英文逗号分隔的字符串 -->
<KeepAlive include="a,b">
<component :is="view" />
</KeepAlive>
<!-- 正则表达式 (需使用 `v-bind`) -->
<KeepAlive :include="/a|b/">
<component :is="view" />
</KeepAlive>
<!-- 数组 (需使用 `v-bind`) -->
<KeepAlive :include="['a', 'b']">
<component :is="view" />
</KeepAlive>
2.2 最大缓存实例数
我们可以通过传入 max prop 来限制可被缓存的最大组件实例数。 的行为在指定了 max 后类似一个 LRU 缓存:如果缓存的实例数量即将超过指定的那个最大数量,则最久没有被访问的缓存实例将被销毁,以便为新的实例腾出空间。
<KeepAlive :max="10">
<component :is="activeComponent" />
</KeepAlive>
2.3 缓存实例的生命周期
vue3文档看到的。
当一个组件实例从 DOM 上移除但因为被 缓存而仍作为组件树的一部分时,它将变为不活跃状态而不是被卸载。当一个组件实例作为缓存树的一部分插入到 DOM 中时,它将重新被激活。
一个持续存在的组件可以通过 onActivated() 和 onDeactivated() 注册相应的两个状态的生命周期钩子:
<script setup>
import { shallowRef } from "vue";
import A from "./components/A.vue";
import B from "./components/B.vue";
const current = shallowRef(A);
</script>
<template>
<div class="demo">
<label><input type="radio" v-model="current" :value="A" /> A</label>
<label><input type="radio" v-model="current" :value="B" /> B</label>
<keep-alive>
<component :is="current"></component>
</keep-alive>
</div>
</template>
<!-- ComponentA.vue -->
<script setup>
import { ref, onMounted, onActivated, onDeactivated } from 'vue';
const count = ref(0);
onMounted(() => {
console.log('ComponentA mounted');
});
onActivated(() => {
console.log('ComponentA activated');
});
onDeactivated(() => {
console.log('ComponentA deactivated');
});
const increment = () => {
count.value++;
};
</script>
<template>
<div>
<h2>组件 A</h2>
<p>计数: {{ count }}</p>
<button @click="increment">增加</button>
</div>
</template>
<!-- ComponentB.vue -->
<script setup>
import { ref, onMounted, onActivated, onDeactivated } from 'vue';
const count = ref(0);
onMounted(() => {
console.log('ComponentB mounted');
});
onActivated(() => {
console.log('ComponentB activated');
});
onDeactivated(() => {
console.log('ComponentB deactivated');
});
const increment = () => {
count.value++;
};
</script>
<template>
<div>
<h2>组件 B</h2>
<p>计数: {{ count }}</p>
<button @click="increment">增加</button>
</div>
</template>
1.当应用首次加载时,ComponentA 会被挂载,控制台会输出 “ComponentA mounted” 和 “ComponentA activated”。
2.当切换到 ComponentB 时:
ComponentA 会被停用,控制台输出 “ComponentA deactivated”。
ComponentB 会被挂载和激活,控制台输出 “ComponentB mounted” 和 “ComponentB activated”。
3.当再次切换回 ComponentA 时:
ComponentB 会被停用,控制台输出 “ComponentB deactivated”。
ComponentA 会被重新激活,控制台只输出 “ComponentA activated”(不会再次挂载)。
4.由于使用了 ,两个组件的状态(例如 count 值)会被保留,即使它们不在 DOM 中。
5.onActivated() 钩子在组件每次被插入到 DOM 时调用,无论是首次挂载还是从缓存中重新激活。
6.onDeactivated() 钩子在组件每次从 DOM 中移除时调用,但组件实例仍然保留在内存中。
原文地址:https://blog.csdn.net/qq_45030898/article/details/142883302
免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!