feat: optiminize message&img display

This commit is contained in:
butterfly 2024-04-19 19:28:48 +08:00
parent 1074fffe79
commit 37cc87531c
10 changed files with 132 additions and 43 deletions

View File

@ -0,0 +1,52 @@
import { CSSProperties } from "react";
import { getMessageImages } from "@/app/utils";
import { RequestMessage } from "@/app/client/api";
interface ImgsProps {
message: RequestMessage;
isMobileScreen?: boolean;
}
export default function Imgs(props: ImgsProps) {
const { message, isMobileScreen } = props;
const imgSrcs = getMessageImages(message);
if (imgSrcs.length < 1) {
return <></>;
}
let imgVars = {
"--imgs-width": `calc(var(--max-message-width) - ${
imgSrcs.length - 1
}*0.25rem)`,
"--img-width": `calc(var(--imgs-width)/ ${imgSrcs.length})`,
};
if (isMobileScreen) {
imgVars = {
"--imgs-width": `calc(var(--max-message-width) - ${
imgSrcs.length - 1
}*0.25rem)`,
"--img-width": `calc(var(--imgs-width)/ ${imgSrcs.length})`,
};
}
return (
<div
className={`w-[100%] mt-[0.625rem] flex gap-1`}
style={imgVars as CSSProperties}
>
{imgSrcs.map((image, index) => {
return (
<div
key={index}
className="flex-1 min-w-[var(--img-width)] pb-[var(--img-width)] object-cover bg-cover bg-no-repeat bg-center box-border rounded-chat-img"
style={{
backgroundImage: `url(${image})`,
}}
/>
);
})}
</div>
);
}

View File

@ -1,6 +1,6 @@
import { useLocation } from "react-router-dom";
import { useMemo, ReactNode } from "react";
import { Path, SlotID } from "@/app/constant";
import { Path, SIDEBAR_ID, SlotID } from "@/app/constant";
import { getLang } from "@/app/locales";
import useMobileScreen from "@/app/hooks/useMobileScreen";
@ -47,7 +47,9 @@ export default function Screen(props: ScreenProps) {
props.noAuth
) : (
<>
<div className={sidebarClassName}>{props.sidebar}</div>
<div className={sidebarClassName} id={SIDEBAR_ID}>
{props.sidebar}
</div>
<div
className={pageClassName}

View File

@ -49,6 +49,8 @@ export enum StoreKey {
Sync = "sync",
}
export const NARROW_SIDEBAR_WIDTH = 100;
export const DEFAULT_SIDEBAR_WIDTH = 340;
export const MAX_SIDEBAR_WIDTH = 440;
export const MIN_SIDEBAR_WIDTH = 230;
@ -383,3 +385,5 @@ export const internalWhiteWebDavEndpoints = [
"https://webdav.yandex.com",
"https://app.koofr.net/dav/Koofr",
];
export const SIDEBAR_ID = "sidebar";

View File

@ -20,6 +20,7 @@ import useRelativePosition, {
Orientation,
} from "@/app/hooks/useRelativePosition";
import MessageActions, { RenderMessage } from "./MessageActions";
import Imgs from "@/app/components/Imgs";
export type { RenderMessage };
@ -186,7 +187,11 @@ export default function ChatMessagePanel(props: ChatMessagePanelProps) {
</>
)}
</div>
<div className={`group relative max-w-message-width`}>
<div
className={`group relative flex-1 flex ${
isUser ? "flex-row-reverse" : ""
}`}
>
<div
className={` pointer-events-none text-gray-500 text-right text-time whitespace-nowrap transition-all duration-500 text-sm absolute z-1 ${
isUser ? "right-0" : "left-0"
@ -198,10 +203,10 @@ export default function ChatMessagePanel(props: ChatMessagePanelProps) {
</div>
<div
className={`transition-all duration-300 select-text break-words font-common text-sm-title ${
isUser ? "rounded-user-message" : "rounded-bot-message"
} box-border peer py-2 px-3 ${
isUser ? "text-right bg-message-bg" : " bg-white"
}`}
isUser
? "rounded-user-message bg-message-bg"
: "rounded-bot-message bg-white"
} box-border peer py-2 px-3`}
onPointerMoveCapture={(e) =>
getRelativePosition(e.currentTarget, message.id)
}
@ -221,22 +226,11 @@ export default function ChatMessagePanel(props: ChatMessagePanelProps) {
fontSize={fontSize}
parentRef={scrollRef}
defaultShow={i >= messages.length - 6}
className={isUser ? " text-white" : "text-black"}
className={`max-w-message-width ${
isUser ? " text-white" : "text-black"
}`}
/>
{getMessageImages(message).length > 0 && (
<div className={`w-[100%]`}>
{getMessageImages(message).map((image, index) => {
return (
<img
className={`w-[100%] mt-2.5 rounded-chat-img`}
key={index}
src={image}
alt=""
/>
);
})}
</div>
)}
<Imgs message={message} isMobileScreen={isMobileScreen} />
</div>
<MessageActions
className={actionsBarPosition}

View File

@ -3,8 +3,9 @@ import {
MAX_SIDEBAR_WIDTH,
MIN_SIDEBAR_WIDTH,
} from "@/app/constant";
import { useAppConfig } from "../store/config";
import { useAppConfig } from "@/app/store/config";
import { useRef } from "react";
import { updateGlobalCSSVars } from "@/app/utils/client";
export default function useDragSideBar() {
const limit = (x: number) =>
@ -35,9 +36,11 @@ export default function useDragSideBar() {
const d = e.clientX - startX.current;
const nextWidth = limit(startDragWidth.current + d);
const { menuWidth } = updateGlobalCSSVars(nextWidth);
document.documentElement.style.setProperty(
"--sidebar-width",
`${nextWidth}px`,
"--menu-width",
`${menuWidth}px`,
);
config.update((config) => {
config.sidebarWidth = nextWidth;
@ -62,7 +65,7 @@ export default function useDragSideBar() {
// useLayoutEffect(() => {
// const barWidth = limit(config.sidebarWidth ?? DEFAULT_SIDEBAR_WIDTH);
// document.documentElement.style.setProperty("--sidebar-width", `${barWidth}px`);
// document.documentElement.style.setProperty("--menu-width", `${barWidth}px`);
// }, [config.sidebarWidth]);
return {

View File

@ -8,8 +8,10 @@ import {
DEFAULT_SIDEBAR_WIDTH,
MAX_SIDEBAR_WIDTH,
MIN_SIDEBAR_WIDTH,
SIDEBAR_ID,
} from "@/app/constant";
import { useAppConfig } from "../store/config";
import { useAppConfig } from "@/app/store/config";
import { updateGlobalCSSVars } from "@/app/utils/client";
export const MOBILE_MAX_WIDTH = 768;
@ -42,16 +44,10 @@ export default function useListenWinResize() {
}
}
nextSidebar = Math.max(
MIN_SIDEBAR_WIDTH,
Math.min(MAX_SIDEBAR_WIDTH, nextSidebar),
);
document.documentElement.style.setProperty(
"--sidebar-width",
`${nextSidebar}px`,
);
const { menuWidth } = updateGlobalCSSVars(nextSidebar);
config.update((config) => {
config.sidebarWidth = nextSidebar;
config.sidebarWidth = menuWidth;
});
});
}

View File

@ -28,4 +28,5 @@ body {
--tip-popover-color: #434360;
--chat-panel-bg: rgb(249, 250, 251, 1);
--siderbar-mobile-height: 3.125rem;
--max-message-width: calc(var(--chat-panel-max-width) * 0.6);
}

View File

@ -61,7 +61,7 @@
--window-width: 90vw;
--window-height: 90vh;
// --sidebar-width: 300px;
--sidebar-width: 300px;
--window-content-width: calc(100% - var(--sidebar-width));
--message-max-width: 80%;
--full-height: 100%;
@ -71,7 +71,7 @@
:root {
--window-width: 100vw;
--window-height: var(--full-height);
// --sidebar-width: 100vw;
--sidebar-width: 100vw;
--window-content-width: var(--window-width);
--message-max-width: 100%;
}

34
app/utils/client.ts Normal file
View File

@ -0,0 +1,34 @@
import {
MAX_SIDEBAR_WIDTH,
MIN_SIDEBAR_WIDTH,
SIDEBAR_ID,
WINDOW_WIDTH_MD,
} from "@/app/constant";
export function updateGlobalCSSVars(nextSidebar: number) {
const windowSize = window.innerWidth;
const inMobile = windowSize <= WINDOW_WIDTH_MD;
nextSidebar = Math.max(
MIN_SIDEBAR_WIDTH,
Math.min(MAX_SIDEBAR_WIDTH, nextSidebar),
);
const menuWidth = inMobile ? 0 : nextSidebar;
const navigateBarWidth = inMobile
? 0
: document.querySelector(`#${SIDEBAR_ID}`)?.clientWidth ?? 0;
const chatPanelWidth = windowSize - navigateBarWidth - menuWidth;
document.documentElement.style.setProperty("--menu-width", `${menuWidth}px`);
document.documentElement.style.setProperty(
"--navigate-bar-width",
`${navigateBarWidth}px`,
);
document.documentElement.style.setProperty(
"--chat-panel-max-width",
`${chatPanelWidth}px`,
);
return { menuWidth };
}

View File

@ -37,7 +37,7 @@ module.exports = {
'md': '15rem',
'lg': '21.25rem',
'2xl': '27.5rem',
'page': 'calc(100% - var(--sidebar-width))',
'page': 'calc(100% - var(--menu-width))',
'thumbnail': '5rem',
'actions-popover': '203px',
},
@ -52,12 +52,14 @@ module.exports = {
'setting-panel-mobile': 'calc(100vh - var(--siderbar-mobile-height))',
},
flexBasis: {
'sidebar': 'var(--sidebar-width)',
'page': 'calc(100% - var(--sidebar-width))',
'sidebar': 'var(--menu-width)',
'page': 'calc(100% - var(--menu-width))',
'message-width': 'var(--max-message-width)',
},
spacing: {
'chat-header-gap': '0.625rem',
'chat-panel-mobile': 'var(--siderbar-mobile-height)'
'chat-panel-mobile': 'var(--siderbar-mobile-height)',
'message-img': 'calc((100%- var(--img-gap-count)*0.25rem)/var(--img-count))',
},
backgroundImage: {
'message-bg': 'linear-gradient(259deg, #9786FF 8.42%, #4A5CFF 90.13%)',
@ -67,8 +69,9 @@ module.exports = {
'time': 'all ease 0.6s',
'message': 'all ease 0.3s',
},
maxHeight: {},
maxWidth: {
'message-width': 'var(--max-message-width, 80%)'
'message-width': 'var(--max-message-width)',
},
backgroundColor: {
'select-btn': 'rgba(0, 0, 0, 0.05)',