alternative tangled frontend (extremely wip)

chore: prettier

serenity f5d65204 3cc3215f

+171 -159
+12 -12
src/components/Animated/UnderlinedLink.tsx
··· 1 - import { motion } from 'motion/react' 2 - import { ReactNode } from 'react' 1 + import { motion } from "motion/react"; 2 + import { ReactNode } from "react"; 3 3 4 4 export const UnderlineLink = ({ 5 5 href, 6 6 children, 7 - className = 'text-[#cba6f7]', 8 - underlineColor = 'bg-[#cba6f7]', 7 + className = "text-[#cba6f7]", 8 + underlineColor = "bg-[#cba6f7]", 9 9 }: { 10 - href: string 11 - children: ReactNode 12 - className?: string 13 - underlineColor?: string 10 + href: string; 11 + children: ReactNode; 12 + className?: string; 13 + underlineColor?: string; 14 14 }) => { 15 15 return ( 16 16 <motion.a ··· 21 21 > 22 22 {children} 23 23 <motion.span 24 - className={`absolute bottom-1 left-0 w-full h-0.25 origin-center ${underlineColor}`} 24 + className={`absolute bottom-1 left-0 h-0.25 w-full origin-center ${underlineColor}`} 25 25 variants={{ 26 26 initial: { scaleX: 0 }, 27 27 hover: { scaleX: 1 }, 28 28 }} 29 29 transition={{ 30 - type: 'spring', 30 + type: "spring", 31 31 duration: 0.25, 32 32 bounce: 0.3, 33 33 }} 34 34 /> 35 35 </motion.a> 36 - ) 37 - } 36 + ); 37 + };
+23 -22
src/components/Auth/SignIn.tsx
··· 1 - import { UnderlineLink } from '@/components/Animated/UnderlinedLink' 2 - import { LucideAtSign } from '@/components/Icons/LucideAtSign' 3 - import { LucideCircleUserRound } from '@/components/Icons/LucideCircleUserRound' 4 - import { LucideInfo } from '@/components/Icons/LucideInfo' 5 - import { LucideLogIn } from '@/components/Icons/LucideLogIn' 6 - import { useState } from 'react' 1 + import { UnderlineLink } from "@/components/Animated/UnderlinedLink"; 2 + import { LucideAtSign } from "@/components/Icons/LucideAtSign"; 3 + import { LucideCircleUserRound } from "@/components/Icons/LucideCircleUserRound"; 4 + import { LucideInfo } from "@/components/Icons/LucideInfo"; 5 + import { LucideLogIn } from "@/components/Icons/LucideLogIn"; 6 + import { useState } from "react"; 7 7 8 8 export const SignIn = () => { 9 - const [handle, setHandle] = useState('') 10 - const isValidHandle = handle.includes('.') 9 + const [handle, setHandle] = useState(""); 10 + const isValidHandle = handle.includes("."); 11 11 12 12 return ( 13 - <div className="bg-surface0 flex flex-col items-center m-36 rounded-md max-w-1/4 px-6 py-4 border-1 border-surface1"> 13 + <div className="bg-surface0 border-surface1 m-36 flex max-w-1/4 flex-col items-center rounded-md border-1 px-6 py-4"> 14 14 <LucideCircleUserRound 15 15 height={28} 16 16 width={28} 17 17 className="mt-4 mb-1" 18 18 /> 19 - <h2 className="font-semibold text-xl tracking-wide">Sign In</h2> 19 + <h2 className="text-xl font-semibold tracking-wide">Sign In</h2> 20 20 <p className="text-subtext m-4"> 21 - Continue with an{' '} 21 + Continue with an{" "} 22 22 <UnderlineLink 23 23 href="https://atproto.com" 24 24 underlineColor="bg-accent" 25 25 className="text-accent" 26 26 > 27 27 Atmosphere 28 - </UnderlineLink>{' '} 28 + </UnderlineLink>{" "} 29 29 account 30 30 </p> 31 31 <div className="w-full"> ··· 37 37 height={14} 38 38 width={14} 39 39 /> 40 - <div className="absolute bottom-full left-1/2 mb-2 w-64 -translate-x-1/2 rounded-lg bg-surface1 px-3 py-2 text-sm opacity-0 pointer-events-none transition-opacity group-hover:pointer-events-auto group-hover:opacity-100"> 40 + <div className="bg-surface1 pointer-events-none absolute bottom-full left-1/2 mb-2 w-64 -translate-x-1/2 rounded-lg px-3 py-2 text-sm opacity-0 transition-opacity group-hover:pointer-events-auto group-hover:opacity-100"> 41 41 If you have a Bluesky, Blacksky, Tangled, or any 42 - other ATProto account, you can use that account's handle. 43 - <div className="absolute left-1/2 top-full -translate-x-1/2 border-4 border-transparent border-t-surface1" /> 42 + other ATProto account, you can use that account's 43 + handle. 44 + <div className="border-t-surface1 absolute top-full left-1/2 -translate-x-1/2 border-4 border-transparent" /> 44 45 </div> 45 46 </div> 46 47 </div> 47 - <div className="flex items-center rounded-sm border border-surface1 overflow-hidden transition-all group has-[:focus]:border-accent"> 48 - <LucideAtSign className="text-subtext px-2 w-max h-full group-has-[:focus]:text-accent transition-all" /> 49 - <div className="w-px bg-surface1 group-has-[:focus]:bg-accent self-stretch transition-all" /> 48 + <div className="border-surface1 group has-[:focus]:border-accent flex items-center overflow-hidden rounded-sm border transition-all"> 49 + <LucideAtSign className="text-subtext group-has-[:focus]:text-accent h-full w-max px-2 transition-all" /> 50 + <div className="bg-surface1 group-has-[:focus]:bg-accent w-px self-stretch transition-all" /> 50 51 <input 51 52 placeholder="akshay.tngl.sh" 52 - className="w-full p-1 focus:outline-0 rounded-tr-sm rounded-br-sm py-2 pl-2 peer transition-all" 53 + className="peer w-full rounded-tr-sm rounded-br-sm p-1 py-2 pl-2 transition-all focus:outline-0" 53 54 onChange={(e) => setHandle(e.target.value)} 54 55 /> 55 56 </div> 56 57 </div> 57 58 <button 58 59 disabled={!isValidHandle} 59 - className="cursor-pointer p-2 transition-all hover:bg-positive hover:text-crust rounded-sm w-full m-2 mt-6 mb-2 flex items-center gap-2 justify-center disabled:cursor-not-allowed hover:disabled:bg-surface1 hover:disabled:text-text bg-accent text-crust disabled:bg-surface1 disabled:text-text" 60 + className="hover:bg-positive hover:text-crust hover:disabled:bg-surface1 hover:disabled:text-text bg-accent text-crust disabled:bg-surface1 disabled:text-text m-2 mt-6 mb-2 flex w-full cursor-pointer items-center justify-center gap-2 rounded-sm p-2 transition-all disabled:cursor-not-allowed" 60 61 > 61 62 <p>Continue</p> 62 63 <LucideLogIn /> 63 64 </button> 64 65 </div> 65 - ) 66 - } 66 + ); 67 + };
+3 -3
src/components/Icons/Branding/StrandIcon.tsx
··· 1 - import { LucideSpool } from '@/components/Icons/LucideSpool' 1 + import { LucideSpool } from "@/components/Icons/LucideSpool"; 2 2 3 3 export const StrandIcon = () => { 4 - return <LucideSpool /> 5 - } 4 + return <LucideSpool />; 5 + };
+2 -2
src/components/Icons/LucideAtSign.tsx
··· 1 - import { SVGProps } from 'react' 1 + import { SVGProps } from "react"; 2 2 3 3 export function LucideAtSign(props: SVGProps<SVGSVGElement>) { 4 4 return ( ··· 21 21 <path d="M16 8v5a3 3 0 0 0 6 0v-1a10 10 0 1 0-4 8" /> 22 22 </g> 23 23 </svg> 24 - ) 24 + ); 25 25 }
+2 -2
src/components/Icons/LucideCircleUserRound.tsx
··· 1 - import { SVGProps } from 'react' 1 + import { SVGProps } from "react"; 2 2 3 3 export function LucideCircleUserRound(props: SVGProps<SVGSVGElement>) { 4 4 return ( ··· 22 22 <circle cx="12" cy="12" r="10" /> 23 23 </g> 24 24 </svg> 25 - ) 25 + ); 26 26 }
+2 -2
src/components/Icons/LucideInfo.tsx
··· 1 - import { SVGProps } from 'react' 1 + import { SVGProps } from "react"; 2 2 3 3 export function LucideInfo(props: SVGProps<SVGSVGElement>) { 4 4 return ( ··· 21 21 <path d="M12 16v-4m0-4h.01" /> 22 22 </g> 23 23 </svg> 24 - ) 24 + ); 25 25 }
+2 -2
src/components/Icons/LucideLogIn.tsx
··· 1 - import { SVGProps } from 'react' 1 + import { SVGProps } from "react"; 2 2 3 3 export function LucideLogIn(props: SVGProps<SVGSVGElement>) { 4 4 return ( ··· 19 19 d="m10 17l5-5l-5-5m5 5H3m12-9h4a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2h-4" 20 20 /> 21 21 </svg> 22 - ) 22 + ); 23 23 }
+2 -2
src/components/Icons/LucideSpool.tsx
··· 1 - import { SVGProps } from 'react' 1 + import { SVGProps } from "react"; 2 2 3 3 export function LucideSpool(props: SVGProps<SVGSVGElement>) { 4 4 return ( ··· 21 21 <path d="m7 10.56l12.558-3.642A2 2 0 0 0 19.018 3H5a2 2 0 0 0-.558 3.921l1.115.32A2 2 0 0 1 7 9.163v7.178" /> 22 22 </g> 23 23 </svg> 24 - ) 24 + ); 25 25 }
+7
src/components/Nav/NavBarUnauthed.tsx
··· 1 + export const NavBarUnauthed = () => { 2 + return ( 3 + <div> 4 + <p>Unauthed Nav Bar</p> 5 + </div> 6 + ); 7 + };
+3 -3
src/integrations/tanstack-query/devtools.tsx
··· 1 - import { ReactQueryDevtoolsPanel } from '@tanstack/react-query-devtools' 1 + import { ReactQueryDevtoolsPanel } from "@tanstack/react-query-devtools"; 2 2 3 3 export default { 4 - name: 'Tanstack Query', 4 + name: "Tanstack Query", 5 5 render: <ReactQueryDevtoolsPanel />, 6 - } 6 + };
+6 -6
src/integrations/tanstack-query/root-provider.tsx
··· 1 - import { QueryClient, QueryClientProvider } from '@tanstack/react-query' 1 + import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; 2 2 3 3 export function getContext() { 4 - const queryClient = new QueryClient() 4 + const queryClient = new QueryClient(); 5 5 return { 6 6 queryClient, 7 - } 7 + }; 8 8 } 9 9 10 10 export function Provider({ 11 11 children, 12 12 queryClient, 13 13 }: { 14 - children: React.ReactNode 15 - queryClient: QueryClient 14 + children: React.ReactNode; 15 + queryClient: QueryClient; 16 16 }) { 17 17 return ( 18 18 <QueryClientProvider client={queryClient}> 19 19 {children} 20 20 </QueryClientProvider> 21 - ) 21 + ); 22 22 }
+47 -47
src/lib/consts.ts
··· 1 - const __DEV__oAuthCallbackUrl = 'http://127.0.0.1:8081/login/' 1 + const __DEV__oAuthCallbackUrl = "http://127.0.0.1:8081/login/"; 2 2 3 3 const oAuthScopes = [ 4 - 'atproto', 4 + "atproto", 5 5 6 - 'repo:sh.tangled.publicKey', 7 - 'repo:sh.tangled.repo', 8 - 'repo:sh.tangled.repo.pull', 9 - 'repo:sh.tangled.repo.pull.comment', 10 - 'repo:sh.tangled.repo.artifact', 11 - 'repo:sh.tangled.repo.issue', 12 - 'repo:sh.tangled.repo.issue.comment', 13 - 'repo:sh.tangled.repo.collaborator', 14 - 'repo:sh.tangled.knot', 15 - 'repo:sh.tangled.knot.member', 16 - 'repo:sh.tangled.spindle', 17 - 'repo:sh.tangled.spindle.member', 18 - 'repo:sh.tangled.graph.follow', 19 - 'repo:sh.tangled.feed.star', 20 - 'repo:sh.tangled.feed.reaction', 21 - 'repo:sh.tangled.label.definition', 22 - 'repo:sh.tangled.label.op', 23 - 'repo:sh.tangled.string', 24 - 'repo:sh.tangled.actor.profile', 6 + "repo:sh.tangled.publicKey", 7 + "repo:sh.tangled.repo", 8 + "repo:sh.tangled.repo.pull", 9 + "repo:sh.tangled.repo.pull.comment", 10 + "repo:sh.tangled.repo.artifact", 11 + "repo:sh.tangled.repo.issue", 12 + "repo:sh.tangled.repo.issue.comment", 13 + "repo:sh.tangled.repo.collaborator", 14 + "repo:sh.tangled.knot", 15 + "repo:sh.tangled.knot.member", 16 + "repo:sh.tangled.spindle", 17 + "repo:sh.tangled.spindle.member", 18 + "repo:sh.tangled.graph.follow", 19 + "repo:sh.tangled.feed.star", 20 + "repo:sh.tangled.feed.reaction", 21 + "repo:sh.tangled.label.definition", 22 + "repo:sh.tangled.label.op", 23 + "repo:sh.tangled.string", 24 + "repo:sh.tangled.actor.profile", 25 25 26 - 'blob:*/*', 26 + "blob:*/*", 27 27 28 - 'rpc:sh.tangled.repo.create?aud=*', 29 - 'rpc:sh.tangled.repo.delete?aud=*', 30 - 'rpc:sh.tangled.repo.merge?aud=*', 31 - 'rpc:sh.tangled.repo.hiddenRef?aud=*', 32 - 'rpc:sh.tangled.repo.deleteBranch?aud=*', 33 - 'rpc:sh.tangled.repo.setDefaultBranch?aud=*', 34 - 'rpc:sh.tangled.repo.forkSync?aud=*', 35 - 'rpc:sh.tangled.repo.forkStatus?aud=*', 36 - 'rpc:sh.tangled.repo.mergeCheck?aud=*', 37 - 'rpc:sh.tangled.pipeline.cancelPipeline?aud=*', 38 - 'rpc:sh.tangled.repo.addSecret?aud=*', 39 - 'rpc:sh.tangled.repo.removeSecret?aud=*', 40 - 'rpc:sh.tangled.repo.listSecrets?aud=*', 41 - ] 28 + "rpc:sh.tangled.repo.create?aud=*", 29 + "rpc:sh.tangled.repo.delete?aud=*", 30 + "rpc:sh.tangled.repo.merge?aud=*", 31 + "rpc:sh.tangled.repo.hiddenRef?aud=*", 32 + "rpc:sh.tangled.repo.deleteBranch?aud=*", 33 + "rpc:sh.tangled.repo.setDefaultBranch?aud=*", 34 + "rpc:sh.tangled.repo.forkSync?aud=*", 35 + "rpc:sh.tangled.repo.forkStatus?aud=*", 36 + "rpc:sh.tangled.repo.mergeCheck?aud=*", 37 + "rpc:sh.tangled.pipeline.cancelPipeline?aud=*", 38 + "rpc:sh.tangled.repo.addSecret?aud=*", 39 + "rpc:sh.tangled.repo.removeSecret?aud=*", 40 + "rpc:sh.tangled.repo.listSecrets?aud=*", 41 + ]; 42 42 43 43 const oAuthScopesString = oAuthScopes 44 44 .reduce((prev, curr) => `${prev} ${curr}`) 45 - .trim() 45 + .trim(); 46 46 47 47 export const __DEV__loopbackOAuthMetadata = { 48 48 client_id: `http://localhost?redirect_uri=${encodeURIComponent(__DEV__oAuthCallbackUrl)}&scope=${encodeURIComponent(oAuthScopesString)}`, 49 49 redirect_uris: [__DEV__oAuthCallbackUrl], 50 50 scope: oAuthScopesString, 51 - token_endpoint_auth_method: 'none', 52 - response_types: ['code'], 53 - grant_types: ['authorization_code', 'refresh_token'], 54 - application_type: 'web', 51 + token_endpoint_auth_method: "none", 52 + response_types: ["code"], 53 + grant_types: ["authorization_code", "refresh_token"], 54 + application_type: "web", 55 55 dpop_bound_access_tokens: true, 56 - subject_type: 'public', 57 - client_name: 'Strand Localhost', 58 - } 56 + subject_type: "public", 57 + client_name: "Strand Localhost", 58 + }; 59 59 60 - export const DEFAULT_STALE_TIME = 5 * 60 * 1000 60 + export const DEFAULT_STALE_TIME = 5 * 60 * 1000; 61 61 62 62 export const CONSTELLATION_URL = new URL( 63 - 'https://constellation.microcosm.blue/', 64 - ) 63 + "https://constellation.microcosm.blue/", 64 + );
+2 -2
src/lib/styles/theme.ts
··· 1 1 // TODO: restrict key to our expected strings 2 2 export const impurelyApplyThemeOverride = (key: string, value: string) => { 3 - document.documentElement.style.setProperty(`--color-${key}`, value); 4 - } 3 + document.documentElement.style.setProperty(`--color-${key}`, value); 4 + };
+10 -10
src/router.tsx
··· 1 - import { createRouter } from '@tanstack/react-router' 2 - import { setupRouterSsrQueryIntegration } from '@tanstack/react-router-ssr-query' 3 - import * as TanstackQuery from './integrations/tanstack-query/root-provider' 1 + import { createRouter } from "@tanstack/react-router"; 2 + import { setupRouterSsrQueryIntegration } from "@tanstack/react-router-ssr-query"; 3 + import * as TanstackQuery from "./integrations/tanstack-query/root-provider"; 4 4 5 5 // Import the generated route tree 6 - import { routeTree } from './routeTree.gen' 6 + import { routeTree } from "./routeTree.gen"; 7 7 8 8 // Create a new router instance 9 9 export const getRouter = () => { 10 - const rqContext = TanstackQuery.getContext() 10 + const rqContext = TanstackQuery.getContext(); 11 11 12 12 const router = createRouter({ 13 13 routeTree, ··· 15 15 ...rqContext, 16 16 }, 17 17 18 - defaultPreload: 'intent', 19 - }) 18 + defaultPreload: "intent", 19 + }); 20 20 21 21 setupRouterSsrQueryIntegration({ 22 22 router, 23 23 queryClient: rqContext.queryClient, 24 - }) 24 + }); 25 25 26 - return router 27 - } 26 + return router; 27 + };
+16 -16
src/routes/__root.tsx
··· 2 2 HeadContent, 3 3 Scripts, 4 4 createRootRouteWithContext, 5 - } from '@tanstack/react-router' 6 - import { TanStackRouterDevtoolsPanel } from '@tanstack/react-router-devtools' 7 - import { TanStackDevtools } from '@tanstack/react-devtools' 5 + } from "@tanstack/react-router"; 6 + import { TanStackRouterDevtoolsPanel } from "@tanstack/react-router-devtools"; 7 + import { TanStackDevtools } from "@tanstack/react-devtools"; 8 8 9 - import TanStackQueryDevtools from '../integrations/tanstack-query/devtools' 9 + import TanStackQueryDevtools from "../integrations/tanstack-query/devtools"; 10 10 11 - import appCss from '../styles.css?url' 11 + import appCss from "../styles.css?url"; 12 12 13 - import type { QueryClient } from '@tanstack/react-query' 13 + import type { QueryClient } from "@tanstack/react-query"; 14 14 15 15 interface MyRouterContext { 16 - queryClient: QueryClient 16 + queryClient: QueryClient; 17 17 } 18 18 19 19 export const Route = createRootRouteWithContext<MyRouterContext>()({ 20 20 head: () => ({ 21 21 meta: [ 22 22 { 23 - charSet: 'utf-8', 23 + charSet: "utf-8", 24 24 }, 25 25 { 26 - name: 'viewport', 27 - content: 'width=device-width, initial-scale=1', 26 + name: "viewport", 27 + content: "width=device-width, initial-scale=1", 28 28 }, 29 29 { 30 - title: 'Strand', 30 + title: "Strand", 31 31 }, 32 32 ], 33 33 links: [ 34 34 { 35 - rel: 'stylesheet', 35 + rel: "stylesheet", 36 36 href: appCss, 37 37 }, 38 38 ], 39 39 }), 40 40 41 41 shellComponent: RootDocument, 42 - }) 42 + }); 43 43 44 44 function RootDocument({ children }: { children: React.ReactNode }) { 45 45 return ( ··· 51 51 {children} 52 52 <TanStackDevtools 53 53 config={{ 54 - position: 'bottom-right', 54 + position: "bottom-right", 55 55 }} 56 56 plugins={[ 57 57 { 58 - name: 'Tanstack Router', 58 + name: "Tanstack Router", 59 59 render: <TanStackRouterDevtoolsPanel />, 60 60 }, 61 61 TanStackQueryDevtools, ··· 64 64 <Scripts /> 65 65 </body> 66 66 </html> 67 - ) 67 + ); 68 68 }
+4 -4
src/routes/_authed.tsx
··· 1 - import { createFileRoute, Outlet } from '@tanstack/react-router' 1 + import { createFileRoute, Outlet } from "@tanstack/react-router"; 2 2 3 - export const Route = createFileRoute('/_authed')({ 3 + export const Route = createFileRoute("/_authed")({ 4 4 component: RouteComponent, 5 - }) 5 + }); 6 6 7 7 function RouteComponent() { 8 8 return ( ··· 10 10 <p>Hello "/_authed"!</p> 11 11 <Outlet /> 12 12 </div> 13 - ) 13 + ); 14 14 }
+4 -4
src/routes/_authed/oauth/callback.tsx
··· 1 - import { createFileRoute } from '@tanstack/react-router' 1 + import { createFileRoute } from "@tanstack/react-router"; 2 2 3 - export const Route = createFileRoute('/_authed/oauth/callback')({ 3 + export const Route = createFileRoute("/_authed/oauth/callback")({ 4 4 component: RouteComponent, 5 - }) 5 + }); 6 6 7 7 function RouteComponent() { 8 - return <div>Hello "/reserved/oauth/callback"!</div> 8 + return <div>Hello "/reserved/oauth/callback"!</div>; 9 9 }
+5 -5
src/routes/index.tsx
··· 1 - import { createFileRoute, Link } from '@tanstack/react-router' 1 + import { createFileRoute, Link } from "@tanstack/react-router"; 2 2 3 - export const Route = createFileRoute('/')({ component: App }) 3 + export const Route = createFileRoute("/")({ component: App }); 4 4 5 5 function App() { 6 6 return ( 7 - <div className="min-w-screen flex items-center justify-center pt-8 flex-col gap-4"> 7 + <div className="flex min-w-screen flex-col items-center justify-center gap-4 pt-8"> 8 8 <h1 className="text-xl font-bold"> 9 9 The better frontend for the better forge. 10 10 </h1> 11 11 <Link 12 12 to="/login" 13 - className="transition-all hover:bg-overlay0 bg-surface0 text-text p-2 rounded-xs" 13 + className="hover:bg-overlay0 bg-surface0 text-text rounded-xs p-2 transition-all" 14 14 > 15 15 Sign in 16 16 </Link> 17 17 </div> 18 - ) 18 + ); 19 19 }
+11 -7
src/routes/login.tsx
··· 1 - import { SignIn } from '@/components/Auth/SignIn' 2 - import { createFileRoute } from '@tanstack/react-router' 1 + import { SignIn } from "@/components/Auth/SignIn"; 2 + import { NavBarUnauthed } from "@/components/Nav/NavBarUnauthed"; 3 + import { createFileRoute } from "@tanstack/react-router"; 3 4 4 - export const Route = createFileRoute('/login')({ 5 + export const Route = createFileRoute("/login")({ 5 6 component: RouteComponent, 6 - }) 7 + }); 7 8 8 9 function RouteComponent() { 9 10 return ( 10 - <div className="min-w-screen flex items-center justify-center pt-8 flex-col gap-4"> 11 - <SignIn /> 11 + <div className="flex min-w-screen flex-col items-center"> 12 + <NavBarUnauthed /> 13 + <div className="flex w-full justify-center pt-8"> 14 + <SignIn /> 15 + </div> 12 16 </div> 13 - ) 17 + ); 14 18 }
+8 -8
src/styles.css
··· 1 - @import 'tailwindcss'; 1 + @import "tailwindcss"; 2 2 3 - @import '@fontsource-variable/hanken-grotesk'; 4 - @import '@fontsource/amiri'; 5 - @import '@fontsource/maple-mono'; 6 - @import '@fontsource/maple-mono/400-italic.css'; 3 + @import "@fontsource-variable/hanken-grotesk"; 4 + @import "@fontsource/amiri"; 5 + @import "@fontsource/maple-mono"; 6 + @import "@fontsource/maple-mono/400-italic.css"; 7 7 8 8 @theme { 9 - --font-sans: 'Hanken Grotesk Variable', sans-serif; 10 - --font-serif: 'Amiri', serif; 11 - --font-mono: 'Maple Mono', monospace; 9 + --font-sans: "Hanken Grotesk Variable", sans-serif; 10 + --font-serif: "Amiri", serif; 11 + --font-mono: "Maple Mono", monospace; 12 12 13 13 --color-crust: oklch(0.1286 0 0); 14 14 --color-mantle: oklch(0.1776 0 0);