2024-11-17 11:45:08 +08:00
|
|
|
<script lang="ts" setup>
|
2025-01-13 21:51:37 +08:00
|
|
|
import { computed, onMounted, onUnmounted, ref } from 'vue'
|
2024-11-17 11:45:08 +08:00
|
|
|
|
|
|
|
type Widget = {
|
|
|
|
icon: string[]
|
|
|
|
url: string
|
|
|
|
title: string
|
|
|
|
}
|
|
|
|
|
2024-12-01 13:09:44 +08:00
|
|
|
const props = defineProps({
|
2025-01-13 21:51:37 +08:00
|
|
|
navColor: {
|
|
|
|
default: false,
|
|
|
|
type: Boolean,
|
|
|
|
},
|
|
|
|
}),
|
|
|
|
// 使用 ref 跟踪是否滚动
|
|
|
|
scrolled = ref(false),
|
|
|
|
littleWidget: Widget[] = [
|
|
|
|
{
|
|
|
|
icon: ['fas', 'gauge'],
|
|
|
|
url: '/netdata/',
|
|
|
|
title: 'Pi Dashboard',
|
|
|
|
},
|
|
|
|
{
|
|
|
|
icon: ['fas', 'cloud'],
|
|
|
|
url: '/nas/',
|
|
|
|
title: 'Nextcloud',
|
|
|
|
},
|
|
|
|
{
|
|
|
|
icon: ['fas', 'code-branch'],
|
|
|
|
url: '/git/',
|
|
|
|
title: 'Git Repository',
|
|
|
|
},
|
|
|
|
],
|
|
|
|
// Const logoUrl = getAssetURL("w.png")
|
|
|
|
logoType: string = 'logo',
|
|
|
|
showLogo = computed(() => logoType === 'text'),
|
|
|
|
isExpended = ref<boolean>(false),
|
|
|
|
route = useRoute(),
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
entry = [
|
|
|
|
{
|
|
|
|
title: '主页',
|
|
|
|
icon: ['fas', 'home'],
|
|
|
|
entry: [],
|
|
|
|
to: 'index',
|
|
|
|
},
|
|
|
|
{
|
|
|
|
title: '文章',
|
|
|
|
icon: ['fas', 'pen'],
|
|
|
|
entry: [
|
|
|
|
{
|
|
|
|
title: '博客',
|
|
|
|
url: false,
|
|
|
|
to: 'article',
|
|
|
|
},
|
|
|
|
{
|
|
|
|
title: '日记',
|
|
|
|
url: false,
|
|
|
|
to: 'diary',
|
|
|
|
},
|
|
|
|
],
|
|
|
|
},
|
|
|
|
{
|
|
|
|
title: '作品',
|
|
|
|
icon: ['fas', 'brush'],
|
|
|
|
entry: [
|
|
|
|
{
|
|
|
|
title: '软件',
|
|
|
|
url: false,
|
|
|
|
to: 'soft',
|
|
|
|
},
|
|
|
|
{
|
|
|
|
title: '仓库',
|
|
|
|
url: true,
|
|
|
|
to: 'https://cantyonion.site/git/',
|
|
|
|
},
|
|
|
|
],
|
|
|
|
},
|
|
|
|
{
|
|
|
|
title: '杂谈',
|
|
|
|
icon: ['fas', 'chess-rook'],
|
|
|
|
entry: [],
|
|
|
|
to: 'talk',
|
|
|
|
},
|
|
|
|
],
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
menuExpanded = () => {
|
|
|
|
isExpended.value = !isExpended.value
|
|
|
|
},
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
menuClose = () => {
|
|
|
|
isExpended.value = false
|
|
|
|
},
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
// 监听 scroll 事件
|
|
|
|
handleScroll = () => {
|
|
|
|
scrolled.value = window.scrollY > 0
|
|
|
|
},
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
debouncedScroll = debounce(handleScroll, 10),
|
2024-11-17 11:45:08 +08:00
|
|
|
|
2025-01-13 21:51:37 +08:00
|
|
|
alwaysBlueBackground = computed(() => route.name !== 'index' || props.navColor)
|
2024-11-17 11:45:08 +08:00
|
|
|
|
|
|
|
// 在组件挂载和卸载时添加和移除事件监听
|
|
|
|
onMounted(() => {
|
|
|
|
window.addEventListener('scroll', debouncedScroll)
|
|
|
|
})
|
|
|
|
|
|
|
|
onUnmounted(() => {
|
|
|
|
window.removeEventListener('scroll', debouncedScroll)
|
|
|
|
})
|
|
|
|
</script>
|
|
|
|
|
|
|
|
<template>
|
2025-01-13 21:51:37 +08:00
|
|
|
<nav
|
|
|
|
:class="{ 'bg-transparent': !scrolled && !alwaysBlueBackground,
|
|
|
|
'bg-blue-400': scrolled || alwaysBlueBackground,
|
|
|
|
'shadow': scrolled }"
|
|
|
|
class="fixed top-0 z-20 h-16 w-full text-white transition-all duration-300"
|
2024-11-17 11:45:08 +08:00
|
|
|
>
|
|
|
|
<div class="container mx-auto flex h-16 w-full items-center justify-between px-4 md:px-0 xl:max-w-screen-xl">
|
|
|
|
<!-- 下拉菜单按钮 -->
|
2025-01-13 21:51:37 +08:00
|
|
|
<div
|
|
|
|
class="flex h-8 w-10 items-center justify-center rounded-md border-gray-600 md:hidden"
|
|
|
|
@click="menuExpanded"
|
2024-11-17 11:45:08 +08:00
|
|
|
>
|
2025-01-13 21:51:37 +08:00
|
|
|
<font-awesome-icon
|
|
|
|
:icon="['fas', 'bars']"
|
|
|
|
class="h-6"
|
|
|
|
/>
|
2024-11-17 11:45:08 +08:00
|
|
|
</div>
|
|
|
|
<!-- Logo -->
|
|
|
|
<div class="absolute left-1/2 -translate-x-1/2 md:relative md:left-0 md:translate-x-0">
|
|
|
|
<!-- 文字模式 -->
|
2025-01-13 21:51:37 +08:00
|
|
|
<div
|
|
|
|
v-if="showLogo"
|
|
|
|
class="h-full text-4xl min-w-16 logo py-3.5"
|
|
|
|
>
|
2024-11-17 11:45:08 +08:00
|
|
|
<span>CantyOni_on's Index</span>
|
|
|
|
</div>
|
|
|
|
<!-- 图片模式 -->
|
2025-01-13 21:51:37 +08:00
|
|
|
<div
|
|
|
|
v-else
|
|
|
|
class="py-2"
|
|
|
|
>
|
|
|
|
<img
|
|
|
|
src="~/assets/images/logo/w.png"
|
|
|
|
alt=""
|
|
|
|
class="h-12 w-12"
|
|
|
|
>
|
2024-11-17 11:45:08 +08:00
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
|
|
|
|
<!-- Entry -->
|
2025-01-13 21:51:37 +08:00
|
|
|
<div
|
|
|
|
:class="{ 'h-screen opacity-100 visible': isExpended, 'h-0 opacity-0 invisible': !isExpended }"
|
|
|
|
class="absolute top-full right-0 left-0 bg-white transition-all md:visible md:relative md:top-0 md:flex
|
|
|
|
md:h-auto md:bg-transparent md:opacity-100"
|
2024-11-17 11:45:08 +08:00
|
|
|
>
|
2025-01-13 21:51:37 +08:00
|
|
|
<nav-bar-entry-item
|
|
|
|
v-for="item in entry"
|
|
|
|
:key="item.title"
|
|
|
|
:entry="item.entry"
|
|
|
|
:icon="item.icon"
|
|
|
|
:title="item.title"
|
|
|
|
:to="item.to"
|
|
|
|
@on-go="menuClose"
|
2024-11-17 11:45:08 +08:00
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
|
|
|
|
<!-- 快速跳转小组件 -->
|
|
|
|
<div class="flex items-center justify-between gap-4 text-xl">
|
2025-01-13 21:51:37 +08:00
|
|
|
<a
|
|
|
|
v-for="item in littleWidget"
|
|
|
|
:key="item.url"
|
|
|
|
:href="item.url"
|
|
|
|
:title="item.title"
|
|
|
|
class="transition-all hover:scale-125"
|
|
|
|
>
|
|
|
|
<font-awesome-icon :icon="item.icon" />
|
2024-11-17 11:45:08 +08:00
|
|
|
</a>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</nav>
|
2024-11-17 13:05:55 +08:00
|
|
|
|
|
|
|
<!-- 用于隔开元素 -->
|
2025-01-13 21:51:37 +08:00
|
|
|
<div
|
|
|
|
v-if="alwaysBlueBackground"
|
|
|
|
class="h-16 w-full"
|
|
|
|
/>
|
2024-11-17 11:45:08 +08:00
|
|
|
</template>
|
|
|
|
|
|
|
|
<style scoped>
|
|
|
|
.logo {
|
|
|
|
font-family: BaconyScript, serif;
|
|
|
|
}
|
2025-01-13 21:51:37 +08:00
|
|
|
</style>
|