Implement menu side of watched status filtering
This commit is contained in:
parent
629f2ba9d0
commit
e1fbc92e08
10 changed files with 99 additions and 19 deletions
|
|
@ -41,6 +41,9 @@ impl SimpleComponent for CollatableFilmGrid {
|
|||
FilmCollationMenuOutput::SortBy(sorting, direction) => {
|
||||
FilmGridInput::SortBy(sorting, direction)
|
||||
}
|
||||
FilmCollationMenuOutput::ApplyWatchedFilter(watched_filter) => {
|
||||
FilmGridInput::ApplyWatchedFilter(watched_filter)
|
||||
}
|
||||
},
|
||||
);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,28 +1,35 @@
|
|||
use gtk4::prelude::{
|
||||
BoxExt, ButtonExt, EntryExt, ListBoxRowExt, ObjectExt, OrientableExt, PopoverExt, WidgetExt,
|
||||
BoxExt, ButtonExt, EntryExt, ListBoxRowExt, ObjectExt, OrientableExt, PopoverExt,
|
||||
ToggleButtonExt, WidgetExt,
|
||||
};
|
||||
use gtk4::{Align, Button, Entry, Label, ListBox, MenuButton, Orientation, Popover};
|
||||
use gtk4::{Align, Button, Entry, Label, ListBox, MenuButton, Orientation, Popover, ToggleButton};
|
||||
use relm4::{ComponentParts, ComponentSender, SimpleComponent, component};
|
||||
|
||||
use crate::ui::components::sorting_popover_entry::sorting_popover_entry;
|
||||
use crate::ui::filtering::WatchedFilter;
|
||||
use crate::ui::sorting::{FilmsSorting, SortingDirection};
|
||||
use crate::ui::widget_extensions::ComponentSenderExt;
|
||||
|
||||
|
||||
|
||||
pub struct FilmCollationMenu {
|
||||
sorted_by: FilmsSorting,
|
||||
sort_direction: SortingDirection,
|
||||
watched_filter: Option<WatchedFilter>,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum FilmCollationMenuInput {
|
||||
SortBy(FilmsSorting),
|
||||
ToggleSortOrder,
|
||||
ToggleWatchedFilter,
|
||||
ToggleUnwatchedFilter,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum FilmCollationMenuOutput {
|
||||
SortBy(FilmsSorting, SortingDirection),
|
||||
ApplyWatchedFilter(Option<WatchedFilter>),
|
||||
}
|
||||
|
||||
#[component(pub)]
|
||||
|
|
@ -89,12 +96,33 @@ impl SimpleComponent for FilmCollationMenu {
|
|||
},
|
||||
},
|
||||
},
|
||||
|
||||
Entry {
|
||||
set_width_request: 230,
|
||||
set_placeholder_text: Some("Search"),
|
||||
set_secondary_icon_name: Some("system-search-symbolic"),
|
||||
set_secondary_icon_sensitive: false,
|
||||
},
|
||||
|
||||
gtk4::Box {
|
||||
set_orientation: Orientation::Horizontal,
|
||||
set_css_classes: &["linked"],
|
||||
|
||||
ToggleButton {
|
||||
set_icon_name: "eye-outline-filled-symbolic",
|
||||
#[watch]
|
||||
#[block_signal(watched_toggled)]
|
||||
set_active: model.watched_filter == Some(WatchedFilter::OnlyWatched),
|
||||
connect_toggled => FilmCollationMenuInput::ToggleWatchedFilter @watched_toggled,
|
||||
},
|
||||
ToggleButton {
|
||||
set_icon_name: "eye-closed-symbolic",
|
||||
#[watch]
|
||||
#[block_signal(unwatched_toggled)]
|
||||
set_active: model.watched_filter == Some(WatchedFilter::OnlyUnwatched),
|
||||
connect_toggled => FilmCollationMenuInput::ToggleUnwatchedFilter @unwatched_toggled,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -106,6 +134,7 @@ impl SimpleComponent for FilmCollationMenu {
|
|||
let model = FilmCollationMenu {
|
||||
sorted_by: FilmsSorting::Name,
|
||||
sort_direction: SortingDirection::Ascending,
|
||||
watched_filter: None,
|
||||
};
|
||||
let widgets = view_output!();
|
||||
ComponentParts { model, widgets }
|
||||
|
|
@ -120,7 +149,7 @@ impl SimpleComponent for FilmCollationMenu {
|
|||
FilmCollationMenuInput::SortBy(sorting) => {
|
||||
self.sorted_by = sorting;
|
||||
self.sort_direction = SortingDirection::Ascending;
|
||||
sender.output_sender().emit(FilmCollationMenuOutput::SortBy(
|
||||
sender.emit_output(FilmCollationMenuOutput::SortBy(
|
||||
sorting,
|
||||
SortingDirection::Ascending,
|
||||
));
|
||||
|
|
@ -130,11 +159,37 @@ impl SimpleComponent for FilmCollationMenu {
|
|||
SortingDirection::Ascending => SortingDirection::Descending,
|
||||
SortingDirection::Descending => SortingDirection::Ascending,
|
||||
};
|
||||
sender.output_sender().emit(FilmCollationMenuOutput::SortBy(
|
||||
sender.emit_output(FilmCollationMenuOutput::SortBy(
|
||||
self.sorted_by,
|
||||
self.sort_direction,
|
||||
));
|
||||
}
|
||||
FilmCollationMenuInput::ToggleWatchedFilter => {
|
||||
match self.watched_filter {
|
||||
Some(WatchedFilter::OnlyWatched) => {
|
||||
self.watched_filter = None;
|
||||
}
|
||||
_ => {
|
||||
self.watched_filter = Some(WatchedFilter::OnlyWatched);
|
||||
}
|
||||
}
|
||||
sender.emit_output(FilmCollationMenuOutput::ApplyWatchedFilter(
|
||||
self.watched_filter,
|
||||
));
|
||||
}
|
||||
FilmCollationMenuInput::ToggleUnwatchedFilter => {
|
||||
match self.watched_filter {
|
||||
Some(WatchedFilter::OnlyUnwatched) => {
|
||||
self.watched_filter = None;
|
||||
}
|
||||
_ => {
|
||||
self.watched_filter = Some(WatchedFilter::OnlyUnwatched);
|
||||
}
|
||||
}
|
||||
sender.emit_output(FilmCollationMenuOutput::ApplyWatchedFilter(
|
||||
self.watched_filter,
|
||||
));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ use relm4::{ComponentParts, ComponentSender, SimpleComponent, component};
|
|||
|
||||
use crate::ui::components::sorting_popover_entry::sorting_popover_entry;
|
||||
use crate::ui::sorting::{SeriesSorting, SortingDirection};
|
||||
use crate::ui::widget_extensions::ComponentSenderExt;
|
||||
|
||||
|
||||
|
||||
|
|
@ -118,24 +119,20 @@ impl SimpleComponent for SeriesCollationMenu {
|
|||
SeriesCollationMenuInput::SortBy(sorting) => {
|
||||
self.sorted_by = sorting;
|
||||
self.sort_direction = SortingDirection::Ascending;
|
||||
sender
|
||||
.output_sender()
|
||||
.emit(SeriesCollationMenuOutput::SortBy(
|
||||
sorting,
|
||||
SortingDirection::Ascending,
|
||||
));
|
||||
sender.emit_output(SeriesCollationMenuOutput::SortBy(
|
||||
sorting,
|
||||
SortingDirection::Ascending,
|
||||
));
|
||||
}
|
||||
SeriesCollationMenuInput::ToggleSortOrder => {
|
||||
self.sort_direction = match self.sort_direction {
|
||||
SortingDirection::Ascending => SortingDirection::Descending,
|
||||
SortingDirection::Descending => SortingDirection::Ascending,
|
||||
};
|
||||
sender
|
||||
.output_sender()
|
||||
.emit(SeriesCollationMenuOutput::SortBy(
|
||||
self.sorted_by,
|
||||
self.sort_direction,
|
||||
));
|
||||
sender.emit_output(SeriesCollationMenuOutput::SortBy(
|
||||
self.sorted_by,
|
||||
self.sort_direction,
|
||||
));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ use gtk4::{Align, Button, IconSize, Image, Justification, Label, Orientation, To
|
|||
use relm4::{Component, ComponentParts, ComponentSender, RelmWidgetExt, component};
|
||||
|
||||
use crate::persist::data_manager::{DataManager, DataManagerError};
|
||||
use crate::ui::widget_extensions::ComponentSenderExt;
|
||||
use crate::views::overview::FilmOverview;
|
||||
|
||||
|
||||
|
|
@ -97,9 +98,7 @@ impl Component for FilmDetails {
|
|||
match message {
|
||||
FilmDetailsInput::WatchedStatusChanged(watched) => {
|
||||
self.film_overview.watched = watched;
|
||||
sender
|
||||
.output_sender()
|
||||
.emit(FilmDetailsOutput::WatchedStatusChanged(watched));
|
||||
sender.emit_output(FilmDetailsOutput::WatchedStatusChanged(watched));
|
||||
|
||||
sender.oneshot_command(clone!(
|
||||
#[strong(rename_to = uuid)]
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ use relm4::{Component, ComponentParts, ComponentSender, component};
|
|||
use crate::persist::data_manager::{DataManager, DataManagerError};
|
||||
use crate::ui::components::media_grid_item::FilmGridItem;
|
||||
use crate::ui::factory_sorting::sort_factory_vec;
|
||||
use crate::ui::filtering::WatchedFilter;
|
||||
use crate::ui::sorting::{
|
||||
FilmsSorting, SortingDirection, cmp_films_by_name, cmp_films_by_rel_date, cmp_films_by_runtime,
|
||||
};
|
||||
|
|
@ -20,6 +21,7 @@ pub struct FilmGrid {
|
|||
#[derive(Debug)]
|
||||
pub enum FilmGridInput {
|
||||
SortBy(FilmsSorting, SortingDirection),
|
||||
ApplyWatchedFilter(Option<WatchedFilter>),
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
|
|
@ -96,6 +98,7 @@ impl Component for FilmGrid {
|
|||
}
|
||||
});
|
||||
}
|
||||
FilmGridInput::ApplyWatchedFilter(_watched_filter) => {}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
5
src/ui/filtering.rs
Normal file
5
src/ui/filtering.rs
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
|
||||
pub enum WatchedFilter {
|
||||
OnlyWatched,
|
||||
OnlyUnwatched,
|
||||
}
|
||||
|
|
@ -1,5 +1,6 @@
|
|||
mod components;
|
||||
mod factory_sorting;
|
||||
mod filtering;
|
||||
mod sorting;
|
||||
mod widget_extensions;
|
||||
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ use gtk4::prelude::{BoxExt, IsA};
|
|||
use gtk4::{Label, Widget};
|
||||
use libadwaita::Dialog;
|
||||
use libadwaita::prelude::AdwDialogExt;
|
||||
use relm4::{Component, ComponentSender};
|
||||
|
||||
|
||||
|
||||
|
|
@ -66,3 +67,15 @@ impl AttrListExt for AttrList {
|
|||
self.insert(AttrFontDesc::new(&font_desc));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
pub trait ComponentSenderExt<C: Component> {
|
||||
fn emit_output(&self, message: C::Output);
|
||||
}
|
||||
|
||||
impl<C: Component> ComponentSenderExt<C> for ComponentSender<C> {
|
||||
fn emit_output(&self, message: C::Output) {
|
||||
self.output_sender().emit(message);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue