| ... | ... | @@ -122,6 +122,7 @@ import { |
| 122 | 122 | backgroundActivitySharedPolicySettings, |
| 123 | 123 | durationToSeconds, |
| 124 | 124 | formatDiagnosticsDescription, |
| 125 | getChangedTypographySettingLabels, |
| 125 | 126 | normalizeIntervalSeconds, |
| 126 | 127 | PROVIDER_HEALTH_INTERVAL_STEP_SECONDS, |
| 127 | 128 | hasChangedBackgroundActivitySettings, |
| ... | ... | @@ -493,16 +494,7 @@ export function useSettingsRestore(onRestored?: () => void) { |
| 493 | 494 | ? ["Auto-settle inactive threads"] |
| 494 | 495 | : []), |
| 495 | 496 | ...(settings.wordWrap !== DEFAULT_UNIFIED_SETTINGS.wordWrap ? ["Word wrap"] : []), |
| 496 | | ...(settings.fontFamilySans !== DEFAULT_UNIFIED_SETTINGS.fontFamilySans |
| 497 | | ? ["Interface font"] |
| 498 | | : []), |
| 499 | | ...(settings.fontFamilyComposer !== DEFAULT_UNIFIED_SETTINGS.fontFamilyComposer |
| 500 | | ? ["Prompt font"] |
| 501 | | : []), |
| 502 | | ...(settings.fontFamilyCode !== DEFAULT_UNIFIED_SETTINGS.fontFamilyCode ? ["Code font"] : []), |
| 503 | | ...(settings.fontFamilyTerminal !== DEFAULT_UNIFIED_SETTINGS.fontFamilyTerminal |
| 504 | | ? ["Terminal font"] |
| 505 | | : []), |
| 497 | ...getChangedTypographySettingLabels(settings), |
| 506 | 498 | ...(settings.diffIgnoreWhitespace !== DEFAULT_UNIFIED_SETTINGS.diffIgnoreWhitespace |
| 507 | 499 | ? ["Diff whitespace changes"] |
| 508 | 500 | : []), |
| ... | ... | @@ -652,6 +644,10 @@ export function useSettingsRestore(onRestored?: () => void) { |
| 652 | 644 | fontFamilyComposer: DEFAULT_UNIFIED_SETTINGS.fontFamilyComposer, |
| 653 | 645 | fontFamilyCode: DEFAULT_UNIFIED_SETTINGS.fontFamilyCode, |
| 654 | 646 | fontFamilyTerminal: DEFAULT_UNIFIED_SETTINGS.fontFamilyTerminal, |
| 647 | fontSizeInterface: DEFAULT_UNIFIED_SETTINGS.fontSizeInterface, |
| 648 | fontSizePrompt: DEFAULT_UNIFIED_SETTINGS.fontSizePrompt, |
| 649 | fontSizeCode: DEFAULT_UNIFIED_SETTINGS.fontSizeCode, |
| 650 | fontSizeTerminal: DEFAULT_UNIFIED_SETTINGS.fontSizeTerminal, |
| 655 | 651 | }); |
| 656 | 652 | onRestored?.(); |
| 657 | 653 | }, [ |
| ... | ... | @@ -1105,13 +1101,21 @@ function InterfaceFontRow({ preview }: { preview?: ReactNode }) { |
| 1105 | 1101 | {...searchableSetting("interface-font")} |
| 1106 | 1102 | description="Everything outside code blocks and the terminal." |
| 1107 | 1103 | defaultFamily={defaults.sans} |
| 1104 | defaultValue={DEFAULT_UNIFIED_SETTINGS.fontFamilySans} |
| 1108 | 1105 | value={settings.fontFamilySans} |
| 1109 | 1106 | onValueChange={(fontFamilySans) => updateSettings({ fontFamilySans })} |
| 1107 | onReset={() => |
| 1108 | updateSettings({ |
| 1109 | fontFamilySans: DEFAULT_UNIFIED_SETTINGS.fontFamilySans, |
| 1110 | fontSizeInterface: DEFAULT_UNIFIED_SETTINGS.fontSizeInterface, |
| 1111 | }) |
| 1112 | } |
| 1110 | 1113 | size={{ |
| 1111 | 1114 | label: "Interface font size", |
| 1112 | 1115 | min: MIN_INTERFACE_FONT_SIZE, |
| 1113 | 1116 | max: MAX_INTERFACE_FONT_SIZE, |
| 1114 | 1117 | value: settings.fontSizeInterface, |
| 1118 | defaultValue: DEFAULT_UNIFIED_SETTINGS.fontSizeInterface, |
| 1115 | 1119 | onChange: (fontSizeInterface) => updateSettings({ fontSizeInterface }), |
| 1116 | 1120 | }} |
| 1117 | 1121 | {...(preview !== undefined ? { preview } : {})} |
| ... | ... | @@ -1128,13 +1132,21 @@ function PromptFontRow() { |
| 1128 | 1132 | {...searchableSetting("prompt-font")} |
| 1129 | 1133 | description="Only the box you write prompts in. Mono works well here." |
| 1130 | 1134 | defaultFamily={defaults.interfaceFamily} |
| 1135 | defaultValue={DEFAULT_UNIFIED_SETTINGS.fontFamilyComposer} |
| 1131 | 1136 | value={settings.fontFamilyComposer} |
| 1132 | 1137 | onValueChange={(fontFamilyComposer) => updateSettings({ fontFamilyComposer })} |
| 1138 | onReset={() => |
| 1139 | updateSettings({ |
| 1140 | fontFamilyComposer: DEFAULT_UNIFIED_SETTINGS.fontFamilyComposer, |
| 1141 | fontSizePrompt: DEFAULT_UNIFIED_SETTINGS.fontSizePrompt, |
| 1142 | }) |
| 1143 | } |
| 1133 | 1144 | size={{ |
| 1134 | 1145 | label: "Prompt font size", |
| 1135 | 1146 | min: MIN_PROMPT_FONT_SIZE, |
| 1136 | 1147 | max: MAX_PROMPT_FONT_SIZE, |
| 1137 | 1148 | value: settings.fontSizePrompt, |
| 1149 | defaultValue: DEFAULT_UNIFIED_SETTINGS.fontSizePrompt, |
| 1138 | 1150 | onChange: (fontSizePrompt) => updateSettings({ fontSizePrompt }), |
| 1139 | 1151 | }} |
| 1140 | 1152 | preview={<PromptFontPreview />} |
| ... | ... | @@ -1160,14 +1172,22 @@ function CodeFontRow({ |
| 1160 | 1172 | {...(title !== undefined ? { title } : {})} |
| 1161 | 1173 | description={description} |
| 1162 | 1174 | defaultFamily={defaults.code} |
| 1175 | defaultValue={DEFAULT_UNIFIED_SETTINGS.fontFamilyCode} |
| 1163 | 1176 | value={settings.fontFamilyCode} |
| 1164 | 1177 | onValueChange={(fontFamilyCode) => updateSettings({ fontFamilyCode })} |
| 1178 | onReset={() => |
| 1179 | updateSettings({ |
| 1180 | fontFamilyCode: DEFAULT_UNIFIED_SETTINGS.fontFamilyCode, |
| 1181 | fontSizeCode: DEFAULT_UNIFIED_SETTINGS.fontSizeCode, |
| 1182 | }) |
| 1183 | } |
| 1165 | 1184 | requireMonospace |
| 1166 | 1185 | size={{ |
| 1167 | 1186 | label: "Code font size", |
| 1168 | 1187 | min: MIN_CODE_FONT_SIZE, |
| 1169 | 1188 | max: MAX_CODE_FONT_SIZE, |
| 1170 | 1189 | value: settings.fontSizeCode, |
| 1190 | defaultValue: DEFAULT_UNIFIED_SETTINGS.fontSizeCode, |
| 1171 | 1191 | onChange: (fontSizeCode) => updateSettings({ fontSizeCode }), |
| 1172 | 1192 | }} |
| 1173 | 1193 | preview={preview ?? <CodeFontPreview />} |
| ... | ... | @@ -1184,14 +1204,22 @@ function TerminalFontRow() { |
| 1184 | 1204 | {...searchableSetting("terminal-font")} |
| 1185 | 1205 | description="Terminal output, independent from code blocks and diffs." |
| 1186 | 1206 | defaultFamily={defaults.code} |
| 1207 | defaultValue={DEFAULT_UNIFIED_SETTINGS.fontFamilyTerminal} |
| 1187 | 1208 | value={settings.fontFamilyTerminal} |
| 1188 | 1209 | onValueChange={(fontFamilyTerminal) => updateSettings({ fontFamilyTerminal })} |
| 1210 | onReset={() => |
| 1211 | updateSettings({ |
| 1212 | fontFamilyTerminal: DEFAULT_UNIFIED_SETTINGS.fontFamilyTerminal, |
| 1213 | fontSizeTerminal: DEFAULT_UNIFIED_SETTINGS.fontSizeTerminal, |
| 1214 | }) |
| 1215 | } |
| 1189 | 1216 | requireMonospace |
| 1190 | 1217 | size={{ |
| 1191 | 1218 | label: "Terminal font size", |
| 1192 | 1219 | min: MIN_TERMINAL_FONT_SIZE, |
| 1193 | 1220 | max: MAX_TERMINAL_FONT_SIZE, |
| 1194 | 1221 | value: settings.fontSizeTerminal, |
| 1222 | defaultValue: DEFAULT_UNIFIED_SETTINGS.fontSizeTerminal, |
| 1195 | 1223 | onChange: (fontSizeTerminal) => updateSettings({ fontSizeTerminal }), |
| 1196 | 1224 | }} |
| 1197 | 1225 | preview={ |
| ... | ... | @@ -1369,9 +1397,11 @@ function FontFamilySettingsRow({ |
| 1369 | 1397 | title, |
| 1370 | 1398 | description, |
| 1371 | 1399 | defaultFamily, |
| 1400 | defaultValue, |
| 1372 | 1401 | preview, |
| 1373 | 1402 | value, |
| 1374 | 1403 | onValueChange, |
| 1404 | onReset, |
| 1375 | 1405 | requireMonospace = false, |
| 1376 | 1406 | size, |
| 1377 | 1407 | }: { |
| ... | ... | @@ -1380,11 +1410,21 @@ function FontFamilySettingsRow({ |
| 1380 | 1410 | description: string; |
| 1381 | 1411 | /** What an unset preference renders as, e.g. "Menlo". */ |
| 1382 | 1412 | defaultFamily: string; |
| 1413 | /** The persisted family value supplied by the unified settings defaults. */ |
| 1414 | defaultValue: string; |
| 1383 | 1415 | preview?: ReactNode; |
| 1384 | 1416 | value: string; |
| 1385 | 1417 | onValueChange: (value: string) => void; |
| 1418 | onReset: () => void; |
| 1386 | 1419 | requireMonospace?: boolean; |
| 1387 | | size: { label: string; min: number; max: number; value: number; onChange: (v: number) => void }; |
| 1420 | size: { |
| 1421 | label: string; |
| 1422 | min: number; |
| 1423 | max: number; |
| 1424 | value: number; |
| 1425 | defaultValue: number; |
| 1426 | onChange: (v: number) => void; |
| 1427 | }; |
| 1388 | 1428 | }) { |
| 1389 | 1429 | const trimmed = value.trim(); |
| 1390 | 1430 | // The fallback input edits a draft; the preference only commits once typing |
| ... | ... | @@ -1431,12 +1471,18 @@ function FontFamilySettingsRow({ |
| 1431 | 1471 | // Flag an unknown name only once typing pauses, and never for an empty |
| 1432 | 1472 | // field - that is the starting state, not a rejected entry. |
| 1433 | 1473 | const draftPending = draftSettled && draftTrimmed.length > 0 && draftTrimmed !== trimmed; |
| 1474 | const resetToDefault = () => { |
| 1475 | if (commitTimerRef.current !== null) { |
| 1476 | window.clearTimeout(commitTimerRef.current); |
| 1477 | commitTimerRef.current = null; |
| 1478 | } |
| 1479 | setDraft(defaultValue); |
| 1480 | setDraftSettled(true); |
| 1481 | onReset(); |
| 1482 | }; |
| 1434 | 1483 | const resetAction = |
| 1435 | | trimmed.length > 0 ? ( |
| 1436 | | <SettingResetButton |
| 1437 | | label={`${title.toLowerCase()} family`} |
| 1438 | | onClick={() => onValueChange("")} |
| 1439 | | /> |
| 1484 | value !== defaultValue || size.value !== size.defaultValue ? ( |
| 1485 | <SettingResetButton label={title.toLowerCase()} onClick={resetToDefault} /> |
| 1440 | 1486 | ) : null; |
| 1441 | 1487 | const fontEnumeration = useFontEnumeration(); |
| 1442 | 1488 | // Everyone starts on the plain input; focusing it is the user gesture that |