magicui
208 строк · 5.2 Кб
1"use client";
2
3import { DropdownMenuTriggerProps } from "@radix-ui/react-dropdown-menu";
4import * as React from "react";
5// import { NpmCommands } from "types/unist";
6
7import { Icons } from "@/components/icons";
8import { Button } from "@/components/ui/button";
9import {
10DropdownMenu,
11DropdownMenuContent,
12DropdownMenuItem,
13DropdownMenuTrigger,
14} from "@/components/ui/dropdown-menu";
15import { Event, trackEvent } from "@/lib/events";
16import { cn } from "@/lib/utils";
17
18interface CopyButtonProps extends React.HTMLAttributes<HTMLButtonElement> {
19value: string;
20src?: string;
21event?: Event["name"];
22}
23
24async function copyToClipboardWithMeta(value: string, event?: Event) {
25navigator.clipboard.writeText(value);
26if (event) {
27trackEvent(event);
28}
29}
30
31export function CopyButton({
32value,
33className,
34src,
35event,
36...props
37}: CopyButtonProps) {
38const [hasCopied, setHasCopied] = React.useState(false);
39
40React.useEffect(() => {
41setTimeout(() => {
42setHasCopied(false);
43}, 2000);
44}, [hasCopied]);
45
46return (
47<Button
48size="icon"
49variant="ghost"
50className={cn(
51"relative z-10 h-6 w-6 text-zinc-50 hover:bg-background/70 hover:text-zinc-50",
52className,
53)}
54onClick={() => {
55copyToClipboardWithMeta(
56value,
57event
58? {
59name: event,
60properties: {
61name: src!,
62code: value,
63},
64}
65: undefined,
66);
67setHasCopied(true);
68}}
69{...props}
70>
71<span className="sr-only">Copy</span>
72{hasCopied ? (
73<Icons.check className="h-3 w-3" />
74) : (
75<Icons.copy className="h-3 w-3" />
76)}
77</Button>
78);
79}
80
81interface CopyWithClassNamesProps extends DropdownMenuTriggerProps {
82value: string;
83classNames: string;
84className?: string;
85}
86
87export function CopyWithClassNames({
88value,
89classNames,
90className,
91...props
92}: CopyWithClassNamesProps) {
93const [hasCopied, setHasCopied] = React.useState(false);
94
95React.useEffect(() => {
96setTimeout(() => {
97setHasCopied(false);
98}, 2000);
99}, [hasCopied]);
100
101const copyToClipboard = React.useCallback((value: string) => {
102copyToClipboardWithMeta(value);
103setHasCopied(true);
104}, []);
105
106return (
107<DropdownMenu>
108<DropdownMenuTrigger asChild>
109<Button
110size="icon"
111variant="ghost"
112className={cn(
113"relative z-10 h-6 w-6 text-zinc-50 hover:bg-zinc-700 hover:text-zinc-50",
114className,
115)}
116>
117{hasCopied ? (
118<Icons.check className="h-3 w-3" />
119) : (
120<Icons.copy className="h-3 w-3" />
121)}
122<span className="sr-only">Copy</span>
123</Button>
124</DropdownMenuTrigger>
125<DropdownMenuContent align="end">
126<DropdownMenuItem onClick={() => copyToClipboard(value)}>
127<Icons.react className="mr-2 h-4 w-4" />
128<span>Component</span>
129</DropdownMenuItem>
130<DropdownMenuItem onClick={() => copyToClipboard(classNames)}>
131<Icons.tailwind className="mr-2 h-4 w-4" />
132<span>Classname</span>
133</DropdownMenuItem>
134</DropdownMenuContent>
135</DropdownMenu>
136);
137}
138
139// interface CopyNpmCommandButtonProps extends DropdownMenuTriggerProps {
140// commands: Required<NpmCommands>;
141// }
142
143// export function CopyNpmCommandButton({
144// commands,
145// className,
146// ...props
147// }: CopyNpmCommandButtonProps) {
148// const [hasCopied, setHasCopied] = React.useState(false);
149
150// React.useEffect(() => {
151// setTimeout(() => {
152// setHasCopied(false);
153// }, 2000);
154// }, [hasCopied]);
155
156// const copyCommand = React.useCallback(
157// (value: string, pm: "npm" | "pnpm" | "yarn") => {
158// copyToClipboardWithMeta(value, {
159// name: "copy_npm_command",
160// properties: {
161// command: value,
162// pm,
163// },
164// });
165// setHasCopied(true);
166// },
167// []
168// );
169
170// return (
171// <DropdownMenu>
172// <DropdownMenuTrigger asChild>
173// <Button
174// size="icon"
175// variant="ghost"
176// className={cn(
177// "relative z-10 h-6 w-6 text-zinc-50 hover:bg-zinc-700 hover:text-zinc-50",
178// className
179// )}
180// >
181// {hasCopied ? (
182// <Icons.check className="h-3 w-3" />
183// ) : (
184// <Icons.copy className="h-3 w-3" />
185// )}
186// <span className="sr-only">Copy</span>
187// </Button>
188// </DropdownMenuTrigger>
189// <DropdownMenuContent align="end">
190// <DropdownMenuItem
191// onClick={() => copyCommand(commands.__npmCommand__, "npm")}
192// >
193// npm
194// </DropdownMenuItem>
195// <DropdownMenuItem
196// onClick={() => copyCommand(commands.__yarnCommand__, "yarn")}
197// >
198// yarn
199// </DropdownMenuItem>
200// <DropdownMenuItem
201// onClick={() => copyCommand(commands.__pnpmCommand__, "pnpm")}
202// >
203// pnpm
204// </DropdownMenuItem>
205// </DropdownMenuContent>
206// </DropdownMenu>
207// );
208// }
209