From a685597b70242eb4c6b38d30c5356ad79418176d Mon Sep 17 00:00:00 2001 From: Miguel Solorio Date: Thu, 8 May 2025 16:00:55 -0700 Subject: UI Polish for theme selector (#294) --- .../src/ui/components/shared/RadioButtonSelect.tsx | 101 ++++++++++++++------- 1 file changed, 70 insertions(+), 31 deletions(-) (limited to 'packages/cli/src/ui/components/shared') diff --git a/packages/cli/src/ui/components/shared/RadioButtonSelect.tsx b/packages/cli/src/ui/components/shared/RadioButtonSelect.tsx index 3db8b678..377be3e3 100644 --- a/packages/cli/src/ui/components/shared/RadioButtonSelect.tsx +++ b/packages/cli/src/ui/components/shared/RadioButtonSelect.tsx @@ -27,7 +27,12 @@ export interface RadioSelectItem { */ export interface RadioButtonSelectProps { /** An array of items to display as radio options. */ - items: Array>; + items: Array< + RadioSelectItem & { + themeNameDisplay?: string; + themeTypeDisplay?: string; + } + >; /** The initial index selected */ initialIndex?: number; @@ -42,33 +47,6 @@ export interface RadioButtonSelectProps { isFocused?: boolean; } -/** - * Custom indicator component displaying radio button style (◉/○). - */ -function RadioIndicator({ - isSelected = false, -}: InkSelectIndicatorProps): React.JSX.Element { - return ( - - - {isSelected ? '◉' : '○'} - - - ); -} - -/** - * Custom item component for displaying the label with appropriate color. - */ -function RadioItem({ - isSelected = false, - label, -}: InkSelectItemProps): React.JSX.Element { - return ( - {label} - ); -} - /** * A specialized SelectInput component styled to look like radio buttons. * It uses '◉' for selected and '○' for unselected items. @@ -80,7 +58,7 @@ export function RadioButtonSelect({ initialIndex, onSelect, onHighlight, - isFocused, + isFocused, // This prop indicates if the current RadioButtonSelect group is focused }: RadioButtonSelectProps): React.JSX.Element { const handleSelect = (item: RadioSelectItem) => { onSelect(item.value); @@ -90,11 +68,72 @@ export function RadioButtonSelect({ onHighlight(item.value); } }; + + /** + * Custom indicator component displaying radio button style (◉/○). + * Color changes based on whether the item is selected and if its group is focused. + */ + function DynamicRadioIndicator({ + isSelected = false, + }: InkSelectIndicatorProps): React.JSX.Element { + let indicatorColor = Colors.Foreground; // Default for not selected + if (isSelected) { + if (isFocused) { + // Group is focused, selected item is AccentGreen + indicatorColor = Colors.AccentGreen; + } else { + // Group is NOT focused, selected item is Foreground + indicatorColor = Colors.Foreground; + } + } + return ( + + {isSelected ? '●' : '○'} + + ); + } + + /** + * Custom item component for displaying the label. + * Color changes based on whether the item is selected and if its group is focused. + * Now also handles displaying theme type with custom color. + */ + function CustomThemeItemComponent( + props: InkSelectItemProps, + ): React.JSX.Element { + const { isSelected = false, label } = props; + const itemWithThemeProps = props as typeof props & { + themeNameDisplay?: string; + themeTypeDisplay?: string; + }; + + let textColor = Colors.Foreground; + if (isSelected) { + textColor = isFocused ? Colors.AccentGreen : Colors.Foreground; + } + + if ( + itemWithThemeProps.themeNameDisplay && + itemWithThemeProps.themeTypeDisplay + ) { + return ( + + {itemWithThemeProps.themeNameDisplay}{' '} + + {itemWithThemeProps.themeTypeDisplay} + + + ); + } + + return {label}; + } + initialIndex = initialIndex ?? 0; return (