Start work on dark-mode, fix heading scroll position

This commit is contained in:
Riyyi
2025-03-31 15:02:51 +02:00
parent c26c74a2fb
commit 86e08604dd
18 changed files with 243 additions and 53 deletions
+1 -1
View File
@@ -7,7 +7,7 @@
<script setup lang="ts">
useHead({
titleTemplate: (titleChunk) => {
titleTemplate: (titleChunk: string): string => {
return titleChunk ? `${titleChunk} - website-vue` : 'website-vue';
}
})
-4
View File
@@ -15,10 +15,6 @@ body {
background-color: #f4f4f4;
}
nav {
box-shadow: 0 .25rem .5rem rgba(0,0,0,.28) !important;
}
/* Main content */
/*----------------------------------------*/
+2
View File
@@ -21,6 +21,8 @@ declare module 'vue' {
IFaHome: typeof import('~icons/fa/home')['default']
IFaLink: typeof import('~icons/fa/link')['default']
IFaLinkedinSquare: typeof import('~icons/fa/linkedin-square')['default']
IFaMoonO: typeof import('~icons/fa/moon-o')['default']
IFaSolidSun: typeof import('~icons/fa-solid/sun')['default']
IMdiAccountBox: typeof import('~icons/mdi/account-box')['default']
RouterLink: typeof import('vue-router')['RouterLink']
RouterView: typeof import('vue-router')['RouterView']
+10
View File
@@ -28,3 +28,13 @@
</BCollapse>
</BNavbar>
</template>
<style scoped>
nav {
box-shadow: 0 .25rem .5rem rgba(0, 0, 0, .28);
}
[data-bs-theme=dark] nav {
box-shadow: 0 .25rem .5rem rgba(255, 0, 0, .28);
}
</style>
+23
View File
@@ -0,0 +1,23 @@
<template>
<div class="position-fixed corner">
<template v-if="store.colorMode === 'dark'">
<IFaSolidSun @click="store.toggleColorMode" />
</template>
<template v-else>
<IFaMoonO @click="store.toggleColorMode" />
</template>
</div>
</template>
<style scoped>
.corner {
right: 10px;
bottom: 10px;
}
</style>
<script setup lang="ts">
import { useStateStore } from "@/stores/stateStore";
const store = useStateStore();
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h1>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h1>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h1)))
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h2>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h2>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h2)))
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h3>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h3>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h3)))
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h4>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h4>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h4)))
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h5>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h5>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h5)))
</script>
+18
View File
@@ -0,0 +1,18 @@
<template>
<h6>
<span :id="props.id"></span>
<a v-if="props.id && generate" :href="`#${props.id}`">
<slot />
</a>
<slot v-else />
</h6>
</template>
<script setup lang="ts">
import { computed, useRuntimeConfig } from "#imports"
const props = defineProps<{ id?: string }>()
const { headings } = useRuntimeConfig().public.mdc
const generate = computed(() => props.id && ((typeof headings?.anchorLinks === "boolean" && headings?.anchorLinks === true) || (typeof headings?.anchorLinks === "object" && headings?.anchorLinks?.h6)))
</script>
+1
View File
@@ -10,4 +10,5 @@
</div>
<SharedFooter />
</div>
<ToggleColorMode />
</template>
+12 -3
View File
@@ -15,8 +15,19 @@
<style scoped>
/* Target element in child components with :deep */
/* Select any <h> */
:deep(:is(h1, h2, h3, h4, h5, h6):has(span)) {
position: relative;
}
/* Select any <span> inside a <h> */
:deep(:is(h1, h2, h3, h4, h5, h6) span) {
position: absolute;
top: -65px;
}
/* Select any <a> inside a <h> */
:deep(:is(h1, h2, h3, h4, h5, h6) > a) {
:deep(:is(h1, h2, h3, h4, h5, h6) a) {
color: inherit;
text-decoration: none;
}
@@ -50,8 +61,6 @@
<script setup lang="ts">
const { params } = useRoute();
console.log(params);
const { data: article } = await useAsyncData(
`article-${params.slug}`,
() => queryCollection("content").path("/articles/" + params.slug).first()
+16
View File
@@ -0,0 +1,16 @@
import { defineStore } from "pinia"
import { ref } from "vue";
export const useStateStore = defineStore("state", () => {
const colorMode = ref<string>("light");
const toggleColorMode = (): void => {
colorMode.value = colorMode.value === "dark" ? "light" : "dark";
const html = document.querySelector("html") as HTMLElement;
html.setAttribute('data-bs-theme', colorMode.value);
};
return { colorMode, toggleColorMode }
}, {
persist: process.env.NODE_ENV === 'development' ? true : false,
})