mirror of
https://github.com/enricoros/big-AGI.git
synced 2026-05-10 21:50:14 -07:00
UI: rhythm (line heights)
This commit is contained in:
@@ -6,6 +6,7 @@ import { SxProps } from '@mui/joy/styles/types';
|
||||
import CloseIcon from '@mui/icons-material/Close';
|
||||
|
||||
import { DConversationId, DEphemeral, useChatStore } from '~/common/state/store-chats';
|
||||
import { lineHeightChatText } from '~/common/app.theme';
|
||||
|
||||
|
||||
const StateLine = styled(Typography)(({ theme }) => ({
|
||||
@@ -15,7 +16,7 @@ const StateLine = styled(Typography)(({ theme }) => ({
|
||||
fontSize: theme.fontSize.xs,
|
||||
fontFamily: theme.fontFamily.code,
|
||||
marginLeft: theme.spacing(1),
|
||||
lineHeight: 2,
|
||||
lineHeight: lineHeightChatText,
|
||||
}));
|
||||
|
||||
function isPrimitive(value: any): boolean {
|
||||
@@ -93,7 +94,7 @@ function EphemeralItem({ conversationId, ephemeral }: { conversationId: string,
|
||||
|
||||
{/* Left pane (console) */}
|
||||
<Grid xs={12} md={ephemeral.state ? 6 : 12}>
|
||||
<Typography fontSize='smaller' sx={{ overflowWrap: 'anywhere', whiteSpace: 'break-spaces', lineHeight: 1.75 }}>
|
||||
<Typography fontSize='smaller' sx={{ overflowWrap: 'anywhere', whiteSpace: 'break-spaces', lineHeight: lineHeightChatText }}>
|
||||
{ephemeral.text}
|
||||
</Typography>
|
||||
</Grid>
|
||||
|
||||
@@ -26,6 +26,7 @@ import { DConversationId, useChatStore } from '~/common/state/store-chats';
|
||||
import { SpeechResult, useSpeechRecognition } from '~/common/components/useSpeechRecognition';
|
||||
import { countModelTokens } from '~/common/util/token-counter';
|
||||
import { launchAppCall } from '~/common/app.routes';
|
||||
import { lineHeightTextarea } from '~/common/app.theme';
|
||||
import { playSoundUrl } from '~/common/util/audioUtils';
|
||||
import { supportsClipboardRead } from '~/common/util/clipboardUtils';
|
||||
import { useDebouncer } from '~/common/components/useDebouncer';
|
||||
@@ -465,7 +466,7 @@ export function Composer(props: {
|
||||
'&:focus-within': {
|
||||
backgroundColor: 'background.popup',
|
||||
},
|
||||
lineHeight: 1.75,
|
||||
lineHeight: lineHeightTextarea,
|
||||
}} />
|
||||
|
||||
{tokenLimit > 0 && (tokensComposer > 0 || (tokensHistory + tokensReponseMax) > 0) && (
|
||||
|
||||
@@ -3,7 +3,7 @@ import TimeAgo from 'react-timeago';
|
||||
import { shallow } from 'zustand/shallow';
|
||||
import { cleanupEfficiency, Diff as TextDiff, makeDiff } from '@sanity/diff-match-patch';
|
||||
|
||||
import { Avatar, Box, Button, CircularProgress, IconButton, ListDivider, ListItem, ListItemDecorator, MenuItem, Stack, Switch, Tooltip, Typography } from '@mui/joy';
|
||||
import { Avatar, Box, Button, CircularProgress, IconButton, ListDivider, ListItem, ListItemDecorator, MenuItem, Switch, Tooltip, Typography } from '@mui/joy';
|
||||
import { SxProps } from '@mui/joy/styles/types';
|
||||
import AccountTreeIcon from '@mui/icons-material/AccountTree';
|
||||
import ClearIcon from '@mui/icons-material/Clear';
|
||||
@@ -29,7 +29,7 @@ import { KeyStroke } from '~/common/components/KeyStroke';
|
||||
import { Link } from '~/common/components/Link';
|
||||
import { SystemPurposeId, SystemPurposes } from '../../../../data';
|
||||
import { copyToClipboard } from '~/common/util/clipboardUtils';
|
||||
import { cssRainbowColorKeyframes } from '~/common/app.theme';
|
||||
import { cssRainbowColorKeyframes, lineHeightChatText } from '~/common/app.theme';
|
||||
import { prettyBaseModel } from '~/common/util/modelUtils';
|
||||
import { useUIPreferencesStore } from '~/common/state/store-ui';
|
||||
|
||||
@@ -409,15 +409,19 @@ export function ChatMessage(props: {
|
||||
// per-blocks css
|
||||
const blockSx: SxProps = {
|
||||
my: 'auto',
|
||||
lineHeight: lineHeightChatText,
|
||||
};
|
||||
const typographySx: SxProps = {
|
||||
lineHeight: lineHeightChatText,
|
||||
};
|
||||
const codeSx: SxProps = {
|
||||
// backgroundColor: fromAssistant ? 'background.level1' : 'background.level1',
|
||||
backgroundColor: props.codeBackground ? props.codeBackground : fromAssistant ? 'neutral.plainHoverBg' : 'primary.plainActiveBg',
|
||||
boxShadow: 'xs',
|
||||
fontFamily: 'code',
|
||||
fontSize: '14px',
|
||||
fontSize: '0.875rem',
|
||||
fontVariantLigatures: 'none',
|
||||
lineHeight: 1.75,
|
||||
lineHeight: lineHeightChatText,
|
||||
borderRadius: 'var(--joy-radius-sm)',
|
||||
};
|
||||
|
||||
@@ -482,7 +486,12 @@ export function ChatMessage(props: {
|
||||
{/* Edit / Blocks */}
|
||||
{isEditing
|
||||
|
||||
? <InlineTextarea initialText={messageText} onEdit={handleTextEdited} sx={{ ...blockSx, lineHeight: 1.75, flexGrow: 1 }} />
|
||||
? <InlineTextarea
|
||||
initialText={messageText} onEdit={handleTextEdited}
|
||||
sx={{
|
||||
...blockSx,
|
||||
flexGrow: 1,
|
||||
}} />
|
||||
|
||||
: <Box
|
||||
onContextMenu={(ENABLE_SELECTION_RIGHT_CLICK_MENU && props.onMessageEdit) ? event => handleMouseUp(event.nativeEvent) : undefined}
|
||||
@@ -526,12 +535,12 @@ export function ChatMessage(props: {
|
||||
: block.type === 'image'
|
||||
? <RenderImage key={'image-' + index} imageBlock={block} isFirst={!index} allowRunAgain={props.isBottom === true} onRunAgain={handleOpsConversationRestartFrom} />
|
||||
: block.type === 'latex'
|
||||
? <RenderLatex key={'latex-' + index} latexBlock={block} />
|
||||
? <RenderLatex key={'latex-' + index} latexBlock={block} sx={typographySx} />
|
||||
: block.type === 'diff'
|
||||
? <RenderTextDiff key={'latex-' + index} diffBlock={block} />
|
||||
? <RenderTextDiff key={'latex-' + index} diffBlock={block} sx={typographySx} />
|
||||
: (renderMarkdown && props.noMarkdown !== true && !fromSystem && !(fromUser && block.content.startsWith('/')))
|
||||
? <RenderMarkdown key={'text-md-' + index} textBlock={block} />
|
||||
: <RenderText key={'text-' + index} textBlock={block} />)}
|
||||
? <RenderMarkdown key={'text-md-' + index} textBlock={block} sx={typographySx} />
|
||||
: <RenderText key={'text-' + index} textBlock={block} sx={typographySx} />)}
|
||||
|
||||
{isCollapsed && (
|
||||
<Button variant='plain' color='neutral' onClick={handleUncollapse}>... expand ...</Button>
|
||||
|
||||
@@ -17,7 +17,6 @@ const RenderLatexDynamic = React.lazy(async () => {
|
||||
export const RenderLatex = ({ latexBlock, sx }: { latexBlock: LatexBlock; sx?: SxProps; }) =>
|
||||
<Box
|
||||
sx={{
|
||||
lineHeight: 1.75,
|
||||
mx: 1.5,
|
||||
...(sx || {}),
|
||||
}}>
|
||||
|
||||
@@ -1,15 +1,16 @@
|
||||
import * as React from 'react';
|
||||
|
||||
import type { SxProps } from '@mui/joy/styles/types';
|
||||
import { Box, useTheme } from '@mui/joy';
|
||||
|
||||
import { TextBlock } from './blocks';
|
||||
import type { TextBlock } from './blocks';
|
||||
|
||||
|
||||
// Dynamically import ReactMarkdown using React.lazy
|
||||
const ReactMarkdown = React.lazy(async () => {
|
||||
const [markdownModule, remarkGfmModule] = await Promise.all([
|
||||
import('react-markdown'),
|
||||
import('remark-gfm')
|
||||
import('remark-gfm'),
|
||||
]);
|
||||
|
||||
// Pass the dynamically imported remarkGfm as children
|
||||
@@ -21,7 +22,7 @@ const ReactMarkdown = React.lazy(async () => {
|
||||
});
|
||||
|
||||
|
||||
export const RenderMarkdown = ({ textBlock }: { textBlock: TextBlock }) => {
|
||||
export const RenderMarkdown = (props: { textBlock: TextBlock, sx?: SxProps }) => {
|
||||
const theme = useTheme();
|
||||
return (
|
||||
<Box
|
||||
@@ -30,13 +31,15 @@ export const RenderMarkdown = ({ textBlock }: { textBlock: TextBlock }) => {
|
||||
mx: '12px !important', // margin: 1.5 like other blocks
|
||||
'& table': { width: 'inherit !important' }, // un-break auto-width (tables have 'max-content', which overflows)
|
||||
'--color-canvas-default': 'transparent !important', // remove the default background color
|
||||
fontFamily: `inherit !important`, // use the default font family
|
||||
lineHeight: '1.75 !important', // line-height: 1.75 like the text block
|
||||
// NOTE: the following are not needed because the CSS is under our control, and we
|
||||
// disabled the redefintions there
|
||||
// fontFamily: `inherit !important`, // use the default font family
|
||||
...(props.sx || {}),
|
||||
}}>
|
||||
|
||||
{/* Using React.Suspense / React.Lazy loading this */}
|
||||
<React.Suspense fallback={<div>Loading...</div>}>
|
||||
<ReactMarkdown>{textBlock.content}</ReactMarkdown>
|
||||
<ReactMarkdown>{props.textBlock.content}</ReactMarkdown>
|
||||
</React.Suspense>
|
||||
</Box>
|
||||
);
|
||||
|
||||
@@ -13,7 +13,6 @@ export const RenderText = ({ textBlock, sx }: { textBlock: TextBlock; sx?: SxPro
|
||||
return (
|
||||
<Typography
|
||||
sx={{
|
||||
lineHeight: 1.75,
|
||||
mx: 1.5,
|
||||
display: 'flex', alignItems: 'baseline',
|
||||
overflowWrap: 'anywhere',
|
||||
|
||||
@@ -38,14 +38,13 @@ export const RenderTextDiff = ({ diffBlock, sx }: { diffBlock: DiffBlock; sx?: S
|
||||
return (
|
||||
<Typography
|
||||
sx={{
|
||||
lineHeight: 1.75,
|
||||
mx: 1.5,
|
||||
// display: 'flex', alignItems: 'baseline',
|
||||
overflowWrap: 'anywhere',
|
||||
whiteSpace: 'break-spaces',
|
||||
...(sx || {}),
|
||||
display: 'block',
|
||||
zIndex: 200,
|
||||
...(sx || {}),
|
||||
}}
|
||||
>
|
||||
{textDiffs.map(([op, text], index) =>
|
||||
|
||||
@@ -7,6 +7,7 @@ import SearchIcon from '@mui/icons-material/Search';
|
||||
import TelegramIcon from '@mui/icons-material/Telegram';
|
||||
|
||||
import { DConversationId, useChatStore } from '~/common/state/store-chats';
|
||||
import { lineHeightTextarea } from '~/common/app.theme';
|
||||
import { navigateToPersonas } from '~/common/app.routes';
|
||||
import { useUIPreferencesStore } from '~/common/state/store-ui';
|
||||
|
||||
@@ -268,7 +269,7 @@ export function PersonaSelector(props: { conversationId: DConversationId, runExa
|
||||
'&:focus-within': {
|
||||
backgroundColor: 'background.popup',
|
||||
},
|
||||
lineHeight: 1.75,
|
||||
lineHeight: lineHeightTextarea,
|
||||
mt: 1,
|
||||
}} />
|
||||
)}
|
||||
|
||||
@@ -10,6 +10,7 @@ import { GoodModal } from '~/common/components/GoodModal';
|
||||
import { GoodTooltip } from '~/common/components/GoodTooltip';
|
||||
import { apiQuery } from '~/common/util/trpc.client';
|
||||
import { copyToClipboard } from '~/common/util/clipboardUtils';
|
||||
import { lineHeightChatText, lineHeightTextarea } from '~/common/app.theme';
|
||||
import { useFormRadioLlmType } from '~/common/components/forms/useFormRadioLlmType';
|
||||
|
||||
import { LLMChainStep, useLLMChain } from './useLLMChain';
|
||||
@@ -174,7 +175,7 @@ export function PersonaCreator() {
|
||||
'&:focus-within': {
|
||||
backgroundColor: 'background.popup',
|
||||
},
|
||||
lineHeight: 1.75,
|
||||
lineHeight: lineHeightTextarea,
|
||||
mb: 1.5,
|
||||
}}
|
||||
/>
|
||||
@@ -219,7 +220,7 @@ export function PersonaCreator() {
|
||||
<Alert variant='soft' color='success' sx={{ mb: 1 }}>
|
||||
You may now copy the text below and use it as Custom prompt!
|
||||
</Alert>
|
||||
<Typography level='title-sm' sx={{ lineHeight: 1.75 }}>
|
||||
<Typography level='title-sm' sx={{ lineHeight: lineHeightChatText }}>
|
||||
{chainOutput}
|
||||
</Typography>
|
||||
</CardContent>
|
||||
|
||||
@@ -146,6 +146,9 @@ export const themeBgApp = 'background.level1';
|
||||
export const themeBgAppDarker = 'background.level2';
|
||||
export const themeBgAppChatComposer = 'background.surface';
|
||||
|
||||
export const lineHeightChatText = 1.75;
|
||||
export const lineHeightTextarea = 1.75;
|
||||
|
||||
export const bodyFontClassName = inter.className;
|
||||
export const themeBreakpoints = appTheme.breakpoints.values;
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@ import { FormLabelStart } from '~/common/components/forms/FormLabelStart';
|
||||
import { GoodModal } from '~/common/components/GoodModal';
|
||||
import { Section } from '~/common/components/Section';
|
||||
import { countModelTokens } from '~/common/util/token-counter';
|
||||
import { lineHeightTextarea } from '~/common/app.theme';
|
||||
|
||||
import { summerizeToFitContextBudget } from './summerize';
|
||||
|
||||
@@ -141,8 +142,7 @@ export function ContentReducer(props: {
|
||||
minRows={4} maxRows={8}
|
||||
value={reducedText}
|
||||
sx={{
|
||||
fontSize: '14px',
|
||||
lineHeight: 1.75,
|
||||
lineHeight: lineHeightTextarea,
|
||||
}} />
|
||||
|
||||
<TokenBadgeMemo direct={reducedTokens} limit={props.tokenLimit} absoluteBottomRight />
|
||||
|
||||
Reference in New Issue
Block a user