Get to the point where we are fairly happy with our uncrustify config. Fixes #6.
This commit is contained in:
parent
d07d3dfe50
commit
62de9c2032
58 changed files with 4811 additions and 1946 deletions
|
@ -38,25 +38,26 @@ enum {
|
|||
N_SIGNALS
|
||||
};
|
||||
|
||||
static guint playback_engine_signals[N_SIGNALS] = { 0 };
|
||||
static guint playback_engine_signals[N_SIGNALS] = {
|
||||
0
|
||||
};
|
||||
|
||||
extern KotoCartographer *koto_maps;
|
||||
extern KotoCurrentPlaylist *current_playlist;
|
||||
extern KotoCartographer * koto_maps;
|
||||
extern KotoCurrentPlaylist * current_playlist;
|
||||
|
||||
KotoPlaybackEngine *playback_engine;
|
||||
KotoPlaybackEngine * playback_engine;
|
||||
|
||||
struct _KotoPlaybackEngine {
|
||||
GObject parent_class;
|
||||
GstElement *player;
|
||||
GstElement *playbin;
|
||||
GstElement *suppress_video;
|
||||
GstBus *monitor;
|
||||
GstElement * player;
|
||||
GstElement * playbin;
|
||||
GstElement * suppress_video;
|
||||
GstBus * monitor;
|
||||
|
||||
GstQuery *duration_query;
|
||||
GstQuery *position_query;
|
||||
GstQuery * duration_query;
|
||||
GstQuery * position_query;
|
||||
|
||||
KotoIndexedTrack *current_track;
|
||||
NotifyNotification *track_notification;
|
||||
KotoIndexedTrack * current_track;
|
||||
|
||||
gboolean is_muted;
|
||||
gboolean is_repeat_enabled;
|
||||
|
@ -74,22 +75,24 @@ struct _KotoPlaybackEngine {
|
|||
struct _KotoPlaybackEngineClass {
|
||||
GObjectClass parent_class;
|
||||
|
||||
void (* is_playing) (KotoPlaybackEngine *engine);
|
||||
void (* is_paused) (KotoPlaybackEngine *engine);
|
||||
void (* play_state_changed) (KotoPlaybackEngine *engine);
|
||||
void (* tick_duration) (KotoPlaybackEngine *engine);
|
||||
void (* tick_track) (KotoPlaybackEngine *engine);
|
||||
void (* track_changed) (KotoPlaybackEngine *engine);
|
||||
void (* track_repeat_changed) (KotoPlaybackEngine *engine);
|
||||
void (* track_shuffle_changed) (KotoPlaybackEngine *engine);
|
||||
void (* is_playing) (KotoPlaybackEngine * engine);
|
||||
void (* is_paused) (KotoPlaybackEngine * engine);
|
||||
void (* play_state_changed) (KotoPlaybackEngine * engine);
|
||||
void (* tick_duration) (KotoPlaybackEngine * engine);
|
||||
void (* tick_track) (KotoPlaybackEngine * engine);
|
||||
void (* track_changed) (KotoPlaybackEngine * engine);
|
||||
void (* track_repeat_changed) (KotoPlaybackEngine * engine);
|
||||
void (* track_shuffle_changed) (KotoPlaybackEngine * engine);
|
||||
};
|
||||
|
||||
G_DEFINE_TYPE(KotoPlaybackEngine, koto_playback_engine, G_TYPE_OBJECT);
|
||||
|
||||
static void koto_playback_engine_class_init(KotoPlaybackEngineClass *c) {
|
||||
static void koto_playback_engine_class_init(KotoPlaybackEngineClass * c) {
|
||||
c->play_state_changed = NULL;
|
||||
|
||||
GObjectClass *gobject_class;
|
||||
GObjectClass * gobject_class;
|
||||
|
||||
|
||||
gobject_class = G_OBJECT_CLASS(c);
|
||||
|
||||
playback_engine_signals[SIGNAL_IS_PLAYING] = g_signal_new(
|
||||
|
@ -189,7 +192,7 @@ static void koto_playback_engine_class_init(KotoPlaybackEngineClass *c) {
|
|||
);
|
||||
}
|
||||
|
||||
static void koto_playback_engine_init(KotoPlaybackEngine *self) {
|
||||
static void koto_playback_engine_init(KotoPlaybackEngine * self) {
|
||||
self->current_track = NULL;
|
||||
|
||||
self->player = gst_pipeline_new("player");
|
||||
|
@ -223,8 +226,9 @@ static void koto_playback_engine_init(KotoPlaybackEngine *self) {
|
|||
}
|
||||
}
|
||||
|
||||
void koto_playback_engine_backwards(KotoPlaybackEngine *self) {
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
void koto_playback_engine_backwards(KotoPlaybackEngine * self) {
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
|
||||
|
||||
if (!KOTO_IS_PLAYLIST(playlist)) { // If we do not have a playlist currently
|
||||
return;
|
||||
|
@ -242,7 +246,8 @@ void koto_playback_engine_current_playlist_changed() {
|
|||
return;
|
||||
}
|
||||
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
|
||||
|
||||
if (!KOTO_IS_PLAYLIST(playlist)) { // If we do not have a playlist currently
|
||||
return;
|
||||
|
@ -251,8 +256,9 @@ void koto_playback_engine_current_playlist_changed() {
|
|||
koto_playback_engine_set_track_by_uuid(playback_engine, koto_playlist_go_to_next(playlist)); // Go to "next" which is the first track
|
||||
}
|
||||
|
||||
void koto_playback_engine_forwards(KotoPlaybackEngine *self) {
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
void koto_playback_engine_forwards(KotoPlaybackEngine * self) {
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist); // Get the current playlist
|
||||
|
||||
|
||||
if (!KOTO_IS_PLAYLIST(playlist)) { // If we do not have a playlist currently
|
||||
return;
|
||||
|
@ -265,12 +271,14 @@ void koto_playback_engine_forwards(KotoPlaybackEngine *self) {
|
|||
}
|
||||
}
|
||||
|
||||
KotoIndexedTrack* koto_playback_engine_get_current_track(KotoPlaybackEngine *self) {
|
||||
KotoIndexedTrack * koto_playback_engine_get_current_track(KotoPlaybackEngine * self) {
|
||||
return self->current_track;
|
||||
}
|
||||
|
||||
gint64 koto_playback_engine_get_duration(KotoPlaybackEngine *self) {
|
||||
gint64 koto_playback_engine_get_duration(KotoPlaybackEngine * self) {
|
||||
gint64 duration = 0;
|
||||
|
||||
|
||||
if (gst_element_query(self->player, self->duration_query)) { // Able to query our duration
|
||||
gst_query_parse_duration(self->duration_query, NULL, &duration); // Get the duration
|
||||
duration = duration / GST_SECOND; // Divide by NS to get seconds
|
||||
|
@ -279,9 +287,11 @@ gint64 koto_playback_engine_get_duration(KotoPlaybackEngine *self) {
|
|||
return duration;
|
||||
}
|
||||
|
||||
gdouble koto_playback_engine_get_progress(KotoPlaybackEngine *self) {
|
||||
gdouble koto_playback_engine_get_progress(KotoPlaybackEngine * self) {
|
||||
gdouble progress = 0.0;
|
||||
gint64 gstprog = 0;
|
||||
|
||||
|
||||
if (gst_element_query(self->playbin, self->position_query)) { // Able to get our position
|
||||
gst_query_parse_position(self->position_query, NULL, &gstprog); // Get the progress
|
||||
|
||||
|
@ -295,31 +305,39 @@ gdouble koto_playback_engine_get_progress(KotoPlaybackEngine *self) {
|
|||
return progress;
|
||||
}
|
||||
|
||||
GstState koto_playback_engine_get_state(KotoPlaybackEngine *self) {
|
||||
GstState koto_playback_engine_get_state(KotoPlaybackEngine * self) {
|
||||
return GST_STATE(self->player);
|
||||
}
|
||||
|
||||
gboolean koto_playback_engine_get_track_repeat(KotoPlaybackEngine *self) {
|
||||
gboolean koto_playback_engine_get_track_repeat(KotoPlaybackEngine * self) {
|
||||
return self->is_repeat_enabled;
|
||||
}
|
||||
|
||||
gboolean koto_playback_engine_get_track_shuffle(KotoPlaybackEngine *self) {
|
||||
gboolean koto_playback_engine_get_track_shuffle(KotoPlaybackEngine * self) {
|
||||
(void) self;
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
|
||||
|
||||
if (!KOTO_IS_PLAYLIST(playlist)) { // Don't have a playlist currently
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
gboolean currently_shuffling = FALSE;
|
||||
|
||||
|
||||
g_object_get(playlist, "is-shuffle-enabled", ¤tly_shuffling, NULL); // Get the current is-shuffle-enabled
|
||||
|
||||
return currently_shuffling;
|
||||
}
|
||||
|
||||
gboolean koto_playback_engine_monitor_changed(GstBus *bus, GstMessage *msg, gpointer user_data) {
|
||||
gboolean koto_playback_engine_monitor_changed(
|
||||
GstBus * bus,
|
||||
GstMessage * msg,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) bus;
|
||||
KotoPlaybackEngine *self = user_data;
|
||||
KotoPlaybackEngine * self = user_data;
|
||||
|
||||
|
||||
switch (GST_MESSAGE_TYPE(msg)) {
|
||||
case GST_MESSAGE_ASYNC_DONE:
|
||||
|
@ -357,7 +375,7 @@ gboolean koto_playback_engine_monitor_changed(GstBus *bus, GstMessage *msg, gpoi
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
void koto_playback_engine_play(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_play(KotoPlaybackEngine * self) {
|
||||
self->is_playing = TRUE;
|
||||
gst_element_set_state(self->player, GST_STATE_PLAYING); // Set our state to play
|
||||
|
||||
|
@ -374,23 +392,33 @@ void koto_playback_engine_play(KotoPlaybackEngine *self) {
|
|||
koto_update_mpris_playback_state(GST_STATE_PLAYING);
|
||||
}
|
||||
|
||||
void koto_playback_engine_pause(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_pause(KotoPlaybackEngine * self) {
|
||||
self->is_playing = FALSE;
|
||||
gst_element_change_state(self->player, GST_STATE_CHANGE_PLAYING_TO_PAUSED);
|
||||
koto_update_mpris_playback_state(GST_STATE_PAUSED);
|
||||
}
|
||||
|
||||
void koto_playback_engine_set_position(KotoPlaybackEngine *self, int position) {
|
||||
void koto_playback_engine_set_position(
|
||||
KotoPlaybackEngine * self,
|
||||
int position
|
||||
) {
|
||||
gst_element_seek_simple(self->playbin, GST_FORMAT_TIME, GST_SEEK_FLAG_FLUSH, position * GST_SECOND);
|
||||
}
|
||||
|
||||
void koto_playback_engine_set_track_repeat(KotoPlaybackEngine *self, gboolean enable_repeat) {
|
||||
void koto_playback_engine_set_track_repeat(
|
||||
KotoPlaybackEngine * self,
|
||||
gboolean enable_repeat
|
||||
) {
|
||||
self->is_repeat_enabled = enable_repeat;
|
||||
g_signal_emit(self, playback_engine_signals[SIGNAL_TRACK_REPEAT_CHANGE], 0); // Emit our track repeat changed event
|
||||
}
|
||||
|
||||
void koto_playback_engine_set_track_shuffle(KotoPlaybackEngine *self, gboolean enable_shuffle) {
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
void koto_playback_engine_set_track_shuffle(
|
||||
KotoPlaybackEngine * self,
|
||||
gboolean enable_shuffle
|
||||
) {
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
|
||||
|
||||
if (!KOTO_IS_PLAYLIST(playlist)) { // Don't have a playlist currently
|
||||
return;
|
||||
|
@ -400,12 +428,16 @@ void koto_playback_engine_set_track_shuffle(KotoPlaybackEngine *self, gboolean e
|
|||
g_signal_emit(self, playback_engine_signals[SIGNAL_TRACK_SHUFFLE_CHANGE], 0); // Emit our track shuffle changed event
|
||||
}
|
||||
|
||||
void koto_playback_engine_set_track_by_uuid(KotoPlaybackEngine *self, gchar *track_uuid) {
|
||||
void koto_playback_engine_set_track_by_uuid(
|
||||
KotoPlaybackEngine * self,
|
||||
gchar * track_uuid
|
||||
) {
|
||||
if (track_uuid == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
KotoIndexedTrack *track = koto_cartographer_get_track_by_uuid(koto_maps, track_uuid); // Get the track from cartographer
|
||||
KotoIndexedTrack * track = koto_cartographer_get_track_by_uuid(koto_maps, track_uuid); // Get the track from cartographer
|
||||
|
||||
|
||||
if (!KOTO_IS_INDEXED_TRACK(track)) { // Not a track
|
||||
return;
|
||||
|
@ -413,12 +445,15 @@ void koto_playback_engine_set_track_by_uuid(KotoPlaybackEngine *self, gchar *tra
|
|||
|
||||
self->current_track = track;
|
||||
|
||||
gchar *track_file_path = NULL;
|
||||
gchar * track_file_path = NULL;
|
||||
|
||||
|
||||
g_object_get(track, "path", &track_file_path, NULL); // Get the path to the track
|
||||
|
||||
koto_playback_engine_stop(self); // Stop current track
|
||||
|
||||
gchar *gst_filename = gst_filename_to_uri(track_file_path, NULL); // Get the gst supported file naem
|
||||
gchar * gst_filename = gst_filename_to_uri(track_file_path, NULL); // Get the gst supported file naem
|
||||
|
||||
|
||||
g_object_set(self->playbin, "uri", gst_filename, NULL);
|
||||
g_free(gst_filename); // Free the filename
|
||||
|
@ -429,34 +464,36 @@ void koto_playback_engine_set_track_by_uuid(KotoPlaybackEngine *self, gchar *tra
|
|||
koto_playback_engine_set_position(self, 0);
|
||||
koto_playback_engine_set_volume(self, self->volume); // Re-enforce our volume on the updated playbin
|
||||
|
||||
GVariant *metadata = koto_indexed_track_get_metadata_vardict(track); // Get the GVariantBuilder variable dict for the metadata
|
||||
GVariantDict *metadata_dict = g_variant_dict_new(metadata);
|
||||
GVariant * metadata = koto_indexed_track_get_metadata_vardict(track); // Get the GVariantBuilder variable dict for the metadata
|
||||
GVariantDict * metadata_dict = g_variant_dict_new(metadata);
|
||||
|
||||
|
||||
g_signal_emit(self, playback_engine_signals[SIGNAL_TRACK_CHANGE], 0); // Emit our track change signal
|
||||
koto_update_mpris_info_for_track(self->current_track);
|
||||
|
||||
GVariant *track_name_var = g_variant_dict_lookup_value(metadata_dict, "xesam:title", NULL); // Get the GVariant for the name of the track
|
||||
const gchar *track_name = g_variant_get_string(track_name_var, NULL); // Get the string of the track name
|
||||
GVariant * track_name_var = g_variant_dict_lookup_value(metadata_dict, "xesam:title", NULL); // Get the GVariant for the name of the track
|
||||
const gchar * track_name = g_variant_get_string(track_name_var, NULL); // Get the string of the track name
|
||||
|
||||
GVariant *album_name_var = g_variant_dict_lookup_value(metadata_dict, "xesam:album", NULL); // Get the GVariant for the album name
|
||||
const gchar *album_name = g_variant_get_string(album_name_var, NULL); // Get the string for the album name
|
||||
GVariant * album_name_var = g_variant_dict_lookup_value(metadata_dict, "xesam:album", NULL); // Get the GVariant for the album name
|
||||
const gchar * album_name = g_variant_get_string(album_name_var, NULL); // Get the string for the album name
|
||||
|
||||
GVariant *artist_name_var = g_variant_dict_lookup_value(metadata_dict, "playbackengine:artist", NULL); // Get the GVariant for the name of the artist
|
||||
const gchar *artist_name = g_variant_get_string(artist_name_var, NULL); // Get the string for the artist name
|
||||
GVariant * artist_name_var = g_variant_dict_lookup_value(metadata_dict, "playbackengine:artist", NULL); // Get the GVariant for the name of the artist
|
||||
const gchar * artist_name = g_variant_get_string(artist_name_var, NULL); // Get the string for the artist name
|
||||
|
||||
gchar *artist_album_combo = g_strjoin(" - ", artist_name, album_name, NULL); // Join artist and album name separated by " - "
|
||||
gchar * artist_album_combo = g_strjoin(" - ", artist_name, album_name, NULL); // Join artist and album name separated by " - "
|
||||
|
||||
gchar * icon_name = "audio-x-generic-symbolic";
|
||||
|
||||
gchar *icon_name = "audio-x-generic-symbolic";
|
||||
|
||||
if (g_variant_dict_contains(metadata_dict, "mpris:artUrl")) { // If we have artwork specified
|
||||
GVariant *art_url_var = g_variant_dict_lookup_value(metadata_dict, "mpris:artUrl", NULL); // Get the GVariant for the art URL
|
||||
const gchar *art_uri = g_variant_get_string(art_url_var, NULL); // Get the string for the artwork
|
||||
GVariant * art_url_var = g_variant_dict_lookup_value(metadata_dict, "mpris:artUrl", NULL); // Get the GVariant for the art URL
|
||||
const gchar * art_uri = g_variant_get_string(art_url_var, NULL); // Get the string for the artwork
|
||||
icon_name = koto_utils_replace_string_all(g_strdup(art_uri), "file://", "");
|
||||
}
|
||||
|
||||
// Super important note: We are not using libnotify directly because the synchronous nature of notify_notification_send seems to result in dbus timeouts
|
||||
if (g_find_program_in_path("notify-send") != NULL) { // Have notify-send
|
||||
char *argv[12];
|
||||
char * argv[12];
|
||||
argv[0] = "notify-send";
|
||||
argv[1] = "-a";
|
||||
argv[2] = "Koto";
|
||||
|
@ -474,14 +511,18 @@ void koto_playback_engine_set_track_by_uuid(KotoPlaybackEngine *self, gchar *tra
|
|||
}
|
||||
}
|
||||
|
||||
void koto_playback_engine_set_volume(KotoPlaybackEngine *self, gdouble volume) {
|
||||
void koto_playback_engine_set_volume(
|
||||
KotoPlaybackEngine * self,
|
||||
gdouble volume
|
||||
) {
|
||||
self->volume = volume;
|
||||
g_object_set(self->playbin, "volume", self->volume, NULL);
|
||||
}
|
||||
|
||||
void koto_playback_engine_stop(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_stop(KotoPlaybackEngine * self) {
|
||||
gst_element_set_state(self->player, GST_STATE_NULL);
|
||||
GstPad *pad = gst_element_get_static_pad(self->player, "sink"); // Get the static pad of the audio element
|
||||
GstPad * pad = gst_element_get_static_pad(self->player, "sink"); // Get the static pad of the audio element
|
||||
|
||||
|
||||
if (!GST_IS_PAD(pad)) {
|
||||
return;
|
||||
|
@ -491,7 +532,7 @@ void koto_playback_engine_stop(KotoPlaybackEngine *self) {
|
|||
koto_update_mpris_playback_state(GST_STATE_NULL);
|
||||
}
|
||||
|
||||
void koto_playback_engine_toggle(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_toggle(KotoPlaybackEngine * self) {
|
||||
if (self->is_playing) { // Currently playing
|
||||
koto_playback_engine_pause(self); // Pause
|
||||
} else {
|
||||
|
@ -500,7 +541,8 @@ void koto_playback_engine_toggle(KotoPlaybackEngine *self) {
|
|||
}
|
||||
|
||||
gboolean koto_playback_engine_tick_duration(gpointer user_data) {
|
||||
KotoPlaybackEngine *self = user_data;
|
||||
KotoPlaybackEngine * self = user_data;
|
||||
|
||||
|
||||
if (self->is_playing) { // Is playing
|
||||
g_signal_emit(self, playback_engine_signals[SIGNAL_TICK_DURATION], 0); // Emit our 1s track tick
|
||||
|
@ -512,7 +554,8 @@ gboolean koto_playback_engine_tick_duration(gpointer user_data) {
|
|||
}
|
||||
|
||||
gboolean koto_playback_engine_tick_track(gpointer user_data) {
|
||||
KotoPlaybackEngine *self = user_data;
|
||||
KotoPlaybackEngine * self = user_data;
|
||||
|
||||
|
||||
if (self->is_playing) { // Is playing
|
||||
g_signal_emit(self, playback_engine_signals[SIGNAL_TICK_TRACK], 0); // Emit our 100ms track tick
|
||||
|
@ -523,14 +566,14 @@ gboolean koto_playback_engine_tick_track(gpointer user_data) {
|
|||
return self->is_playing;
|
||||
}
|
||||
|
||||
void koto_playback_engine_toggle_track_repeat(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_toggle_track_repeat(KotoPlaybackEngine * self) {
|
||||
koto_playback_engine_set_track_repeat(self, !self->is_repeat_enabled);
|
||||
}
|
||||
|
||||
void koto_playback_engine_toggle_track_shuffle(KotoPlaybackEngine *self) {
|
||||
void koto_playback_engine_toggle_track_shuffle(KotoPlaybackEngine * self) {
|
||||
koto_playback_engine_set_track_shuffle(self, !koto_playback_engine_get_track_shuffle(self)); // Invert the currently shuffling vale
|
||||
}
|
||||
|
||||
KotoPlaybackEngine* koto_playback_engine_new() {
|
||||
KotoPlaybackEngine * koto_playback_engine_new() {
|
||||
return g_object_new(KOTO_TYPE_PLAYBACK_ENGINE, NULL);
|
||||
}
|
||||
|
|
|
@ -25,10 +25,10 @@ G_BEGIN_DECLS
|
|||
|
||||
/**
|
||||
* Type Definition
|
||||
**/
|
||||
**/
|
||||
|
||||
#define KOTO_TYPE_PLAYBACK_ENGINE (koto_playback_engine_get_type())
|
||||
#define KOTO_PLAYBACK_ENGINE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), KOTO_TYPE_PLAYBACK_ENGINE, KotoPlaybackEngine))
|
||||
#define KOTO_PLAYBACK_ENGINE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), KOTO_TYPE_PLAYBACK_ENGINE, KotoPlaybackEngine))
|
||||
#define KOTO_IS_PLAYBACK_ENGINE(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), KOTO_TYPE_PLAYBACK_ENGINE))
|
||||
|
||||
typedef struct _KotoPlaybackEngine KotoPlaybackEngine;
|
||||
|
@ -39,32 +39,75 @@ GType koto_playback_engine_get_type(void) G_GNUC_CONST;
|
|||
|
||||
/**
|
||||
* Playback Engine Functions
|
||||
**/
|
||||
**/
|
||||
|
||||
KotoPlaybackEngine * koto_playback_engine_new();
|
||||
|
||||
void koto_playback_engine_backwards(KotoPlaybackEngine * self);
|
||||
|
||||
KotoPlaybackEngine* koto_playback_engine_new();
|
||||
void koto_playback_engine_backwards(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_current_playlist_changed();
|
||||
void koto_playback_engine_forwards(KotoPlaybackEngine *self);
|
||||
KotoIndexedTrack* koto_playback_engine_get_current_track(KotoPlaybackEngine *self);
|
||||
gint64 koto_playback_engine_get_duration(KotoPlaybackEngine *self);
|
||||
GstState koto_playback_engine_get_state(KotoPlaybackEngine *self);
|
||||
gdouble koto_playback_engine_get_progress(KotoPlaybackEngine *self);
|
||||
gboolean koto_playback_engine_get_track_repeat(KotoPlaybackEngine *self);
|
||||
gboolean koto_playback_engine_get_track_shuffle(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_mute(KotoPlaybackEngine *self);
|
||||
gboolean koto_playback_engine_monitor_changed(GstBus *bus, GstMessage *msg, gpointer user_data);
|
||||
void koto_playback_engine_pause(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_play(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_toggle(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_set_position(KotoPlaybackEngine *self, int position);
|
||||
void koto_playback_engine_set_track_repeat(KotoPlaybackEngine *self, gboolean enable_repeat);
|
||||
void koto_playback_engine_set_track_shuffle(KotoPlaybackEngine *self, gboolean enable_shuffle);
|
||||
void koto_playback_engine_set_track_by_uuid(KotoPlaybackEngine *self, gchar *track_uuid);
|
||||
void koto_playback_engine_set_volume(KotoPlaybackEngine *self, gdouble volume);
|
||||
void koto_playback_engine_stop(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_toggle_track_repeat(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_toggle_track_shuffle(KotoPlaybackEngine *self);
|
||||
void koto_playback_engine_update_duration(KotoPlaybackEngine *self);
|
||||
|
||||
void koto_playback_engine_forwards(KotoPlaybackEngine * self);
|
||||
|
||||
KotoIndexedTrack * koto_playback_engine_get_current_track(KotoPlaybackEngine * self);
|
||||
|
||||
gint64 koto_playback_engine_get_duration(KotoPlaybackEngine * self);
|
||||
|
||||
GstState koto_playback_engine_get_state(KotoPlaybackEngine * self);
|
||||
|
||||
gdouble koto_playback_engine_get_progress(KotoPlaybackEngine * self);
|
||||
|
||||
gboolean koto_playback_engine_get_track_repeat(KotoPlaybackEngine * self);
|
||||
|
||||
gboolean koto_playback_engine_get_track_shuffle(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_mute(KotoPlaybackEngine * self);
|
||||
|
||||
gboolean koto_playback_engine_monitor_changed(
|
||||
GstBus * bus,
|
||||
GstMessage * msg,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void koto_playback_engine_pause(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_play(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_toggle(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_set_position(
|
||||
KotoPlaybackEngine * self,
|
||||
int position
|
||||
);
|
||||
|
||||
void koto_playback_engine_set_track_repeat(
|
||||
KotoPlaybackEngine * self,
|
||||
gboolean enable_repeat
|
||||
);
|
||||
|
||||
void koto_playback_engine_set_track_shuffle(
|
||||
KotoPlaybackEngine * self,
|
||||
gboolean enable_shuffle
|
||||
);
|
||||
|
||||
void koto_playback_engine_set_track_by_uuid(
|
||||
KotoPlaybackEngine * self,
|
||||
gchar * track_uuid
|
||||
);
|
||||
|
||||
void koto_playback_engine_set_volume(
|
||||
KotoPlaybackEngine * self,
|
||||
gdouble volume
|
||||
);
|
||||
|
||||
void koto_playback_engine_stop(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_toggle_track_repeat(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_toggle_track_shuffle(KotoPlaybackEngine * self);
|
||||
|
||||
void koto_playback_engine_update_duration(KotoPlaybackEngine * self);
|
||||
|
||||
gboolean koto_playback_engine_tick_duration(gpointer user_data);
|
||||
|
||||
gboolean koto_playback_engine_tick_track(gpointer user_data);
|
||||
|
|
|
@ -21,30 +21,30 @@
|
|||
#include "engine.h"
|
||||
#include "media-keys.h"
|
||||
|
||||
extern GtkWindow *main_window;
|
||||
extern KotoPlaybackEngine *playback_engine;
|
||||
extern GtkWindow * main_window;
|
||||
extern KotoPlaybackEngine * playback_engine;
|
||||
|
||||
GDBusConnection *media_keys_dbus_conn = NULL;
|
||||
GDBusProxy *media_keys_proxy = NULL;
|
||||
GDBusNodeInfo *media_keys_introspection_data = NULL;
|
||||
GDBusConnection * media_keys_dbus_conn = NULL;
|
||||
GDBusProxy * media_keys_proxy = NULL;
|
||||
GDBusNodeInfo * media_keys_introspection_data = NULL;
|
||||
|
||||
static const gchar introspection_xml[] =
|
||||
"<node name='/org/gnome/SettingsDaemon/MediaKeys'>"
|
||||
" <interface name='org.gnome.SettingsDaemon.MediaKeys'>"
|
||||
" <annotation name='org.freedesktop.DBus.GLib.CSymbol' value='gsd_media_keys_manager'/>"
|
||||
" <method name='GrabMediaPlayerKeys'>"
|
||||
" <arg name='application' direction='in' type='s'/>"
|
||||
" <arg name='time' direction='in' type='u'/>"
|
||||
" </method>"
|
||||
" <method name='ReleaseMediaPlayerKeys'>"
|
||||
" <arg name='application' direction='in' type='s'/>"
|
||||
" </method>"
|
||||
" <signal name='MediaPlayerKeyPressed'>"
|
||||
" <arg name='application' type='s'/>"
|
||||
" <arg name='key' type='s'/>"
|
||||
" </signal>"
|
||||
" </interface>"
|
||||
"</node>";
|
||||
"<node name='/org/gnome/SettingsDaemon/MediaKeys'>"
|
||||
" <interface name='org.gnome.SettingsDaemon.MediaKeys'>"
|
||||
" <annotation name='org.freedesktop.DBus.GLib.CSymbol' value='gsd_media_keys_manager'/>"
|
||||
" <method name='GrabMediaPlayerKeys'>"
|
||||
" <arg name='application' direction='in' type='s'/>"
|
||||
" <arg name='time' direction='in' type='u'/>"
|
||||
" </method>"
|
||||
" <method name='ReleaseMediaPlayerKeys'>"
|
||||
" <arg name='application' direction='in' type='s'/>"
|
||||
" </method>"
|
||||
" <signal name='MediaPlayerKeyPressed'>"
|
||||
" <arg name='application' type='s'/>"
|
||||
" <arg name='key' type='s'/>"
|
||||
" </signal>"
|
||||
" </interface>"
|
||||
"</node>";
|
||||
|
||||
void grab_media_keys() {
|
||||
if (media_keys_proxy == NULL) { // No connection
|
||||
|
@ -63,19 +63,32 @@ void grab_media_keys() {
|
|||
);
|
||||
}
|
||||
|
||||
void handle_media_keys_async_done(GObject *source_object, GAsyncResult *res, gpointer user_data) {
|
||||
void handle_media_keys_async_done(
|
||||
GObject * source_object,
|
||||
GAsyncResult * res,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) user_data;
|
||||
g_dbus_proxy_call_finish(G_DBUS_PROXY(source_object), res, NULL); // Ensure we finish our call
|
||||
}
|
||||
|
||||
void handle_media_keys_signal(GDBusProxy *proxy, const gchar *sender_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) {
|
||||
(void) proxy; (void) sender_name; (void) user_data;
|
||||
void handle_media_keys_signal(
|
||||
GDBusProxy * proxy,
|
||||
const gchar * sender_name,
|
||||
const gchar * signal_name,
|
||||
GVariant * parameters,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) proxy;
|
||||
(void) sender_name;
|
||||
(void) user_data;
|
||||
if (g_strcmp0(signal_name, "MediaPlayerKeyPressed") != 0) { // Not MediaPlayerKeyPressed
|
||||
return;
|
||||
}
|
||||
|
||||
gchar *application_name = NULL;
|
||||
gchar *key = NULL;
|
||||
gchar * application_name = NULL;
|
||||
gchar * key = NULL;
|
||||
|
||||
|
||||
g_variant_get(parameters, "(ss)", &application_name, &key);
|
||||
|
||||
|
@ -100,13 +113,21 @@ void handle_media_keys_signal(GDBusProxy *proxy, const gchar *sender_name, const
|
|||
}
|
||||
}
|
||||
|
||||
void handle_window_enter(GtkEventControllerFocus *controller, gpointer user_data) {
|
||||
(void) controller; (void) user_data;
|
||||
void handle_window_enter(
|
||||
GtkEventControllerFocus * controller,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) controller;
|
||||
(void) user_data;
|
||||
grab_media_keys(); // Grab our media keys
|
||||
}
|
||||
|
||||
void handle_window_leave(GtkEventControllerFocus *controller, gpointer user_data) {
|
||||
(void) controller; (void) user_data;
|
||||
void handle_window_leave(
|
||||
GtkEventControllerFocus * controller,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) controller;
|
||||
(void) user_data;
|
||||
release_media_keys(); // Release our media keys
|
||||
}
|
||||
|
||||
|
@ -115,7 +136,8 @@ void release_media_keys() {
|
|||
return;
|
||||
}
|
||||
|
||||
GVariant *params = g_variant_new_string(g_strdup("com.github.joshstrobl.koto"));
|
||||
GVariant * params = g_variant_new_string(g_strdup("com.github.joshstrobl.koto"));
|
||||
|
||||
|
||||
g_dbus_proxy_call(
|
||||
media_keys_proxy,
|
||||
|
@ -133,8 +155,9 @@ void setup_mediakeys_interface() {
|
|||
media_keys_introspection_data = g_dbus_node_info_new_for_xml(introspection_xml, NULL);
|
||||
g_assert(media_keys_introspection_data != NULL);
|
||||
|
||||
GDBusConnection *bus;
|
||||
GError *error = NULL;
|
||||
GDBusConnection * bus;
|
||||
GError * error = NULL;
|
||||
|
||||
|
||||
bus = g_bus_get_sync(G_BUS_TYPE_SESSION, NULL, &error);
|
||||
|
||||
|
@ -169,7 +192,9 @@ void setup_mediakeys_interface() {
|
|||
0
|
||||
);
|
||||
|
||||
GtkEventController *focus_controller = gtk_event_controller_focus_new(); // Create a new focus controller
|
||||
GtkEventController * focus_controller = gtk_event_controller_focus_new(); // Create a new focus controller
|
||||
|
||||
|
||||
g_signal_connect(focus_controller, "enter", G_CALLBACK(handle_window_enter), NULL);
|
||||
g_signal_connect(focus_controller, "leave", G_CALLBACK(handle_window_leave), NULL);
|
||||
gtk_widget_add_controller(GTK_WIDGET(main_window), focus_controller);
|
||||
|
|
|
@ -22,11 +22,33 @@
|
|||
G_BEGIN_DECLS
|
||||
|
||||
void grab_media_keys();
|
||||
void handle_media_keys_async_done(GObject *source_object, GAsyncResult *res, gpointer user_data);
|
||||
void handle_media_keys_signal(GDBusProxy *proxy, const gchar *sender_name, const gchar *signal_name, GVariant *parameters, gpointer user_data);
|
||||
void handle_window_enter(GtkEventControllerFocus *controller, gpointer user_data);
|
||||
void handle_window_leave(GtkEventControllerFocus *controller, gpointer user_data);
|
||||
|
||||
void handle_media_keys_async_done(
|
||||
GObject * source_object,
|
||||
GAsyncResult * res,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void handle_media_keys_signal(
|
||||
GDBusProxy * proxy,
|
||||
const gchar * sender_name,
|
||||
const gchar * signal_name,
|
||||
GVariant * parameters,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void handle_window_enter(
|
||||
GtkEventControllerFocus * controller,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void handle_window_leave(
|
||||
GtkEventControllerFocus * controller,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void release_media_keys();
|
||||
|
||||
void setup_mediakeys_interface();
|
||||
|
||||
G_END_DECLS
|
||||
|
|
|
@ -20,12 +20,18 @@
|
|||
#include <gstreamer-1.0/gst/gst.h>
|
||||
#include "../koto-utils.h"
|
||||
|
||||
GHashTable *supported_mimes_hash = NULL;
|
||||
GList *supported_mimes = NULL;
|
||||
GHashTable * supported_mimes_hash = NULL;
|
||||
GList * supported_mimes = NULL;
|
||||
|
||||
gboolean koto_playback_engine_gst_caps_iter(
|
||||
GstCapsFeatures * features,
|
||||
GstStructure * structure,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) features;
|
||||
(void) user_data;
|
||||
gchar * caps_name = (gchar*) gst_structure_get_name(structure); // Get the name, typically a mimetype
|
||||
|
||||
gboolean koto_playback_engine_gst_caps_iter(GstCapsFeatures *features, GstStructure *structure, gpointer user_data) {
|
||||
(void) features; (void) user_data;
|
||||
gchar *caps_name = (gchar*) gst_structure_get_name(structure); // Get the name, typically a mimetype
|
||||
|
||||
if (g_str_has_prefix(caps_name, "unknown")) { // Is unknown
|
||||
return TRUE;
|
||||
|
@ -42,11 +48,16 @@ gboolean koto_playback_engine_gst_caps_iter(GstCapsFeatures *features, GstStruct
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
void koto_playback_engine_gst_pad_iter(gpointer list_data, gpointer user_data) {
|
||||
void koto_playback_engine_gst_pad_iter(
|
||||
gpointer list_data,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) user_data;
|
||||
GstStaticPadTemplate *templ = list_data;
|
||||
GstStaticPadTemplate * templ = list_data;
|
||||
|
||||
|
||||
if (templ->direction == GST_PAD_SINK) { // Is a sink pad
|
||||
GstCaps *capabilities = gst_static_pad_template_get_caps(templ); // Get the capabilities
|
||||
GstCaps * capabilities = gst_static_pad_template_get_caps(templ); // Get the capabilities
|
||||
gst_caps_foreach(capabilities, koto_playback_engine_gst_caps_iter, NULL); // Iterate over and add to mimes
|
||||
gst_caps_unref(capabilities);
|
||||
}
|
||||
|
@ -55,12 +66,14 @@ void koto_playback_engine_gst_pad_iter(gpointer list_data, gpointer user_data) {
|
|||
void koto_playback_engine_get_supported_mimetypes() {
|
||||
// Credit for code goes to https://github.com/mopidy/mopidy/issues/812#issuecomment-75868363
|
||||
// These are GstElementFactory
|
||||
GList *elements = gst_element_factory_list_get_elements(GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER | GST_ELEMENT_FACTORY_TYPE_DEMUXER | GST_ELEMENT_FACTORY_TYPE_PARSER | GST_ELEMENT_FACTORY_TYPE_DECODER | GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO, GST_RANK_NONE);
|
||||
GList * elements = gst_element_factory_list_get_elements(GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER | GST_ELEMENT_FACTORY_TYPE_DEMUXER | GST_ELEMENT_FACTORY_TYPE_PARSER | GST_ELEMENT_FACTORY_TYPE_DECODER | GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO, GST_RANK_NONE);
|
||||
|
||||
GList * ele;
|
||||
|
||||
|
||||
GList *ele;
|
||||
for (ele = elements; ele != NULL; ele = ele->next) { // For each of the elements
|
||||
// GList of GstStaticPadTemplate
|
||||
GList *static_pads = (GList*) gst_element_factory_get_static_pad_templates(ele->data); // Get the pads
|
||||
GList * static_pads = (GList*) gst_element_factory_get_static_pad_templates(ele->data); // Get the pads
|
||||
g_list_foreach(static_pads, koto_playback_engine_gst_pad_iter, NULL);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,8 +21,17 @@
|
|||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
gboolean koto_bplayback_engine_gst_caps_iter(GstCapsFeatures *features, GstStructure *structure, gpointer user_data);
|
||||
void koto_playback_engine_gst_pad_iter(gpointer list_data, gpointer user_data);
|
||||
void koto_playback_engine_get_supported_mimetypes(GList *mimes);
|
||||
gboolean koto_bplayback_engine_gst_caps_iter(
|
||||
GstCapsFeatures * features,
|
||||
GstStructure * structure,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void koto_playback_engine_gst_pad_iter(
|
||||
gpointer list_data,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void koto_playback_engine_get_supported_mimetypes(GList * mimes);
|
||||
|
||||
G_END_DECLS
|
||||
|
|
|
@ -28,73 +28,78 @@
|
|||
#include "mimes.h"
|
||||
#include "mpris.h"
|
||||
|
||||
extern KotoCartographer *koto_maps;
|
||||
extern KotoCurrentPlaylist *current_playlist;
|
||||
extern GtkApplication *app;
|
||||
extern GtkWindow *main_window;
|
||||
extern KotoPlaybackEngine *playback_engine;
|
||||
extern GList *supported_mimes;
|
||||
extern KotoCartographer * koto_maps;
|
||||
extern KotoCurrentPlaylist * current_playlist;
|
||||
extern GtkApplication * app;
|
||||
extern GtkWindow * main_window;
|
||||
extern KotoPlaybackEngine * playback_engine;
|
||||
extern GList * supported_mimes;
|
||||
|
||||
GDBusConnection *dbus_conn = NULL;
|
||||
GDBusConnection * dbus_conn = NULL;
|
||||
guint mpris_bus_id = 0;
|
||||
GDBusNodeInfo *introspection_data = NULL;
|
||||
GDBusNodeInfo * introspection_data = NULL;
|
||||
|
||||
static const gchar introspection_xml[] =
|
||||
"<node>"
|
||||
" <interface name='org.mpris.MediaPlayer2'>"
|
||||
" <method name='Raise' />"
|
||||
" <method name='Quit' />"
|
||||
" <property type='b' name='CanQuit' access='read' />"
|
||||
" <property type='b' name='CanRaise' access='read' />"
|
||||
" <property type='b' name='HasTrackList' access='read' />"
|
||||
" <property type='s' name='Identity' access='read' />"
|
||||
" <property type='s' name='DesktopEntry' access='read' />"
|
||||
" <property type='as' name='SupportedUriSchemas' access='read' />"
|
||||
" <property type='as' name='SupportedMimeTypes' access='read' />"
|
||||
" </interface>"
|
||||
" <interface name='org.mpris.MediaPlayer2.Player'>"
|
||||
" <method name='Next' />"
|
||||
" <method name='Previous' />"
|
||||
" <method name='Pause' />"
|
||||
" <method name='PlayPause' />"
|
||||
" <method name='Stop' />"
|
||||
" <method name='Play' />"
|
||||
" <method name='Seek'>"
|
||||
" <arg type='x' name='offset' />"
|
||||
" </method>"
|
||||
" <method name='SetPosition'>"
|
||||
" <arg type='o' name='track_id' />"
|
||||
" <arg type='x' name='pos' />"
|
||||
" </method>"
|
||||
" <property type='s' name='PlaybackStatus' access='read' />"
|
||||
" <property type='s' name='LoopStatus' access='readwrite' />"
|
||||
" <property type='d' name='Rate' access='readwrite' />"
|
||||
" <property type='b' name='Shuffle' access='readwrite' />"
|
||||
" <property type='a{sv}' name='Metadata' access='read' />"
|
||||
" <property type='d' name='Volume' access='readwrite' />"
|
||||
" <property type='x' name='Position' access='read' />"
|
||||
" <property type='d' name='MinimumRate' access='read' />"
|
||||
" <property type='d' name='MaximumRate' access='read' />"
|
||||
" <property type='b' name='CanGoNext' access='read' />"
|
||||
" <property type='b' name='CanGoPrevious' access='read' />"
|
||||
" <property type='b' name='CanPlay' access='read' />"
|
||||
" <property type='b' name='CanPause' access='read' />"
|
||||
" <property type='b' name='CanSeek' access='read' />"
|
||||
" <property type='b' name='CanControl' access='read' />"
|
||||
" </interface>"
|
||||
"</node>";
|
||||
"<node>"
|
||||
" <interface name='org.mpris.MediaPlayer2'>"
|
||||
" <method name='Raise' />"
|
||||
" <method name='Quit' />"
|
||||
" <property type='b' name='CanQuit' access='read' />"
|
||||
" <property type='b' name='CanRaise' access='read' />"
|
||||
" <property type='b' name='HasTrackList' access='read' />"
|
||||
" <property type='s' name='Identity' access='read' />"
|
||||
" <property type='s' name='DesktopEntry' access='read' />"
|
||||
" <property type='as' name='SupportedUriSchemas' access='read' />"
|
||||
" <property type='as' name='SupportedMimeTypes' access='read' />"
|
||||
" </interface>"
|
||||
" <interface name='org.mpris.MediaPlayer2.Player'>"
|
||||
" <method name='Next' />"
|
||||
" <method name='Previous' />"
|
||||
" <method name='Pause' />"
|
||||
" <method name='PlayPause' />"
|
||||
" <method name='Stop' />"
|
||||
" <method name='Play' />"
|
||||
" <method name='Seek'>"
|
||||
" <arg type='x' name='offset' />"
|
||||
" </method>"
|
||||
" <method name='SetPosition'>"
|
||||
" <arg type='o' name='track_id' />"
|
||||
" <arg type='x' name='pos' />"
|
||||
" </method>"
|
||||
" <property type='s' name='PlaybackStatus' access='read' />"
|
||||
" <property type='s' name='LoopStatus' access='readwrite' />"
|
||||
" <property type='d' name='Rate' access='readwrite' />"
|
||||
" <property type='b' name='Shuffle' access='readwrite' />"
|
||||
" <property type='a{sv}' name='Metadata' access='read' />"
|
||||
" <property type='d' name='Volume' access='readwrite' />"
|
||||
" <property type='x' name='Position' access='read' />"
|
||||
" <property type='d' name='MinimumRate' access='read' />"
|
||||
" <property type='d' name='MaximumRate' access='read' />"
|
||||
" <property type='b' name='CanGoNext' access='read' />"
|
||||
" <property type='b' name='CanGoPrevious' access='read' />"
|
||||
" <property type='b' name='CanPlay' access='read' />"
|
||||
" <property type='b' name='CanPause' access='read' />"
|
||||
" <property type='b' name='CanSeek' access='read' />"
|
||||
" <property type='b' name='CanControl' access='read' />"
|
||||
" </interface>"
|
||||
"</node>";
|
||||
|
||||
void handle_method_call(
|
||||
GDBusConnection *connection,
|
||||
const gchar *sender,
|
||||
const gchar *object_path,
|
||||
const gchar *interface_name,
|
||||
const gchar *method_name,
|
||||
GVariant *parameters,
|
||||
GDBusMethodInvocation *invocation,
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * method_name,
|
||||
GVariant * parameters,
|
||||
GDBusMethodInvocation * invocation,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) connection; (void) sender; (void) object_path; (void) parameters; (void) invocation; (void) user_data;
|
||||
(void) connection;
|
||||
(void) sender;
|
||||
(void) object_path;
|
||||
(void) parameters;
|
||||
(void) invocation;
|
||||
(void) user_data;
|
||||
|
||||
if (g_strcmp0(interface_name, "org.mpris.MediaPlayer2") == 0) { // Root mediaplayer2 interface
|
||||
if (g_strcmp0(method_name, "Raise") == 0) { // Raise the window
|
||||
|
@ -140,17 +145,24 @@ void handle_method_call(
|
|||
}
|
||||
}
|
||||
|
||||
GVariant* handle_get_property(
|
||||
GDBusConnection *connection,
|
||||
const gchar *sender,
|
||||
const gchar *object_path,
|
||||
const gchar *interface_name,
|
||||
const gchar *property_name,
|
||||
GError **error,
|
||||
GVariant * handle_get_property(
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * property_name,
|
||||
GError ** error,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) connection; (void) sender; (void) object_path; (void) interface_name; (void) error; (void) user_data;
|
||||
GVariant *ret;
|
||||
(void) connection;
|
||||
(void) sender;
|
||||
(void) object_path;
|
||||
(void) interface_name;
|
||||
(void) error;
|
||||
(void) user_data;
|
||||
GVariant * ret;
|
||||
|
||||
|
||||
ret = NULL;
|
||||
|
||||
if (g_strcmp0(property_name, "CanQuit") == 0) { // If property is CanQuit
|
||||
|
@ -162,7 +174,7 @@ GVariant* handle_get_property(
|
|||
}
|
||||
|
||||
if (g_strcmp0(property_name, "HasTrackList") == 0) { // If property is HasTrackList
|
||||
KotoPlaylist *playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
KotoPlaylist * playlist = koto_current_playlist_get_playlist(current_playlist);
|
||||
if (KOTO_IS_PLAYLIST(playlist)) {
|
||||
ret = g_variant_new_boolean(koto_playlist_get_length(playlist) > 0);
|
||||
} else { // Don't have a playlist
|
||||
|
@ -179,15 +191,15 @@ GVariant* handle_get_property(
|
|||
}
|
||||
|
||||
if (g_strcmp0(property_name, "SupportedUriSchemas") == 0) { // Supported URI Schemas
|
||||
GVariantBuilder *builder = g_variant_builder_new(G_VARIANT_TYPE("as")); // Array of strings
|
||||
GVariantBuilder * builder = g_variant_builder_new(G_VARIANT_TYPE("as")); // Array of strings
|
||||
g_variant_builder_add(builder, "s", "file");
|
||||
ret = g_variant_new("as", builder);
|
||||
g_variant_builder_unref(builder); // Unref builder since we no longer need it
|
||||
}
|
||||
|
||||
if (g_strcmp0(property_name, "SupportedMimeTypes") == 0) { // Supported mimetypes
|
||||
GVariantBuilder *builder = g_variant_builder_new(G_VARIANT_TYPE("as")); // Array of strings
|
||||
GList *mimes;
|
||||
GVariantBuilder * builder = g_variant_builder_new(G_VARIANT_TYPE("as")); // Array of strings
|
||||
GList * mimes;
|
||||
mimes = NULL;
|
||||
|
||||
for (mimes = supported_mimes; mimes != NULL; mimes = mimes->next) { // For each mimetype
|
||||
|
@ -200,21 +212,21 @@ GVariant* handle_get_property(
|
|||
}
|
||||
|
||||
if (g_strcmp0(property_name, "Metadata") == 0) { // Metadata
|
||||
KotoIndexedTrack *current_track = koto_playback_engine_get_current_track(playback_engine);
|
||||
KotoIndexedTrack * current_track = koto_playback_engine_get_current_track(playback_engine);
|
||||
|
||||
if (KOTO_IS_INDEXED_TRACK(current_track)) { // Currently playing a track
|
||||
ret = koto_indexed_track_get_metadata_vardict(current_track);
|
||||
} else { // No track
|
||||
GVariantBuilder *builder = g_variant_builder_new(G_VARIANT_TYPE_VARDICT); // Create an empty builder
|
||||
GVariantBuilder * builder = g_variant_builder_new(G_VARIANT_TYPE_VARDICT); // Create an empty builder
|
||||
ret = g_variant_builder_end(builder); // return the vardict
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
(g_strcmp0(property_name, "CanPlay") == 0) ||
|
||||
(g_strcmp0(property_name, "CanPause") == 0)
|
||||
(g_strcmp0(property_name, "CanPlay") == 0) ||
|
||||
(g_strcmp0(property_name, "CanPause") == 0)
|
||||
) {
|
||||
KotoIndexedTrack *current_track = koto_playback_engine_get_current_track(playback_engine);
|
||||
KotoIndexedTrack * current_track = koto_playback_engine_get_current_track(playback_engine);
|
||||
ret = g_variant_new_boolean(KOTO_IS_INDEXED_TRACK(current_track));
|
||||
}
|
||||
|
||||
|
@ -232,7 +244,7 @@ GVariant* handle_get_property(
|
|||
ret = g_variant_new_boolean(TRUE);
|
||||
}
|
||||
|
||||
if (g_strcmp0(property_name, "CanControl") == 0){ // Can Control
|
||||
if (g_strcmp0(property_name, "CanControl") == 0) { // Can Control
|
||||
ret = g_variant_new_boolean(TRUE);
|
||||
}
|
||||
|
||||
|
@ -252,16 +264,21 @@ GVariant* handle_get_property(
|
|||
}
|
||||
|
||||
gboolean handle_set_property(
|
||||
GDBusConnection *connection,
|
||||
const gchar *sender,
|
||||
const gchar *object_path,
|
||||
const gchar *interface_name,
|
||||
const gchar *property_name,
|
||||
GVariant *value,
|
||||
GError **error,
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * property_name,
|
||||
GVariant * value,
|
||||
GError ** error,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) connection; (void) sender; (void) interface_name; (void) object_path; (void) error; (void) user_data;
|
||||
(void) connection;
|
||||
(void) sender;
|
||||
(void) interface_name;
|
||||
(void) object_path;
|
||||
(void) error;
|
||||
(void) user_data;
|
||||
|
||||
if (g_strcmp0(property_name, "LoopStatus") == 0) { // Changing LoopStatus
|
||||
koto_playback_engine_set_track_repeat(playback_engine, g_variant_get_boolean(value)); // Set the loop status state
|
||||
|
@ -277,7 +294,8 @@ gboolean handle_set_property(
|
|||
}
|
||||
|
||||
void koto_update_mpris_playback_state(GstState state) {
|
||||
GVariantBuilder *builder = g_variant_builder_new(G_VARIANT_TYPE_ARRAY);
|
||||
GVariantBuilder * builder = g_variant_builder_new(G_VARIANT_TYPE_ARRAY);
|
||||
|
||||
|
||||
if (state == GST_STATE_PLAYING) {
|
||||
g_variant_builder_add(builder, "{sv}", "PlaybackStatus", g_variant_new_string("Playing"));
|
||||
|
@ -287,7 +305,8 @@ void koto_update_mpris_playback_state(GstState state) {
|
|||
g_variant_builder_add(builder, "{sv}", "PlaybackStatus", g_variant_new_string("Stopped"));
|
||||
}
|
||||
|
||||
g_dbus_connection_emit_signal(dbus_conn,
|
||||
g_dbus_connection_emit_signal(
|
||||
dbus_conn,
|
||||
NULL,
|
||||
"/org/mpris/MediaPlayer2",
|
||||
"org.freedesktop.DBus.Properties",
|
||||
|
@ -297,24 +316,32 @@ void koto_update_mpris_playback_state(GstState state) {
|
|||
);
|
||||
}
|
||||
|
||||
void koto_update_mpris_info_for_track(KotoIndexedTrack *track) {
|
||||
void koto_update_mpris_info_for_track(KotoIndexedTrack * track) {
|
||||
if (!KOTO_IS_INDEXED_TRACK(track)) {
|
||||
return;
|
||||
}
|
||||
|
||||
GVariant *metadata = koto_indexed_track_get_metadata_vardict(track); // Get the GVariantBuilder variable dict for the metadata
|
||||
GVariant * metadata = koto_indexed_track_get_metadata_vardict(track); // Get the GVariantBuilder variable dict for the metadata
|
||||
|
||||
|
||||
koto_update_mpris_info_for_track_with_metadata(track, metadata);
|
||||
}
|
||||
|
||||
void koto_update_mpris_info_for_track_with_metadata(KotoIndexedTrack *track, GVariant *metadata) {
|
||||
void koto_update_mpris_info_for_track_with_metadata(
|
||||
KotoIndexedTrack * track,
|
||||
GVariant * metadata
|
||||
) {
|
||||
if (!KOTO_IS_INDEXED_TRACK(track)) {
|
||||
return;
|
||||
}
|
||||
|
||||
GVariantBuilder *builder = g_variant_builder_new(G_VARIANT_TYPE_ARRAY);
|
||||
GVariantBuilder * builder = g_variant_builder_new(G_VARIANT_TYPE_ARRAY);
|
||||
|
||||
|
||||
g_variant_builder_add(builder, "{sv}", "Metadata", metadata);
|
||||
|
||||
g_dbus_connection_emit_signal(dbus_conn,
|
||||
g_dbus_connection_emit_signal(
|
||||
dbus_conn,
|
||||
NULL,
|
||||
"/org/mpris/MediaPlayer2",
|
||||
"org.freedesktop.DBus.Properties",
|
||||
|
@ -331,10 +358,16 @@ static const GDBusInterfaceVTable main_mpris_interface_vtable = {
|
|||
{ 0 }
|
||||
};
|
||||
|
||||
void on_main_mpris_bus_acquired(GDBusConnection *connection, const gchar *name, gpointer user_data) {
|
||||
(void) name; (void) user_data;
|
||||
void on_main_mpris_bus_acquired(
|
||||
GDBusConnection * connection,
|
||||
const gchar * name,
|
||||
gpointer user_data
|
||||
) {
|
||||
(void) name;
|
||||
(void) user_data;
|
||||
dbus_conn = connection;
|
||||
g_dbus_connection_register_object(dbus_conn,
|
||||
g_dbus_connection_register_object(
|
||||
dbus_conn,
|
||||
"/org/mpris/MediaPlayer2",
|
||||
introspection_data->interfaces[0],
|
||||
&main_mpris_interface_vtable,
|
||||
|
@ -343,7 +376,8 @@ void on_main_mpris_bus_acquired(GDBusConnection *connection, const gchar *name,
|
|||
NULL
|
||||
);
|
||||
|
||||
g_dbus_connection_register_object(dbus_conn,
|
||||
g_dbus_connection_register_object(
|
||||
dbus_conn,
|
||||
"/org/mpris/MediaPlayer2",
|
||||
introspection_data->interfaces[1],
|
||||
&main_mpris_interface_vtable,
|
||||
|
@ -357,7 +391,8 @@ void setup_mpris_interfaces() {
|
|||
introspection_data = g_dbus_node_info_new_for_xml(introspection_xml, NULL);
|
||||
g_assert(introspection_data != NULL);
|
||||
|
||||
mpris_bus_id = g_bus_own_name(G_BUS_TYPE_SESSION,
|
||||
mpris_bus_id = g_bus_own_name(
|
||||
G_BUS_TYPE_SESSION,
|
||||
"org.mpris.MediaPlayer2.koto",
|
||||
G_BUS_NAME_OWNER_FLAGS_NONE,
|
||||
on_main_mpris_bus_acquired,
|
||||
|
|
|
@ -22,10 +22,50 @@
|
|||
#include "../indexer/structs.h"
|
||||
|
||||
void koto_update_mpris_playback_state(GstState state);
|
||||
void koto_update_mpris_info_for_track(KotoIndexedTrack *track);
|
||||
void koto_update_mpris_info_for_track_with_metadata(KotoIndexedTrack *track, GVariant *metadata);
|
||||
void handle_method_call(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer user_data);
|
||||
GVariant* handle_get_property(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer user_data);
|
||||
gboolean handle_set_property(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer user_data);
|
||||
void on_main_mpris_bus_acquired(GDBusConnection *connection, const gchar *name, gpointer user_data);
|
||||
|
||||
void koto_update_mpris_info_for_track(KotoIndexedTrack * track);
|
||||
|
||||
void koto_update_mpris_info_for_track_with_metadata(
|
||||
KotoIndexedTrack * track,
|
||||
GVariant * metadata
|
||||
);
|
||||
|
||||
void handle_method_call(
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * method_name,
|
||||
GVariant * parameters,
|
||||
GDBusMethodInvocation * invocation,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
GVariant * handle_get_property(
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * property_name,
|
||||
GError ** error,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
gboolean handle_set_property(
|
||||
GDBusConnection * connection,
|
||||
const gchar * sender,
|
||||
const gchar * object_path,
|
||||
const gchar * interface_name,
|
||||
const gchar * property_name,
|
||||
GVariant * value,
|
||||
GError ** error,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void on_main_mpris_bus_acquired(
|
||||
GDBusConnection * connection,
|
||||
const gchar * name,
|
||||
gpointer user_data
|
||||
);
|
||||
|
||||
void setup_mpris_interfaces();
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue