Skip to content

Commit

Permalink
search dropdown
Browse files Browse the repository at this point in the history
  • Loading branch information
RhysSullivan committed Oct 18, 2024
1 parent 208f420 commit 7471471
Show file tree
Hide file tree
Showing 5 changed files with 284 additions and 10 deletions.
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
"dependencies": {
"@next/env": "^14.2.15",
"@radix-ui/react-icons": "^1.3.0",
"@radix-ui/react-scroll-area": "^1.2.0",
"@radix-ui/react-slot": "^1.1.0",
"@vercel/functions": "^1.4.2",
"@vercel/postgres": "^0.10.0",
Expand Down
154 changes: 151 additions & 3 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

9 changes: 2 additions & 7 deletions src/app/layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { Input } from "@/components/ui/input";
import { Search } from "lucide-react";
import { artSupplies } from "./data";
import Link from "next/link";
import { SearchDropdownComponent } from "@/components/search-dropdown";

const helvetica = localFont({
src: "./fonts/HelveticaNeueLTPro-Md.woff",
Expand Down Expand Up @@ -43,13 +44,7 @@ export default function RootLayout({
NextMaster
</Link>
</div>
<div className="relative">
<Input
placeholder="Search"
className="w-[300px] font-sans font-medium md:w-[450px]"
/>
<Search className="absolute right-2 top-2.5 h-4 w-4 text-muted-foreground" />
</div>
<SearchDropdownComponent />
<div className="flex flex-row justify-between space-x-4">
<Link
href="/order"
Expand Down
82 changes: 82 additions & 0 deletions src/components/search-dropdown.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
"use client";

import { useState } from "react";
import { Input } from "@/components/ui/input";
import { ScrollArea } from "@/components/ui/scroll-area";
import { Search } from "lucide-react";

type Item = {
id: string;
name: string;
icon: string;
};

const items: Item[] = [
{ id: "1", name: "aluminum", icon: "/placeholder.svg?height=40&width=40" },
{
id: "2",
name: "aluminum extrusions",
icon: "/placeholder.svg?height=40&width=40",
},
{
id: "3",
name: "aluminum tubing",
icon: "/placeholder.svg?height=40&width=40",
},
{
id: "4",
name: "allen wrenches",
icon: "/placeholder.svg?height=40&width=40",
},
{
id: "5",
name: "all thread rods",
icon: "/placeholder.svg?height=40&width=40",
},
];

export function SearchDropdownComponent() {
const [searchTerm, setSearchTerm] = useState("");
const [isOpen, setIsOpen] = useState(false);

const filteredItems = items.filter((item) =>
item.name.toLowerCase().includes(searchTerm.toLowerCase()),
);

return (
<div className="relative w-full max-w-sm">
<div className="relative">
<Input
type="text"
placeholder="Search..."
value={searchTerm}
onChange={(e) => {
setSearchTerm(e.target.value);
setIsOpen(e.target.value.length > 0);
}}
className="w-[300px] font-sans font-medium md:w-[450px]"
/>
<Search className="absolute right-2 top-2.5 h-4 w-4 text-muted-foreground" />
</div>
{isOpen && filteredItems.length > 0 && (
<div className="absolute z-10 mt-1 w-full rounded-md border border-gray-200 bg-white shadow-lg">
<ScrollArea className="h-[300px]">
{filteredItems.map((item) => (
<div
key={item.id}
className="flex cursor-pointer items-center p-2 hover:bg-gray-100"
onClick={() => {
setSearchTerm(item.name);
setIsOpen(false);
}}
>
<img src={item.icon} alt="" className="mr-2 h-10 w-10" />
<span>{item.name}</span>
</div>
))}
</ScrollArea>
</div>
)}
</div>
);
}
48 changes: 48 additions & 0 deletions src/components/ui/scroll-area.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
"use client"

import * as React from "react"
import * as ScrollAreaPrimitive from "@radix-ui/react-scroll-area"

import { cn } from "@/lib/utils"

const ScrollArea = React.forwardRef<
React.ElementRef<typeof ScrollAreaPrimitive.Root>,
React.ComponentPropsWithoutRef<typeof ScrollAreaPrimitive.Root>
>(({ className, children, ...props }, ref) => (
<ScrollAreaPrimitive.Root
ref={ref}
className={cn("relative overflow-hidden", className)}
{...props}
>
<ScrollAreaPrimitive.Viewport className="h-full w-full rounded-[inherit]">
{children}
</ScrollAreaPrimitive.Viewport>
<ScrollBar />
<ScrollAreaPrimitive.Corner />
</ScrollAreaPrimitive.Root>
))
ScrollArea.displayName = ScrollAreaPrimitive.Root.displayName

const ScrollBar = React.forwardRef<
React.ElementRef<typeof ScrollAreaPrimitive.ScrollAreaScrollbar>,
React.ComponentPropsWithoutRef<typeof ScrollAreaPrimitive.ScrollAreaScrollbar>
>(({ className, orientation = "vertical", ...props }, ref) => (
<ScrollAreaPrimitive.ScrollAreaScrollbar
ref={ref}
orientation={orientation}
className={cn(
"flex touch-none select-none transition-colors",
orientation === "vertical" &&
"h-full w-2.5 border-l border-l-transparent p-[1px]",
orientation === "horizontal" &&
"h-2.5 flex-col border-t border-t-transparent p-[1px]",
className
)}
{...props}
>
<ScrollAreaPrimitive.ScrollAreaThumb className="relative flex-1 rounded-full bg-border" />
</ScrollAreaPrimitive.ScrollAreaScrollbar>
))
ScrollBar.displayName = ScrollAreaPrimitive.ScrollAreaScrollbar.displayName

export { ScrollArea, ScrollBar }

0 comments on commit 7471471

Please sign in to comment.