From 154efe17421ca96d433fcc1f820ad460e1675bdc Mon Sep 17 00:00:00 2001 From: Mohamed Bassem Date: Sat, 26 Jul 2025 12:58:01 +0000 Subject: feat: Configurable number of grid columns. Fixes #1713 --- apps/web/components/dashboard/ViewOptions.tsx | 115 ++++++++++++++++++++++++++ 1 file changed, 115 insertions(+) create mode 100644 apps/web/components/dashboard/ViewOptions.tsx (limited to 'apps/web/components/dashboard/ViewOptions.tsx') diff --git a/apps/web/components/dashboard/ViewOptions.tsx b/apps/web/components/dashboard/ViewOptions.tsx new file mode 100644 index 00000000..6367421f --- /dev/null +++ b/apps/web/components/dashboard/ViewOptions.tsx @@ -0,0 +1,115 @@ +"use client"; + +import React from "react"; +import { ButtonWithTooltip } from "@/components/ui/button"; +import { + DropdownMenu, + DropdownMenuContent, + DropdownMenuItem, + DropdownMenuSeparator, + DropdownMenuTrigger, +} from "@/components/ui/dropdown-menu"; +import { Slider } from "@/components/ui/slider"; +import { + useBookmarkLayout, + useGridColumns, +} from "@/lib/userLocalSettings/bookmarksLayout"; +import { + updateBookmarksLayout, + updateGridColumns, +} from "@/lib/userLocalSettings/userLocalSettings"; +import { + Check, + LayoutDashboard, + LayoutGrid, + LayoutList, + List, + LucideIcon, + Settings, +} from "lucide-react"; + +type LayoutType = "masonry" | "grid" | "list" | "compact"; + +const iconMap: Record = { + masonry: LayoutDashboard, + grid: LayoutGrid, + list: LayoutList, + compact: List, +}; + +const layoutNames: Record = { + masonry: "Masonry", + grid: "Grid", + list: "List", + compact: "Compact", +}; + +export default function ViewOptions() { + const layout = useBookmarkLayout(); + const gridColumns = useGridColumns(); + const [tempColumns, setTempColumns] = React.useState(gridColumns); + + const showColumnSlider = layout === "grid" || layout === "masonry"; + + // Update temp value when actual value changes + React.useEffect(() => { + setTempColumns(gridColumns); + }, [gridColumns]); + + return ( + + + + + + + +
Layout
+ {(Object.keys(iconMap) as LayoutType[]).map((key) => ( + await updateBookmarksLayout(key as LayoutType)} + > +
+ {React.createElement(iconMap[key as LayoutType], { size: 18 })} + {layoutNames[key]} +
+ {layout === key && } +
+ ))} + + {showColumnSlider && ( + <> + +
+
+ Columns + + {tempColumns} + +
+ setTempColumns(value)} + onValueCommit={([value]) => updateGridColumns(value)} + min={1} + max={6} + step={1} + className="w-full" + /> +
+ 1 + 6 +
+
+ + )} +
+
+ ); +} -- cgit v1.2.3-70-g09d2