actually start implementing the backend slowly

This commit is contained in:
Soph :3 2026-01-04 15:49:32 +02:00
parent 37ae49b66e
commit 342fd30d62
19 changed files with 977 additions and 136 deletions

View file

@ -1,5 +1,5 @@
<script lang="ts">
import { Status, type Friend , type Group, type Server } from "$lib";
import { type Data } from "$lib";
import * as Collapsible from "$lib/components/ui/collapsible/index.js";
import * as Sidebar from "$lib/components/ui/sidebar/index.js";
import * as Dialog from "$lib/components/ui/dialog/index.js";
@ -11,9 +11,9 @@
import CirclePlus from '@lucide/svelte/icons/circle-plus';
import Input from "./ui/input/input.svelte";
import Button, { buttonVariants } from "./ui/button/button.svelte";
import FriendComponent from "./Friend.svelte";
import User from "./extra/User.svelte";
let { currentPage = $bindable<string|null>(), data, ...restProps }: {currentPage: string|null, data: { friends: Friend[], groups: Group[], servers: Server[] }}= $props();
let { currentPage = $bindable<string|null>(), data, ...restProps }: {currentPage: string|null, data: Data }= $props();
</script>
<Sidebar.Root {...restProps}>
@ -33,75 +33,126 @@
<div class="w-full flex gap-2 justify-center">
<Dialog.Root>
<Dialog.Trigger>
<Button variant="outline" size="icon">
<UserRoundPlus />
</Button>
</Dialog.Trigger>
<Dialog.Content class="sm:max-w-[425px]">
<Dialog.Header>
<Dialog.Title>Add a friend</Dialog.Title>
<Dialog.Description>
Add a friend using their username.
</Dialog.Description>
</Dialog.Header>
<Dialog.Trigger>
<Button variant="outline" size="icon">
<UserRoundPlus />
</Button>
</Dialog.Trigger>
<Input></Input>
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>Cancel</Dialog.Close>
<Button type="submit">Send request.</Button>
</Dialog.Footer>
</Dialog.Content>
<Dialog.Content class="sm:max-w-[425px]">
<form method="POST" action="?/addFriend">
<Dialog.Header>
<Dialog.Title>Add a friend</Dialog.Title>
<Dialog.Description>
Add a friend using their username.
</Dialog.Description>
</Dialog.Header>
<Input name="username" placeholder="username" required />
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>
Cancel
</Dialog.Close>
<Button type="submit">Send request</Button>
</Dialog.Footer>
</form>
</Dialog.Content>
</Dialog.Root>
<Dialog.Root>
<Dialog.Trigger>
<Button variant="outline" size="icon">
<UsersRound />
</Button>
</Dialog.Trigger>
<Dialog.Content class="sm:max-w-[425px]">
<Dialog.Header>
<Dialog.Title>Create a group</Dialog.Title>
<Dialog.Description>
Add friends into your group!
</Dialog.Description>
</Dialog.Header>
{#each data.friends as friend (friend.id)}
<Dialog.Trigger>
<Button variant="outline" size="icon">
<UsersRound />
</Button>
</Dialog.Trigger>
<FriendComponent onclick={(e) => {
e.preventDefault();
currentPage = friend.id;
}} {friend}></FriendComponent>
<Dialog.Content class="sm:max-w-[425px]">
<form method="POST" action="?/createGroup">
<Dialog.Header>
<Dialog.Title>Create a group</Dialog.Title>
<Dialog.Description>
Add friends into your group!
</Dialog.Description>
</Dialog.Header>
{/each}
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>Cancel</Dialog.Close>
<Button type="submit">Create group</Button>
</Dialog.Footer>
</Dialog.Content>
{#each data.friends as friend (friend.id)}
<label class="flex items-center gap-2">
<input
type="checkbox"
name="member"
value={friend.id}
/>
<User user={friend} />
</label>
{/each}
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>
Cancel
</Dialog.Close>
<Button type="submit">Create group</Button>
</Dialog.Footer>
</form>
</Dialog.Content>
</Dialog.Root>
<Dialog.Root>
<Dialog.Trigger>
<Button variant="outline" size="icon">
<CirclePlus />
<Dialog.Trigger>
<Button variant="outline" size="icon">
<CirclePlus />
</Button>
</Dialog.Trigger>
</Button>
</Dialog.Trigger>
<Dialog.Content class="sm:max-w-[425px]">
<Dialog.Header>
<Dialog.Title>Join a server</Dialog.Title>
<Dialog.Description>
Enter it's link into the input box here.
</Dialog.Description>
</Dialog.Header>
<Input></Input>
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>Cancel</Dialog.Close>
<Button type="submit">Create group</Button>
</Dialog.Footer>
</Dialog.Content>
<Dialog.Content class="sm:max-w-[425px]">
<form method="POST" action="?/joinServer">
<Dialog.Header>
<Dialog.Title>Join a server</Dialog.Title>
<Dialog.Description>
Enter an invite link.
</Dialog.Description>
</Dialog.Header>
<Input name="invite" placeholder="invite link" required />
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>
Cancel
</Dialog.Close>
<Button type="submit">Join</Button>
</Dialog.Footer>
</form>
</Dialog.Content>
</Dialog.Root>
<Dialog.Root>
<Dialog.Trigger>
<Button variant="outline" size="icon">
<PlusIcon />
</Button>
</Dialog.Trigger>
<Dialog.Content class="sm:max-w-[425px]">
<form method="POST" action="?/createServer">
<Dialog.Header>
<Dialog.Title>Create a server</Dialog.Title>
<Dialog.Description>
Name your new server.
</Dialog.Description>
</Dialog.Header>
<Input name="name" placeholder="Server name" required />
<Dialog.Footer>
<Dialog.Close class={buttonVariants({ variant: "outline" })}>
Cancel
</Dialog.Close>
<Button type="submit">Create</Button>
</Dialog.Footer>
</form>
</Dialog.Content>
</Dialog.Root>
</div>
</Sidebar.MenuItem>
</Sidebar.Menu>
@ -128,10 +179,10 @@
<Sidebar.MenuSubItem>
<Sidebar.MenuSubButton>
<FriendComponent onclick={(e) => {
<User onclick={(e) => {
e.preventDefault();
currentPage = friend.id;
}} {friend}></FriendComponent>
}} user={friend}></User>
</Sidebar.MenuSubButton>
</Sidebar.MenuSubItem>
{/each}
@ -194,7 +245,7 @@
e.preventDefault();
currentPage = server.id;
}} href="##" class="flex items-center gap-2">
<img src={server.image} alt={server.name} class="size-6 rounded-full" />
<img src={"https://api.dicebear.com/7.x/pixel-art/svg?seed=" + server.name} alt={server.name} class="size-6 rounded-full" />
{server.name}
</a>
</Sidebar.MenuSubButton>

