diff --git a/hammond-gtk/src/headerbar.rs b/hammond-gtk/src/headerbar.rs index ddd485d..32008d2 100644 --- a/hammond-gtk/src/headerbar.rs +++ b/hammond-gtk/src/headerbar.rs @@ -9,7 +9,7 @@ use utils; use std::sync::{Arc, Mutex}; -pub fn get_headerbar(db: &Arc>, stack: >k::Stack) -> gtk::HeaderBar { +pub fn get_headerbar(db: Arc>, stack: gtk::Stack) -> gtk::HeaderBar { let builder = include_str!("../gtk/headerbar.ui"); let builder = gtk::Builder::new_from_string(builder); @@ -65,7 +65,7 @@ pub fn get_headerbar(db: &Arc>, stack: >k::Stack) -> g let db_clone = db.clone(); // FIXME: There appears to be a memmory leak here. refresh_button.connect_clicked(move |_| { - utils::refresh_db(&db_clone, &stack_clone); + utils::refresh_db(db_clone.clone(), stack_clone.clone()); }); header diff --git a/hammond-gtk/src/main.rs b/hammond-gtk/src/main.rs index 60da407..99bf6be 100644 --- a/hammond-gtk/src/main.rs +++ b/hammond-gtk/src/main.rs @@ -1,10 +1,9 @@ #![cfg_attr(feature = "cargo-clippy", allow(clone_on_ref_ptr))] -// extern crate glib; - extern crate gdk; extern crate gdk_pixbuf; extern crate gio; +extern crate glib; extern crate gtk; extern crate diesel; @@ -55,7 +54,7 @@ fn build_ui(app: >k::Application) { }); // Get the headerbar - let header = headerbar::get_headerbar(&db, &stack); + let header = headerbar::get_headerbar(db, stack); // Uncomment this when etag implementation is fixed and refesh_db thread is non blocking. // utils::refresh_db(&db, &stack); window.set_titlebar(&header); diff --git a/hammond-gtk/src/utils.rs b/hammond-gtk/src/utils.rs index bbf11af..441d64c 100644 --- a/hammond-gtk/src/utils.rs +++ b/hammond-gtk/src/utils.rs @@ -1,6 +1,6 @@ #![cfg_attr(feature = "cargo-clippy", allow(clone_on_ref_ptr))] -// use glib; +use glib; use gtk; // use gtk::prelude::*; @@ -11,25 +11,37 @@ use hammond_data::models::Source; use diesel::prelude::SqliteConnection; use std::thread; +use std::cell::RefCell; use std::sync::{Arc, Mutex}; +use std::sync::mpsc::{channel, Receiver}; use views::podcasts_view; -pub fn refresh_db(db: &Arc>, stack: >k::Stack) { +thread_local!( + static GLOBAL: RefCell>, + gtk::Stack, + Receiver)>> = RefCell::new(None)); + +pub fn refresh_db(db: Arc>, stack: gtk::Stack) { + let (sender, receiver) = channel(); + let db_clone = db.clone(); - let handle = thread::spawn(move || { + GLOBAL.with(move |global| { + *global.borrow_mut() = Some((db_clone, stack, receiver)); + }); + + // The implementation of how this is done is probably terrible but it works!. + let db_clone = db.clone(); + thread::spawn(move || { let t = hammond_data::index_feed::index_loop(&db_clone, false); if t.is_err() { error!("Error While trying to update the database."); error!("Error msg: {}", t.unwrap_err()); }; - }); - // FIXME: atm freezing the ui till update is done. - // Make it instead emmit a signal on update completion. - // TODO: emit a signal in order to update the podcast widget. - let _ = handle.join(); + sender.send(true).expect("Couldn't send data to channel");; - podcasts_view::update_podcasts_view(db, stack); + glib::idle_add(receive); + }); } pub fn refresh_feed(db: &Arc>, stack: >k::Stack, source: &mut Source) { @@ -54,7 +66,6 @@ pub fn refresh_feed(db: &Arc>, stack: >k::Stack, sourc // Make it instead emmit a signal on update completion. // TODO: emit a signal in order to update the podcast widget. let _ = handle.join(); - podcasts_view::update_podcasts_view(db, stack); } @@ -77,3 +88,14 @@ pub fn refresh_feed(db: &Arc>, stack: >k::Stack, sourc // info!("{}", markup); // markup // } + +fn receive() -> glib::Continue { + GLOBAL.with(|global| { + if let Some((ref db, ref stack, ref reciever)) = *global.borrow() { + if let Ok(_) = reciever.try_recv() { + podcasts_view::update_podcasts_view(db, stack); + } + } + }); + glib::Continue(false) +} diff --git a/hammond-gtk/src/widgets/episode.rs b/hammond-gtk/src/widgets/episode.rs index 753c4ae..ed4758a 100644 --- a/hammond-gtk/src/widgets/episode.rs +++ b/hammond-gtk/src/widgets/episode.rs @@ -100,6 +100,7 @@ fn epidose_widget( ep } + pub fn episodes_listbox(connection: &Arc>, pd_title: &str) -> gtk::ListBox { // TODO: handle unwraps. let m = connection.lock().unwrap(); diff --git a/hammond-gtk/src/widgets/podcast.rs b/hammond-gtk/src/widgets/podcast.rs index 43e0bbe..f30842c 100644 --- a/hammond-gtk/src/widgets/podcast.rs +++ b/hammond-gtk/src/widgets/podcast.rs @@ -29,7 +29,7 @@ pub fn podcast_widget( if let Some(t) = title { title_label.set_text(t); - let listbox = episodes_listbox(&connection.clone(), t); + let listbox = episodes_listbox(&connection, t); view.add(&listbox); }