From 79fcfc53391343b29966943964af1256494ba59d Mon Sep 17 00:00:00 2001 From: Thomas Perl Date: Wed, 21 Oct 2009 13:49:14 +0200 Subject: [PATCH] initial version of headphoned --- makefile | 12 ++++++ src/headphoned.c | 113 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 125 insertions(+) create mode 100644 makefile create mode 100644 src/headphoned.c diff --git a/makefile b/makefile new file mode 100644 index 0000000..2c5105e --- /dev/null +++ b/makefile @@ -0,0 +1,12 @@ +OBJS = src/headphoned.o +PROG = headphoned +CFLAGS += `pkg-config --cflags glib-2.0 gconf-2.0 libosso` -Os -Wall +LDFLAGS += `pkg-config --libs glib-2.0 gconf-2.0 libosso` + +$(PROG): $(OBJS) + $(CC) $(LDFLAGS) $(LIBS) $^ -o $@ + strip $@ + +clean: + rm -f $(PROG) $(OBJS) + diff --git a/src/headphoned.c b/src/headphoned.c new file mode 100644 index 0000000..b5cce6e --- /dev/null +++ b/src/headphoned.c @@ -0,0 +1,113 @@ +#include +#include +#include +#include +#include + +#define STATE_FILE "/sys/devices/platform/gpio-switch/headphone/state" +#define STATE_CONNECTED_STR "connected" +#define STATE_DISCONNECTED_STR "disconnected" + +#define GCONF_VOLUME_CONTROL "/apps/osso/sound/master_volume" + +#define MEDIA_SERVER_SRVC "com.nokia.osso_media_server" +#define MEDIA_SERVER_PATH "/com/nokia/osso_media_server" +#define MEDIA_SERVER_INTF "com.nokia.osso_media_server.music" +#define MEDIA_SERVER_METH "pause" + +//#define ENABLE_VOLUME_CONTROL +#define ENABLE_PAUSE_ON_DISCONNECT + + +enum { STATE_UNKNOWN, STATE_CONNECTED, STATE_DISCONNECTED, STATE_COUNT }; + +typedef struct { + GConfClient* client; + osso_context_t* osso; + guint state; + gint volume[STATE_COUNT]; +} Headphoned; + +void +on_volume_changed(GConfClient* client, guint gnxn_id, GConfEntry* entry, + gpointer data) +{ + Headphoned* headphoned = (Headphoned*)data; + headphoned->volume[headphoned->state] = gconf_value_get_int(entry->value); +} + +Headphoned* +headphoned_new() +{ + Headphoned* this = g_new0(Headphoned, 1); + assert(this != NULL); + + this->osso = osso_initialize("headphoned", "1.0", FALSE, NULL); + assert(this->osso != NULL); + +#ifdef ENABLE_VOLUME_CONTROL + this->client = gconf_client_get_default(); + gconf_client_add_dir(this->client, GCONF_VOLUME_CONTROL, + GCONF_CLIENT_PRELOAD_NONE, NULL); + gconf_client_notify_add(this->client, GCONF_VOLUME_CONTROL, + on_volume_changed, this, NULL, NULL); +#endif + + return this; +} + +gboolean +on_file_changed(GIOChannel* source, GIOCondition condition, gpointer data) +{ + Headphoned* headphoned = (Headphoned*)data; +#ifdef ENABLE_VOLUME_CONTROL + gint volume = headphoned->volume[headphoned->state]; +#endif + gchar* result; + + g_io_channel_seek_position(source, 0, G_SEEK_SET, NULL); + g_io_channel_read_line(source, &result, NULL, NULL, NULL); + g_strstrip(result); + + if (g_ascii_strcasecmp(result, STATE_CONNECTED_STR) == 0) { + headphoned->state = STATE_CONNECTED; + } else { + headphoned->state = STATE_DISCONNECTED; +#ifdef ENABLE_PAUSE_ON_DISCONNECT + osso_rpc_run(headphoned->osso, + MEDIA_SERVER_SRVC, + MEDIA_SERVER_PATH, + MEDIA_SERVER_INTF, + MEDIA_SERVER_METH, + NULL, + DBUS_TYPE_INVALID); +#endif + } + +#ifdef ENABLE_VOLUME_CONTROL + gint new_volume = headphoned->volume[headphoned->state]; + if (new_volume != volume) { + gconf_client_set_int(headphoned->client, GCONF_VOLUME_CONTROL, + new_volume, NULL); + gconf_client_suggest_sync(headphoned->client, NULL); + gconf_client_clear_cache(headphoned->client); + } +#endif + + g_free(result); + return TRUE; +} + +int +main(int argc, char* argv[]) +{ + g_type_init(); + GMainLoop* loop = g_main_loop_new(NULL, FALSE); + + GIOChannel* state = g_io_channel_new_file(STATE_FILE, "r", NULL); + g_io_add_watch(state, G_IO_PRI, on_file_changed, headphoned_new()); + + g_main_loop_run(loop); + return 0; +} + -- 1.7.9.5