mirror of
https://github.com/ClipFusion-org/clipfusion.git
synced 2025-08-03 14:45:09 +00:00
settings page redesign
This commit is contained in:
parent
c262d07c1a
commit
efc16d554f
@ -48,7 +48,7 @@ export default async function RootLayout({
|
||||
<ThemeProvider>
|
||||
<SidebarProvider>
|
||||
<Dashboard/>
|
||||
<main className="relative mt-safe">
|
||||
<main className="relative mt-safe h-screen">
|
||||
<PersistenceProvider>
|
||||
{children}
|
||||
</PersistenceProvider>
|
||||
|
@ -3,57 +3,51 @@ import { Button } from "@/components/ui/button";
|
||||
import { Label } from "@/components/ui/label";
|
||||
import { SidebarTrigger } from "@/components/ui/sidebar";
|
||||
import { Tooltip, TooltipContent, TooltipTrigger } from "@/components/ui/tooltip";
|
||||
import { InfoIcon } from "lucide-react";
|
||||
import { ChartPieIcon, InfoIcon } from "lucide-react";
|
||||
import { ReactNode, useEffect, useState } from "react";
|
||||
import { usePersistenceContext } from "../persistence-provider";
|
||||
import StaticSidebarTrigger from "@/components/static-sidebar-trigger";
|
||||
import ScrollFadingTitle from "@/components/scroll-fading-title";
|
||||
|
||||
function PersistentStorageControl({
|
||||
status
|
||||
}: {
|
||||
status: string | null
|
||||
}): ReactNode {
|
||||
const { persist } = usePersistenceContext();
|
||||
if (status == null) return <Label className="text-muted-foreground">No information</Label>;
|
||||
if (status == "never") return <Label className="text-red-500">Unavailable</Label>;
|
||||
if (status == "prompt") return <Button onClick={persist}>Enable</Button>;
|
||||
return <Label className="text-green-400">Enabled</Label>;
|
||||
};
|
||||
import SidebarTriggerAdjustable from "@/components/sidebar-trigger-adjustable";
|
||||
import Search from "@/components/search";
|
||||
import { useIsMobile } from "@/hooks/use-mobile";
|
||||
import { cn } from "@/lib/utils";
|
||||
import AscendingCard from "@/components/ascending-card";
|
||||
import Link from "next/link";
|
||||
|
||||
export default function Settings(): ReactNode {
|
||||
const [status, setStatus] = useState<string | null>(null);
|
||||
const isMobile = useIsMobile();
|
||||
|
||||
useEffect(() => {
|
||||
setStatus(localStorage.getItem("persistence-status"));
|
||||
}, []);
|
||||
const SearchContainer = isMobile ? "div" : SidebarTriggerAdjustable;
|
||||
const cardWidth = isMobile ? "w-full" : "w-2xl";
|
||||
|
||||
return (
|
||||
<div className="p-5 w-full">
|
||||
<div className="flex flex-row items-center gap-2">
|
||||
<StaticSidebarTrigger/>
|
||||
<ScrollFadingTitle>
|
||||
<h2 className="font-bold break-keep text-xl sm:text-2xl md:text-3xl lg:text-4xl leading-none">Settings</h2>
|
||||
</ScrollFadingTitle>
|
||||
</div>
|
||||
<div className="flex flex-col gap-1 md:lg:gap-2 mt-2 md:mt-4 lg:mt-5">
|
||||
<h3 className="font-semibold break-keep text-lg sm:text-xl md:text-2xl lg:text-3xl leading-none">Storage</h3>
|
||||
<div className="">
|
||||
<div className="flex flex-row justify-between items-center w-full max-w-96">
|
||||
<div className="flex flex-row gap-2 items-center">
|
||||
<Label>Persistent Storage</Label>
|
||||
<Tooltip>
|
||||
<TooltipTrigger>
|
||||
<InfoIcon size="15" className="opacity-60 hover:opacity-80"/>
|
||||
</TooltipTrigger>
|
||||
<TooltipContent>
|
||||
Persistent storage prevents browser from deleting your local data to free up space for other websites.
|
||||
</TooltipContent>
|
||||
</Tooltip>
|
||||
</div>
|
||||
<PersistentStorageControl status={status}/>
|
||||
</div>
|
||||
<div className="p-5 w-full h-full">
|
||||
<div className="flex flex-col gap-2">
|
||||
<div className="flex flex-row items-center gap-2">
|
||||
<StaticSidebarTrigger />
|
||||
<ScrollFadingTitle>
|
||||
<h2 className="font-bold break-keep text-xl sm:text-2xl md:text-3xl lg:text-4xl leading-none">Settings</h2>
|
||||
</ScrollFadingTitle>
|
||||
</div>
|
||||
<div className="flex flex-col sticky top-safe bg-background gap-2 mt-2 pb-2 pt-2 p-5 w-[100% + 5 * var(--spacing)] z-10 -mx-5">
|
||||
<SearchContainer className={cn("flex justify-center",)}>
|
||||
<Search placeholder="Search Settings" className={cardWidth} />
|
||||
</SearchContainer>
|
||||
</div>
|
||||
</div>
|
||||
<div className="flex flex-col justify-center items-center w-full gap-1 md:lg:gap-2 mt-2">
|
||||
<Link href="/settings/storage" className="w-full flex items-center justify-center">
|
||||
<AscendingCard className={`flex flex-row gap-3 p-3 ${cardWidth}`}>
|
||||
<div className="flex items-center justify-center">
|
||||
<ChartPieIcon />
|
||||
</div>
|
||||
<div className="flex flex-col items-start">
|
||||
<h3 className="font-semibold break-keep text-lg sm:text-xl">Storage</h3>
|
||||
<p className="text-sm text-secondary-foreground">Memory usage, media, cache etc.</p>
|
||||
</div>
|
||||
</AscendingCard>
|
||||
</Link>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
67
src/app/settings/storage/page.tsx
Normal file
67
src/app/settings/storage/page.tsx
Normal file
@ -0,0 +1,67 @@
|
||||
"use client";
|
||||
import { usePersistenceContext } from "@/app/persistence-provider";
|
||||
import ScrollFadingTitle from "@/components/scroll-fading-title";
|
||||
import Search from "@/components/search";
|
||||
import SidebarTriggerAdjustable from "@/components/sidebar-trigger-adjustable";
|
||||
import StaticSidebarTrigger from "@/components/static-sidebar-trigger";
|
||||
import { Button } from "@/components/ui/button";
|
||||
import { Label } from "@/components/ui/label";
|
||||
import { useIsMobile } from "@/hooks/use-mobile";
|
||||
import { cn } from "@/lib/utils";
|
||||
import { ArrowLeftIcon } from "lucide-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { ReactNode, useEffect, useState } from "react";
|
||||
|
||||
function PersistentStorageControl({
|
||||
status
|
||||
}: {
|
||||
status: string | null
|
||||
}): ReactNode {
|
||||
const { persist } = usePersistenceContext();
|
||||
if (status == null) return <Label className="text-muted-foreground">No information</Label>;
|
||||
if (status == "never") return <Label className="text-red-500">Unavailable</Label>;
|
||||
if (status == "prompt") return <Button onClick={persist}>Enable</Button>;
|
||||
return <Label className="text-green-400">Enabled</Label>;
|
||||
};
|
||||
|
||||
export default function Storage() {
|
||||
const [status, setStatus] = useState<string | null>(null);
|
||||
const router = useRouter();
|
||||
const isMobile = useIsMobile();
|
||||
|
||||
useEffect(() => {
|
||||
setStatus(localStorage.getItem("persistence-status"));
|
||||
}, []);
|
||||
|
||||
const SearchContainer = isMobile ? "div" : SidebarTriggerAdjustable;
|
||||
const cardWidth = isMobile ? "w-full" : "w-2xl";
|
||||
|
||||
return (
|
||||
<div className="p-5 w-full h-screen">
|
||||
<div className="flex flex-col gap-2">
|
||||
<div className="flex flex-row items-center gap-2">
|
||||
<StaticSidebarTrigger>
|
||||
<Button className="fixed size-7 ml-10 z-40 transition-colors" variant="ghost" size="icon" onClick={() => router.back()}>
|
||||
<ArrowLeftIcon/>
|
||||
</Button>
|
||||
</StaticSidebarTrigger>
|
||||
<ScrollFadingTitle className="flex flex-row items-center">
|
||||
<div className="ml-10"/>
|
||||
<h2 className="font-bold break-keep text-xl sm:text-2xl md:text-3xl lg:text-4xl leading-none">Storage</h2>
|
||||
</ScrollFadingTitle>
|
||||
</div>
|
||||
<div className="flex flex-col sticky top-safe bg-background gap-2 mt-2 pb-2 pt-2 p-5 w-[100% + 5 * var(--spacing)] z-10 -mx-5">
|
||||
<SearchContainer className={cn("flex justify-center", cardWidth)}>
|
||||
<Search placeholder="Search Settings" className={cardWidth} />
|
||||
</SearchContainer>
|
||||
</div>
|
||||
</div>
|
||||
<div className="flex flex-row justify-between items-center w-full max-w-96">
|
||||
<div className="flex flex-row gap-2 items-center">
|
||||
<Label>Persistent Storage</Label>
|
||||
</div>
|
||||
<PersistentStorageControl status={status} />
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
7
src/components/ascending-card/AscendingCard.tsx
Normal file
7
src/components/ascending-card/AscendingCard.tsx
Normal file
@ -0,0 +1,7 @@
|
||||
import { ComponentProps } from "react";
|
||||
import { Card } from "../ui/card";
|
||||
import { cn } from "@/lib/utils";
|
||||
|
||||
export const AscendingCard = (props: ComponentProps<typeof Card>) => (
|
||||
<Card {...props} className={cn("shadow-md hover:scale-[101%] hover:drop-shadow-xl duration-100", props.className)}/>
|
||||
);
|
3
src/components/ascending-card/index.ts
Normal file
3
src/components/ascending-card/index.ts
Normal file
@ -0,0 +1,3 @@
|
||||
import { AscendingCard } from "./AscendingCard";
|
||||
|
||||
export default AscendingCard;
|
@ -1,12 +1,18 @@
|
||||
"use client";
|
||||
import { ReactNode } from "react";
|
||||
import { SidebarTrigger } from "../ui/sidebar";
|
||||
|
||||
export const StaticSidebarTrigger = () => {
|
||||
export const StaticSidebarTrigger = ({
|
||||
children
|
||||
}: {
|
||||
children?: ReactNode
|
||||
}) => {
|
||||
return (
|
||||
<>
|
||||
<div className="ml-10"/>
|
||||
<div className="absolute top-0 left-0 pl-6 pt-4 md:p-6 overscroll-auto">
|
||||
<SidebarTrigger className={`fixed mr-2 z-40 transition-colors`} size="lg" tabIndex={0}/>
|
||||
{children}
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
|
Loading…
Reference in New Issue
Block a user