mirror of
https://github.com/lumehq/lume.git
synced 2025-03-28 02:31:49 +01:00
update notification
This commit is contained in:
parent
f0fb1bee1e
commit
13ca8a2c54
@ -33,6 +33,10 @@ button {
|
||||
@apply outline-fuchsia-500;
|
||||
}
|
||||
|
||||
iframe {
|
||||
height: auto !important;
|
||||
}
|
||||
|
||||
/* For Webkit-based browsers (Chrome, Safari and Opera) */
|
||||
.scrollbar-hide::-webkit-scrollbar {
|
||||
display: none;
|
||||
|
@ -56,8 +56,8 @@ export const MentionNote = memo(function MentionNote({ id }: { id: string }) {
|
||||
},
|
||||
}}
|
||||
>
|
||||
{data?.content?.parsed?.length > 200
|
||||
? data.content.parsed.substring(0, 200) + '...'
|
||||
{data?.content?.parsed?.length > 160
|
||||
? data.content.parsed.substring(0, 160) + '...'
|
||||
: data.content.parsed}
|
||||
</ReactMarkdown>
|
||||
</div>
|
||||
|
@ -2,7 +2,7 @@ import ReactPlayer from 'react-player/es6';
|
||||
|
||||
export function VideoPreview({ urls }: { urls: string[] }) {
|
||||
return (
|
||||
<div className="relative mb-2 mt-3 flex w-full max-w-[420px] flex-col gap-2">
|
||||
<div className="relative mb-2 mt-3 flex w-full flex-col gap-2">
|
||||
{urls.map((url) => (
|
||||
<ReactPlayer
|
||||
key={url}
|
||||
|
5
src/shared/notification/index.tsx
Normal file
5
src/shared/notification/index.tsx
Normal file
@ -0,0 +1,5 @@
|
||||
export * from './user';
|
||||
export * from './modal';
|
||||
export * from './types/reaction';
|
||||
export * from './types/repost';
|
||||
export * from './types/mention';
|
@ -6,8 +6,7 @@ import { useCallback } from 'react';
|
||||
import { useNDK } from '@libs/ndk/provider';
|
||||
|
||||
import { BellIcon, CancelIcon, LoaderIcon } from '@shared/icons';
|
||||
import { NotificationUser } from '@shared/notification/user';
|
||||
import { User } from '@shared/user';
|
||||
import { NotiMention, NotiReaction, NotiRepost } from '@shared/notification';
|
||||
|
||||
import { nHoursAgo } from '@utils/date';
|
||||
import { LumeEvent } from '@utils/types';
|
||||
@ -22,7 +21,9 @@ export function NotificationModal({ pubkey }: { pubkey: string }) {
|
||||
{ '#p': [pubkey], kinds: [1, 6, 7, 9735] },
|
||||
{ since: nHoursAgo(24) }
|
||||
);
|
||||
return events as unknown as LumeEvent[];
|
||||
const filterSelf = events.filter((el) => el.pubkey !== pubkey);
|
||||
const sorted = filterSelf.sort((a, b) => a.created_at - b.created_at);
|
||||
return sorted as unknown as LumeEvent[];
|
||||
},
|
||||
{
|
||||
refetchOnWindowFocus: false,
|
||||
@ -33,36 +34,13 @@ export function NotificationModal({ pubkey }: { pubkey: string }) {
|
||||
(event: NDKEvent) => {
|
||||
switch (event.kind) {
|
||||
case 1:
|
||||
return (
|
||||
<div key={event.id} className="flex flex-col px-5 py-2">
|
||||
<User pubkey={event.pubkey} time={event.created_at} isChat={true} />
|
||||
<div className="-mt-[20px] pl-[49px]">
|
||||
<p className="select-text whitespace-pre-line break-words text-base text-zinc-100">
|
||||
{event.content}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
return <NotiMention key={event.id} event={event} />;
|
||||
case 6:
|
||||
return (
|
||||
<div key={event.id} className="flex flex-col px-5 py-2">
|
||||
<NotificationUser pubkey={event.pubkey} desc="repost your post" />
|
||||
</div>
|
||||
);
|
||||
return <NotiRepost key={event.id} event={event} />;
|
||||
case 7:
|
||||
return (
|
||||
<div key={event.id} className="flex flex-col px-5 py-2">
|
||||
<NotificationUser pubkey={event.pubkey} desc="liked your post" />
|
||||
</div>
|
||||
);
|
||||
case 9735:
|
||||
return (
|
||||
<div key={event.id} className="flex flex-col px-5 py-2">
|
||||
<NotificationUser pubkey={event.pubkey} desc="zapped your post" />
|
||||
</div>
|
||||
);
|
||||
return <NotiReaction key={event.id} event={event} />;
|
||||
default:
|
||||
return <div className="flex flex-col px-5 py-2">{event.content}</div>;
|
||||
return null;
|
||||
}
|
||||
},
|
||||
[data]
|
||||
|
34
src/shared/notification/types/mention.tsx
Normal file
34
src/shared/notification/types/mention.tsx
Normal file
@ -0,0 +1,34 @@
|
||||
import { NDKEvent } from '@nostr-dev-kit/ndk';
|
||||
import { useMemo } from 'react';
|
||||
|
||||
import { MentionNote, NoteContent } from '@shared/notes';
|
||||
import { NotiUser } from '@shared/notification';
|
||||
|
||||
import { formatCreatedAt } from '@utils/createdAt';
|
||||
import { parser } from '@utils/parser';
|
||||
|
||||
export function NotiMention({ event }: { event: NDKEvent }) {
|
||||
const replyTo = event.tags.find((e) => e[0] === 'e')?.[1];
|
||||
const createdAt = formatCreatedAt(event.created_at);
|
||||
const content = useMemo(() => parser(event), [event]);
|
||||
|
||||
return (
|
||||
<div className="flex h-min flex-col px-5 py-2">
|
||||
<div className="flex items-start justify-between">
|
||||
<div className="flex items-start gap-1">
|
||||
<NotiUser pubkey={event.pubkey} />
|
||||
<p className="leading-none text-zinc-400">reply your post</p>
|
||||
</div>
|
||||
<div>
|
||||
<span className="leading-none text-zinc-500">{createdAt}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="-mt-4 pl-[35px]">
|
||||
<div>
|
||||
<NoteContent content={content} />
|
||||
</div>
|
||||
{replyTo && <MentionNote id={replyTo} />}
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
26
src/shared/notification/types/reaction.tsx
Normal file
26
src/shared/notification/types/reaction.tsx
Normal file
@ -0,0 +1,26 @@
|
||||
import { NDKEvent } from '@nostr-dev-kit/ndk';
|
||||
|
||||
import { MentionNote } from '@shared/notes';
|
||||
import { NotiUser } from '@shared/notification';
|
||||
|
||||
import { formatCreatedAt } from '@utils/createdAt';
|
||||
|
||||
export function NotiReaction({ event }: { event: NDKEvent }) {
|
||||
const root = event.tags.find((e) => e[0] === 'e')?.[1];
|
||||
const createdAt = formatCreatedAt(event.created_at);
|
||||
|
||||
return (
|
||||
<div className="flex h-min flex-col px-5 py-2">
|
||||
<div className="flex items-start justify-between">
|
||||
<div className="flex items-start gap-1">
|
||||
<NotiUser pubkey={event.pubkey} />
|
||||
<p className="leading-none text-zinc-400">reacted {event.content}</p>
|
||||
</div>
|
||||
<div>
|
||||
<span className="leading-none text-zinc-500">{createdAt}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="-mt-4 pl-[35px]">{root && <MentionNote id={root} />}</div>
|
||||
</div>
|
||||
);
|
||||
}
|
26
src/shared/notification/types/repost.tsx
Normal file
26
src/shared/notification/types/repost.tsx
Normal file
@ -0,0 +1,26 @@
|
||||
import { NDKEvent } from '@nostr-dev-kit/ndk';
|
||||
|
||||
import { MentionNote } from '@shared/notes';
|
||||
import { NotiUser } from '@shared/notification';
|
||||
|
||||
import { formatCreatedAt } from '@utils/createdAt';
|
||||
|
||||
export function NotiRepost({ event }: { event: NDKEvent }) {
|
||||
const root = event.tags.find((e) => e[0] === 'e')?.[1];
|
||||
const createdAt = formatCreatedAt(event.created_at);
|
||||
|
||||
return (
|
||||
<div className="flex h-min flex-col px-5 py-2">
|
||||
<div className="flex items-start justify-between">
|
||||
<div className="flex items-start gap-1">
|
||||
<NotiUser pubkey={event.pubkey} />
|
||||
<p className="leading-none text-zinc-400">repost your post</p>
|
||||
</div>
|
||||
<div>
|
||||
<span className="leading-none text-zinc-500">{createdAt}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="-mt-4 pl-[35px]">{root && <MentionNote id={root} />}</div>
|
||||
</div>
|
||||
);
|
||||
}
|
@ -3,39 +3,35 @@ import { Image } from '@shared/image';
|
||||
import { DEFAULT_AVATAR } from '@stores/constants';
|
||||
|
||||
import { useProfile } from '@utils/hooks/useProfile';
|
||||
import { shortenKey } from '@utils/shortenKey';
|
||||
import { displayNpub } from '@utils/shortenKey';
|
||||
|
||||
export function NotificationUser({ pubkey, desc }: { pubkey: string; desc: string }) {
|
||||
export function NotiUser({ pubkey }: { pubkey: string }) {
|
||||
const { status, user } = useProfile(pubkey);
|
||||
|
||||
if (status === 'loading') {
|
||||
return (
|
||||
<div className="flex items-center gap-2">
|
||||
<div className="relative h-11 w-11 shrink-0 animate-pulse rounded-md bg-zinc-800" />
|
||||
<div className="flex items-start gap-2">
|
||||
<div className="relative h-8 w-8 shrink-0 animate-pulse rounded-md bg-zinc-800" />
|
||||
<div className="flex w-full flex-1 flex-col items-start gap-1 text-start">
|
||||
<span className="h-4 w-1/2 animate-pulse rounded bg-zinc-800" />
|
||||
<span className="h-3 w-1/3 animate-pulse rounded bg-zinc-800" />
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="flex items-center justify-start gap-2">
|
||||
<div className="relative h-11 w-11 shrink rounded-md">
|
||||
<div className="flex shrink-0 items-start justify-start gap-2">
|
||||
<div className="w-88 relative h-8 shrink rounded-md">
|
||||
<Image
|
||||
src={user.image}
|
||||
fallback={DEFAULT_AVATAR}
|
||||
alt={pubkey}
|
||||
className="h-11 w-11 rounded-md object-cover"
|
||||
className="w-88 h-8 rounded-md object-cover"
|
||||
/>
|
||||
</div>
|
||||
<div className="inline-flex flex-1 items-center justify-start gap-1 text-start">
|
||||
<span className="leading-none text-zinc-400">
|
||||
{user.nip05 || user.name || user.displayName || shortenKey(pubkey)}
|
||||
</span>
|
||||
<span className="leading-none text-zinc-400">{desc}</span>
|
||||
</div>
|
||||
<span className="max-w-[10rem] truncate leading-none text-zinc-200">
|
||||
{user.nip05 || user.name || user.displayName || displayNpub(pubkey, 16)}
|
||||
</span>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
@ -18,7 +18,6 @@ export function useProfile(pubkey: string, fallback?: string) {
|
||||
const current = Math.floor(Date.now() / 1000);
|
||||
const cache = await getUserMetadata(pubkey);
|
||||
if (cache && parseInt(cache.created_at) + 86400 >= current) {
|
||||
console.log('cache hit:', cache);
|
||||
return JSON.parse(cache.content);
|
||||
} else {
|
||||
const filter: NDKFilter = { kinds: [0], authors: [pubkey] };
|
||||
|
Loading…
x
Reference in New Issue
Block a user