website/src/lib/Nav/Nav.svelte

142 lines
2.8 KiB
Svelte
Raw Normal View History

<script lang="ts">
2023-02-21 23:24:42 +05:30
import ThemeToggle from "./ThemeToggle.svelte";
import Link from "./Link.svelte";
import Logo from "./Logo.svelte";
import { slide } from "svelte/transition";
2023-02-03 23:25:33 +05:30
import { quintOut } from "svelte/easing";
2023-02-21 23:24:42 +05:30
const links = [
{ href: "/instances", text: "Instances" },
{ href: "/donate", text: "Donate" },
{ href: "/pubnix", text: "Pubnix" },
{ href: "/contact", text: "Contact" },
{ href: "/team", text: "Team" },
{
href: "https://wiki.projectsegfau.lt/",
text: "Wiki",
external: true
},
2023-03-30 12:30:36 +05:30
{ href: "/blog", text: "Blog" },
2023-02-21 23:24:42 +05:30
{
href: "https://status.projectsegfau.lt/",
text: "Status",
external: true
},
{ href: "/legal", text: "Legal" },
{
href: "https://matrix.to/#/#project-segfault:projectsegfau.lt/",
text: "Matrix",
icon: "i-simple-icons:matrix"
},
2023-05-05 12:37:56 +05:30
{
href: "https://join.jabber.network/#general@conference.projectsegfau.lt?join",
text: "XMPP",
icon: "i-simple-icons:xmpp"
},
2023-02-21 23:24:42 +05:30
{
href: "https://github.com/ProjectSegfault/",
text: "GitHub",
icon: "i-simple-icons:github"
}
];
2023-02-21 23:24:42 +05:30
const allowedWidth = 890;
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
let width: number;
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
$: showMenu = width > allowedWidth;
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
const navStyles =
"flex items-center justify-between lt-navPlus1:(flex-col items-start) gap-2 p-4 bg-secondary z-50 mb-16";
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
const linkContainerStyles =
"flex items-center gap-4 bg-secondary children:(no-underline text-text)";
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
let nav: HTMLElement;
2023-02-21 23:24:42 +05:30
let lastScrollTop: number;
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
let scrollTop: number;
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
const handleScroll = () => {
if (!showMenu) {
if (scrollTop > lastScrollTop) {
nav.style.top = "-80px";
} else {
nav.style.top = "0";
}
}
2022-12-27 20:58:47 +05:30
2023-02-21 23:24:42 +05:30
lastScrollTop = scrollTop;
};
2022-12-27 20:58:47 +05:30
</script>
2022-07-27 22:20:48 +05:30
2023-02-21 23:24:42 +05:30
<svelte:window
bind:innerWidth={width}
bind:scrollY={scrollTop}
on:scroll={handleScroll}
/>
2022-07-27 22:20:48 +05:30
2022-12-27 20:58:47 +05:30
<nav
2023-02-21 23:24:42 +05:30
class="{navStyles} sticky w-full top-0 z-50 js transition-top duration-200"
bind:this={nav}
2022-12-27 20:58:47 +05:30
>
2023-02-21 23:24:42 +05:30
<!-- Slot for the progress bar -->
<slot />
<div class="flex items-center justify-between w-full">
<Logo />
<button
on:click={() => (showMenu = !showMenu)}
aria-label="Toggle menu"
2022-10-01 18:41:54 +05:30
>
2023-02-21 23:24:42 +05:30
<div
class="{showMenu
2023-02-03 23:25:33 +05:30
? 'i-ic:outline-close'
2023-02-21 23:24:42 +05:30
: 'i-ic:outline-menu'} navPlus1:hidden"
2022-12-27 20:58:47 +05:30
/>
2023-02-21 23:24:42 +05:30
</button>
2022-07-27 22:20:48 +05:30
</div>
2023-02-21 23:24:42 +05:30
{#if showMenu}
2022-12-27 20:58:47 +05:30
<div
2023-02-21 23:24:42 +05:30
class="
{linkContainerStyles}
lt-navPlus1:(flex-col !items-start fixed pl-4 pb-4 z-50 w-full left-0 top-16)
"
2023-02-03 23:25:33 +05:30
transition:slide={{ duration: 300, easing: quintOut }}
2022-12-27 20:58:47 +05:30
>
2023-02-21 23:24:42 +05:30
{#each links as link}
<Link
{link}
on:click={() =>
width < allowedWidth
? (showMenu = false)
: (showMenu = true)}
/>
2022-12-27 20:58:47 +05:30
{/each}
2023-02-21 23:24:42 +05:30
<ThemeToggle />
2022-12-27 20:58:47 +05:30
</div>
{/if}
</nav>
2022-08-24 21:37:30 +05:30
2023-02-21 23:24:42 +05:30
<noscript>
<nav class="{navStyles} no-js">
<Logo />
<div
class="
{linkContainerStyles}
lt-navPlus1:(grid grid-cols-2 p-1)
"
>
{#each links as link}
<Link {link} />
{/each}
</div>
</nav>
<style>
.js {
display: none;
}
</style>
</noscript>