Skip to main content

codetether_agent/tui/ui/webview/
chat.rs

1use ratatui::{
2    Frame,
3    layout::Rect,
4    style::{Color, Style},
5    text::Line,
6    widgets::{Block, Borders, Paragraph, Wrap},
7};
8
9use crate::tui::app::state::App;
10
11/// Minimum terminal size for webview layout.
12const MIN_WIDTH: u16 = 90;
13const MIN_HEIGHT: u16 = 18;
14
15pub fn render_webview_chat_center(f: &mut Frame, app: &App, area: Rect, lines: &[Line<'static>]) {
16    let visible = area.height.saturating_sub(2) as usize;
17    let scroll = app
18        .state
19        .chat_scroll
20        .min(lines.len().saturating_sub(visible));
21    let block = Block::default()
22        .borders(Borders::NONE)
23        .style(Style::default().fg(Color::default()));
24    let para = Paragraph::new(lines.to_vec())
25        .block(block)
26        .wrap(Wrap { trim: false })
27        .scroll((scroll as u16, 0));
28    f.render_widget(para, area);
29}
30
31pub fn render_webview_input(f: &mut Frame, app: &App, area: Rect) {
32    let mode_label = if app.state.input_mode == crate::tui::models::InputMode::Command {
33        " [CMD]"
34    } else {
35        ""
36    };
37    let title = format!(" Input{mode_label} ");
38    let block = Block::default()
39        .borders(Borders::ALL)
40        .title(title)
41        .border_style(Style::default().fg(Color::Cyan));
42    let para = Paragraph::new(app.state.input.as_str())
43        .block(block)
44        .wrap(Wrap { trim: false });
45    f.render_widget(para, area);
46}
47
48pub fn terminal_too_small(area: Rect) -> bool {
49    area.width < MIN_WIDTH || area.height < MIN_HEIGHT
50}