mirror of
https://github.com/QwenLM/qwen-code.git
synced 2025-12-20 08:47:44 +00:00
Feature custom themes logic (#2639)
Co-authored-by: Jacob Richman <jacob314@gmail.com>
This commit is contained in:
@@ -36,22 +36,45 @@ export function ThemeDialog({
|
||||
SettingScope.User,
|
||||
);
|
||||
|
||||
const capitalize = (s: string) => s.charAt(0).toUpperCase() + s.slice(1);
|
||||
// Track the currently highlighted theme name
|
||||
const [highlightedThemeName, setHighlightedThemeName] = useState<
|
||||
string | undefined
|
||||
>(settings.merged.theme || DEFAULT_THEME.name);
|
||||
|
||||
// Generate theme items filtered by selected scope
|
||||
const customThemes =
|
||||
selectedScope === SettingScope.User
|
||||
? settings.user.settings.customThemes || {}
|
||||
: settings.merged.customThemes || {};
|
||||
const builtInThemes = themeManager
|
||||
.getAvailableThemes()
|
||||
.filter((theme) => theme.type !== 'custom');
|
||||
const customThemeNames = Object.keys(customThemes);
|
||||
const capitalize = (s: string) => s.charAt(0).toUpperCase() + s.slice(1);
|
||||
// Generate theme items
|
||||
const themeItems = themeManager.getAvailableThemes().map((theme) => ({
|
||||
label: theme.name,
|
||||
value: theme.name,
|
||||
themeNameDisplay: theme.name,
|
||||
themeTypeDisplay: capitalize(theme.type),
|
||||
}));
|
||||
const themeItems = [
|
||||
...builtInThemes.map((theme) => ({
|
||||
label: theme.name,
|
||||
value: theme.name,
|
||||
themeNameDisplay: theme.name,
|
||||
themeTypeDisplay: capitalize(theme.type),
|
||||
})),
|
||||
...customThemeNames.map((name) => ({
|
||||
label: name,
|
||||
value: name,
|
||||
themeNameDisplay: name,
|
||||
themeTypeDisplay: 'Custom',
|
||||
})),
|
||||
];
|
||||
const [selectInputKey, setSelectInputKey] = useState(Date.now());
|
||||
|
||||
// Determine which radio button should be initially selected in the theme list
|
||||
// This should reflect the theme *saved* for the selected scope, or the default
|
||||
// Find the index of the selected theme, but only if it exists in the list
|
||||
const selectedThemeName = settings.merged.theme || DEFAULT_THEME.name;
|
||||
const initialThemeIndex = themeItems.findIndex(
|
||||
(item) => item.value === (settings.merged.theme || DEFAULT_THEME.name),
|
||||
(item) => item.value === selectedThemeName,
|
||||
);
|
||||
// If not found, fallback to the first theme
|
||||
const safeInitialThemeIndex = initialThemeIndex >= 0 ? initialThemeIndex : 0;
|
||||
|
||||
const scopeItems = [
|
||||
{ label: 'User Settings', value: SettingScope.User },
|
||||
@@ -66,6 +89,11 @@ export function ThemeDialog({
|
||||
[onSelect, selectedScope],
|
||||
);
|
||||
|
||||
const handleThemeHighlight = (themeName: string) => {
|
||||
setHighlightedThemeName(themeName);
|
||||
onHighlight(themeName);
|
||||
};
|
||||
|
||||
const handleScopeHighlight = useCallback((scope: SettingScope) => {
|
||||
setSelectedScope(scope);
|
||||
setSelectInputKey(Date.now());
|
||||
@@ -182,7 +210,6 @@ export function ThemeDialog({
|
||||
// The code block is slightly longer than the diff, so give it more space.
|
||||
const codeBlockHeight = Math.ceil(availableHeightForPanes * 0.6);
|
||||
const diffHeight = Math.floor(availableHeightForPanes * 0.4);
|
||||
const themeType = capitalize(themeManager.getActiveTheme().type);
|
||||
return (
|
||||
<Box
|
||||
borderStyle="round"
|
||||
@@ -204,9 +231,9 @@ export function ThemeDialog({
|
||||
<RadioButtonSelect
|
||||
key={selectInputKey}
|
||||
items={themeItems}
|
||||
initialIndex={initialThemeIndex}
|
||||
initialIndex={safeInitialThemeIndex}
|
||||
onSelect={handleThemeSelect}
|
||||
onHighlight={onHighlight}
|
||||
onHighlight={handleThemeHighlight}
|
||||
isFocused={currenFocusedSection === 'theme'}
|
||||
maxItemsToShow={8}
|
||||
showScrollArrows={true}
|
||||
@@ -233,40 +260,44 @@ export function ThemeDialog({
|
||||
|
||||
{/* Right Column: Preview */}
|
||||
<Box flexDirection="column" width="55%" paddingLeft={2}>
|
||||
<Text bold>{themeType} Theme Preview</Text>
|
||||
<Box
|
||||
borderStyle="single"
|
||||
borderColor={Colors.Gray}
|
||||
paddingTop={includePadding ? 1 : 0}
|
||||
paddingBottom={includePadding ? 1 : 0}
|
||||
paddingLeft={1}
|
||||
paddingRight={1}
|
||||
flexDirection="column"
|
||||
>
|
||||
{colorizeCode(
|
||||
`# python function
|
||||
def fibonacci(n):
|
||||
a, b = 0, 1
|
||||
for _ in range(n):
|
||||
a, b = b, a + b
|
||||
return a`,
|
||||
'python',
|
||||
codeBlockHeight,
|
||||
colorizeCodeWidth,
|
||||
)}
|
||||
<Box marginTop={1} />
|
||||
<DiffRenderer
|
||||
diffContent={`--- a/util.py
|
||||
+++ b/util.py
|
||||
@@ -1,3 +1,3 @@
|
||||
def greet(name):
|
||||
- print("Hello, " + name)
|
||||
+ print(f"Hello, {name}!")
|
||||
`}
|
||||
availableTerminalHeight={diffHeight}
|
||||
terminalWidth={colorizeCodeWidth}
|
||||
/>
|
||||
</Box>
|
||||
<Text bold>Preview</Text>
|
||||
{/* Get the Theme object for the highlighted theme, fallback to default if not found */}
|
||||
{(() => {
|
||||
const previewTheme =
|
||||
themeManager.getTheme(
|
||||
highlightedThemeName || DEFAULT_THEME.name,
|
||||
) || DEFAULT_THEME;
|
||||
return (
|
||||
<Box
|
||||
borderStyle="single"
|
||||
borderColor={Colors.Gray}
|
||||
paddingTop={includePadding ? 1 : 0}
|
||||
paddingBottom={includePadding ? 1 : 0}
|
||||
paddingLeft={1}
|
||||
paddingRight={1}
|
||||
flexDirection="column"
|
||||
>
|
||||
{colorizeCode(
|
||||
`# function
|
||||
-def fibonacci(n):
|
||||
- a, b = 0, 1
|
||||
- for _ in range(n):
|
||||
- a, b = b, a + b
|
||||
- return a`,
|
||||
'python',
|
||||
codeBlockHeight,
|
||||
colorizeCodeWidth,
|
||||
)}
|
||||
<Box marginTop={1} />
|
||||
<DiffRenderer
|
||||
diffContent={`--- a/old_file.txt\n+++ b/new_file.txt\n@@ -1,6 +1,7 @@\n # function\n-def fibonacci(n):\n- a, b = 0, 1\n- for _ in range(n):\n- a, b = b, a + b\n- return a\n+def fibonacci(n):\n+ a, b = 0, 1\n+ for _ in range(n):\n+ a, b = b, a + b\n+ return a\n+\n+print(fibonacci(10))\n`}
|
||||
availableTerminalHeight={diffHeight}
|
||||
terminalWidth={colorizeCodeWidth}
|
||||
theme={previewTheme}
|
||||
/>
|
||||
</Box>
|
||||
);
|
||||
})()}
|
||||
</Box>
|
||||
</Box>
|
||||
<Box marginTop={1}>
|
||||
|
||||
Reference in New Issue
Block a user