changxi 0.3.0

TUI EPUB Reader
use crate::app::{App, ViewMode};
use crate::ui::components::{
    BookmarkBrowser, ChapterBrowser, ContinuousReadingView, CoverView, Footer, Header, LibraryView,
    SearchView,
};
use crate::ui::{Component, View};
use ratatui::{
    Frame,
    layout::{Constraint, Direction, Layout},
};
use ratatui_image::picker::Picker;

pub struct ContinuousView {
    header: Header,
    footer: Footer,
    continuous_reading_view: ContinuousReadingView,
    cover_view: CoverView,
    chapter_browser: ChapterBrowser,
    bookmark_browser: BookmarkBrowser,
    library_view: LibraryView,
    search_view: SearchView,
}

impl ContinuousView {
    pub fn new() -> Self {
        Self {
            header: Header,
            footer: Footer,
            continuous_reading_view: ContinuousReadingView,
            cover_view: CoverView,
            chapter_browser: ChapterBrowser,
            bookmark_browser: BookmarkBrowser,
            library_view: LibraryView,
            search_view: SearchView,
        }
    }
}

impl View for ContinuousView {
    fn render(&self, f: &mut Frame, app: &mut App, picker: &mut Picker) {
        let size = f.area();

        let chunks = Layout::default()
            .direction(Direction::Vertical)
            .constraints([
                Constraint::Length(3),
                Constraint::Min(0),
                Constraint::Length(3),
            ])
            .split(size);

        // Header always renders at the top
        self.header.render(f, chunks[0], app, picker);

        // Main content depends on app mode
        match app.mode {
            ViewMode::Reading | ViewMode::Visual => self
                .continuous_reading_view
                .render(f, chunks[1], app, picker),
            ViewMode::Cover => self.cover_view.render(f, chunks[1], app, picker),
            ViewMode::ChapterBrowser => self.chapter_browser.render(f, chunks[1], app, picker),
            ViewMode::BookmarkBrowser | ViewMode::BookmarkRenaming => {
                self.bookmark_browser.render(f, chunks[1], app, picker)
            }
            ViewMode::Library => self.library_view.render(f, chunks[1], app, picker),
            ViewMode::Search => self.search_view.render(f, chunks[1], app, picker),
        }

        // Footer always renders at the bottom
        self.footer.render(f, chunks[2], app, picker);
    }
}