vtcode_core/ui/
tui_compat.rs1use crate::config::KeyboardProtocolConfig;
7use crate::config::loader::VTCodeConfig;
8use crate::config::types::ReasoningEffortLevel;
9use crate::ui::slash::SlashCommandInfo;
10use crate::ui::theme::ThemeStyles;
11use crate::ui::tui::{
12 InlineTheme, KeyboardProtocolSettings, LayoutModeOverride, ReasoningDisplayMode,
13 SessionSurface, SlashCommandItem, UiMode,
14};
15#[cfg(feature = "tui")]
16use vtcode_tui::ui::theme::ThemeStyles as TuiThemeStyles;
17
18#[cfg(feature = "tui")]
19use crate::ui::tui::{FullscreenInteractionSettings, SessionAppearanceConfig};
20
21#[cfg(not(feature = "tui"))]
22use crate::ui::tui::SessionAppearanceConfig;
23
24pub fn reasoning_to_selection_string(level: ReasoningEffortLevel) -> String {
27 level.as_str().to_owned()
28}
29
30pub fn reasoning_from_selection_string(s: &str) -> ReasoningEffortLevel {
32 ReasoningEffortLevel::parse(s).unwrap_or_default()
33}
34
35pub fn to_tui_surface(preference: crate::config::types::UiSurfacePreference) -> SessionSurface {
36 match preference {
37 crate::config::types::UiSurfacePreference::Auto => SessionSurface::Auto,
38 crate::config::types::UiSurfacePreference::Alternate => SessionSurface::Alternate,
39 crate::config::types::UiSurfacePreference::Inline => SessionSurface::Inline,
40 }
41}
42
43pub fn to_tui_keyboard_protocol(keyboard: KeyboardProtocolConfig) -> KeyboardProtocolSettings {
44 KeyboardProtocolSettings {
45 enabled: keyboard.enabled,
46 mode: keyboard.mode,
47 disambiguate_escape_codes: keyboard.disambiguate_escape_codes,
48 report_event_types: keyboard.report_event_types,
49 report_alternate_keys: keyboard.report_alternate_keys,
50 report_all_keys: keyboard.report_all_keys,
51 }
52}
53
54#[cfg(feature = "tui")]
55pub fn to_tui_fullscreen(config: &VTCodeConfig) -> FullscreenInteractionSettings {
56 FullscreenInteractionSettings {
57 mouse_capture: config.ui.fullscreen.mouse_capture,
58 copy_on_select: config.ui.fullscreen.copy_on_select,
59 scroll_speed: config.ui.fullscreen.scroll_speed,
60 }
61}
62
63pub fn inline_theme_from_core_styles(styles: &ThemeStyles) -> InlineTheme {
65 crate::ui::tui::theme_from_color_fields(
66 styles.foreground,
67 styles.background,
68 styles.primary,
69 styles.secondary,
70 styles.tool,
71 styles.tool_detail,
72 styles.pty_output,
73 )
74}
75
76#[cfg(feature = "tui")]
77pub fn tui_theme_styles_from_core(styles: &ThemeStyles) -> TuiThemeStyles {
78 TuiThemeStyles {
79 info: styles.info,
80 error: styles.error,
81 output: styles.output,
82 response: styles.response,
83 reasoning: styles.reasoning,
84 tool: styles.tool,
85 tool_detail: styles.tool_detail,
86 tool_output: styles.tool_output,
87 pty_output: styles.pty_output,
88 status: styles.status,
89 mcp: styles.mcp,
90 user: styles.user,
91 primary: styles.primary,
92 secondary: styles.secondary,
93 foreground: styles.foreground,
94 background: styles.background,
95 }
96}
97
98#[cfg(not(feature = "tui"))]
99pub fn tui_theme_styles_from_core(styles: &ThemeStyles) -> ThemeStyles {
100 styles.clone()
101}
102
103pub fn to_tui_slash_commands(commands: &[SlashCommandInfo]) -> Vec<SlashCommandItem> {
104 commands
105 .iter()
106 .map(|cmd| SlashCommandItem::new(cmd.name, cmd.description))
107 .collect()
108}
109
110pub fn to_tui_appearance(config: &VTCodeConfig) -> SessionAppearanceConfig {
111 let reduce_motion_mode =
112 config.ui.reduce_motion_mode || matches!(config.tui.animations, Some(false));
113 SessionAppearanceConfig {
114 theme: config.agent.theme.clone(),
115 ui_mode: match config.ui.display_mode {
116 crate::config::UiDisplayMode::Full => UiMode::Full,
117 crate::config::UiDisplayMode::Minimal => UiMode::Minimal,
118 crate::config::UiDisplayMode::Focused => UiMode::Focused,
119 },
120 show_sidebar: config.ui.show_sidebar,
121 min_content_width: 40,
122 min_navigation_width: 20,
123 navigation_width_percent: 25,
124 transcript_bottom_padding: 0,
125 dim_completed_todos: config.ui.dim_completed_todos,
126 message_block_spacing: if config.ui.message_block_spacing {
127 1
128 } else {
129 0
130 },
131 layout_mode: match config.ui.layout_mode {
132 crate::config::LayoutModeOverride::Auto => LayoutModeOverride::Auto,
133 crate::config::LayoutModeOverride::Compact => LayoutModeOverride::Compact,
134 crate::config::LayoutModeOverride::Standard => LayoutModeOverride::Standard,
135 crate::config::LayoutModeOverride::Wide => LayoutModeOverride::Wide,
136 },
137 reasoning_display_mode: match config.ui.reasoning_display_mode {
138 crate::config::ReasoningDisplayMode::Always => ReasoningDisplayMode::Always,
139 crate::config::ReasoningDisplayMode::Toggle => ReasoningDisplayMode::Toggle,
140 crate::config::ReasoningDisplayMode::Hidden => ReasoningDisplayMode::Hidden,
141 },
142 reasoning_visible_default: config.ui.reasoning_visible_default,
143 vim_mode: config.ui.vim_mode,
144 readline_mode: false,
145 screen_reader_mode: config.ui.screen_reader_mode,
146 reduce_motion_mode,
147 reduce_motion_keep_progress_animation: config.ui.reduce_motion_keep_progress_animation,
148 hide_header: config.ui.hide_header,
149 customization: Default::default(),
150 }
151}