adding zap modal

This commit is contained in:
zmeyer44 2023-10-16 19:40:56 -04:00
parent 4af75fda4f
commit ae64e536dc
9 changed files with 239 additions and 62 deletions

View File

@ -1,3 +1,5 @@
"use client";
import Link from "next/link";
import {
RiHome6Fill,
@ -17,14 +19,36 @@ import {
TooltipProvider,
TooltipTrigger,
} from "@/components/ui/tooltip";
import ZapPicker from "@/components/Modals/ZapPicker";
import { useModal } from "@/app/_providers/modal/provider";
import { IconType } from "react-icons";
type NavigationLink = {
type: "link";
href: string;
};
type NavigationButton = {
type: "button";
onClick: () => void;
};
type NavigationElement = {
name: string;
label: string;
icon: IconType;
current: boolean;
active: boolean;
} & (NavigationLink | NavigationButton);
export default function Sidebar() {
const navigation = [
const modal = useModal();
const navigation: NavigationElement[] = [
{
href: "",
name: "home",
label: "Home",
icon: RiHome6Fill,
type: "link",
current: true,
active: true,
},
@ -33,6 +57,7 @@ export default function Sidebar() {
name: "explore",
label: "Explore",
icon: RiCompassLine,
type: "link",
current: false,
active: false,
},
@ -41,14 +66,16 @@ export default function Sidebar() {
name: "messages",
label: "Messages",
icon: RiQuestionAnswerLine,
type: "link",
current: false,
active: false,
},
{
href: "",
onClick: () => modal?.show(<ZapPicker />),
name: "zap",
label: "Zap Flockstr",
icon: HiOutlineLightningBolt,
type: "button",
current: false,
active: true,
},
@ -59,62 +86,123 @@ export default function Sidebar() {
<div className="flex flex-1 flex-col">
<div className="flex flex-col items-stretch gap-y-2 p-4">
{navigation.map((item) => {
if (item.active) {
return (
<Link
key={item.name}
href={item.href}
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</Link>
);
if (item.type === "link") {
if (item.active) {
return (
<Link
key={item.name}
href={item.href}
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</Link>
);
} else {
return (
<TooltipProvider key={item.name}>
<Tooltip delayDuration={100}>
<TooltipTrigger>
<div
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</div>
</TooltipTrigger>
<TooltipContent align="start">
<p>Coming Soon</p>
</TooltipContent>
</Tooltip>
</TooltipProvider>
);
}
} else {
return (
<TooltipProvider key={item.name}>
<Tooltip delayDuration={100}>
<TooltipTrigger>
<div
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</div>
</TooltipTrigger>
<TooltipContent align="start">
<p>Coming Soon</p>
</TooltipContent>
</Tooltip>
</TooltipProvider>
);
if (item.active) {
return (
<button
key={item.name}
onClick={item.onClick}
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</button>
);
} else {
return (
<TooltipProvider key={item.name}>
<Tooltip delayDuration={100}>
<TooltipTrigger>
<div
className={cn(
"center group relative min-h-[48px] min-w-[48px] rounded-lg hover:bg-muted xl:justify-start xl:gap-x-4 xl:p-2.5",
item.current
? "text-foreground"
: "text-muted-foreground hover:text-foreground",
)}
>
<item.icon
className={cn("h-6 w-6 shrink-0")}
aria-hidden="true"
/>
<span className="hidden text-base xl:flex">
{item.label}
</span>
</div>
</TooltipTrigger>
<TooltipContent align="start">
<p>Coming Soon</p>
</TooltipContent>
</Tooltip>
</TooltipProvider>
);
}
}
})}
<div className="center py-2 xl:justify-start">
<Button size={"icon"} className="xl:hidden">
<Button
onClick={() => modal?.show(<ZapPicker />)}
size={"icon"}
className="xl:hidden"
>
<RiAddFill className="h-6 w-6" />
</Button>
<Button size={"lg"} className="hidden xl:flex">
<Button
onClick={() => modal?.show(<ZapPicker />)}
size={"lg"}
className="hidden xl:flex"
>
<div className="center gap-x-1.5">
<RiAddFill className="h-6 w-6" />
<span>Add Note</span>

View File

@ -55,7 +55,7 @@ export default function AuthActions() {
<>
<Button
onClick={() => modal?.show(<LoginModal />)}
className="rounded-sm px-5"
className="rounded-sm px-5 font-medium"
>
Login
</Button>
@ -154,7 +154,7 @@ export function Relays() {
{ndk?.explicitRelayUrls?.map((r) => (
<DropdownMenuGroup key={r}>
<DropdownMenuItem className="flex items-center gap-x-2 overflow-hidden">
<StatusIndicator status="offline" />
<StatusIndicator status="online" />
<span className="w-full truncate">{r}</span>
</DropdownMenuItem>
</DropdownMenuGroup>

View File

@ -4,7 +4,7 @@ import Link from "next/link";
export default function LandingPage() {
return (
<div className="h-[calc(100svh_-_var(--header-height))] p-2 lg:p-5">
<div className="min-h-[calc(100svh_-_var(--header-height))] p-2 lg:p-5">
<section className="flex h-full w-full flex-col items-center gap-3">
<div className="flex h-full w-full flex-col items-center gap-y-12 rounded-[35px] bg-black p-6 pt-20 @container md:p-20 md:py-20">
<div className="flex flex-col gap-y-6 text-center md:self-start md:pb-4 lg:max-w-md lg:text-left">

View File

@ -55,6 +55,12 @@
--header-height: 72px;
--bottom-nav-height: 56px;
}
/* @media (min-width: 640px) {
:root {
--header-height: 64px;
}
} */
@media all and (display-mode: standalone) {
:root {
--bottom-nav-height: 76px;

BIN
bun.lockb

Binary file not shown.

View File

@ -37,15 +37,15 @@ export default function CreatorCard({
fill
unoptimized
/>
<div className="absolute inset-0 bg-background/60 backdrop-blur-md transition-all">
<div className="absolute inset-0 bg-zinc-800/20 backdrop-blur-lg transition-all">
<div className="group relative flex h-full w-full flex-col items-center justify-end transition-all">
<CardHeader className="absolute inset-x-0 top-[59%] transform pt-4 text-center transition-all duration-300 group-hover:top-[8px] group-hover:ml-[75px] group-hover:text-left">
<Link href={`/${npub}`}>
<CardTitle className="hover:underline">
<CardTitle className="text-zinc-100 hover:underline">
{getNameToShow({ profile, npub })}
</CardTitle>
</Link>
<CardDescription className="line-clamp-3 group-hover:text-xs">
<CardDescription className="line-clamp-3 text-zinc-200 group-hover:text-xs">
{profile?.about}
</CardDescription>
</CardHeader>

View File

@ -0,0 +1,82 @@
"use client";
import { useState, useRef, useEffect } from "react";
import Template from "./Template";
import { Button } from "@/components/ui/button";
import { useModal } from "@/app/_providers/modal/provider";
import { nip19 } from "nostr-tools";
// import { useKeys } from "@/app/_providers/keysProvider";
import { useNDK } from "@/app/_providers/ndk";
import useCurrentUser from "@/lib/hooks/useCurrentUser";
import { HiOutlineLightningBolt } from "react-icons/hi";
import { RiSubtractFill, RiAddFill } from "react-icons/ri";
import { formatCount } from "@/lib/utils";
const intervals = [
10, 25, 50, 75, 100, 150, 200, 250, 350, 500, 750, 1000, 1250, 1500, 2_000,
2_500, 3_000, 3_500, 4_000, 5_000, 6_000, 7_500, 10_000, 12_500, 15_000,
20_000, 25_000, 30_000, 40_000, 50_000, 75_000, 100_000, 150_000, 200_000,
300_000, 500_000, 750_000, 1_000_000, 1_250_000, 1_500_000, 2_000_000,
];
export default function ZapPicker() {
const { loginWithNip07 } = useNDK();
const { loginWithPubkey, currentUser } = useCurrentUser();
const [isLoading, setIsLoading] = useState(false);
const modal = useModal();
const [sats, setSats] = useState(2000);
function onClick(type: "+" | "-") {
setSats((prev) => {
let index = intervals.findIndex((i) => prev === i);
if (type === "+") {
index++;
} else {
index--;
}
return intervals.at(index) ?? 2000;
});
}
return (
<Template title="Send Zap!" className="md:max-w-[400px]">
<div className="flex flex-col gap-y-5">
<div className="pb-2">
<div className="flex items-center justify-center space-x-2">
<Button
variant="outline"
size="icon"
className="h-8 w-8 shrink-0 rounded-full"
onClick={() => onClick("-")}
disabled={sats <= 10}
>
<RiSubtractFill className="h-4 w-4" />
<span className="sr-only">Decrease</span>
</Button>
<div className="flex-1 text-center">
<div className="text-5xl font-bold tracking-tighter">
{formatCount(sats)}
</div>
<div className="text-[0.70rem] uppercase text-muted-foreground">
Satoshis
</div>
</div>
<Button
variant="outline"
size="icon"
className="h-8 w-8 shrink-0 rounded-full"
onClick={() => onClick("+")}
disabled={sats >= 2_000_000}
>
<RiAddFill className="h-4 w-4" />
<span className="sr-only">Increase</span>
</Button>
</div>
</div>
<Button className="w-full gap-x-1">
<span>Send Zap</span>
<HiOutlineLightningBolt className="h-4 w-4" />
</Button>
</div>
</Template>
);
}

View File

@ -52,8 +52,8 @@ export default function VideoCard({ className, card }: VideoCardProps) {
</div>
<div className="flex-1 space-y-2 text-base">
<h3 className="line-clamp-2 font-medium leading-none">{card.title}</h3>
<div className="flex items-center gap-x-3">
<div className="flex flex-col items-start gap-y-1">
<div className="flex flex-col items-start gap-y-1">
<div className="flex items-center gap-x-3">
{!!startTime && (
<div className="center gap-x-1 text-xs text-muted-foreground">
<RxClock className="h-4 w-4 text-primary" />
@ -76,8 +76,8 @@ export default function VideoCard({ className, card }: VideoCardProps) {
</div>
</div>
</div>
<div className="-mt-1 flex flex-wrap-reverse gap-2 overflow-x-hidden">
{card.tags.slice(0, 4).map((tag) => (
<div className="-mt-1 flex flex-wrap-reverse gap-2 overflow-x-scroll scrollbar-none">
{card.tags.slice(0, 3).map((tag) => (
<Badge key={tag}>{tag}</Badge>
))}
</div>

View File

@ -44,6 +44,7 @@
"react-hook-form": "^7.47.0",
"react-icons": "^4.11.0",
"react-player": "^2.13.0",
"recharts": "^2.9.0",
"sonner": "^1.0.3",
"tailwind-merge": "^1.14.0",
"tailwind-scrollbar": "^3.0.5",