Skip to content

Commit

Permalink
feat: add label color on the side toolbar
Browse files Browse the repository at this point in the history
  • Loading branch information
invisal committed Mar 22, 2024
1 parent 253f15c commit 3fd4451
Show file tree
Hide file tree
Showing 8 changed files with 196 additions and 50 deletions.
2 changes: 1 addition & 1 deletion src/app/client/page-client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,5 @@ export default function ClientPageBody() {
return new DatabaseDriver(config.url, config.token as string);
}, []);

return <MainScreen driver={driver} />;
return <MainScreen driver={driver} color="blue" />;
}
5 changes: 4 additions & 1 deletion src/app/client/r/page-client.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
"use client";

import { SavedConnectionLabel } from "@/app/connect/saved-connection-storage";
import MainScreen from "@/components/main-connection";
import RemoteDriver from "@/drivers/remote-driver";
import { useSearchParams } from "next/navigation";
Expand All @@ -8,9 +9,11 @@ import { useMemo } from "react";
export default function ClientPageBody({
token,
name,
color,
}: Readonly<{
token: string;
name: string;
color: SavedConnectionLabel;
}>) {
const params = useSearchParams();

Expand All @@ -24,5 +27,5 @@ export default function ClientPageBody({
return <div>Something wrong</div>;
}

return <MainScreen driver={driver} />;
return <MainScreen driver={driver} color={color} />;
}
9 changes: 8 additions & 1 deletion src/app/client/r/page.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { SavedConnectionLabel } from "@/app/connect/saved-connection-storage";
import { db } from "@/db";
import { database } from "@/db/schema";
import { getSessionFromCookie } from "@/lib/auth";
Expand Down Expand Up @@ -28,5 +29,11 @@ export default async function SessionPage({
return <div>Not found</div>;
}

return <ClientPageBody token={session.id} name={databaseInfo.name ?? ""} />;
return (
<ClientPageBody
token={session.id}
name={databaseInfo.name ?? ""}
color={(databaseInfo?.color as SavedConnectionLabel) ?? "blue"}
/>
);
}
12 changes: 7 additions & 5 deletions src/app/client/s/page-client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,22 @@ import { useMemo } from "react";

export default function ClientPageBody() {
const params = useSearchParams();

const driver = useMemo(() => {
const conn = useMemo(() => {
const connectionParams = params.get("p");
if (!connectionParams) return null;

const conn = SavedConnectionLocalStorage.get(connectionParams);
if (!conn) return null;
return conn;
}, [params]);

const driver = useMemo(() => {
if (!conn) return null;
return new DatabaseDriver(conn.config.url, conn.config.token);
}, [params]);
}, [conn]);

if (!driver) {
return <div>Something wrong</div>;
}

return <MainScreen driver={driver} />;
return <MainScreen driver={driver} color={conn?.label ?? "blue"} />;
}
36 changes: 31 additions & 5 deletions src/components/database-gui.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,27 @@ import {
ResizablePanelGroup,
} from "@/components/ui/resizable";
import { useEffect, useState } from "react";
import SchemaView from "./schema-sidebar";
import WindowTabs, { WindowTabItemProps } from "./windows-tab";
import TableDataContent from "./tabs/table-data-tab";
import useMessageListener from "@/hooks/useMessageListener";
import { MessageChannelName } from "@/messages/const";
import { OpenTabsProps } from "@/messages/openTabs";
import QueryWindow from "@/components/tabs/query-tab";
import SchemaEditorTab from "@/components/tabs/schema-editor-tab";
import { LucideCode, LucideTable, LucideTableProperties } from "lucide-react";
import {
LucideCode,
LucideDatabase,
LucideSettings,
LucideTable,
LucideTableProperties,
} from "lucide-react";
import SidebarTab from "./sidebar-tab";
import SchemaView from "./schema-sidebar";
import { SavedConnectionLabel } from "@/app/connect/saved-connection-storage";

export default function DatabaseGui() {
export default function DatabaseGui({
color,
}: Readonly<{ color: SavedConnectionLabel }>) {
const DEFAULT_WIDTH = 300;

const [defaultWidthPercentage, setDefaultWidthPercentage] = useState(20);
Expand Down Expand Up @@ -101,9 +111,25 @@ export default function DatabaseGui() {
<div className="h-screen w-screen flex flex-col">
<ResizablePanelGroup direction="horizontal">
<ResizablePanel minSize={5} defaultSize={defaultWidthPercentage}>
<SchemaView />
<SidebarTab
color={color}
tabs={[
{
key: "database",
name: "Database",
content: <SchemaView />,
icon: LucideDatabase,
},
{
key: "setting",
name: "Setting",
content: <div className="p-2">Setting</div>,
icon: LucideSettings,
},
]}
/>
</ResizablePanel>
<ResizableHandle withHandle />
<ResizableHandle />
<ResizablePanel defaultSize={100 - defaultWidthPercentage}>
<WindowTabs
tabs={tabs}
Expand Down
28 changes: 22 additions & 6 deletions src/components/main-connection.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,20 @@ import { useRouter } from "next/navigation";
import { SchemaProvider } from "@/context/SchemaProvider";
import ThemeProvider from "@/context/theme-provider";
import { BaseDriver } from "@/drivers/base-driver";
import { SavedConnectionLabel } from "@/app/connect/saved-connection-storage";

export interface ConnectionCredential {
url: string;
token: string;
}

function MainConnection({ driver }: { driver: BaseDriver }) {
function MainConnection({
driver,
color,
}: {
driver: BaseDriver;
color: SavedConnectionLabel;
}) {
useEffect(() => {
return () => {
driver.close();
Expand All @@ -27,7 +34,7 @@ function MainConnection({ driver }: { driver: BaseDriver }) {
<ThemeProvider>
<DatabaseDriverProvider driver={driver}>
<SchemaProvider>
<DatabaseGui />
<DatabaseGui color={color} />
</SchemaProvider>
</DatabaseDriverProvider>
</ThemeProvider>
Expand All @@ -44,7 +51,10 @@ function InvalidSession() {
return <div></div>;
}

function MainConnectionContainer({ driver }: Readonly<{ driver: BaseDriver }>) {
function MainConnectionContainer({
driver,
color,
}: Readonly<{ driver: BaseDriver; color: SavedConnectionLabel }>) {
const router = useRouter();

/**
Expand All @@ -68,7 +78,7 @@ function MainConnectionContainer({ driver }: Readonly<{ driver: BaseDriver }>) {
<>
<AutoCompleteProvider>
<TooltipProvider>
<MainConnection driver={driver} />
<MainConnection driver={driver} color={color} />
</TooltipProvider>
</AutoCompleteProvider>
<ContextMenuHandler />
Expand All @@ -78,6 +88,12 @@ function MainConnectionContainer({ driver }: Readonly<{ driver: BaseDriver }>) {
);
}

export default function MainScreen({ driver }: { driver: BaseDriver }) {
return <MainConnectionContainer driver={driver} />;
export default function MainScreen({
driver,
color,
}: {
driver: BaseDriver;
color: SavedConnectionLabel;
}) {
return <MainConnectionContainer driver={driver} color={color} />;
}
33 changes: 2 additions & 31 deletions src/components/schema-sidebar.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,4 @@
import {
LucidePlus,
LucideSearch,
LucideSun,
LucideSunMoon,
} from "lucide-react";
import { appVersion } from "@/env";
import { useTheme } from "@/context/theme-provider";
import { LucidePlus, LucideSearch } from "lucide-react";
import { useCallback, useState } from "react";
import SchemaList from "./schema-sidebar-list";
import { buttonVariants } from "./ui/button";
Expand All @@ -20,7 +13,6 @@ import { openTabs } from "@/messages/openTabs";

export default function SchemaView() {
const [search, setSearch] = useState("");
const { theme, toggleTheme } = useTheme();

const onNewTable = useCallback(() => {
openTabs({
Expand All @@ -31,7 +23,7 @@ export default function SchemaView() {
}, []);

return (
<div className="flex flex-col h-full overflow-hidden">
<div className="flex flex-col overflow-hidden flex-grow">
<div className="pt-2 px-2 flex h-10 -ml-3">
<div className="bg-secondary rounded overflow-hidden flex items-center ml-3 flex-grow">
<div className="text-sm px-2 h-full flex items-center">
Expand Down Expand Up @@ -71,27 +63,6 @@ export default function SchemaView() {
</DropdownMenuContent>
</DropdownMenu>
</div>

<div className="bg-blue-700 h-8 flex items-center px-2 text-white">
<span>LibSQL</span>
<strong>Studio</strong>
<span className="text-xs ml-2">v{appVersion}</span>
<div className="grow" />
<div
role="button"
className="px-2 flex items-center h-full -mr-2"
tabIndex={-1}
onClick={() => {
toggleTheme();
}}
>
{theme === "dark" ? (
<LucideSun className="w-4 h-4" />
) : (
<LucideSunMoon className="w-4 h-4" />
)}
</div>
</div>
</div>
);
}
121 changes: 121 additions & 0 deletions src/components/sidebar-tab.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
import { SavedConnectionLabel } from "@/app/connect/saved-connection-storage";
import { useTheme } from "@/context/theme-provider";
import { cn } from "@/lib/utils";
import {
LucideArrowLeft,
LucideIcon,
LucideMoon,
LucideSun,
} from "lucide-react";
import Link from "next/link";
import { ReactElement, useState } from "react";

export interface SidebarTabItem {
key: string;
icon: LucideIcon;
name: string;
content: ReactElement;
}

interface SidebarTabProps {
color: SavedConnectionLabel;
tabs: SidebarTabItem[];
}

export default function SidebarTab({ tabs, color }: Readonly<SidebarTabProps>) {
const [selectedIndex, setSelectedIndex] = useState(0);
const { theme, toggleTheme } = useTheme();
const [loadedIndex, setLoadedIndex] = useState(() => {
const a = new Array(tabs.length).fill(false);
a[0] = true;
return a;
});

let bgColor = "bg-blue-500 dark:bg-blue-700";
let textColor = "text-white";

if (color === "red") {
bgColor = "bg-red-500 dark:bg-red-700";
} else if (color === "yellow") {
bgColor = "bg-yellow-400 dark:bg-yellow-500";
textColor = "text-black";
} else if (color === "green") {
bgColor = "bg-green-500 dark:bg-green-600";
} else if (color === "gray") {
bgColor = "bg-gray-500 dark:bg-gray-800";
}

return (
<div className="flex h-full">
<div className={cn("flex-shrink-0 flex flex-col gap-2 pt-6", bgColor)}>
{tabs.map(({ key, name, icon: Icon }, idx) => {
return (
<button
title={name}
key={key}
onClick={() => {
if (!loadedIndex[idx]) {
loadedIndex[idx] = true;
setLoadedIndex([...loadedIndex]);
}

if (idx !== selectedIndex) {
setSelectedIndex(idx);
}
}}
className={
idx === selectedIndex
? "p-2 bg-background cursor-pointer"
: cn("p-2 cursor cursor-pointer", textColor)
}
>
<Icon className="w-7 h-7" />
</button>
);
})}

<div className="grow" />

<Link href="/connect">
<button className={cn("p-2 cursor-pointer", bgColor)}>
<LucideArrowLeft className={cn("w-7 h-7", textColor)} />
</button>
</Link>

<button
className="p-2 rounded-lg mb-2 cursor-pointer"
onClick={() => toggleTheme()}
>
{theme === "dark" ? (
<LucideMoon className={cn("w-7 h-7", textColor)} />
) : (
<LucideSun className={cn("w-7 h-7", textColor)} />
)}
</button>
</div>
<div className="relative flex h-full grow overflow-hidden">
{tabs.map((tab, tabIndex) => {
const selected = selectedIndex === tabIndex;

return (
<div
key={tab.key}
style={{
contentVisibility: selected ? "auto" : "hidden",
zIndex: selected ? 1 : 0,
position: "absolute",
display: "flex",
left: 0,
right: 5,
bottom: 0,
top: 0,
}}
>
{loadedIndex[tabIndex] && tab.content}
</div>
);
})}
</div>
</div>
);
}

0 comments on commit 3fd4451

Please sign in to comment.