fix(app): standardize workspace typography

Use the shared interface text tier across the workspace header, conversation, and composer so the working surface no longer shifts between adjacent font sizes.
This commit is contained in:
Mohamed Boudra
2026-08-16 15:59:44 +02:00
parent 42245d139a
commit a9e3be168c
6 changed files with 42 additions and 28 deletions
+11 -9
View File
@@ -354,8 +354,10 @@ const userMessageStylesheet = StyleSheet.create((theme) => ({
},
text: {
color: theme.colors.foreground,
fontSize: theme.fontSize.base,
...(isWeb ? { lineHeight: 22, overflowWrap: "anywhere" as const } : {}),
fontSize: theme.fontSize.sm,
...(isWeb
? { lineHeight: Math.round(theme.fontSize.sm * 1.4), overflowWrap: "anywhere" as const }
: {}),
},
imagePreviewContainer: {
flexDirection: "row",
@@ -1093,7 +1095,7 @@ const expandableBadgeStylesheet = StyleSheet.create((theme) => ({
},
label: {
color: theme.colors.foregroundMuted,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
flexShrink: 0,
},
@@ -1108,7 +1110,7 @@ const expandableBadgeStylesheet = StyleSheet.create((theme) => ({
flexShrink: 1,
minWidth: 0,
color: theme.colors.foregroundMuted,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
marginLeft: theme.spacing[2],
},
@@ -1117,7 +1119,7 @@ const expandableBadgeStylesheet = StyleSheet.create((theme) => ({
},
shimmerText: {
color: "transparent",
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
},
spacer: {
@@ -1950,14 +1952,14 @@ const speakMessageStylesheet = StyleSheet.create((theme) => ({
},
headerLabel: {
fontFamily: theme.fontFamily.ui,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
color: theme.colors.foregroundMuted,
},
text: {
fontFamily: theme.fontFamily.ui,
fontSize: theme.fontSize.base,
lineHeight: 22,
fontSize: theme.fontSize.sm,
lineHeight: Math.round(theme.fontSize.sm * 1.4),
color: theme.colors.foreground,
},
}));
@@ -2260,7 +2262,7 @@ const todoListCardStylesheet = StyleSheet.create((theme) => ({
},
emptyText: {
color: theme.colors.foregroundMuted,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
},
}));
+2 -2
View File
@@ -1915,9 +1915,9 @@ const styles = StyleSheet.create((theme: Theme) => ({
textInput: {
width: "100%",
color: theme.colors.foreground,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
lineHeight: theme.fontSize.base * 1.4,
lineHeight: theme.fontSize.sm * 1.4,
...(isWeb
? ({
outlineStyle: "none",
@@ -3942,14 +3942,8 @@ const styles = StyleSheet.create((theme) => ({
flex: 1,
minHeight: 0,
},
// Compact steps the whole header down one rung of the scale. The title and the project line
// stack there, so at the shared size they read as two headings rather than a subject and its
// caption, and they cost two full lines of a header that has none to spare.
headerTitle: {
fontSize: {
xs: theme.fontSize.sm,
md: theme.fontSize.base,
},
fontSize: theme.fontSize.sm,
},
headerTitleContainer: {
flex: 1,
@@ -3999,7 +3993,7 @@ const styles = StyleSheet.create((theme) => ({
color: theme.colors.foregroundMuted,
fontSize: {
xs: theme.fontSize.xs,
md: theme.fontSize.base,
md: theme.fontSize.sm,
},
flexShrink: 1,
minWidth: 0,
@@ -3,6 +3,24 @@ import { createCompactMarkdownStyles, createMarkdownStyles } from "./markdown-st
import { darkTheme } from "./theme";
describe("createMarkdownStyles", () => {
it("uses the standard interface size for conversation prose and list markers", () => {
const styles = createMarkdownStyles(darkTheme);
const proseLineHeight = Math.round(darkTheme.fontSize.sm * 1.4);
expect(styles.body).toMatchObject({
fontSize: darkTheme.fontSize.sm,
lineHeight: proseLineHeight,
});
expect(styles.bullet_list_icon).toMatchObject({
fontSize: darkTheme.fontSize.sm,
lineHeight: proseLineHeight,
});
expect(styles.ordered_list_icon).toMatchObject({
fontSize: darkTheme.fontSize.sm,
lineHeight: proseLineHeight,
});
});
it("applies shrink-and-wrap constraints to long markdown text and links", () => {
const styles = createMarkdownStyles(darkTheme);
+7 -7
View File
@@ -19,10 +19,10 @@ export function createMarkdownStyles(theme: Theme) {
body: {
...webSelectableTextStyle,
color: theme.colors.foreground,
fontSize: theme.fontSize.base,
// Prose line-height scales with the UI ramp (≈22 at base 16), NOT the
fontSize: theme.fontSize.sm,
// Prose line-height scales with the UI ramp, not the
// code-size-coupled lineHeight.diff token used by code/diff surfaces.
lineHeight: Math.round(theme.fontSize.base * 1.4),
lineHeight: Math.round(theme.fontSize.sm * 1.4),
flexShrink: 1,
minWidth: 0,
width: "100%" as const,
@@ -283,17 +283,17 @@ export function createMarkdownStyles(theme: Theme) {
...webSelectableTextStyle,
color: theme.colors.foregroundMuted,
marginRight: 4,
fontSize: theme.fontSize.base,
lineHeight: 22,
fontSize: theme.fontSize.sm,
lineHeight: Math.round(theme.fontSize.sm * 1.4),
},
ordered_list_icon: {
...webSelectableTextStyle,
color: theme.colors.foregroundMuted,
marginRight: 4,
fontSize: theme.fontSize.base,
fontSize: theme.fontSize.sm,
fontWeight: theme.fontWeight.normal,
lineHeight: 22,
lineHeight: Math.round(theme.fontSize.sm * 1.4),
minWidth: 12,
},