Checkpoint SHD dashboard design system

This commit is contained in:
JB
2026-07-24 21:31:35 -04:00
commit 5e113454ee
52 changed files with 3128 additions and 0 deletions
+42
View File
@@ -0,0 +1,42 @@
<script lang="ts">
import { page } from '$app/state';
import type { Snippet } from 'svelte';
let { user, children }: {
user: { username: string; role: string } | null;
children: Snippet;
} = $props();
const links = [
{ href: '/builds', label: 'Discover' },
{ href: '/builder', label: 'Builder' },
{ href: '/guides', label: 'Guides' }
];
</script>
<header class="site-header">
<a class="brand" href="/" aria-label="SHD.build home">
<span class="brand-mark">SHD</span><span>SHD<b>.build</b></span>
</a>
<nav aria-label="Main navigation">
{#each links as link}
<a class:active={page.url.pathname.startsWith(link.href)} href={link.href}>{link.label}</a>
{/each}
{#if user}
<a class:active={page.url.pathname.startsWith('/account')} href="/account">My Profile</a>
{/if}
{#if user?.role === 'admin'}
<a class:active={page.url.pathname.startsWith('/admin')} href="/admin/stats">Admin</a>
{/if}
</nav>
{#if user}
<div class="account">
<a href="/account"><small>AGENT</small>{user.username}</a>
<form method="POST" action="/sign-in?/logout"><button>SIGN OUT →</button></form>
</div>
{:else}
<a class="sign-in" href="/sign-in">SIGN IN →</a>
{/if}
</header>
{@render children()}
+11
View File
@@ -0,0 +1,11 @@
<script lang="ts">
import { enhance } from '$app/forms';
import type { Snippet } from 'svelte';
let { action, method = 'POST', class: className = '', children }: { action: string; method?: 'POST'; class?: string; children: Snippet<[boolean]> } = $props();
let pending = $state(false);
</script>
<form {action} {method} class={className} use:enhance={() => { if (pending) return; pending = true; return async ({ update }) => { try { await update(); } finally { pending = false; } }; }}>
<fieldset disabled={pending} aria-busy={pending}>{@render children(pending)}</fieldset>
</form>
<style>fieldset{border:0;padding:0;margin:0;min-width:0}fieldset[aria-busy=true]{opacity:.7}</style>