From 8b50243bfdb60f491527930f99674a606595762a Mon Sep 17 00:00:00 2001 From: Kinfe Michael Tariku <65047246+Kinfe123@users.noreply.github.com> Date: Tue, 20 Feb 2024 21:18:28 +0300 Subject: [PATCH] fmt on hero (#31) * fmt on landing page * adding cn utils * adding checkmark for copy * fmt fix --- .../_components/copy-to-clipboard.tsx | 13 +++- src/app/(landing)/_components/hover-card.tsx | 77 +++++++++++++++++++ src/app/(landing)/page.tsx | 21 +---- src/server/db/util.ts | 8 ++ 4 files changed, 99 insertions(+), 20 deletions(-) create mode 100644 src/app/(landing)/_components/hover-card.tsx diff --git a/src/app/(landing)/_components/copy-to-clipboard.tsx b/src/app/(landing)/_components/copy-to-clipboard.tsx index ab70ac7..a41ee31 100644 --- a/src/app/(landing)/_components/copy-to-clipboard.tsx +++ b/src/app/(landing)/_components/copy-to-clipboard.tsx @@ -2,17 +2,24 @@ import { Button } from "@/components/ui/button"; import { Input } from "@/components/ui/input"; -import { CopyIcon } from "@radix-ui/react-icons"; +import { cn } from "@/lib/utils"; +import { CopyIcon , CheckIcon} from "@radix-ui/react-icons"; +import { useState } from "react"; import { toast } from "sonner"; export const CopyToClipboard = ({ text }: { text: string }) => { + + const [copied , setCopied] = useState(false) const copyToClipboard = async () => { + setCopied(true) + setTimeout(() => { + setCopied(false) + } , 2000) await navigator.clipboard.writeText(text); toast("Copied to clipboard", { icon: , }); }; - return (
{ className="bg-secondary text-muted-foreground" />
); diff --git a/src/app/(landing)/_components/hover-card.tsx b/src/app/(landing)/_components/hover-card.tsx new file mode 100644 index 0000000..414219c --- /dev/null +++ b/src/app/(landing)/_components/hover-card.tsx @@ -0,0 +1,77 @@ +'use client'; +import { Card, CardDescription, CardHeader, CardTitle } from '@/components/ui/card'; +import React, { type SVGProps, useRef, useState, FC, type ForwardRefExoticComponent, type RefAttributes } from 'react'; + + + +type FeaturesProps = { + name: string; + description: string; + logo: React.ReactNode; +} + +const CardSpotlight = (props: FeaturesProps) => { + const divRef = useRef(null); + const [isFocused, setIsFocused] = useState(false); + const [position, setPosition] = useState({ x: 0, y: 0 }); + const [opacity, setOpacity] = useState(0); + + const handleMouseMove = (e: React.MouseEvent) => { + if (!divRef.current || isFocused) return; + + const div = divRef.current; + const rect = div.getBoundingClientRect(); + + setPosition({ x: e.clientX - rect.left, y: e.clientY - rect.top }); + }; + + const handleFocus = () => { + setIsFocused(true); + setOpacity(1); + }; + + const handleBlur = () => { + setIsFocused(false); + setOpacity(0); + }; + + const handleMouseEnter = () => { + setOpacity(1); + }; + + const handleMouseLeave = () => { + setOpacity(0); + }; + + return ( + + +
+
+ + {props.logo} +
+ + {props.name} + {props.description} + + + + ); +}; + +export default CardSpotlight; diff --git a/src/app/(landing)/page.tsx b/src/app/(landing)/page.tsx index 1ca89c6..483dd3c 100644 --- a/src/app/(landing)/page.tsx +++ b/src/app/(landing)/page.tsx @@ -16,12 +16,7 @@ import { StripeLogo, ReactEmail, } from "./_components/feature-icons"; -import { - Card, - CardDescription, - CardHeader, - CardTitle, -} from "@/components/ui/card"; +import CardSpotlight from "./_components/hover-card"; export const metadata: Metadata = { title: "Next.js Lucia Auth Starter Template", @@ -83,14 +78,14 @@ const features = [ const HomePage = () => { return ( <> -
+
-

+

Next.js Lucia Auth Starter Template

@@ -128,15 +123,7 @@ const HomePage = () => {

{features.map((feature) => ( - -
- -
- - {feature.name} - {feature.description} - -
+ } /> ))}
diff --git a/src/server/db/util.ts b/src/server/db/util.ts index ca4ebe1..2dd957a 100644 --- a/src/server/db/util.ts +++ b/src/server/db/util.ts @@ -1,4 +1,12 @@ import { mysqlTableCreator } from "drizzle-orm/mysql-core"; import { DATABASE_PREFIX as prefix } from "@/lib/constants"; +import { twMerge } from "tailwind-merge"; +import clsx, {type ClassValue } from "clsx"; export const mysqlTable = mysqlTableCreator((name) => `${prefix}_${name}`); + + +export function cn(...inputs: ClassValue[]) { + return twMerge(clsx(inputs)) + } + \ No newline at end of file