Chrysoblog/src/routes/+page.svelte

254 lines
5.3 KiB
Svelte

<script lang="ts">
import { onMount } from 'svelte';
import { derived } from 'svelte/store'
import { routes } from "$lib/sitemap.ts"
import { Separator } from "$lib/components/ui/separator/index.js";
import { theme, getThemeObject } from '$lib/theme'
import { Rss } from "lucide-svelte";
import ThemeSwitch from "$lib/components/ThemeSwitch.svelte"
import Cover from "$lib/Cover.svelte"
let scrollPosition: number = .5;
let scrollHeight: number = 1;
let progress: number = 0;
let button_blog;
onMount(() => {
let entity_blog = document.getElementById("visor");
let link_about = document.getElementById("link-about");
});
function onScroll() {
if (scrollHeight > 1) {
progress = Math.max(0, Math.min(1, scrollPosition / scrollHeight));
}
}
import type { PageData } from './$types';
export let data: PageData;
const { name, Content } = data;
import metadata from '$content/metadata.json';
const iconMap: Map<string, string> = {
"orcid": "fa-brands fa-orcid",
"google-scholar": "fa-brands fa-google-scholar",
"discord": "fa-brands fa-discord",
"email": "fa-solid fa-envelope",
"bitbucket": "fa-brands fa-bitbucket",
"github": "fa-brands fa-github",
"gitlab": "fa-brands fa-gitlab",
"open-source": "fa-brands fa-osi",
"bluesky": "fa-brands fa-bluesky",
"youtube": "fa-brands fa-youtube",
"instagram": "fa-brands fa-instagram",
"bandcamp": "fa-brands fa-bandcamp",
"pixiv": "fa-brands fa-pixiv",
};
const iconLinks: [string, string][] = Object.entries(metadata.links).map(
([key, link]) => [iconMap[key], link]);
const frontCover = derived(
theme,
($theme) => getThemeObject($theme, metadata.frontCover)
)
</script>
<svelte:head>
<title>{metadata.name}</title>
</svelte:head>
<div id="cover" style="opacity: {1 - progress}">
<Cover />
</div>
<div id="cover-mobile">
<div id="navbar">
<div>
<p class="text-2xl floater-elem" style="color: #888">{metadata.frontDescription}</p>
</div>
<div id="link-container" class="h-5 items-center">
<a class="nav-link" href="#bio">Bio</a>
{#each routes as item}
{#if item.route !== "/"}
<a
href={item.route}
class="nav-link"
class:disabled-link={item.disabled}>{item.name}</a>
{/if}
{/each}
<a class="icon nav-link" href="/rss.xml"><Rss /></a>
<ThemeSwitch />
</div>
</div>
</div>
<main>
<div id="bio">
<div class="p-1">
<div class="flex">
<div id="info flex-col">
<p id="bio-name">{name}</p>
<div class="w-100">
{#each iconLinks as [cl, link]}
<a class="icon m-1" href={link}><i class="fa-xl {cl}"></i></a>
{/each}
</div>
</div>
<div id="avatar">
<img id="avatar-img" src={metadata.picture} alt={metadata.name} />
</div>
</div>
</div>
<article id="bio-core" class="prose lg:prose-xl dark:prose-dark">
<Content />
</article>
</div>
</main>
<svelte:window
bind:scrollY={scrollPosition}
bind:innerHeight={scrollHeight}
on:scroll={onScroll}
/>
<style>
#cover {
background:
repeating-linear-gradient(129deg, transparent, #aaa 1px, #aaa 2px, transparent 1px, transparent 60px),
repeating-linear-gradient(11deg, transparent, #aaa 1px, #aaa 2px, transparent 1px, transparent 40px),
#707078
;
/*
position: absolute;
background-size: contain;
background-position: center center; */
z-index: -10;
overscroll-behaviour: none;
}
:global(#cover > svg) {
max-width: 100svw;
max-height: 100svh;
z-index: -10;
width: 100%;
height: 100%;
}
:global(svg a) {
pointer-events: all;
:global(path) {
filter: contrast(50%);
}
:global(.effect) {
visibility: hidden;
}
&:hover,
&:focus {
:global(.effect) {
visibility: visible;
}
:global(path) {
filter: contrast(100%);
}
}
}
:global(svg .shadow) {
pointer-events: none;
}
.nav-link {
display: inline-block;
}
#cover-mobile {
display: flex;
flex-direction: column;
overscroll-behavior: none;
}
#navbar {
display: flex;
flex-wrap: wrap;
justify-content: center;
flex-direction: column;
margin-top: auto;
margin-bottom: auto;
div {
padding-left: 5%;
}
}
#link-container {
display: flex;
flex-direction: column;
align-items: flex-start;
}
@media (max-width: 700px) {
#cover {
height: 0;
width: 0;
visibility: hidden;
}
#cover-mobile {
visibility: visible;
height: 100svh;
}
}
@media (min-width: 701px) {
#cover {
min-width: 100svw;
min-height: 100svh;
visibility: visible;
}
#cover-mobile {
visibility: hidden;
height: 0;
width: 0;
}
}
main {
width: 100%;
@apply bg-background;
@apply dark:bg-gray-800;
/*box-shadow:
0px -5px 5px var(--shadow);*/
}
#bio {
max-width: max(50vw, 100vh);
margin-left: auto;
margin-right: auto;
padding: 20px 10px 50px 10px;
min-height: 100vh;
}
#bio-name {
font-family: serif;
font-size: min(10vw, 60px);
display: inline-block;
color: var(--name);
}
#avatar {
line-height: 0;
display: inline-block;
margin: 5px;
margin-right: auto;
border: 1px solid var(--name);
border-radius: 50%;
aspect-ratio: 1;
max-width: 20%;
@apply ml-auto mr-0;
}
#avatar-img {
min-height: 100%;
min-width: 100%;
object-fit: cover;
border-radius: 50%;
}
#bio-core {
width: 100%;
}
#bio-core > :global(*):not(h1):not(h2) {
margin-left: 50px;
}
#bio-core > :global(h1) {
font-weight: normal;
border-bottom: 1px solid;
}
</style>