mirror of
https://github.com/spacebarchat/client.git
synced 2024-11-22 02:12:38 +01:00
rework image scaling to work better on mobile
This commit is contained in:
parent
a9f4aa1ba5
commit
0dbb5a7fe2
@ -2,29 +2,45 @@ import { APIAttachment } from "@spacebarchat/spacebar-api-types/v9";
|
|||||||
import styled from "styled-components";
|
import styled from "styled-components";
|
||||||
import { modalController } from "../../controllers/modals";
|
import { modalController } from "../../controllers/modals";
|
||||||
import useLogger from "../../hooks/useLogger";
|
import useLogger from "../../hooks/useLogger";
|
||||||
import { calculateImageRatio, calculateScaledDimensions } from "../../utils/Message";
|
|
||||||
import { getFileDetails, zoomFit } from "../../utils/Utils";
|
import { getFileDetails, zoomFit } from "../../utils/Utils";
|
||||||
import Audio from "../media/Audio";
|
import Audio from "../media/Audio";
|
||||||
import File from "../media/File";
|
import File from "../media/File";
|
||||||
import Video from "../media/Video";
|
import Video from "../media/Video";
|
||||||
|
|
||||||
|
const MAX_ATTACHMENT_HEIGHT = 350;
|
||||||
|
|
||||||
|
function adjustDimensions(width: number, height: number): { adjustedWidth: number; adjustedHeight: number } {
|
||||||
|
const aspectRatio = width / height;
|
||||||
|
|
||||||
|
let adjustedWidth: number = width * aspectRatio;
|
||||||
|
let adjustedHeight: number = height * aspectRatio;
|
||||||
|
|
||||||
|
// Ensure the adjusted height does not exceed the maximum height
|
||||||
|
if (adjustedHeight > MAX_ATTACHMENT_HEIGHT) {
|
||||||
|
const scale = MAX_ATTACHMENT_HEIGHT / adjustedHeight;
|
||||||
|
adjustedWidth *= scale;
|
||||||
|
adjustedHeight = MAX_ATTACHMENT_HEIGHT;
|
||||||
|
}
|
||||||
|
|
||||||
|
return { adjustedWidth: Math.floor(adjustedWidth), adjustedHeight: Math.floor(adjustedHeight) };
|
||||||
|
}
|
||||||
|
|
||||||
const Attachment = styled.div<{ withPointer?: boolean }>`
|
const Attachment = styled.div<{ withPointer?: boolean }>`
|
||||||
cursor: ${(props) => (props.withPointer ? "pointer" : "default")};
|
cursor: ${(props) => (props.withPointer ? "pointer" : "default")};
|
||||||
padding: 2px 0;
|
padding: 2px 0;
|
||||||
width: min-content;
|
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const Image = styled.img`
|
const Image = styled.img`
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
|
width: 100%;
|
||||||
|
height: auto;
|
||||||
`;
|
`;
|
||||||
|
|
||||||
interface AttachmentProps {
|
interface AttachmentProps {
|
||||||
attachment: APIAttachment;
|
attachment: APIAttachment;
|
||||||
maxWidth?: number;
|
|
||||||
maxHeight?: number;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export default function MessageAttachment({ attachment, maxWidth, maxHeight }: AttachmentProps) {
|
export default function MessageAttachment({ attachment }: AttachmentProps) {
|
||||||
const logger = useLogger("MessageAttachment");
|
const logger = useLogger("MessageAttachment");
|
||||||
|
|
||||||
const url = attachment.proxy_url && attachment.proxy_url.length > 0 ? attachment.proxy_url : attachment.url;
|
const url = attachment.proxy_url && attachment.proxy_url.length > 0 ? attachment.proxy_url : attachment.url;
|
||||||
@ -32,16 +48,17 @@ export default function MessageAttachment({ attachment, maxWidth, maxHeight }: A
|
|||||||
const details = getFileDetails(attachment);
|
const details = getFileDetails(attachment);
|
||||||
let finalElement: JSX.Element = <></>;
|
let finalElement: JSX.Element = <></>;
|
||||||
if (details.isImage && details.isEmbeddable) {
|
if (details.isImage && details.isEmbeddable) {
|
||||||
const ratio = calculateImageRatio(attachment.width!, attachment.height!, maxWidth, maxHeight);
|
const width = attachment.width!;
|
||||||
const { scaledWidth, scaledHeight } = calculateScaledDimensions(
|
const height = attachment.height!;
|
||||||
attachment.width!,
|
const { adjustedWidth, adjustedHeight } = adjustDimensions(width, height);
|
||||||
attachment.height!,
|
|
||||||
ratio,
|
|
||||||
maxWidth,
|
|
||||||
maxHeight,
|
|
||||||
);
|
|
||||||
finalElement = (
|
finalElement = (
|
||||||
<Image src={url} alt={attachment.filename} width={scaledWidth} height={scaledHeight} loading="lazy" />
|
<Image
|
||||||
|
src={url}
|
||||||
|
alt={attachment.filename}
|
||||||
|
loading="lazy"
|
||||||
|
style={{ maxWidth: adjustedWidth, maxHeight: adjustedHeight }}
|
||||||
|
/>
|
||||||
);
|
);
|
||||||
} else if (details.isVideo && details.isEmbeddable) {
|
} else if (details.isVideo && details.isEmbeddable) {
|
||||||
finalElement = <Video attachment={attachment} />;
|
finalElement = <Video attachment={attachment} />;
|
||||||
|
@ -100,6 +100,7 @@ function MessageList({ guild, channel }: Props) {
|
|||||||
display: "flex",
|
display: "flex",
|
||||||
flexDirection: "column-reverse",
|
flexDirection: "column-reverse",
|
||||||
marginBottom: 30,
|
marginBottom: 30,
|
||||||
|
overflow: "hidden",
|
||||||
}} // to put endMessage and loader to the top.
|
}} // to put endMessage and loader to the top.
|
||||||
hasMore={hasMore}
|
hasMore={hasMore}
|
||||||
inverse={true}
|
inverse={true}
|
||||||
|
Loading…
Reference in New Issue
Block a user