refactor slideshow code to its component and added Miku & miku background
All checks were successful
Deploy with Docker Compose / deploy (push) Successful in 1m42s

This commit is contained in:
2026-03-05 13:31:28 +00:00
parent 646f93136d
commit aa3f0a189d
7 changed files with 109 additions and 74 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.7 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 114 KiB

View File

@@ -0,0 +1,68 @@
<script setup>
import { ref, computed, onMounted, onUnmounted } from "vue";
import Header from "@/components/text/Header.vue";
const props = defineProps({
images: {
type: Array,
required: true,
},
interval: {
type: Number,
default: 10000,
},
});
const currentIndex = ref(0);
const currentComment = computed(() => props.images[currentIndex.value].comment);
const currentUrl = computed(() => props.images[currentIndex.value].url);
let nextId;
function nextImage() {
clearTimeout(nextId);
currentIndex.value = (currentIndex.value + 1) % props.images.length;
nextId = setTimeout(nextImage, props.interval);
}
onMounted(() => {
nextId = setTimeout(nextImage, props.interval);
});
onUnmounted(() => {
clearTimeout(nextId);
});
</script>
<template>
<Transition name="fade" mode="out-in">
<div class="image-viewer" @click="nextImage" :key="currentIndex">
<Header v-if="currentComment">
{{ currentComment }}
</Header>
<img :src="currentUrl" alt="Image Viewer" />
</div>
</Transition>
</template>
<style scoped>
.image-viewer {
width: 100%;
overflow: hidden;
}
img {
width: 100%;
height: 100%;
object-fit: cover;
}
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.5s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}
</style>

View File

@@ -1,76 +1,15 @@
<script setup>
import { ref, computed, onMounted, onUnmounted } from "vue";
import { Transition } from "vue";
import Header from "@/components/text/Header.vue";
import Slideshow from "@/components/util/Slideshow.vue";
const images = [
{ url: "/img/memes/pidgeon.gif", comment: "鸟" },
// { url: "/img/memes/no_slip.png" },
//{ url: "/img/memes/epic.jpeg" },
// { url: "/img/memes/epic.jpeg" },
// { url: "/img/bedroom/img2.png", comment: "办公桌" },
// { url: "/img/bedroom/img1.png", comment: "床" },
];
const currentIndex = ref(0);
const currentComment = computed(() => images[currentIndex.value].comment);
const currentUrl = computed(() => images[currentIndex.value].url);
let nextId;
function nextImage() {
clearTimeout(nextId);
currentIndex.value = (currentIndex.value + 1) % images.length;
nextId = setTimeout(nextImage, 10000);
}
function nextRandomImage() {
clearTimeout(nextId);
let newIndex;
do {
newIndex = Math.floor(Math.random() * images.length);
} while (newIndex === currentIndex.value);
currentIndex.value = newIndex;
nextId = setTimeout(nextImage, 10000);
}
onMounted(() => {
nextId = setTimeout(nextImage, 10000);
});
onUnmounted(() => {
clearTimeout(nextId);
});
</script>
<template>
<Transition name="fade" mode="out-in">
<div class="image-viewer" @click="nextImage" :key="currentIndex">
<Header v-if="currentComment">
{{ currentComment }}
</Header>
<img :src="currentUrl" alt="Image Viewer" />
</div>
</Transition>
<Slideshow :images="images" />
</template>
<style scoped>
.image-viewer {
width: 100%;
overflow: hidden;
}
img {
width: 100%;
height: 100%;
object-fit: cover;
}
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.5s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}
</style>

View File

@@ -10,6 +10,7 @@ import CommitHistory from "@/components/util/CommitHistory.vue";
import Intro from "./Intro.vue";
import Intro2 from "./Intro2.vue";
import BadApple from "./BadApple.vue";
import Miku from "./Miku.vue";
import Stamps from "./Stamps.vue";
import Listening from "./Listening.vue";
import Links from "./Links.vue";
@@ -21,9 +22,14 @@ import Consumption from "./Consumption.vue";
</script>
<template>
<main class="halftone justify-center flex flex-row w-full h-full">
<main class="bg-random justify-center flex flex-row w-full h-full">
<div class="h-fit flex flex-row">
<div class="a4page-portrait homeGrid relative bdr-1">
<div
class="sidebar border-children background-children place-content-between flex-1 flex flex-col m-10 w-60"
>
<Miku/>
</div>
<div class="a4page-portrait homeGrid relative background-children border-children bdr-1">
<!-- <Intro class="intro" /> -->
<Intro2 class="intro" />
<!-- <BadApple class="intro" /> -->
@@ -37,18 +43,18 @@ import Consumption from "./Consumption.vue";
<Gym class="gym" />
</div>
<div
class="sidebar border-quaternary place-content-between flex-1 flex flex-col m-10 w-60"
class="sidebar place-content-between flex-1 flex flex-col m-10 w-60"
>
<div class="flex flex-col flex-1 gap-2">
<div class="flex flex-col background-children border-children flex-1 gap-2">
<Time
class="bg-bg_primary border-primary border text-center"
class="text-center"
/>
<Timer class="border-primary border bg-bg_primary" />
<Timer/>
<Radio
class="border-primary border bg-bg_primary text-center"
class="text-center"
/>
<CommitHistory
class="border-primary border bg-bg_primary text-center"
class=" text-center"
/>
<!-- <Elle class="flex-1" /> -->
@@ -67,9 +73,11 @@ import Consumption from "./Consumption.vue";
</template>
<style scoped>
.homeGrid > * {
.border-children > * {
border: 2px solid var(--quaternary);
border-color: var(--quaternary);
}
.background-children > * {
background-color: var(--bg_primary);
}
@@ -80,6 +88,7 @@ import Consumption from "./Consumption.vue";
grid-template-rows: repeat(10, 1fr);
}
@media (max-width: 850px) {
.homeGrid {
width: 100%;
@@ -140,4 +149,10 @@ import Consumption from "./Consumption.vue";
grid-column: span 3;
grid-row: span 2;
}
.bg-random {
background-color: var(--bg_primary);
background-image: url("/img/miku/miku2.gif");
background-size: 10px 10px;
}
</style>

View File

@@ -0,0 +1,13 @@
<script setup>
import Slideshow from "@/components/util/Slideshow.vue";
const images = [
{ url: "/img/miku/miku1.gif" },
{ url: "/img/miku/miku2.gif" },
// { url: "/img/miku/miku2.png" },
];
</script>
<template>
<Slideshow class="p-5" :images="images" :interval="10000" />
</template>