View file

@ -1,23 +1,22 @@
<script lang="ts">
import { Status, type Friend } from '$lib';
import { Status, type UserWithStatus } from '$lib';
const {
onclick,
friend
}: { onclick?: (e: MouseEvent) => void, friend: Friend } = $props();
user
}: { onclick?: (e: MouseEvent) => void, user: UserWithStatus } = $props();
</script>
<a {onclick} href="##" class="flex items-center gap-2">
<div class="relative">
<img src={friend.image} alt={friend.name} class="size-6 rounded-full" />
{#if friend.status === Status.OFFLINE}
<img src={"https://api.dicebear.com/7.x/pixel-art/svg?seed=" + user.username} alt={user.username} class="size-6 rounded-full" />
{#if user.status === Status.OFFLINE}
<span class="absolute bottom-0 end-0 block size-2 rounded-full bg-gray-500 ring-1 ring-white"></span>
{:else if friend.status === Status.DND}
{:else if user.status === Status.DND}
<span class="absolute bottom-0 end-0 block size-2 rounded-full bg-red-500 ring-1 ring-white"></span>
{:else if friend.status === Status.ONLINE}
{:else if user.status === Status.ONLINE}
<span class="absolute bottom-0 end-0 block size-2 rounded-full bg-green-500 ring-1 ring-white"></span>
{/if}
</div>
{friend.name}
{user.username}
</a>