use std::cell::RefCell; use std::collections::HashMap; use std::rc::Rc; use crossbeam_channel::unbounded; use gtk::prelude::*; use gtk::Builder; use czkawka_core::big_file::BigFile; use czkawka_core::broken_files::BrokenFiles; use czkawka_core::duplicate::DuplicateFinder; use czkawka_core::empty_files::EmptyFiles; use czkawka_core::empty_folder::EmptyFolder; use czkawka_core::invalid_symlinks::InvalidSymlinks; use czkawka_core::same_music::SameMusic; use czkawka_core::similar_images::SimilarImages; use czkawka_core::similar_videos::SimilarVideos; use czkawka_core::temporary::Temporary; use crate::gui_about::GuiAbout; use crate::gui_bottom_buttons::GuiBottomButtons; use crate::gui_header::GuiHeader; use crate::gui_main_notebook::GuiMainNotebook; use crate::gui_popovers::GuiPopovers; use crate::gui_progress_dialog::GuiProgressDialog; use crate::gui_settings::GuiSettings; use crate::gui_upper_notebook::GuiUpperNotebook; use crate::notebook_enums::*; use crate::taskbar_progress::TaskbarProgress; #[derive(Clone)] pub struct GuiData { // Glade builder pub glade_src: String, pub builder: Builder, // Windows pub window_main: gtk::Window, pub main_notebook: GuiMainNotebook, pub upper_notebook: GuiUpperNotebook, pub popovers: GuiPopovers, pub bottom_buttons: GuiBottomButtons, pub progress_window: GuiProgressDialog, pub about: GuiAbout, pub settings: GuiSettings, pub header: GuiHeader, // Taskbar state pub taskbar_state: Rc>, // Buttons state pub shared_buttons: Rc>>>, // State of search results pub shared_duplication_state: Rc>, pub shared_empty_folders_state: Rc>, pub shared_empty_files_state: Rc>, pub shared_temporary_files_state: Rc>, pub shared_big_files_state: Rc>, pub shared_similar_images_state: Rc>, pub shared_similar_videos_state: Rc>, pub shared_same_music_state: Rc>, pub shared_same_invalid_symlinks: Rc>, pub shared_broken_files_state: Rc>, pub preview_path: Rc>, //// Entry pub entry_info: gtk::Entry, //// Bottom pub text_view_errors: gtk::TextView, pub scrolled_window_errors: gtk::ScrolledWindow, // Used for sending stop signal to thread pub stop_sender: crossbeam_channel::Sender<()>, pub stop_receiver: crossbeam_channel::Receiver<()>, } impl GuiData { pub fn new_with_application(application: >k::Application) -> Self { //// Loading glade file content and build with it help UI let glade_src = include_str!("../ui/main_window.glade").to_string(); let builder = Builder::from_string(glade_src.as_str()); //// Windows let window_main: gtk::Window = builder.object("window_main").unwrap(); window_main.show_all(); window_main.set_title("Czkawka"); window_main.set_application(Some(application)); let main_notebook = GuiMainNotebook::create_from_builder(&builder); let upper_notebook = GuiUpperNotebook::create_from_builder(&builder); let popovers = GuiPopovers::create_from_builder(); let bottom_buttons = GuiBottomButtons::create_from_builder(&builder, &popovers.popover_select); let progress_window = GuiProgressDialog::create_from_builder(&window_main); let about = GuiAbout::create_from_builder(&window_main); let header = GuiHeader::create_from_builder(&builder); let settings = GuiSettings::create_from_builder(&window_main); //////////////////////////////////////////////////////////////////////////////////////////////// // Taskbar state let taskbar_state = Rc::new(RefCell::new(TaskbarProgress::new())); // Buttons State - to remember existence of different buttons on pages let shared_buttons: Rc> = Rc::new(RefCell::new(HashMap::>::new())); // Show by default only search button for i in get_all_main_tabs().iter() { let mut temp_hashmap: HashMap = Default::default(); for button_name in bottom_buttons.buttons_names.iter() { if *button_name == "search" { temp_hashmap.insert(button_name.to_string(), true); } else { temp_hashmap.insert(button_name.to_string(), false); } } shared_buttons.borrow_mut().insert(i.clone(), temp_hashmap); } // State of search results let shared_duplication_state: Rc> = Rc::new(RefCell::new(DuplicateFinder::new())); let shared_empty_folders_state: Rc> = Rc::new(RefCell::new(EmptyFolder::new())); let shared_empty_files_state: Rc> = Rc::new(RefCell::new(EmptyFiles::new())); let shared_temporary_files_state: Rc> = Rc::new(RefCell::new(Temporary::new())); let shared_big_files_state: Rc> = Rc::new(RefCell::new(BigFile::new())); let shared_similar_images_state: Rc> = Rc::new(RefCell::new(SimilarImages::new())); let shared_similar_videos_state: Rc> = Rc::new(RefCell::new(SimilarVideos::new())); let shared_same_music_state: Rc> = Rc::new(RefCell::new(SameMusic::new())); let shared_same_invalid_symlinks: Rc> = Rc::new(RefCell::new(InvalidSymlinks::new())); let shared_broken_files_state: Rc> = Rc::new(RefCell::new(BrokenFiles::new())); let preview_path: Rc> = Rc::new(RefCell::new("".to_string())); //// Entry let entry_info: gtk::Entry = builder.object("entry_info").unwrap(); //// Bottom let text_view_errors: gtk::TextView = builder.object("text_view_errors").unwrap(); let scrolled_window_errors: gtk::ScrolledWindow = builder.object("scrolled_window_errors").unwrap(); scrolled_window_errors.show_all(); // Not sure why needed, but without it text view errors sometimes hide itself // Used for sending stop signal to thread let (stop_sender, stop_receiver): (crossbeam_channel::Sender<()>, crossbeam_channel::Receiver<()>) = unbounded(); Self { glade_src, builder, window_main, main_notebook, upper_notebook, popovers, bottom_buttons, progress_window, about, settings, header, taskbar_state, shared_buttons, shared_duplication_state, shared_empty_folders_state, shared_empty_files_state, shared_temporary_files_state, shared_big_files_state, shared_similar_images_state, shared_similar_videos_state, shared_same_music_state, shared_same_invalid_symlinks, shared_broken_files_state, preview_path, entry_info, text_view_errors, scrolled_window_errors, stop_sender, stop_receiver, } } pub fn update_language(&self) { self.main_notebook.update_language(); self.upper_notebook.update_language(); self.popovers.update_language(); self.bottom_buttons.update_language(); self.progress_window.update_language(); self.about.update_language(); self.header.update_language(); self.settings.update_language(); } }