1
0
mirror of https://github.com/spacebarchat/client.git synced 2024-11-22 02:12:38 +01:00

more fixes for embeds

This commit is contained in:
Puyodead1 2024-04-17 23:01:46 -04:00
parent c0601ad79c
commit 3640e9bf18
No known key found for this signature in database
GPG Key ID: A4FA4FEC0DD353FC
3 changed files with 83 additions and 52 deletions

View File

@ -30,7 +30,6 @@ iframe {
border-inline-start-style: solid;
padding: 12px;
width: fit-content;
background: var(--background-secondary);
border-radius: 4px;
}
@ -45,7 +44,6 @@ iframe {
font-size: 12px;
color: var(--text-secondary);
font-weight: var(--font-weight-regular);
width: fit-content;
}
.embedAuthor {

View File

@ -6,6 +6,27 @@ import { modalController } from "../../controllers/modals";
import Icon from "../Icon";
import styles from "./Embed.module.css";
function getScaledDimensions(originalWidth: number, originalHeight: number, maxWidth: number, maxHeight: number) {
const aspectRatio = originalWidth / originalHeight;
let newWidth = originalWidth;
let newHeight = originalHeight;
if (newWidth > maxWidth) {
newWidth = maxWidth;
newHeight = newWidth / aspectRatio;
}
if (newHeight > maxHeight) {
newHeight = maxHeight;
newWidth = newHeight * aspectRatio;
}
return { width: Math.round(newWidth), height: Math.round(newHeight) };
}
function shouldScaleImage(originalWidth: number, originalHeight: number, maxWidth: number, maxHeight: number) {
return originalWidth > maxWidth || originalHeight > maxHeight;
}
interface Props {
embed: APIEmbed;
width?: number;
@ -14,12 +35,49 @@ interface Props {
}
function EmbedMedia({ embed, width, height, thumbnail }: Props) {
let maxWidth = 400;
let maxHeight = 300;
if (!width || !height) {
if (embed.video) {
width = embed.video.width;
height = embed.video.height;
} else if (embed.image) {
width = embed.image.width;
height = embed.image.height;
} else if (embed.thumbnail) {
if (embed.type !== EmbedType.Image && embed.provider?.name !== "GitHub") {
maxWidth = 80;
maxHeight = 80;
}
width = embed.thumbnail.width;
height = embed.thumbnail.height;
} else {
console.log("No media size provided");
width = 400;
height = 300;
}
}
const originalWidth = width;
const originalHeight = height;
// Scale image if it's too large
if (shouldScaleImage(width!, height!, maxWidth, maxHeight)) {
const { width: newWidth, height: newHeight } = getScaledDimensions(width!, height!, maxWidth, maxHeight);
width = newWidth;
height = newHeight;
}
console.log(`Original size: ${originalWidth}x${originalHeight} - Scaled size: ${width}x${height}`);
switch (embed.provider?.name) {
case "YouTube": {
if (!embed.video?.url) return null;
const url = embed.video.url;
return <iframe loading="lazy" src={url} allowFullScreen style={{ height }} />;
return <iframe loading="lazy" src={url} allowFullScreen style={{ height, width }} />;
}
case "Spotify": {
const url = embed.url;
@ -144,7 +202,7 @@ function EmbedMedia({ embed, width, height, thumbnail }: Props) {
className={thumbnail ? styles.embedThumbnail : styles.embedImage}
src={url}
loading="lazy"
style={{ width: thumbnail ? width : undefined, height }}
style={{ height, width }}
onClick={() => {
modalController.push({
type: "image_viewer",

View File

@ -9,13 +9,11 @@ import Markdown from "../markdown/Markdown";
import MarkdownRenderer from "../markdown/MarkdownRenderer";
import styles from "./Embed.module.css";
import EmbedMedia from "./EmbedMedia";
import { MESSAGE_AREA_PADDING, MessageAreaWidthContext } from "./MessageList";
import { MessageAreaWidthContext } from "./MessageList";
const MAX_EMBED_WIDTH = 400;
const MAX_EMBED_HEIGHT = 640;
const THUMBNAIL_MAX_WIDTH = 80;
const LINK_EMBED_MAX_WIDTH = 516;
const RICH_EMBED_MAX_WIDTH = 428;
const CONTAINER_PADDING = 24;
const MAX_PREVIEW_SIZE = 150;
const EMBEDDABLE_PROVIDERS = ["Spotify" /*, "Bandcamp"*/];
interface Props {
@ -24,19 +22,19 @@ interface Props {
function MessageEmbed({ embed }: Props) {
const c = React.useContext(MessageAreaWidthContext);
const maxWidth = Math.min(c - MESSAGE_AREA_PADDING, MAX_EMBED_WIDTH);
// const maxWidth = Math.min(c - MESSAGE_AREA_PADDING, MAX_EMBED_WIDTH);
function calculateSize(w: number, h: number): { width: number; height: number } {
const limitingWidth = Math.min(w, maxWidth);
const limitingHeight = Math.min(MAX_EMBED_HEIGHT, h);
// function calculateSize(w: number, h: number): { width: number; height: number } {
// const limitingWidth = Math.min(w, maxWidth);
// const limitingHeight = Math.min(MAX_EMBED_HEIGHT, h);
// Calculate smallest possible WxH.
const width = Math.min(limitingWidth, limitingHeight * (w / h));
// // Calculate smallest possible WxH.
// const width = Math.min(limitingWidth, limitingHeight * (w / h));
const height = Math.min(limitingHeight, limitingWidth * (h / w));
// const height = Math.min(limitingHeight, limitingWidth * (h / w));
return { width, height };
}
// return { width, height };
// }
// Determine special embed size.
let mw, mh;
@ -47,42 +45,14 @@ function MessageEmbed({ embed }: Props) {
embed.type === EmbedType.GIFV ||
embed.type === EmbedType.Image;
if (embed.image) {
mw = embed.image?.width ?? MAX_EMBED_WIDTH;
mh = embed.image?.height ?? 0;
} else if (embed.thumbnail) {
mw = embed.thumbnail.width ?? MAX_EMBED_WIDTH;
mh = embed.thumbnail.height ?? 0;
} else {
switch (embed.provider?.name) {
case "YouTube":
case "Bandcamp": {
mw = embed.video?.width ?? 1280;
mh = embed.video?.height ?? 720;
break;
}
case "Twitch":
case "Lightspeed":
case "Streamable": {
mw = 1280;
mh = 720;
break;
}
default: {
mw = MAX_EMBED_WIDTH;
mh = 1;
}
}
}
const { width, height } = calculateSize(mw, mh);
// const { width, height } = calculateSize(mw, mh);
if (
embed.type === EmbedType.GIFV ||
embed.type === EmbedType.Image ||
embed.type === EmbedType.Video ||
(embed.type === EmbedType.Video && embed.provider?.name !== "YouTube") ||
EMBEDDABLE_PROVIDERS.includes(embed.provider?.name ?? "")
) {
return <EmbedMedia embed={embed} width={height} height={height} />;
return <EmbedMedia embed={embed} />;
}
return (
@ -90,10 +60,15 @@ function MessageEmbed({ embed }: Props) {
className={classNames(styles.embed, styles.website)}
style={{
borderInlineStartColor: embed.color ? decimalColorToHex(embed.color) : "var(--background-tertiary)",
maxWidth: width + CONTAINER_PADDING,
maxWidth: 432,
}}
>
<div className={styles.embedGap}>
<div
className={styles.embedGap}
style={{
maxWidth: embed.type === EmbedType.Rich ? RICH_EMBED_MAX_WIDTH : LINK_EMBED_MAX_WIDTH,
}}
>
<div style={{ display: "flex" }}>
<div className={styles.embedGap}>
{embed.type !== EmbedType.Rich && embed.provider && (
@ -178,7 +153,7 @@ function MessageEmbed({ embed }: Props) {
{(largeMedia || embed.type === EmbedType.Rich) && (
<div>
<EmbedMedia embed={embed} width={width} />
<EmbedMedia embed={embed} width={embed.provider?.name === "YouTube" ? 400 : undefined} />
</div>
)}