changxi 0.3.0

TUI EPUB Reader
use crate::app::{App, ViewMode};
use crate::core::Reader;
use crate::ui::{Component, get_border_type};
use ratatui::{
    Frame,
    layout::Rect,
    widgets::{Block, Borders, Paragraph},
};
use ratatui_image::picker::Picker;

pub struct Footer;

impl Component for Footer {
    fn render(&self, f: &mut Frame, area: Rect, app: &mut App, _picker: &mut Picker) {
        let footer_text = match app.mode {
            ViewMode::ChapterBrowser => format!(
                " Chapter Browser | ↑/↓ or j/k: navigate, Enter: select, Esc: back, q: quit | Chapter {}/{} ",
                app.chapter_list_state.selected().unwrap_or(0) + 1,
                app.chapter_titles.len()
            ),
            ViewMode::Reading => {
                let progress = if app.total_height > app.viewport_height {
                    (app.scroll as f64 / (app.total_height - app.viewport_height) as f64 * 100.0)
                        .min(100.0)
                } else {
                    100.0
                };
                format!(
                    " Chapter {}/{} | {:>3.0}% | Tab: chapters, /: search, v: visual, n/N: search results, V: view mode, q: quit, c: cover, l: library, arrows: navigate ",
                    app.current_chapter + 1,
                    app.reader.chapter_count(),
                    progress
                )
            }
            ViewMode::Cover => format!(
                " Cover View | Chapter {}/{} | Tab: chapters, q: quit, c: text, ←/→: prev/next chapter, l: library ",
                app.current_chapter + 1,
                app.reader.chapter_count()
            ),
            ViewMode::Library => {
                " Library | Enter: select, Esc/l: back, s: sort, q: quit, j/k: navigate "
                    .to_string()
            }
            ViewMode::BookmarkBrowser => {
                " Bookmark Browser | Enter: jump, d: delete, r: rename, Esc/b: back, q: quit, j/k: navigate "
                    .to_string()
            }
            ViewMode::BookmarkRenaming => {
                " Rename Bookmark | Enter: finish, Esc: cancel, Backspace: delete ".to_string()
            }
            ViewMode::Search => {
                " Search | Alt+c: case, Tab: type, Enter: search/jump, Esc: back, q: quit, j/k: navigate "
                    .to_string()
            }
            ViewMode::Visual => {
                " Visual Mode | v: anchor, w/b: word, m/Enter: bookmark, arrows/hjkl: move, Esc: back "
                    .to_string()
            }
        };

        let border_type = get_border_type(&app.config);

        f.render_widget(
            Paragraph::new(footer_text).block(
                Block::default()
                    .borders(Borders::ALL)
                    .border_type(border_type),
            ),
            area,
        );
    }
}