Skip to content

Commit

Permalink
feat: added popover
Browse files Browse the repository at this point in the history
  • Loading branch information
vwh committed Oct 6, 2024
1 parent 5b941a7 commit 8b43843
Show file tree
Hide file tree
Showing 7 changed files with 258 additions and 60 deletions.
125 changes: 125 additions & 0 deletions package-lock.json

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

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
"@radix-ui/react-select": "^2.1.1",
"@radix-ui/react-slider": "^1.2.0",
"@radix-ui/react-slot": "^1.1.0",
"@radix-ui/react-tooltip": "^1.1.3",
"class-variance-authority": "^0.7.0",
"clsx": "^2.1.1",
"html-to-image": "^1.11.11",
Expand Down
28 changes: 17 additions & 11 deletions src/components/icons-dialog.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { useMemo, useState, useCallback } from "react";
import { useStore } from "@/store/useStore";

import { formatText } from "@/lib/formatter";
import type { Icons } from "@/types";

import {
Expand All @@ -13,6 +15,8 @@ import {
} from "@/components/ui/dialog";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Tooltiper } from "./tooltiper";

import * as svgs from "lucide-react";

const ICONS_PER_PAGE = 35;
Expand All @@ -37,15 +41,17 @@ export default function IconsDialog() {
.map((name) => {
const SvgComponent = svgs[name as Icons];
return (
<DialogClose key={name}>
<Button
onClick={() => setSelectedSvgName(name as Icons)}
className="flex h-14 w-14 items-center justify-center rounded-lg transition-all hover:opacity-80 md:h-16 md:w-16"
title={name}
>
<SvgComponent className="h-full w-full" />
</Button>
</DialogClose>
<Tooltiper message={formatText(`${name}`)} key={name}>
<DialogClose>
<Button
aria-label={`Select ${name} icon`}
onClick={() => setSelectedSvgName(name as Icons)}
className="flex h-14 w-14 items-center justify-center rounded-lg transition-all hover:opacity-80 md:h-16 md:w-16"
>
<SvgComponent className="h-full w-full" />
</Button>
</DialogClose>
</Tooltiper>
);
});
return { iconButtons: buttons, totalPages };
Expand All @@ -63,8 +69,8 @@ export default function IconsDialog() {
<Dialog>
<DialogTrigger asChild>
<Button
title="Select icon"
variant="outline"
aria-label="Select Icon"
variant="shine"
className="flex h-12 w-full items-center justify-center gap-2"
>
<SvgComponent />
Expand Down
107 changes: 58 additions & 49 deletions src/components/navbar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { variations } from "@/lib/values";
import { handleDownload } from "@/lib/download";
import type { Icons, SvgSettings } from "@/types";

import { Tooltiper } from "./tooltiper";
import { Button } from "@/components/ui/button";

import { DownloadIcon } from "lucide-react";
Expand Down Expand Up @@ -55,29 +56,31 @@ const VariationButton: React.FC<VariationButtonProps> = React.memo(
);

return (
<button
className="transition-all hover:scale-105 hover:opacity-80"
title="Select template"
type="button"
onClick={onClick}
>
<div className="z-50" style={containerStyle}>
<div style={svgWrapperStyle}>
<SvgComponent
fill={svgSettings.fillColor}
fillOpacity={svgSettings.fillOpacity}
fillRule="evenodd"
stroke={svgSettings.svgColor}
strokeWidth={svgSettings.strokeWidth}
strokeLinecap="round"
strokeLinejoin="round"
width={svgSettings.size}
height={svgSettings.size}
style={svgStyle}
/>
<Tooltiper message="Select Template">
<button
className="transition-all hover:scale-105 hover:opacity-80"
aria-label="Select Template"
type="button"
onClick={onClick}
>
<div className="z-50" style={containerStyle}>
<div style={svgWrapperStyle}>
<SvgComponent
fill={svgSettings.fillColor}
fillOpacity={svgSettings.fillOpacity}
fillRule="evenodd"
stroke={svgSettings.svgColor}
strokeWidth={svgSettings.strokeWidth}
strokeLinecap="round"
strokeLinejoin="round"
width={svgSettings.size}
height={svgSettings.size}
style={svgStyle}
/>
</div>
</div>
</div>
</button>
</button>
</Tooltiper>
);
}
);
Expand Down Expand Up @@ -112,30 +115,34 @@ const Navbar: React.FC = () => {

return (
<nav className="flex h-full w-full items-center justify-between gap-2 border-b-2 p-2">
<a
title="View source code"
href="https://github.com/vwh/icon-editor"
target="_blank"
rel="noreferrer"
className="hidden items-center gap-2 text-xl font-bold hover:animate-pulse md:flex"
>
<img
src="./logo.webp"
title="Icons editor logo"
className="h-10 w-auto"
alt="Logo"
/>
<span>Icons Editor</span>
</a>
<div className="flex gap-1">
<button
className="mx-2 items-center justify-center rounded-lg"
type="button"
title="Random Variation"
onClick={handleRandomClick}
<Tooltiper message="View Source Code">
<a
aria-label="View source code"
href="https://github.com/vwh/icon-editor"
target="_blank"
rel="noreferrer"
className="hidden items-center gap-2 text-xl font-bold hover:animate-pulse md:flex"
>
<svgs.Dices className="h-[25px] w-[25px]" />
</button>
<img
src="./logo.webp"
aria-label="Icons editor logo"
className="h-10 w-auto"
alt="Logo"
/>
<span>Icons Editor</span>
</a>
</Tooltiper>
<div className="flex gap-1">
<Tooltiper message="Random Variation">
<button
className="mx-2 items-center justify-center rounded-lg"
type="button"
aria-label="Random Variation"
onClick={handleRandomClick}
>
<svgs.Dices className="h-[25px] w-[25px]" />
</button>
</Tooltiper>
{variations.map((svgSettings, index) => (
<VariationButton
key={index}
Expand All @@ -145,10 +152,12 @@ const Navbar: React.FC = () => {
/>
))}
</div>
<Button title="Download as PNG" onClick={handleDownload}>
<DownloadIcon className="h-6 w-6" />
<span className="ml-2 font-semibold">Download</span>
</Button>
<Tooltiper message="Download as PNG">
<Button aria-label="Download as PNG" onClick={handleDownload}>
<DownloadIcon className="h-6 w-6" />
<span className="ml-2 font-semibold">Download</span>
</Button>
</Tooltiper>
</nav>
);
};
Expand Down
22 changes: 22 additions & 0 deletions src/components/tooltiper.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import {
Tooltip,
TooltipContent,
TooltipProvider,
TooltipTrigger
} from "@/components/ui/tooltip";

interface TooltipProps {
children: React.ReactNode;
message: string;
}

export function Tooltiper({ children, message }: TooltipProps) {
return (
<TooltipProvider>
<Tooltip>
<TooltipTrigger asChild>{children}</TooltipTrigger>
<TooltipContent>{message}</TooltipContent>
</Tooltip>
</TooltipProvider>
);
}
32 changes: 32 additions & 0 deletions src/components/ui/tooltip.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import * as React from "react";
import * as TooltipPrimitive from "@radix-ui/react-tooltip";

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

const TooltipProvider = TooltipPrimitive.Provider;

const Tooltip = ({ children, ...props }) => (
<TooltipPrimitive.Root delayDuration={100} {...props}>
{children}
</TooltipPrimitive.Root>
);

const TooltipTrigger = TooltipPrimitive.Trigger;

const TooltipContent = React.forwardRef<
React.ElementRef<typeof TooltipPrimitive.Content>,
React.ComponentPropsWithoutRef<typeof TooltipPrimitive.Content>
>(({ className, sideOffset = 4, ...props }, ref) => (
<TooltipPrimitive.Content
ref={ref}
sideOffset={sideOffset}
className={cn(
"z-50 overflow-hidden rounded-md border bg-primary px-3 py-1.5 text-sm text-background shadow-md animate-in fade-in-0 zoom-in-95 data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=closed]:zoom-out-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
className
)}
{...props}
/>
));
TooltipContent.displayName = TooltipPrimitive.Content.displayName;

export { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider };
3 changes: 3 additions & 0 deletions src/lib/formatter.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export function formatText(text: string) {
return text.replace(/([A-Z])/g, " $1").trim();
}

0 comments on commit 8b43843

Please sign in to comment.