Skip to content

Commit

Permalink
V6.0.0 - Custom Apps/Games, nicer card
Browse files Browse the repository at this point in the history
  • Loading branch information
IncognitoTGT committed Jun 25, 2024
1 parent e3df115 commit 07cb196
Show file tree
Hide file tree
Showing 7 changed files with 94 additions and 50 deletions.
24 changes: 24 additions & 0 deletions src/components/AssetCard.astro
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
---
interface Props {
asset: Asset;
}
import { Image } from "astro:assets";
import { ASSET_URL, type Asset } from "@/lib/asset";
import { Ban, CircleAlert, UserRoundPlus } from "lucide-astro";
const { asset } = Astro.props;
---

<button data-asset={JSON.stringify(asset)}>
<div class="flex flex-col items-center p-4 bg-secondary size-48 rounded-md space-y-4 duration-150 justify-between border-[1px] hover:border-4">
<Image loading="eager" src={ASSET_URL + asset.image} alt={asset.name} height={145} width={145} class="size-24 rounded-xl bg-accent" />
<section class="inline-flex items-center gap-2" class:list={{ "text-red-600": asset.error, "text-yellow-400": asset.partial }}>
{asset.custom ? <UserRoundPlus class="size-5" /> : null}
{asset.partial ? <CircleAlert class="size-5" /> : null}
{asset.error ? <Ban class="size-5" /> : null}
<span class="text-center font-semibold text-lg line-clamp-1">
{asset.name}
</span>
</section>
</div>
</button>
19 changes: 19 additions & 0 deletions src/lib/asset-script.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { navigate } from "astro:transitions/client";
import type { Asset } from "@/lib/asset";
document.addEventListener("astro:page-load", () => {
const buttons = document.querySelectorAll(
Expand All @@ -23,4 +24,22 @@ document.addEventListener("astro:page-load", () => {
}
});
}
const assetAdd = document.getElementById("add-asset") as HTMLButtonElement | null;
if (assetAdd) {
assetAdd.addEventListener("click", async () => {
const type = assetAdd.dataset.type;
const name = prompt(`Enter the name of the ${type}`);
if (!name) return alert("Invalid name");
const link = prompt(`Enter the link of the ${type}`);
if (!link) return alert("Invalid link");
const response = await fetch("/api/add-asset", {
method: "PUT",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ type, name, link }),
});
const json = await response.json();
if (json.error) return alert(json.error);
if (json.success) return navigate(location.pathname);
});
}
});
1 change: 1 addition & 0 deletions src/lib/asset.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export type Asset = {
link?: string;
links?: { name: string; url: string }[];
say?: string;
custom?: boolean;
partial?: boolean | string;
error?: boolean | string;
blank?: boolean | string;
Expand Down
29 changes: 10 additions & 19 deletions src/pages/ap.astro
Original file line number Diff line number Diff line change
@@ -1,33 +1,24 @@
---
import { Image } from "astro:assets";
import Obfuscated from "@/components/Obfuscated.astro";
import AssetCard from "@/components/AssetCard.astro";
import Layout from "@/layouts/Main.astro";
import { ASSET_URL, type Asset } from "@/lib/asset";
import { LayoutGrid } from "lucide-astro";
import { LayoutGrid, PlusCircle } from "lucide-astro";
const apps: Asset[] = await (await fetch(`${ASSET_URL}/json/apps.json`)).json();
const customApps = (Astro.cookies.get("asset.app")?.json() as Asset[]) ?? [];
---

<Layout>
<div class="flex justify-center py-8 flex-col items-center">
<div class="text-4xl font-bold text-text-secondary inline-flex mb-4">
<div class="flex justify-center py-8 flex-col items-center gap-4">
<div class="text-4xl font-bold text-text-secondary inline-flex">
<LayoutGrid class="size-12 mr-2" />
Apps
</div>
<button class="p-4 bg-interactive hover:bg-interactive-secondary rounded-md font-semibold inline-flex items-center" data-type="app" id="add-asset">
<PlusCircle class="size-5 mr-2" />
Add App
</button>
<div class="flex flex-wrap justify-center gap-4 flex-row mt-30">
{
apps.map((app) => (
<button data-asset={JSON.stringify(app)}>
<div class="flex flex-col items-center p-4 bg-secondary size-48 rounded-md space-y-4 hover:bg-interactive duration-150">
<Image loading="eager" src={ASSET_URL + app.image} alt={app.name} height={145} width={145} class="size-24 rounded-md" />
<Obfuscated
class="text-center font-semibold text-xl text-wrap"
class:list={{ "text-red-600": app.error, "text-yellow-400": app.partial }}
text={app.name}
/>
</div>
</button>
))
}
{[...customApps, ...apps].map((app) => <AssetCard asset={app} />)}
</div>
</div>
</Layout>
Expand Down
28 changes: 28 additions & 0 deletions src/pages/api/add-asset.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import type { Asset } from "@/lib/asset";
import type { APIRoute } from "astro";

export const PUT: APIRoute = async ({ cookies, request }) => {
const body = (await request.json()) as {
type: string;
name: string;
link: string;
};
if (!body.type || !body.name || !body.link) {
return Response.json({ error: "Missing required fields" }, { status: 400 });
}
if (!["app", "game"].includes(body.type)) {
return Response.json({ error: "Invalid asset type" }, { status: 400 });
}
const currentAssets: Asset[] = cookies.get(`asset.${body.type}`)?.json() || [];
currentAssets.push({
name: body.name,
link: body.link,
image: "/media/icons/custom.webp",
custom: true,
});
cookies.set(`asset.${body.type}`, JSON.stringify(currentAssets), {
path: "/",
expires: new Date(Date.now() + 1000 * 60 * 60 * 24 * 365),
});
return Response.json({ success: true });
};
29 changes: 10 additions & 19 deletions src/pages/ga.astro
Original file line number Diff line number Diff line change
@@ -1,33 +1,24 @@
---
import { Image } from "astro:assets";
import Obfuscated from "@/components/Obfuscated.astro";
import AssetCard from "@/components/AssetCard.astro";
import Layout from "@/layouts/Main.astro";
import { ASSET_URL, type Asset } from "@/lib/asset";
import { Gamepad2 } from "lucide-astro";
import { Gamepad2, PlusCircle } from "lucide-astro";
const games: Asset[] = await (await fetch(`${ASSET_URL}/json/games.json`)).json();
const customGames = (Astro.cookies.get("asset.game")?.json() as Asset[]) ?? [];
---

<Layout>
<div class="flex justify-center py-8 flex-col items-center">
<div class="text-4xl font-bold text-text-secondary inline-flex mb-4">
<div class="flex justify-center py-8 flex-col items-center gap-4">
<div class="text-4xl font-bold text-text-secondary inline-flex">
<Gamepad2 class="size-12 mr-2" />
Games
</div>
<button class="p-4 bg-interactive hover:bg-interactive-secondary rounded-md font-semibold inline-flex items-center" data-type="game" id="add-asset">
<PlusCircle class="size-5 mr-2" />
Add Game
</button>
<div class="flex flex-wrap justify-center gap-4 flex-row mt-30">
{
games.map((game) => (
<button data-asset={JSON.stringify(game)}>
<div class="flex flex-col items-center p-4 bg-secondary size-48 rounded-md space-y-4 hover:bg-interactive duration-150">
<Image loading="eager" src={ASSET_URL + game.image} alt={game.name} height={145} width={145} class="size-24 rounded-md" />
<Obfuscated
class="text-center font-semibold text-xl text-wrap"
class:list={{ "text-red-600": game.error, "text-yellow-400": game.partial }}
text={game.name}
/>
</div>
</button>
))
}
{[...customGames, ...games].map((game) => <AssetCard asset={game} />)}
</div>
</div>
</Layout>
Expand Down
14 changes: 2 additions & 12 deletions src/pages/to.astro
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
---
import { Image } from "astro:assets";
import Obfuscated from "@/components/Obfuscated.astro";
import AssetCard from "@/components/AssetCard.astro";
import Layout from "@/layouts/Main.astro";
import { ASSET_URL, type Asset } from "@/lib/asset";
import { Wrench } from "lucide-astro";
Expand All @@ -14,16 +13,7 @@ const tools: Asset[] = await (await fetch(`${ASSET_URL}/json/tools.json`)).json(
Tools
</div>
<div class="flex flex-wrap justify-center gap-4 flex-row mt-30">
{
tools.map((tool) => (
<button>
<div class="flex flex-col items-center p-4 bg-secondary size-48 rounded-md space-y-4 hover:bg-interactive duration-150">
<Image loading="eager" src={ASSET_URL + tool.image} alt={tool.name} height={145} width={145} class="size-24 rounded-md" />
<Obfuscated class="text-center font-semibold text-xl text-wrap" text={tool.name} />
</div>
</button>
))
}
{tools.map((tool) => <AssetCard asset={tool} />)}
</div>
</div>
</Layout>
Expand Down

0 comments on commit 07cb196

Please sign in to comment.