《Vue Router实战教程》21.扩展 RouterLink

欢迎观看《Vue Router 实战(第4版)》视频课程

    1. 扩展 RouterLink

RouterLink 组件提供了足够的 props 来满足大多数基本应用程序的需求,但它并未尝试涵盖所有可能的用例,在某些高级情况下,你可能会发现自己使用了 v-slot。在大多数中型到大型应用程序中,值得创建一个(如果不是多个)自定义 RouterLink 组件,以在整个应用程序中重用它们。例如导航菜单中的链接,处理外部链接,添加 inactive-class 等。

让我们扩展 RouterLink 来处理外部链接,并在 AppLink.vue 文件中添加一个自定义的 inactive-class:

Composition API

<script setup>

import { computed } from 'vue'

import { RouterLink } from 'vue-router'

defineOptions({

inheritAttrs: false,

})

const props = defineProps({

// 如果使用 TypeScript,请添加 @ts-ignore

...RouterLink.props,

inactiveClass: String,

})

const isExternalLink = computed(() => {

return typeof props.to === 'string' && props.to.startsWith('http')

})

</script>

<template>

<a v-if="isExternalLink" v-bind="$attrs" :href="to" target="_blank">

<slot />

</a>

<router-link

v-else

v-bind="$props"

custom

v-slot="{ isActive, href, navigate }"

>

<a

v-bind="$attrs"

:href="href"

@click="navigate"

:class="isActive ? activeClass : inactiveClass"

>

<slot />

</a>

</router-link>

</template>

如果你喜欢使用渲染函数或创建 computed 属性,你可以使用 Composition API 中的 useLink :

import { RouterLink, useLink } from 'vue-router'

export default {

name: 'AppLink',

props: {

// 如果使用 TypeScript,请添加 @ts-ignore

...RouterLink.props,

inactiveClass: String,

},

setup(props) {

// `props` 包含 `to` 和任何其他可以传递给 <router-link> 的 prop

const { navigate, href, route, isActive, isExactActive } = useLink(props)

// profit!

return { isExternalLink }

},

}

在实践中,你可能希望将你的 AppLink 组件用于应用程序的不同部分。例如,使用 Tailwind CSS,你可以用所有的类创建一个 NavLink.vue 组件:

<template>

<AppLink

v-bind="$attrs"

class="inline-flex items-center px-1 pt-1 border-b-2 border-transparent text-sm font-medium leading-5 text-gray-500 hover:text-gray-700 hover:border-gray-300 focus:outline-none focus:text-gray-700 focus:border-gray-300 transition duration-150 ease-in-out"

active-class="border-indigo-500 text-gray-900 focus:border-indigo-700"

inactive-class="text-gray-500 hover:text-gray-700 hover:border-gray-300 focus:text-gray-700 focus:border-gray-300"

>

<slot />

</AppLink>

</template>

Options API

<script>

import { RouterLink } from 'vue-router'

export default {

name: 'AppLink',

inheritAttrs: false,

props: {

// 如果使用 TypeScript,请添加 @ts-ignore

...RouterLink.props,

inactiveClass: String,

},

computed: {

isExternalLink() {

return typeof this.to === 'string' && this.to.startsWith('http')

},

},

}

</script>

<template>

<a v-if="isExternalLink" v-bind="$attrs" :href="to" target="_blank">

<slot />

</a>

<router-link

v-else

v-bind="$props"

custom

v-slot="{ isActive, href, navigate }"

>

<a

v-bind="$attrs"

:href="href"

@click="navigate"

:class="isActive ? activeClass : inactiveClass"

>

<slot />

</a>

</router-link>

</template>

如果你喜欢使用渲染函数或创建 computed 属性,你可以使用 Composition API 中的 useLink :

import { RouterLink, useLink } from 'vue-router'

export default {

name: 'AppLink',

props: {

// 如果使用 TypeScript,请添加 @ts-ignore

...RouterLink.props,

inactiveClass: String,

},

setup(props) {

// `props` 包含 `to` 和任何其他可以传递给 <router-link> 的 prop

const { navigate, href, route, isActive, isExactActive } = useLink(props)

// profit!

return { isExternalLink }

},

}

在实践中,你可能希望将你的 AppLink 组件用于应用程序的不同部分。例如,使用 Tailwind CSS,你可以用所有的类创建一个 NavLink.vue 组件:

<template>

<AppLink

v-bind="$attrs"

class="inline-flex items-center px-1 pt-1 border-b-2 border-transparent text-sm font-medium leading-5 text-gray-500 hover:text-gray-700 hover:border-gray-300 focus:outline-none focus:text-gray-700 focus:border-gray-300 transition duration-150 ease-in-out"

active-class="border-indigo-500 text-gray-900 focus:border-indigo-700"

inactive-class="text-gray-500 hover:text-gray-700 hover:border-gray-300 focus:text-gray-700 focus:border-gray-300"

>

<slot />

</AppLink>

</template>

相关推荐
小小小小宇3 分钟前
前端XSS和CSRF以及CSP
前端
UFIT7 分钟前
NoSQL之redis哨兵
java·前端·算法
超级土豆粉14 分钟前
CSS3 的特性
前端·css·css3
星辰引路-Lefan15 分钟前
深入理解React Hooks的原理与实践
前端·javascript·react.js
wyn2000112826 分钟前
JavaWeb的一些基础技术
前端
江城开朗的豌豆35 分钟前
JavaScript篇:函数间的悄悄话:callee和caller的那些事儿
javascript·面试
Hygge-star40 分钟前
Flask音频处理:构建高效的Web音频应用指南
前端·flask·音视频·pygame·csdn开发云
江城开朗的豌豆1 小时前
JavaScript篇:回调地狱退散!6年老前端教你写出优雅异步代码
前端·javascript·面试
飞鸟malred1 小时前
vite+tailwind封装组件库
前端·react.js·npm
TE-茶叶蛋1 小时前
Vue Fragment vs React Fragment
javascript·vue.js·react.js