HomeView: handle vadjustment with BaseView
Instead of using lazy_static to save the adjustment, pass it to the widget upon creation. If its the first instance created, pass None instead.
This commit is contained in:
parent
e1aba32b9a
commit
63bdc70f0e
@ -29,7 +29,7 @@ pub(crate) struct HomeStack {
|
|||||||
|
|
||||||
impl HomeStack {
|
impl HomeStack {
|
||||||
pub(crate) fn new(sender: Sender<Action>) -> Result<HomeStack, Error> {
|
pub(crate) fn new(sender: Sender<Action>) -> Result<HomeStack, Error> {
|
||||||
let episodes = HomeView::new(sender.clone())?;
|
let episodes = HomeView::new(sender.clone(), None)?;
|
||||||
let empty = EmptyView::new();
|
let empty = EmptyView::new();
|
||||||
let stack = gtk::Stack::new();
|
let stack = gtk::Stack::new();
|
||||||
let state = State::Empty;
|
let state = State::Empty;
|
||||||
@ -54,12 +54,6 @@ impl HomeStack {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn update(&mut self) -> Result<(), Error> {
|
pub(crate) fn update(&mut self) -> Result<(), Error> {
|
||||||
// Copy the vertical scrollbar adjustment from the old view.
|
|
||||||
self.episodes
|
|
||||||
.save_alignment()
|
|
||||||
.map_err(|err| error!("Failed to set episodes_view allignment: {}", err))
|
|
||||||
.ok();
|
|
||||||
|
|
||||||
self.replace_view()?;
|
self.replace_view()?;
|
||||||
// Determine the actuall state.
|
// Determine the actuall state.
|
||||||
self.determine_state().map_err(From::from)
|
self.determine_state().map_err(From::from)
|
||||||
@ -68,7 +62,10 @@ impl HomeStack {
|
|||||||
fn replace_view(&mut self) -> Result<(), Error> {
|
fn replace_view(&mut self) -> Result<(), Error> {
|
||||||
// Get the container of the view
|
// Get the container of the view
|
||||||
let old = &self.episodes.view.container().clone();
|
let old = &self.episodes.view.container().clone();
|
||||||
let eps = HomeView::new(self.sender.clone())?;
|
|
||||||
|
// Copy the vertical scrollbar adjustment from the old view.
|
||||||
|
let vadj = self.episodes.view.get_vadjustment();
|
||||||
|
let eps = HomeView::new(self.sender.clone(), vadj)?;
|
||||||
|
|
||||||
// Remove the old widget and add the new one
|
// Remove the old widget and add the new one
|
||||||
// during this the previous view is removed,
|
// during this the previous view is removed,
|
||||||
|
|||||||
@ -1,11 +1,9 @@
|
|||||||
use chrono::prelude::*;
|
use chrono::prelude::*;
|
||||||
use failure::Error;
|
use failure::Error;
|
||||||
|
|
||||||
use gtk;
|
use gtk::{self, prelude::*, Adjustment};
|
||||||
use gtk::prelude::*;
|
|
||||||
|
|
||||||
use crossbeam_channel::Sender;
|
use crossbeam_channel::Sender;
|
||||||
use fragile::Fragile;
|
|
||||||
use libhandy::{Column, ColumnExt};
|
use libhandy::{Column, ColumnExt};
|
||||||
use podcasts_data::dbqueries;
|
use podcasts_data::dbqueries;
|
||||||
use podcasts_data::EpisodeWidgetModel;
|
use podcasts_data::EpisodeWidgetModel;
|
||||||
@ -16,12 +14,6 @@ use widgets::{BaseView, EpisodeWidget};
|
|||||||
|
|
||||||
use std::cell::Cell;
|
use std::cell::Cell;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use std::sync::Mutex;
|
|
||||||
|
|
||||||
lazy_static! {
|
|
||||||
pub(crate) static ref EPISODES_VIEW_VALIGNMENT: Mutex<Option<Fragile<gtk::Adjustment>>> =
|
|
||||||
Mutex::new(None);
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
enum ListSplit {
|
enum ListSplit {
|
||||||
@ -94,74 +86,51 @@ impl Default for HomeView {
|
|||||||
|
|
||||||
// TODO: REFACTOR ME
|
// TODO: REFACTOR ME
|
||||||
impl HomeView {
|
impl HomeView {
|
||||||
pub(crate) fn new(sender: Sender<Action>) -> Result<Rc<HomeView>, Error> {
|
pub(crate) fn new(
|
||||||
|
sender: Sender<Action>,
|
||||||
|
vadj: Option<Adjustment>,
|
||||||
|
) -> Result<Rc<HomeView>, Error> {
|
||||||
use self::ListSplit::*;
|
use self::ListSplit::*;
|
||||||
|
|
||||||
let view = Rc::new(HomeView::default());
|
let home = Rc::new(HomeView::default());
|
||||||
let ignore = utils::get_ignored_shows()?;
|
let ignore = utils::get_ignored_shows()?;
|
||||||
let episodes = dbqueries::get_episodes_widgets_filter_limit(&ignore, 100)?;
|
let episodes = dbqueries::get_episodes_widgets_filter_limit(&ignore, 100)?;
|
||||||
let now_utc = Utc::now();
|
let now_utc = Utc::now();
|
||||||
|
|
||||||
let view_ = view.clone();
|
let home_weak = Rc::downgrade(&home);
|
||||||
let func = move |ep: EpisodeWidgetModel| {
|
let func = move |ep: EpisodeWidgetModel| {
|
||||||
|
let home = match home_weak.upgrade() {
|
||||||
|
Some(h) => h,
|
||||||
|
None => return,
|
||||||
|
};
|
||||||
|
|
||||||
let epoch = ep.epoch();
|
let epoch = ep.epoch();
|
||||||
let widget = HomeEpisode::new(ep, &sender);
|
let widget = HomeEpisode::new(ep, &sender);
|
||||||
|
|
||||||
match split(&now_utc, i64::from(epoch)) {
|
match split(&now_utc, i64::from(epoch)) {
|
||||||
Today => add_to_box(&widget, &view_.today_list, &view_.today_box),
|
Today => add_to_box(&widget, &home.today_list, &home.today_box),
|
||||||
Yday => add_to_box(&widget, &view_.yday_list, &view_.yday_box),
|
Yday => add_to_box(&widget, &home.yday_list, &home.yday_box),
|
||||||
Week => add_to_box(&widget, &view_.week_list, &view_.week_box),
|
Week => add_to_box(&widget, &home.week_list, &home.week_box),
|
||||||
Month => add_to_box(&widget, &view_.month_list, &view_.month_box),
|
Month => add_to_box(&widget, &home.month_list, &home.month_box),
|
||||||
Rest => add_to_box(&widget, &view_.rest_list, &view_.rest_box),
|
Rest => add_to_box(&widget, &home.rest_list, &home.rest_box),
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let view_ = view.clone();
|
let home_weak = Rc::downgrade(&home);
|
||||||
let callback = move || {
|
let callback = move || {
|
||||||
view_
|
let home = match home_weak.upgrade() {
|
||||||
.set_vadjustment()
|
Some(h) => h,
|
||||||
.map_err(|err| format!("{}", err))
|
None => return,
|
||||||
.ok();
|
};
|
||||||
|
|
||||||
|
if let Some(ref v) = vadj {
|
||||||
|
home.view.set_adjutments(None, Some(v))
|
||||||
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
lazy_load_full(episodes, func, callback);
|
lazy_load_full(episodes, func, callback);
|
||||||
view.view.container().show_all();
|
home.view.container().show_all();
|
||||||
Ok(view)
|
Ok(home)
|
||||||
}
|
|
||||||
|
|
||||||
/// Set scrolled window vertical adjustment.
|
|
||||||
fn set_vadjustment(&self) -> Result<(), Error> {
|
|
||||||
let guard = EPISODES_VIEW_VALIGNMENT
|
|
||||||
.lock()
|
|
||||||
.map_err(|err| format_err!("Failed to lock widget align mutex: {}", err))?;
|
|
||||||
|
|
||||||
if let Some(ref fragile) = *guard {
|
|
||||||
// Copy the vertical scrollbar adjustment from the old view into the new one.
|
|
||||||
let res = fragile
|
|
||||||
.try_get()
|
|
||||||
.map(|x| utils::smooth_scroll_to(self.view.scrolled_window(), &x))
|
|
||||||
.map_err(From::from);
|
|
||||||
|
|
||||||
debug_assert!(res.is_ok());
|
|
||||||
return res;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Save the vertical scrollbar position.
|
|
||||||
pub(crate) fn save_alignment(&self) -> Result<(), Error> {
|
|
||||||
if let Ok(mut guard) = EPISODES_VIEW_VALIGNMENT.lock() {
|
|
||||||
let adj = self
|
|
||||||
.view
|
|
||||||
.scrolled_window()
|
|
||||||
.get_vadjustment()
|
|
||||||
.ok_or_else(|| format_err!("Could not get the adjustment"))?;
|
|
||||||
*guard = Some(Fragile::new(adj));
|
|
||||||
info!("Saved episodes_view alignment.");
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user