Start hooking things up

Still doesn't accept input
This commit is contained in:
Zander Brown 2018-05-29 22:38:56 +01:00
parent 5704018bbf
commit 1c078034f5
3 changed files with 105 additions and 15 deletions

View File

@ -28,7 +28,7 @@
<property name="icon_size">6</property> <property name="icon_size">6</property>
</object> </object>
<packing> <packing>
<property name="left_attach">3</property> <property name="left_attach">1</property>
<property name="top_attach">0</property> <property name="top_attach">0</property>
<property name="height">2</property> <property name="height">2</property>
</packing> </packing>
@ -46,13 +46,14 @@
<property name="value_pos">right</property> <property name="value_pos">right</property>
</object> </object>
<packing> <packing>
<property name="left_attach">1</property> <property name="left_attach">2</property>
<property name="top_attach">1</property> <property name="top_attach">1</property>
<property name="width">2</property> <property name="width">2</property>
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkToggleButton" id="play"> <object class="GtkButton" id="play">
<property name="width_request">60</property>
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="receives_default">True</property> <property name="receives_default">True</property>
@ -79,7 +80,7 @@
<property name="label" translatable="yes">label</property> <property name="label" translatable="yes">label</property>
</object> </object>
<packing> <packing>
<property name="left_attach">1</property> <property name="left_attach">2</property>
<property name="top_attach">0</property> <property name="top_attach">0</property>
</packing> </packing>
</child> </child>
@ -92,7 +93,7 @@
<property name="label" translatable="yes">label</property> <property name="label" translatable="yes">label</property>
</object> </object>
<packing> <packing>
<property name="left_attach">2</property> <property name="left_attach">3</property>
<property name="top_attach">0</property> <property name="top_attach">0</property>
</packing> </packing>
</child> </child>
@ -100,4 +101,4 @@
<class name="playback"/> <class name="playback"/>
</style> </style>
</object> </object>
</interface> </interface>

View File

