Modified self-dm to be a "Note to Self" #89
43
src/element/NoteToSelf.css
Normal file
43
src/element/NoteToSelf.css
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
.nts {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.note-to-self {
|
||||||
|
margin-left: 5px;
|
||||||
|
margin-top: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts .avatar-wrapper {
|
||||||
|
margin-right: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts .avatar {
|
||||||
|
border-width: 1px;
|
||||||
|
width: 40px;
|
||||||
|
height: 40px;
|
||||||
|
}
|
||||||
|
.nts .avatar.clickable {
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts a {
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts a:hover {
|
||||||
|
text-decoration: underline;
|
||||||
|
text-decoration-color: var(--gray-superlight);
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts .name {
|
||||||
|
margin-top: -.2em;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nts .nip05 {
|
||||||
|
margin: 0;
|
||||||
|
margin-top: -.2em;
|
||||||
|
}
|
56
src/element/NoteToSelf.tsx
Normal file
56
src/element/NoteToSelf.tsx
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
import "./NoteToSelf.css";
|
||||||
|
|
||||||
|
import { Link, useNavigate } from "react-router-dom";
|
||||||
|
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
|
||||||
|
import { faBook, faCertificate } from "@fortawesome/free-solid-svg-icons"
|
||||||
|
import useProfile from "../feed/ProfileFeed";
|
||||||
|
import Nip05 from "./Nip05";
|
||||||
|
import { profileLink } from "../Util";
|
||||||
|
|
||||||
|
export interface NoteToSelfProps {
|
||||||
|
pubkey: string,
|
||||||
|
clickable?: boolean
|
||||||
|
className?: string,
|
||||||
|
link?: string
|
||||||
|
};
|
||||||
|
|
||||||
|
function NoteLabel({pubkey, link}:NoteToSelfProps) {
|
||||||
|
const user = useProfile(pubkey)?.get(pubkey);
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
Note to Self <FontAwesomeIcon icon={faCertificate} size="xs" />
|
||||||
|
{user?.nip05 && <Nip05 nip05={user.nip05} pubkey={user.pubkey} />}
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function NoteToSelf({ pubkey, clickable, className, link }: NoteToSelfProps) {
|
||||||
|
const navigate = useNavigate();
|
||||||
|
|
||||||
|
const clickLink = () => {
|
||||||
|
if(clickable) {
|
||||||
|
navigate(link ?? profileLink(pubkey))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className={`nts${className ? ` ${className}` : ""}`}>
|
||||||
|
<div className="avatar-wrapper">
|
||||||
|
<div className={`avatar${clickable ? " clickable" : ""}`}>
|
||||||
|
<FontAwesomeIcon onClick={clickLink} className="note-to-self" icon={faBook} size="2xl" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className="f-grow">
|
||||||
|
<div className="name">
|
||||||
|
{clickable && (
|
||||||
|
<Link to={link ?? profileLink(pubkey)}>
|
||||||
|
<NoteLabel pubkey={pubkey} />
|
||||||
|
</Link>
|
||||||
|
) || (
|
||||||
|
<NoteLabel pubkey={pubkey} />
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
@ -11,6 +11,7 @@ import useEventPublisher from "../feed/EventPublisher";
|
|||||||
import DM from "../element/DM";
|
import DM from "../element/DM";
|
||||||
import { RawEvent } from "../nostr";
|
import { RawEvent } from "../nostr";
|
||||||
import { dmsInChat, isToSelf } from "./MessagesPage";
|
import { dmsInChat, isToSelf } from "./MessagesPage";
|
||||||
|
import NoteToSelf from "../element/NoteToSelf";
|
||||||
|
|
||||||
type RouterParams = {
|
type RouterParams = {
|
||||||
id: string
|
id: string
|
||||||
@ -58,7 +59,11 @@ export default function ChatPage() {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
|
{id === pubKey && (
|
||||||
|
<NoteToSelf className="f-grow mb-10" pubkey={id} />
|
||||||
|
) || (
|
||||||
<ProfileImage pubkey={id} className="f-grow mb10" />
|
<ProfileImage pubkey={id} className="f-grow mb10" />
|
||||||
|
)}
|
||||||
<div className="dm-list" ref={dmListRef}>
|
<div className="dm-list" ref={dmListRef}>
|
||||||
<div>
|
<div>
|
||||||
{sortedDms.map(a => <DM data={a} key={a.id} />)}
|
{sortedDms.map(a => <DM data={a} key={a.id} />)}
|
||||||
|
@ -6,6 +6,7 @@ import ProfileImage from "../element/ProfileImage";
|
|||||||
import { hexToBech32 } from "../Util";
|
import { hexToBech32 } from "../Util";
|
||||||
import { incDmInteraction } from "../state/Login";
|
import { incDmInteraction } from "../state/Login";
|
||||||
import { RootState } from "../state/Store";
|
import { RootState } from "../state/Store";
|
||||||
|
import NoteToSelf from "../element/NoteToSelf";
|
||||||
|
|
||||||
type DmChat = {
|
type DmChat = {
|
||||||
pubkey: HexKey,
|
pubkey: HexKey,
|
||||||
@ -23,7 +24,16 @@ export default function MessagesPage() {
|
|||||||
return extractChats(dms, myPubKey!);
|
return extractChats(dms, myPubKey!);
|
||||||
}, [dms, myPubKey, dmInteraction]);
|
}, [dms, myPubKey, dmInteraction]);
|
||||||
|
|
||||||
|
function noteToSelf(chat: DmChat) {
|
||||||
|
return (
|
||||||
|
<div className="flex mb10" key={chat.pubkey}>
|
||||||
|
<NoteToSelf clickable={true} className="f-grow" link={`/messages/${hexToBech32("npub", chat.pubkey)}`} pubkey={chat.pubkey} />
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
function person(chat: DmChat) {
|
function person(chat: DmChat) {
|
||||||
|
if(chat.pubkey === myPubKey) return noteToSelf(chat)
|
||||||
return (
|
return (
|
||||||
<div className="flex mb10" key={chat.pubkey}>
|
<div className="flex mb10" key={chat.pubkey}>
|
||||||
<ProfileImage pubkey={chat.pubkey} className="f-grow" link={`/messages/${hexToBech32("npub", chat.pubkey)}`} />
|
<ProfileImage pubkey={chat.pubkey} className="f-grow" link={`/messages/${hexToBech32("npub", chat.pubkey)}`} />
|
||||||
@ -47,7 +57,10 @@ export default function MessagesPage() {
|
|||||||
<h3 className="f-grow">Messages</h3>
|
<h3 className="f-grow">Messages</h3>
|
||||||
<div className="btn" onClick={() => markAllRead()}>Mark All Read</div>
|
<div className="btn" onClick={() => markAllRead()}>Mark All Read</div>
|
||||||
</div>
|
</div>
|
||||||
{chats.sort((a, b) => b.newestMessage - a.newestMessage).map(person)}
|
{chats.sort((a, b) => {
|
||||||
|
if(b.pubkey === myPubKey) return 1
|
||||||
|
return b.newestMessage - a.newestMessage
|
||||||
|
}).map(person)}
|
||||||
</>
|
</>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user