Feat: UI / UX

This commit is contained in:
2026-02-16 01:22:40 +01:00
parent b23dd85d0f
commit af6732db1c
37 changed files with 1045 additions and 64 deletions

View File

@@ -183,7 +183,15 @@ fn render_content(frame: &mut Frame, app: &App, area: Rect) {
let has_query = !query.is_empty();
let query_lower = query.to_lowercase();
let lines = cagire_markdown::parse(md, &AppTheme, &ForthHighlighter);
// Populate parse cache for this topic
{
let mut cache = app.ui.help_parsed.borrow_mut();
if cache[app.ui.help_topic].is_none() {
cache[app.ui.help_topic] = Some(cagire_markdown::parse(md, &AppTheme, &ForthHighlighter));
}
}
let cache = app.ui.help_parsed.borrow();
let parsed = cache[app.ui.help_topic].as_ref().unwrap();
let has_search_bar = app.ui.help_search_active || has_query;
let content_area = if has_search_bar {
@@ -201,13 +209,33 @@ fn render_content(frame: &mut Frame, app: &App, area: Rect) {
let visible_height = content_area.height.saturating_sub(6) as usize;
// Calculate total wrapped line count for accurate max_scroll
let total_wrapped: usize = lines
let total_wrapped: usize = parsed
.lines
.iter()
.map(|l| wrapped_line_count(l, content_width))
.sum();
let max_scroll = total_wrapped.saturating_sub(visible_height);
let scroll = app.ui.help_scroll().min(max_scroll);
let mut lines = parsed.lines.clone();
// Highlight focused code block with background tint
if let Some(block_idx) = app.ui.help_focused_block {
if let Some(block) = parsed.code_blocks.get(block_idx) {
let tint_bg = theme.ui.surface;
for line in lines.iter_mut().take(block.end_line).skip(block.start_line) {
for (i, span) in line.spans.iter_mut().enumerate() {
let style = if i < 2 {
span.style.fg(theme.ui.accent).bg(tint_bg)
} else {
span.style.bg(tint_bg)
};
*span = Span::styled(span.content.clone(), style);
}
}
}
}
let lines: Vec<RLine> = if has_query {
lines
.into_iter()