don't hate me, old git is fuck up

This commit is contained in:
Ren Amamiya
2023-02-21 14:58:47 +07:00
commit 672298daf9
103 changed files with 12172 additions and 0 deletions
+83
View File
@@ -0,0 +1,83 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { currentUser } from '@stores/currentUser';
import LikeIcon from '@assets/icons/Like';
import LikeSolidIcon from '@assets/icons/LikeSolid';
import { useStore } from '@nanostores/react';
import { dateToUnix, useNostr, useNostrEvents } from 'nostr-react';
import { getEventHash, signEvent } from 'nostr-tools';
import { useState } from 'react';
export default function Reaction({
eventID,
eventPubkey,
}: {
eventID: string;
eventPubkey: string;
}) {
const { publish } = useNostr();
const [reaction, setReaction] = useState(0);
const [isReact, setIsReact] = useState(false);
const $currentUser: any = useStore(currentUser);
const pubkey = $currentUser.pubkey;
const privkey = $currentUser.privkey;
const { onEvent } = useNostrEvents({
filter: {
'#e': [eventID],
since: 0,
kinds: [7],
limit: 20,
},
});
onEvent((rawMetadata) => {
try {
const content = rawMetadata.content;
if (content === '🤙' || content === '+') {
setReaction(reaction + 1);
}
} catch (err) {
console.error(err, rawMetadata);
}
});
const handleReaction = (e: any) => {
e.stopPropagation();
const event: any = {
content: '+',
kind: 7,
tags: [
['e', eventID],
['p', eventPubkey],
],
created_at: dateToUnix(),
pubkey: pubkey,
};
event.id = getEventHash(event);
event.sig = signEvent(event, privkey);
publish(event);
setIsReact(true);
setReaction(reaction + 1);
};
return (
<button
onClick={(e) => handleReaction(e)}
className="group flex w-16 items-center gap-1.5 text-sm text-zinc-500">
<div className="rounded-lg p-1 group-hover:bg-zinc-800">
{isReact ? (
<LikeSolidIcon className="h-5 w-5 text-red-500" />
) : (
<LikeIcon className="h-5 w-5" />
)}
</div>
<span>{reaction}</span>
</button>
);
}
+23
View File
@@ -0,0 +1,23 @@
import ReplyIcon from '@assets/icons/Reply';
import { useNostrEvents } from 'nostr-react';
export default function Reply({ eventID }: { eventID: string }) {
const { events } = useNostrEvents({
filter: {
'#e': [eventID],
since: 0,
kinds: [1],
limit: 10,
},
});
return (
<button className="group flex w-16 items-center gap-1.5 text-sm text-zinc-500">
<div className="rounded-lg p-1 group-hover:bg-zinc-800">
<ReplyIcon />
</div>
<span>{events.length || 0}</span>
</button>
);
}
+26
View File
@@ -0,0 +1,26 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { truncate } from '@utils/truncate';
import { useNostrEvents } from 'nostr-react';
export default function RootUser({ userPubkey, action }: { userPubkey: string; action: string }) {
const { events } = useNostrEvents({
filter: {
authors: [userPubkey],
kinds: [0],
},
});
if (events !== undefined && events.length > 0) {
const userData: any = JSON.parse(events[0].content);
return (
<div className="text-zinc-400">
<p>
{userData?.name ? userData.name : truncate(userPubkey, 16, ' .... ')} {action}
</p>
</div>
);
} else {
return <></>;
}
}
+80
View File
@@ -0,0 +1,80 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { ImageWithFallback } from '@components/imageWithFallback';
import { truncate } from '@utils/truncate';
import MoreIcon from '@assets/icons/More';
import Avatar from 'boring-avatars';
import { useNostrEvents } from 'nostr-react';
import { memo } from 'react';
import Moment from 'react-moment';
export const User = memo(function User({ pubkey, time }: { pubkey: string; time: any }) {
const { events } = useNostrEvents({
filter: {
authors: [pubkey],
kinds: [0],
},
});
if (events !== undefined && events.length > 0) {
const userData: any = JSON.parse(events[0].content);
return (
<div className="relative flex items-start gap-4">
<div className="relative h-11 w-11 shrink overflow-hidden rounded-full border border-white/10">
{userData?.picture ? (
<ImageWithFallback
src={userData.picture}
alt={pubkey}
fill={true}
className="rounded-full object-cover"
/>
) : (
<Avatar
size={44}
name={pubkey}
variant="beam"
colors={['#FEE2E2', '#FEF3C7', '#F59E0B', '#EC4899', '#D946EF', '#8B5CF6']}
/>
)}
</div>
<div className="flex w-full flex-1 items-start justify-between">
<div className="flex w-full justify-between">
<div className="flex items-center gap-2 text-sm">
<span className="font-bold leading-tight">
{userData?.name ? userData.name : truncate(pubkey, 16, ' .... ')}
</span>
<span className="text-zinc-500">·</span>
<Moment fromNow unix className="text-zinc-500">
{time}
</Moment>
</div>
<div>
<MoreIcon />
</div>
</div>
</div>
</div>
);
} else {
return (
<div className="relative flex animate-pulse items-start gap-4">
<div className="relative h-11 w-11 shrink overflow-hidden rounded-full border border-white/10 bg-zinc-700"></div>
<div className="flex w-full flex-1 items-start justify-between">
<div className="flex w-full justify-between">
<div className="flex items-center gap-2 text-sm">
<div className="h-4 w-16 rounded bg-zinc-700" />
<span className="text-zinc-500">·</span>
<div className="h-4 w-16 rounded bg-zinc-700" />
</div>
<div>
<MoreIcon />
</div>
</div>
</div>
</div>
);
}
});