reorganize code into smaller files & dirs

This commit is contained in:
Martti Malmi
2024-01-04 15:48:19 +02:00
parent 5ea2eb711f
commit afa6d39a56
321 changed files with 671 additions and 671 deletions

View File

@ -0,0 +1,84 @@
import { NostrEvent, NostrLink } from "@snort/system";
import { FormattedMessage } from "react-intl";
import { Link } from "react-router-dom";
import { findTag } from "@/Utils";
import ProfileImage from "../User/ProfileImage";
import Icon from "@/Components/Icons/Icon";
export function LiveEvent({ ev }: { ev: NostrEvent }) {
const title = findTag(ev, "title");
const status = findTag(ev, "status");
const starts = Number(findTag(ev, "starts"));
const host = ev.tags.find(a => a[0] === "p" && a[3] === "host")?.[1] ?? ev.pubkey;
function statusLine() {
switch (status) {
case "live": {
return (
<div className="flex g4 items-center">
<Icon name="signal-01" />
<b className="uppercase">
<FormattedMessage defaultMessage="Live" id="Dn82AL" />
</b>
</div>
);
}
case "ended": {
return (
<b className="uppercase">
<FormattedMessage defaultMessage="Ended" id="TP/cMX" />
</b>
);
}
case "planned": {
return (
<b className="uppercase">
{new Intl.DateTimeFormat(undefined, { dateStyle: "full", timeStyle: "short" }).format(
new Date(starts * 1000),
)}
</b>
);
}
}
}
function cta() {
const link = `https://zap.stream/${NostrLink.fromEvent(ev).encode()}`;
switch (status) {
case "live": {
return (
<Link to={link} target="_blank">
<button className="nowrap">
<FormattedMessage defaultMessage="Join Stream" id="GQPtfk" />
</button>
</Link>
);
}
case "ended": {
if (findTag(ev, "recording")) {
return (
<Link to={link} target="_blank">
<button className="nowrap">
<FormattedMessage defaultMessage="Watch Replay" id="6/hB3S" />
</button>
</Link>
);
}
}
}
}
return (
<div className="sm:flex g12 br p24 bg-primary items-center">
<div>
<ProfileImage pubkey={host} showUsername={false} size={56} />
</div>
<div className="flex flex-col g8 grow">
<div className="font-semibold text-3xl">{title}</div>
<div>{statusLine()}</div>
</div>
<div>{cta()}</div>
</div>
);
}

View File

@ -0,0 +1,54 @@
.stream-list {
display: flex;
gap: 4px;
overflow-x: auto;
}
.stream-list::-webkit-scrollbar {
height: 6.25px;
}
.stream-event {
display: flex;
padding: 8px 12px;
gap: 8px;
text-decoration: none;
}
.stream-event > div:first-of-type {
border-radius: 8px;
height: 49px;
width: 65px;
background-color: var(--gray-light);
background-image: var(--img);
background-position: center;
background-size: cover;
}
.stream-event span.live {
display: flex;
padding: 4px 6px;
justify-content: center;
align-items: center;
gap: 4px;
border-radius: 9px;
background: var(--live);
font-size: 12px;
font-weight: 700;
text-transform: uppercase;
}
.stream-event .details .reactions {
color: var(--font-secondary-color);
}
.stream-event .details > div:nth-of-type(2) {
width: 100px;
min-width: 0;
white-space: nowrap;
text-overflow: ellipsis;
overflow: hidden;
font-size: 16px;
font-weight: 600;
line-height: 24px;
}

View File

@ -0,0 +1,58 @@
import "./LiveStreams.css";
import { NostrEvent, NostrLink } from "@snort/system";
import { findTag } from "@/Utils";
import { CSSProperties, useMemo } from "react";
import { Link } from "react-router-dom";
import useImgProxy from "@/Hooks/useImgProxy";
import Icon from "@/Components/Icons/Icon";
export function LiveStreams({ evs }: { evs: Array<NostrEvent> }) {
const streams = useMemo(() => {
return [...evs].sort((a, b) => {
const aStarts = Number(findTag(a, "starts") ?? a.created_at);
const bStarts = Number(findTag(b, "starts") ?? b.created_at);
return aStarts > bStarts ? -1 : 1;
});
}, [evs]);
if (streams.length === 0) return null;
return (
<div className="stream-list">
{streams.map(v => (
<LiveStreamEvent ev={v} key={`${v.kind}:${v.pubkey}:${findTag(v, "d")}`} />
))}
</div>
);
}
function LiveStreamEvent({ ev }: { ev: NostrEvent }) {
const { proxy } = useImgProxy();
const title = findTag(ev, "title");
const image = findTag(ev, "image");
const status = findTag(ev, "status");
const link = NostrLink.fromEvent(ev).encode(CONFIG.eventLinkPrefix);
const imageProxy = proxy(image ?? "");
return (
<Link className="stream-event" to={`https://zap.stream/${link}`} target="_blank">
<div
style={
{
"--img": `url(${imageProxy})`,
} as CSSProperties
}></div>
<div className="flex flex-col details">
<div className="flex g2">
<span className="live">{status}</span>
<div className="reaction-pill">
<Icon name="zap" size={24} />
<div className="reaction-pill-number">0</div>
</div>
</div>
<div>{title}</div>
</div>
</Link>
);
}