8ccc515a7b
Introduce reusable global CSS modules and apply them across routes to centralize layout/surface patterns. Added GUI/src/styles/global/page-layouts.css and GUI/src/styles/global/surface-patterns.css and imported both in GUI/src/main.ts. Updated Layout.vue, Home.vue, 404NotFound.vue, Impressum.vue and authentication/Login.vue to use hoard-* utility classes (hoard-page, hoard-shell-grid, hoard-kicker, hoard-action-row, hoard-panel-gradient, etc.) and removed duplicated scoped styles. Also updated codexInfo.md to document the new CSS modules and provide usage guidance. This reduces per-page CSS duplication and standardizes gradients, spacing and page-shell behavior.
115 lines
2.8 KiB
Vue
115 lines
2.8 KiB
Vue
<script setup lang="ts">
|
|
import { useRouter } from 'vue-router'
|
|
|
|
import notFoundImage from '@/assets/images/404NotFound.png'
|
|
|
|
const router = useRouter()
|
|
|
|
function navigateBack() {
|
|
if (window.history.length > 1) {
|
|
router.back()
|
|
return
|
|
}
|
|
|
|
router.push('/')
|
|
}
|
|
</script>
|
|
|
|
<template>
|
|
<v-container fluid class="not-found-page hoard-page hoard-page--centered">
|
|
<section class="not-found-shell hoard-panel hoard-shell-grid hoard-panel-gradient">
|
|
<div class="not-found-visual">
|
|
<div class="image-frame">
|
|
<img :src="notFoundImage" alt="Illustration für eine nicht gefundene Seite" class="not-found-image" />
|
|
</div>
|
|
</div>
|
|
|
|
<div class="not-found-content">
|
|
<p class="not-found-kicker hoard-kicker hoard-kicker--wide">Fehler 404</p>
|
|
<h1>Seite nicht gefunden</h1>
|
|
<p class="not-found-text">
|
|
Der Link ist ungültig oder die Seite wurde verschoben. Du kannst direkt zur
|
|
Startseite zurück oder die vorherige Ansicht öffnen.
|
|
</p>
|
|
|
|
<div class="not-found-actions hoard-action-row">
|
|
<v-btn color="primary" prepend-icon="mdi-home" to="/">Zur Startseite</v-btn>
|
|
<v-btn variant="outlined" prepend-icon="mdi-arrow-left" @click="navigateBack">Zurück</v-btn>
|
|
</div>
|
|
</div>
|
|
</section>
|
|
</v-container>
|
|
</template>
|
|
|
|
<style scoped>
|
|
.not-found-shell {
|
|
--hoard-shell-width: 980px;
|
|
--hoard-gradient-angle: 180deg;
|
|
--hoard-gradient-start: color-mix(in srgb, var(--color-surface) 94%, var(--color-primary-100) 6%);
|
|
--hoard-gradient-end: color-mix(in srgb, var(--color-surface) 82%, var(--color-surface-alt) 18%);
|
|
--hoard-gradient-end-stop: 100%;
|
|
|
|
grid-template-columns: minmax(260px, 1fr) minmax(320px, 1fr);
|
|
}
|
|
|
|
.not-found-visual {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
}
|
|
|
|
.image-frame {
|
|
width: min(100%, 360px);
|
|
aspect-ratio: 1 / 1;
|
|
padding: var(--space-4);
|
|
border: 1px solid var(--color-border);
|
|
border-radius: var(--radius-lg);
|
|
background-color: color-mix(in srgb, var(--color-surface-alt) 84%, var(--color-surface) 16%);
|
|
box-shadow: var(--shadow-sm);
|
|
}
|
|
|
|
.not-found-image {
|
|
width: 100%;
|
|
height: 100%;
|
|
object-fit: contain;
|
|
}
|
|
|
|
.not-found-content {
|
|
display: flex;
|
|
flex-direction: column;
|
|
justify-content: center;
|
|
}
|
|
|
|
h1 {
|
|
margin-bottom: var(--space-3);
|
|
font-size: clamp(1.8rem, 2vw + 1rem, 2.4rem);
|
|
font-weight: 700;
|
|
}
|
|
|
|
.not-found-text {
|
|
margin-bottom: var(--space-6);
|
|
max-width: 44ch;
|
|
color: var(--color-text-secondary);
|
|
font-size: 15px;
|
|
}
|
|
|
|
.not-found-actions {
|
|
align-items: center;
|
|
}
|
|
|
|
@media (width <= 960px) {
|
|
.not-found-shell {
|
|
grid-template-columns: 1fr;
|
|
}
|
|
|
|
.not-found-content {
|
|
text-align: center;
|
|
align-items: center;
|
|
}
|
|
|
|
.not-found-actions {
|
|
justify-content: center;
|
|
}
|
|
}
|
|
</style>
|