@ -6,6 +6,7 @@ use gio::{
}; };
use glib; use glib;
use gstreamer_player as gst; use gstreamer_player as gst;
use gstreamer::ClockTime;
use gtk; use gtk;
use gtk::prelude::*; use gtk::prelude::*;
use gtk::SettingsExt as GtkSettingsExt; use gtk::SettingsExt as GtkSettingsExt;
@ -40,7 +41,10 @@ pub enum Action {
MarkAllPlayerNotification(Arc<Podcast>), MarkAllPlayerNotification(Arc<Podcast>),
RemoveShow(Arc<Podcast>), RemoveShow(Arc<Podcast>),
ErrorNotification(String), ErrorNotification(String),
PlayEpisode(String) PlayEpisode(String),
PlayerStateChanged(gst::PlayerState),
PlayerMediaChanged(Option<String>, ClockTime),
PlayerPositionChanged(ClockTime),
} }
#[derive(Debug)] #[derive(Debug)]
@ -104,11 +108,8 @@ impl App {
// Add the overlay to the main window // Add the overlay to the main window
wrap.add(&overlay); wrap.add(&overlay);
let playback = Playback::new(); let playback = Rc::new(Playback::new());
wrap.add(playback.get_widget());
let reveal = gtk::Revealer::new();
reveal.add(&playback.container);
wrap.add(&reveal);
WindowGeometry::from_settings(&settings).apply(&window); WindowGeometry::from_settings(&settings).apply(&window);
@ -123,8 +124,20 @@ impl App {
sender.send(Action::ErrorNotification(format!("Playback: {}", err))).ok(); sender.send(Action::ErrorNotification(format!("Playback: {}", err))).ok();
})); }));
player.connect_state_changed(clone!(sender => move |_,state| {
sender.send(Action::PlayerStateChanged(state)).ok();
}));
player.connect_media_info_updated(clone!(sender => move |_,info| {
sender.send(Action::PlayerMediaChanged(info.get_title(), info.get_duration())).ok();
}));
player.connect_property_position_notify(clone!(sender => move |p| {
sender.send(Action::PlayerPositionChanged(p.get_position())).ok();
}));
gtk::timeout_add(50, clone!(sender, receiver => move || { gtk::timeout_add(50, clone!(sender, receiver => move || {
// Uses receiver, content, header, sender, overlay // Uses receiver, content, header, sender, overlay, playback
match receiver.try_recv() { match receiver.try_recv() {
Ok(Action::RefreshAllViews) => content.update(), Ok(Action::RefreshAllViews) => content.update(),
Ok(Action::RefreshShowsView) => content.update_shows_view(), Ok(Action::RefreshShowsView) => content.update_shows_view(),
@ -185,6 +198,9 @@ impl App {
player.set_uri(&uri); player.set_uri(&uri);
player.play(); player.play();
}, },
Ok(Action::PlayerStateChanged(state)) => playback.state_changed(state),
Ok(Action::PlayerMediaChanged(t, l)) => playback.media_changed(t, l),
Ok(Action::PlayerPositionChanged(t)) => playback.position_changed(t),
Err(_) => (), Err(_) => (),
} }

View File

@ -1,16 +1,32 @@
use gstreamer::ClockTime;
use gstreamer_player as gst;
use gtk; use gtk;
use gtk::prelude::*;
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub struct Playback { pub struct Playback {
pub container: gtk::Grid, reveal: gtk::Revealer,
container: gtk::Grid,
play: gtk::Button,
seek: gtk::Scale,
title: gtk::Label,
time: gtk::Label,
} }
impl Default for Playback { impl Default for Playback {
fn default() -> Self { fn default() -> Self {
let builder = gtk::Builder::new_from_resource("/org/gnome/Hammond/gtk/playback.ui"); let builder = gtk::Builder::new_from_resource("/org/gnome/Hammond/gtk/playback.ui");
let container = builder.get_object("wrapper").unwrap(); let container = builder.get_object("wrapper").unwrap();
let play = builder.get_object("play").unwrap();
let seek = builder.get_object("seek").unwrap();
let title = builder.get_object("title").unwrap();
let time = builder.get_object("time").unwrap();
Playback { container } let reveal = gtk::Revealer::new();
reveal.set_no_show_all(true);
reveal.add(&container);
Playback { reveal, container, play, seek, title, time }
} }
} }
@ -18,4 +34,61 @@ impl Playback {
pub fn new() -> Playback { pub fn new() -> Playback {
Playback::default() Playback::default()
} }
pub fn set_icon(&self, icon: &str) {
let image = gtk::Image::new_from_icon_name(icon, gtk::IconSize::Button.into());
self.play.set_image(Some(&image));
}
pub fn get_widget(&self) -> &gtk::Revealer {
&self.reveal
}
pub fn state_changed(&self, state: gst::PlayerState) {
// Once the playback controls are shown they don't go
// away again so show them unconditionally
self.reveal.show();
self.reveal.set_reveal_child(true);
match state {
gst::PlayerState::Buffering => {
println!("Buffering!!!!!!!");
},
gst::PlayerState::Stopped | gst::PlayerState::Paused => {
println!("Stopped/Paused");
self.set_icon("media-playback-start-symbolic");
},
gst::PlayerState::Playing => {
println!("Playing");
self.set_icon("media-playback-pause-symbolic");
},
_ => {
println!("Weird stuff");
}
}
}
pub fn media_changed(&self, title: Option<String>, length: ClockTime) {
self.reveal.show();
self.reveal.set_reveal_child(true);
if let Some(title) = title {
self.title.set_label(&title);
} else {
self.title.set_label("");
}
if let Some(s) = length.seconds() {
let hours = s / 3600;
let s = s - (hours * 3600);
let mins = s / 60;
let s = s - (mins * 60);
// This is a little nasty
let t = format!("{}:{}:{}", hours, mins, s);
self.time.set_label(&t);
} else {
self.time.set_label("");
}
}
pub fn position_changed(&self, _pos: ClockTime) {
println!("Tada!");
}
} }