Vue3 は、コンポーネント名、カスタム キャッシュ コンポーネント、カスタム クリア キャッシュ コンポーネントを取得します

目次

1. コンポーネント名を取得するツール関数を定義する

2.使用する

3.完全なケース


 コンポーネント名を取得したい場合は、カスタム キャッシュ コンポーネントとカスタム クリア キャッシュ コンポーネントを実行するか、コンポーネントを動的に切り替える必要があります。

しかし、ほとんどの場合、それらはコンポーネントをキャッシュしています

1. コンポーネント名を取得するツール関数を定義する

import router from "@/routes"
export default function getComponentName() {
    let currentMatched = router.currentRoute.value.matched
    let currentComponent = currentMatched[currentMatched.length - 1].components!.default
    let componentName = currentComponent.name || (currentComponent as { __name: string }).__name
    // 如果组件内的 script 没有内容,并且没有自定义组件name,就会返回 undefined
    console.log('componentName',componentName);
    
    return componentName
}

2.ユースケース

ここに index1/2/3 ファイルを用意しましたが、

スクリプト タグにコンテンツが含まれている必要があります。静的ページに相当するコンテンツはありません。未定義が返され、キャッシュする必要はありません。

以下はindex1です。混乱を避けるために、index2/3に入れて手動で変更できます

<template>
    index1
    <button @click="num++">页面1的num++</button>
    <div >{
   
   { num }}</div>
</template>
<script setup lang="ts">
import { ref } from 'vue';
let num = ref(0);
</script>

app.vue

冗長なコードを書かないようにするために、エッジの問題には対処しませんでしたが、コアのキャッシュ コンポーネントは既に完了しています。

<script setup lang="ts">
import router from "./routes";
import getComponentName from "./utils/getComponentName";
import { ref } from "vue";
// 不要缓存的页面
let includeName = ref<string[]>([]);
// 需要缓存的页面
let excludeName = ref<string[]>([]);
// tabs栏
let tabs = ref<{ path: string; name: string; componentName: string }[]>([]);

const goto = async (path: string, name: string) => {
	// 跳转,路由是Promise,是异步的
	await router.push(path);
	// 获取组件名
	let comName = getComponentName();
	// 现在你有 路由路径 和 这个路由路径的组件名
	let tab = {
		path,
		name,
		componentName: comName,
	};

	// 判断是否有这个tab页面,是否都通过测试,如果是空数组则返回true
	let flag = tabs.value.every((item: any) => {
		return item.path !== path;
	});
	// 如果没有就添加新的tab标签
	if (flag) tabs.value.push(tab);

	// 是否有组件名(看1的注释) &&
	// ! 需要缓存的里面是否有这个组件名 &&
	// ! 不要缓存的是否有这个组件名
	if (comName && !includeName.value.includes(comName) && !excludeName.value.includes(comName)) {
		includeName.value.push(comName);
	}
};

//关闭对应的tab标签
const tabRemove = (item: any) => {
	// 获取该路由对应的组件名
	let index = tabs.value.findIndex((v: any) => v.path === item.path);
	// 清除缓存组件名
	let componentName = tabs.value[index].componentName;
	if (componentName) {
		includeName.value.splice(includeName.value.indexOf(componentName), 1);
	}
	// 也把tabs里面的清除
	tabs.value.splice(index, 1);
};
</script>
<template>
	<div>
		菜单栏
		<ul>
			<li @click="goto('/index1', '页面1')">
				<span>去页面1</span>
			</li>
			<li @click="goto('/index2', '页面2')">
				<span>去页面2</span>
			</li>
			<li @click="goto('/index3', '页面3')">
				<span>去页面3</span>
			</li>
		</ul>
	</div>
	<div>
		tab栏
		<ul>
			<li v-for="item in tabs">
				<span @click="router.push(item.path)">{
   
   { item.name }}</span>
				<span @click="tabRemove(item)">X</span>
			</li>
		</ul>
	</div>
	<div>
		页面:
		<router-view v-slot="{ Component }">
			<keep-alive :include="includeName">
				<component :is="Component" />
			</keep-alive>
		</router-view>
	</div>
</template>

<style lang="css" scoped>
li {
	cursor: pointer;
}
</style>

おすすめ

転載: blog.csdn.net/weixin_59916662/article/details/129611803