mirror of
https://github.com/RhenCloud/Cloud-Home.git
synced 2026-01-22 09:29:06 +08:00
feat: 添加背景图片支持和组件切换功能
This commit is contained in:
BIN
public/background.png
Normal file
BIN
public/background.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 2.2 MiB |
195
src/App.vue
195
src/App.vue
@@ -1,20 +1,79 @@
|
||||
<template>
|
||||
<div class="app-shell">
|
||||
<main class="app-body">
|
||||
<router-view />
|
||||
</main>
|
||||
<PageSwitcher />
|
||||
<FooterSection :contact="contact" />
|
||||
<div class="app-shell" :style="backgroundStyle">
|
||||
<div class="background-overlay" :style="overlayStyle"></div>
|
||||
<button
|
||||
class="background-toggle"
|
||||
@click="hideComponents = !hideComponents"
|
||||
:title="hideComponents ? '显示内容' : '隐藏内容'"
|
||||
:class="{ active: hideComponents }"
|
||||
>
|
||||
<span class="toggle-icon">{{ hideComponents ? "👁️" : "🙈" }}</span>
|
||||
<span class="toggle-label">{{ hideComponents ? "显示" : "隐藏" }}</span>
|
||||
</button>
|
||||
<Transition name="fade-down">
|
||||
<main class="app-body" v-if="!hideComponents" key="content">
|
||||
<router-view />
|
||||
</main>
|
||||
</Transition>
|
||||
<Transition name="fade-up">
|
||||
<PageSwitcher v-if="!hideComponents" key="switcher" />
|
||||
</Transition>
|
||||
<Transition name="fade-down">
|
||||
<FooterSection v-if="!hideComponents" :contact="contact" key="footer" />
|
||||
</Transition>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { onMounted } from "vue";
|
||||
import { onMounted, computed, ref } from "vue";
|
||||
import PageSwitcher from "./components/PageSwitcher.vue";
|
||||
import FooterSection from "./components/FooterSection.vue";
|
||||
import siteConfig from "./config/siteConfig";
|
||||
|
||||
const contact = siteConfig.footer;
|
||||
const bg = siteConfig.appearance.background;
|
||||
const isMobile = ref(false);
|
||||
const hideComponents = ref(false);
|
||||
|
||||
// 检测是否为移动设备
|
||||
const checkIfMobile = () => {
|
||||
isMobile.value = window.innerWidth <= 768;
|
||||
};
|
||||
|
||||
onMounted(() => {
|
||||
checkIfMobile();
|
||||
window.addEventListener("resize", checkIfMobile);
|
||||
});
|
||||
|
||||
const getBackgroundImage = () => {
|
||||
if (!bg.enable) return undefined;
|
||||
|
||||
// 根据屏幕尺寸选择图片
|
||||
const image = isMobile.value && bg.mobileImage ? bg.mobileImage : bg.image;
|
||||
|
||||
if (!image) return undefined;
|
||||
|
||||
return image.startsWith("http") ? image : `/public/${image}`;
|
||||
};
|
||||
|
||||
const backgroundStyle = computed(() => {
|
||||
const imageUrl = getBackgroundImage();
|
||||
|
||||
if (!imageUrl) return {};
|
||||
|
||||
return {
|
||||
backgroundImage: `url('${imageUrl}')`,
|
||||
backgroundSize: "cover",
|
||||
backgroundPosition: "center",
|
||||
backgroundAttachment: "fixed",
|
||||
filter: `blur(${bg.blur}px)`,
|
||||
};
|
||||
});
|
||||
|
||||
const overlayStyle = computed(() => {
|
||||
if (!bg.enable || !getBackgroundImage()) return {};
|
||||
return { backgroundColor: bg.overlay };
|
||||
});
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
@@ -22,10 +81,132 @@ const contact = siteConfig.footer;
|
||||
min-height: 100vh;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.background-overlay {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
pointer-events: none;
|
||||
z-index: 0;
|
||||
}
|
||||
|
||||
.background-toggle {
|
||||
position: fixed;
|
||||
bottom: 24px;
|
||||
right: 24px;
|
||||
width: auto;
|
||||
padding: 8px 12px;
|
||||
border-radius: 50px;
|
||||
background: linear-gradient(135deg, rgba(124, 193, 255, 0.15), rgba(124, 193, 255, 0.05));
|
||||
border: 1.5px solid rgba(124, 193, 255, 0.3);
|
||||
color: #7cc1ff;
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
cursor: pointer;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 6px;
|
||||
backdrop-filter: blur(12px);
|
||||
transition: all 0.4s cubic-bezier(0.23, 1, 0.32, 1);
|
||||
box-shadow: 0 8px 32px rgba(124, 193, 255, 0.15), inset 0 1px 0 rgba(255, 255, 255, 0.2);
|
||||
font-family: inherit;
|
||||
}
|
||||
|
||||
.background-toggle:hover {
|
||||
background: linear-gradient(135deg, rgba(124, 193, 255, 0.25), rgba(124, 193, 255, 0.1));
|
||||
border-color: rgba(124, 193, 255, 0.5);
|
||||
transform: translateY(-2px);
|
||||
box-shadow: 0 12px 40px rgba(124, 193, 255, 0.25), inset 0 1px 0 rgba(255, 255, 255, 0.3);
|
||||
}
|
||||
|
||||
.background-toggle:active {
|
||||
transform: translateY(0px);
|
||||
box-shadow: 0 4px 16px rgba(124, 193, 255, 0.15), inset 0 1px 0 rgba(255, 255, 255, 0.2);
|
||||
}
|
||||
|
||||
.background-toggle.active {
|
||||
background: linear-gradient(135deg, rgba(255, 107, 107, 0.2), rgba(255, 107, 107, 0.05));
|
||||
border-color: rgba(255, 107, 107, 0.4);
|
||||
color: #ff6b6b;
|
||||
}
|
||||
|
||||
.background-toggle.active:hover {
|
||||
background: linear-gradient(135deg, rgba(255, 107, 107, 0.3), rgba(255, 107, 107, 0.1));
|
||||
border-color: rgba(255, 107, 107, 0.6);
|
||||
box-shadow: 0 12px 40px rgba(255, 107, 107, 0.2), inset 0 1px 0 rgba(255, 255, 255, 0.2);
|
||||
}
|
||||
|
||||
.toggle-icon {
|
||||
display: inline-block;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.toggle-label {
|
||||
font-size: 12px;
|
||||
letter-spacing: 0.5px;
|
||||
}
|
||||
|
||||
@media (max-width: 640px) {
|
||||
.background-toggle {
|
||||
bottom: 16px;
|
||||
right: 16px;
|
||||
padding: 8px 10px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.toggle-label {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.toggle-icon {
|
||||
font-size: 14px;
|
||||
}
|
||||
}
|
||||
|
||||
.app-body {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* 过渡动画 */
|
||||
/* 上段组件:向上淡出,向下淡入 */
|
||||
.fade-up-enter-active,
|
||||
.fade-up-leave-active {
|
||||
transition: all 0.4s cubic-bezier(0.23, 1, 0.32, 1);
|
||||
}
|
||||
|
||||
.fade-up-enter-from {
|
||||
opacity: 0;
|
||||
transform: translateY(-20px);
|
||||
}
|
||||
|
||||
.fade-up-leave-to {
|
||||
opacity: 0;
|
||||
transform: translateY(20px);
|
||||
}
|
||||
|
||||
/* 下段组件:向下淡出,向上淡入 */
|
||||
.fade-down-enter-active,
|
||||
.fade-down-leave-active {
|
||||
transition: all 0.4s cubic-bezier(0.23, 1, 0.32, 1);
|
||||
}
|
||||
|
||||
.fade-down-enter-from {
|
||||
opacity: 0;
|
||||
transform: translateY(20px);
|
||||
}
|
||||
|
||||
.fade-down-leave-to {
|
||||
opacity: 0;
|
||||
transform: translateY(-20px);
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -35,6 +35,18 @@ const siteConfig = {
|
||||
startDate: "2025-12-06",
|
||||
},
|
||||
|
||||
appearance: {
|
||||
background: {
|
||||
enable: true,
|
||||
// URL 支持:可使用外部 URL 或本地路径
|
||||
// 例如: "https://example.com/bg.jpg" 或 "background.webp"
|
||||
image: "background.png", // 背景图片 URL 或本地路径(桌面端)
|
||||
mobileImage: "https://www.loliapi.com/acg/pe/", // 移动端背景图片(可选,不设置则使用 image)
|
||||
blur: 0, // 背景模糊程度 (0-100)
|
||||
overlay: "rgba(70, 59, 82, 0.4)", // 背景遮罩颜色与透明度
|
||||
},
|
||||
},
|
||||
|
||||
umami: {
|
||||
enable: true,
|
||||
url: "https://cloud.umami.is/script.js",
|
||||
|
||||
Reference in New Issue
Block a user