Scrapboard.org client
1import { useAuth } from "@/lib/hooks/useAuth";
2import { Button } from "./ui/button";
3import { PostView } from "@atproto/api/dist/client/types/app/bsky/feed/defs";
4import { useState } from "react";
5import { Heart } from "lucide-react";
6import clsx from "clsx";
7import LikeCounter from "./LikeCounter";
8
9export function LikeButton({ post }: { post: PostView }) {
10 const { agent } = useAuth();
11 const [likeUri, setLikeUri] = useState<string | null>(null);
12 const [likes, setLikes] = useState(post.likeCount ?? 0);
13 const [isLiked, setLiked] = useState(post.viewer?.like ?? false);
14 return (
15 <Button
16 className="flex items-center gap-2 cursor-pointer hover:bg-black/5 dark:hover:bg-white/5"
17 variant={"ghost"}
18 disabled={!post.viewer}
19 onClick={async () => {
20 if (!agent || !post.viewer) return;
21 if (likeUri == null) {
22 setLiked(true);
23 setLikes(likes + 1);
24 const uri = await agent.like(post.uri, post.cid);
25 setLikeUri(uri.uri);
26 } else {
27 setLiked(false);
28 setLikes(likes - 1);
29 setLikeUri(null);
30 await agent.deleteLike(likeUri);
31 }
32 }}
33 >
34 <Heart
35 className={clsx(
36 "w-5 h-5",
37 isLiked
38 ? "fill-red-500 text-red-500"
39 : "text-black/80 dark:text-white/80"
40 )}
41 />
42 <LikeCounter count={likes || 0} />
43 </Button>
44 );
45}