audacious support added
authorPhilip Kovacs <pkovacs@users.sourceforge.net>
Sat, 7 Jan 2006 07:01:22 +0000 (07:01 +0000)
committerPhilip Kovacs <pkovacs@users.sourceforge.net>
Sat, 7 Jan 2006 07:01:22 +0000 (07:01 +0000)
git-svn-id: https://conky.svn.sourceforge.net/svnroot/conky/trunk/conky@482 7f574dfc-610e-0410-a909-a81674777703

ChangeLog
configure.in
src/Makefile.am
src/audacious.c [new file with mode: 0644]
src/audacious.h [new file with mode: 0644]
src/common.c
src/conky.c
src/conky.h

index abdf983..1070285 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,8 @@
 # $Id$
 
+2006-01-07
+       * Added Audacious media player support.
+
 2006-01-06
        * Fixed infopipe bug (select() affects timer as a side effect on
        Linux!)
index 923705d..8b0eac3 100644 (file)
@@ -1,6 +1,6 @@
-AC_INIT([Conky],[1.3.6_CVS_20060106],[brenden1@users.sourceforge.net])
+AC_INIT([Conky],[1.3.6_CVS_20060107],[brenden1@users.sourceforge.net])
 
-AM_INIT_AUTOMAKE(conky, 1.3.6_CVS_20060106)
+AM_INIT_AUTOMAKE(conky, 1.3.6_CVS_20060107)
 AM_CONFIG_HEADER(src/config.h)
 AC_PROG_LIBTOOL
 
@@ -79,6 +79,24 @@ if test $dah = "yes"; then
 fi
 
 dnl
+dnl Audacious
+dnl
+
+want_audacious=no
+AC_ARG_ENABLE(audacious,
+              [  --enable-audacious      enable if you want Audacious support [[default=no]]],
+              [want_audacious="$enableval"])
+
+AM_CONDITIONAL(BUILD_AUDACIOUS, test x$want_audacious = xyes)
+if test x$want_audacious = xyes; then
+        PKG_CHECK_MODULES([AUDACIOUS], [audacious >= 0.1],
+                          [], [AC_MSG_ERROR([Audacious 0.1 or higher is not installed])])
+        CFLAGS="$CFLAGS $AUDACIOUS_CFLAGS"
+        LIBS="$LIBS $AUDACIOUS_LIBS"
+        AC_DEFINE(AUDACIOUS, 1, [Define if you want BMPx support])
+fi
+
+dnl
 dnl BMPx
 dnl
 
index 8a855c4..e1c7f49 100644 (file)
@@ -1,5 +1,9 @@
 bin_PROGRAMS = conky
 
+if BUILD_AUDACIOUS
+audacious = audacious.c
+endif
+
 if BUILD_BMPX
 bmpx = bmpx.c
 endif
@@ -46,7 +50,7 @@ if BUILD_X11
 x11 = x11.c
 endif
 
-conky_SOURCES = common.c fs.c $(linux) mail.c mixer.c $(seti) $(mpd) $(solaris) $(freebsd) $(netbsd) $(port_monitors) conky.c conky.h $(x11) $(mldonkey) remoted.c remoted.h remotec.c remotec.h $(bmpx) $(infopipe)
+conky_SOURCES = common.c fs.c $(linux) mail.c mixer.c $(seti) $(mpd) $(solaris) $(freebsd) $(netbsd) $(port_monitors) conky.c conky.h $(x11) $(mldonkey) remoted.c remoted.h remotec.c remotec.h $(audacious) $(bmpx) $(infopipe)
 
 AM_LDFLAGS = $(X11_LIBS) $(XFT_LIBS) $(CAIRO_LIBS) $(PTHREAD_LIBS) -lm
 
diff --git a/src/audacious.c b/src/audacious.c
new file mode 100644 (file)
index 0000000..c765380
--- /dev/null
@@ -0,0 +1,154 @@
+/* -------------------------------------------------------------------------
+ * audacious.c:  conky support for Audacious media player
+ *
+ * http://audacious-media-player.org
+ *
+ * Copyright (C) 2005  Philip Kovacs kovacsp3@comcast.net
+ * 
+ * $Id$
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ * --------------------------------------------------------------------------- */
+
+#include <pthread.h>
+/*#include <glib.h>*/
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+#include <audacious/beepctrl.h>
+#include "audacious.h"
+#include "conky.h"
+
+/* access to this item array is synchronized with mutexes */
+static audacious_t g_items;
+
+/* ----------------------------------------
+ * Conky update function for Audacious data.
+ * ---------------------------------------- */
+void update_audacious(void)
+{
+    /* 
+      The worker thread is updating ihe g_items array asynchronously to the main 
+      conky thread.  We merely copy the g_items array into the main thread's info
+      structure when the main thread's update cycle fires.   Note that using the
+      mutexes here makes it easier since we won't have to do any sync in conky.c.
+    */
+    pthread_mutex_lock(&info.audacious.item_mutex);
+    memcpy(&info.audacious.items,g_items,sizeof(g_items));
+    pthread_mutex_unlock(&info.audacious.item_mutex);
+}
+
+
+/* --------------------------------------------------
+ * Worker thread function for Audacious data sampling.
+ * -------------------------------------------------- */ 
+void *audacious_thread_func(void *pvoid)
+{
+    int runnable;
+    static audacious_t items;
+    int session,playpos,frames,length;
+    int rate,freq,chans;
+    char *psong;
+
+    pvoid=(void*)pvoid; /* useless cast to avoid unused var warning */
+    session=0;
+
+    /* Grab the runnable signal.  Should be non-zero here or we do nothing. */
+    pthread_mutex_lock(&info.audacious.runnable_mutex);
+    runnable=info.audacious.runnable;
+    pthread_mutex_unlock(&info.audacious.runnable_mutex );
+
+    /* Loop until the main thread sets the runnable signal to 0. */
+    while(runnable) {
+
+       for (;;) {  /* convenience loop so we can break below */
+       
+            if (!xmms_remote_is_running(session)) {
+                memset(&items,0,sizeof(items));
+               strcpy(items[AUDACIOUS_STATUS],"Not running");
+               break;
+            }
+
+           /* Player status */
+           if (xmms_remote_is_paused(session))
+               strcpy(items[AUDACIOUS_STATUS],"Paused");
+           else if (xmms_remote_is_playing(session))
+                strcpy(items[AUDACIOUS_STATUS],"Playing");
+           else
+                strcpy(items[AUDACIOUS_STATUS],"Stopped");
+
+           /* Current song title */
+           playpos = (int) xmms_remote_get_playlist_pos(session);
+           psong = (char *) xmms_remote_get_playlist_title(session, playpos);
+           if (psong)
+                strncpy(items[AUDACIOUS_SONG],psong,sizeof(items[AUDACIOUS_SONG]));
+
+           /* Current song length as MM:SS */ 
+            frames = xmms_remote_get_playlist_time(session,playpos);
+           length = frames / 1000;
+            snprintf(items[AUDACIOUS_SONG_LENGTH],sizeof(items[AUDACIOUS_SONG_LENGTH]),
+                    "%d:%.2d", length / 60, length % 60);
+        
+           /* Current song length in seconds */
+           snprintf(items[AUDACIOUS_SONG_LENGTH_SECONDS],sizeof(items[AUDACIOUS_SONG_LENGTH_SECONDS]),
+                    "%d", length);
+
+           /* Current song length in frames */
+            snprintf(items[AUDACIOUS_SONG_LENGTH_FRAMES],sizeof(items[AUDACIOUS_SONG_LENGTH_FRAMES]),
+                    "%d", frames);
+
+           /* Current song output length as MM:SS */ 
+            frames = xmms_remote_get_output_time(session);
+           length = frames / 1000;
+            snprintf(items[AUDACIOUS_SONG_OUTPUT_LENGTH],sizeof(items[AUDACIOUS_SONG_OUTPUT_LENGTH]),
+                    "%d:%.2d", length / 60, length % 60);
+        
+           /* Current song output length in seconds */
+           snprintf(items[AUDACIOUS_SONG_OUTPUT_LENGTH_SECONDS],sizeof(items[AUDACIOUS_SONG_OUTPUT_LENGTH_SECONDS]),
+                    "%d", length);
+
+           /* Current song output length in frames */
+            snprintf(items[AUDACIOUS_SONG_OUTPUT_LENGTH_FRAMES],sizeof(items[AUDACIOUS_SONG_OUTPUT_LENGTH_FRAMES]),
+                    "%d", frames);
+
+            /* Current song bitrate */
+            xmms_remote_get_info(session, &rate, &freq, &chans);
+            snprintf(items[AUDACIOUS_SONG_BITRATE],sizeof(items[AUDACIOUS_SONG_BITRATE]), "%d", rate);
+
+            /* Current song frequency */
+            snprintf(items[AUDACIOUS_SONG_FREQUENCY],sizeof(items[AUDACIOUS_SONG_FREQUENCY]), "%d", freq);
+
+            /* Current song channels */
+            snprintf(items[AUDACIOUS_SONG_CHANNELS],sizeof(items[AUDACIOUS_SONG_CHANNELS]), "%d", chans);
+            
+
+           break;
+       }
+
+       /* Deliver the refreshed items array to g_items. */
+       pthread_mutex_lock(&info.audacious.item_mutex);
+        memcpy(&g_items,items,sizeof(items));
+       pthread_mutex_unlock(&info.audacious.item_mutex);
+
+       /* Grab the runnable signal for next loop. */
+        pthread_mutex_lock(&info.audacious.runnable_mutex);
+        runnable=info.audacious.runnable;
+        pthread_mutex_unlock(&info.audacious.runnable_mutex);
+
+       sleep(1);
+    }
+
+    pthread_exit(NULL);
+}
diff --git a/src/audacious.h b/src/audacious.h
new file mode 100644 (file)
index 0000000..c7bde58
--- /dev/null
@@ -0,0 +1,52 @@
+/* -------------------------------------------------------------------------
+ * audacious.h:  conky support for Audacious audio player
+ * 
+ * http://audacious-media-player.org
+ * 
+ * Copyright (C) 2005  Philip Kovacs kovacsp3@comcast.net
+ *
+ * $Id$
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ * --------------------------------------------------------------------------- */
+
+#ifndef AUDACIOUS_H
+#define AUDACIOUS_H
+
+/* 11 keys comprise the audacious information. */
+enum _audacious_keys {
+       AUDACIOUS_STATUS,
+       AUDACIOUS_SONG,
+       AUDACIOUS_SONG_LENGTH,
+       AUDACIOUS_SONG_LENGTH_SECONDS,
+       AUDACIOUS_SONG_LENGTH_FRAMES,
+       AUDACIOUS_SONG_OUTPUT_LENGTH,
+       AUDACIOUS_SONG_OUTPUT_LENGTH_SECONDS,
+       AUDACIOUS_SONG_OUTPUT_LENGTH_FRAMES,
+       AUDACIOUS_SONG_BITRATE,
+       AUDACIOUS_SONG_FREQUENCY,
+       AUDACIOUS_SONG_CHANNELS
+};
+               
+/* 11 slots for the audacious values */
+typedef char audacious_t[11][128];
+
+/* Service routine for the conky main thread */
+void update_audacious(void);
+
+/* Thread function */
+void *audacious_thread_func(void *);
+
+#endif
index 46d9d62..6b4f956 100644 (file)
@@ -226,6 +226,10 @@ void update_stuff()
        if (NEED(INFO_MPD))
                update_mpd();
 #endif
+#ifdef AUDACIOUS
+        if (NEED(INFO_AUDACIOUS))
+                update_audacious();
+#endif
 #ifdef BMPX
        if (NEED(INFO_BMPX))
                update_bmpx();
index 7b9acaa..4fa5625 100644 (file)
@@ -892,6 +892,20 @@ enum text_object_type {
        OBJ_mpd_track,
        OBJ_mpd_percent,
 #endif
+#ifdef AUDACIOUS
+        OBJ_audacious_status,
+        OBJ_audacious_song,
+        OBJ_audacious_song_length,
+        OBJ_audacious_song_length_seconds,
+        OBJ_audacious_song_length_frames,
+        OBJ_audacious_song_output_length,
+        OBJ_audacious_song_output_length_seconds,
+        OBJ_audacious_song_output_length_frames,
+        OBJ_audacious_song_bitrate,
+        OBJ_audacious_song_frequency,
+        OBJ_audacious_song_channels,
+        OBJ_audacious_bar,
+#endif
 #ifdef BMPX
        OBJ_bmpx_title,
        OBJ_bmpx_artist,
@@ -1811,6 +1825,22 @@ int a = stippled_borders, b = 1;
         (void) scan_bar(arg, &obj->data.pair.a, &obj->data.pair.b);
        END
 #endif
+#ifdef AUDACIOUS
+        OBJ(audacious_status, INFO_AUDACIOUS) END
+        OBJ(audacious_song, INFO_AUDACIOUS) END
+        OBJ(audacious_song_length, INFO_AUDACIOUS) END
+        OBJ(audacious_song_length_seconds, INFO_AUDACIOUS) END
+        OBJ(audacious_song_length_frames, INFO_AUDACIOUS) END
+        OBJ(audacious_song_output_length, INFO_AUDACIOUS) END
+        OBJ(audacious_song_output_length_seconds, INFO_AUDACIOUS) END
+        OBJ(audacious_song_output_length_frames, INFO_AUDACIOUS) END
+        OBJ(audacious_song_bitrate, INFO_AUDACIOUS) END
+        OBJ(audacious_song_frequency, INFO_AUDACIOUS) END
+        OBJ(audacious_song_channels, INFO_AUDACIOUS) END
+        OBJ(audacious_bar, INFO_AUDACIOUS)
+            (void) scan_bar(arg, &obj->a, &obj->b);
+        END
+#endif
 #ifdef BMPX
        OBJ(bmpx_title, INFO_BMPX)
                memset(&(info.bmpx), 0, sizeof(struct bmpx_s));
@@ -3105,6 +3135,48 @@ static void generate_text_internal(char *p, int p_max_size, struct text_object *
                                               255.0f));
                        }
 #endif
+#ifdef AUDACIOUS
+                        OBJ(audacious_status) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_STATUS]);
+                        }
+                        OBJ(audacious_song) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG]);
+                       }
+                        OBJ(audacious_song_length) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_LENGTH]);
+                       }
+                        OBJ(audacious_song_length_seconds) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_LENGTH_SECONDS]);
+                       }
+                        OBJ(audacious_song_length_frames) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_LENGTH_FRAMES]);
+                       }
+                        OBJ(audacious_song_output_length) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_OUTPUT_LENGTH]);
+                       }
+                        OBJ(audacious_song_output_length_seconds) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_OUTPUT_LENGTH_SECONDS]);
+                       }
+                        OBJ(audacious_song_output_length_frames) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_OUTPUT_LENGTH_FRAMES]);
+                       }
+                        OBJ(audacious_song_bitrate) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_BITRATE]);
+                       }
+                        OBJ(audacious_song_frequency) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_SONG_FREQUENCY]);
+                       }
+                        OBJ(audacious_song_channels) {
+                           snprintf(p, p_max_size, "%s", cur->audacious.items[AUDACIOUS_STATUS]);
+                       }
+                        OBJ(audacious_bar) {
+                            double progress;
+                            progress= atof(cur->audacious.items[AUDACIOUS_SONG_OUTPUT_LENGTH_SECONDS]) /
+                                      atof(cur->audacious.items[AUDACIOUS_SONG_LENGTH_SECONDS]);
+                            new_bar(p,obj->a,obj->b,(int)(progress*255.0f));
+
+                       }
+#endif
 #ifdef BMPX
                        OBJ(bmpx_title) {
                                snprintf(p, p_max_size, "%s", cur->bmpx.title);
@@ -5493,6 +5565,22 @@ int main(int argc, char **argv)
                ERR("error setting signal handler: %s", strerror(errno) );
        }
 
+#ifdef AUDACIOUS
+       /* joinable thread for audacious activity */
+        pthread_attr_init(&info.audacious.thread_attr);
+       pthread_attr_setdetachstate(&info.audacious.thread_attr, PTHREAD_CREATE_JOINABLE);
+       /* init mutexex */
+       pthread_mutex_init(&info.audacious.item_mutex, NULL);
+       pthread_mutex_init(&info.audacious.runnable_mutex, NULL);
+       /* init runnable condition for worker thread */
+       pthread_mutex_lock(&info.audacious.runnable_mutex);
+       info.audacious.runnable=1;
+       pthread_mutex_unlock(&info.audacious.runnable_mutex);
+       if (pthread_create(&info.audacious.thread, &info.audacious.thread_attr, audacious_thread_func, NULL))
+       {
+           CRIT_ERR("unable to create audacious thread!");
+       }
+#endif
 #ifdef INFOPIPE
        /* joinable thread for infopipe activity */
         pthread_attr_init(&info.infopipe.thread_attr);
@@ -5511,7 +5599,22 @@ int main(int argc, char **argv)
 #endif
 
        main_loop();
-       
+
+#ifdef AUDACIOUS
+        /* signal audacious worker thread to terminate */
+        pthread_mutex_lock(&info.audacious.runnable_mutex);
+        info.audacious.runnable=0;
+        pthread_mutex_unlock(&info.audacious.runnable_mutex);
+        /* destroy thread attribute and wait for thread */
+        pthread_attr_destroy(&info.audacious.thread_attr);
+        if (pthread_join(info.audacious.thread, NULL))
+        {
+            ERR("error joining audacious thread");
+        }
+        /* destroy mutexes */
+        pthread_mutex_destroy(&info.audacious.item_mutex);
+        pthread_mutex_destroy(&info.audacious.runnable_mutex);
+#endif 
 #ifdef INFOPIPE
        /* signal infopipe worker thread to terminate */
        pthread_mutex_lock(&info.infopipe.runnable_mutex);
index 9de5c55..4317d0b 100644 (file)
@@ -9,7 +9,7 @@
 #ifndef _conky_h_
 #define _conky_h_
 
-#ifdef INFOPIPE
+#if defined(AUDACIOUS) || defined(INFOPIPE)
 #include <pthread.h>
 #endif
 #if defined(HAS_MCHECK_H)
@@ -127,6 +127,18 @@ struct mpd_s {
 };
 #endif
 
+#ifdef AUDACIOUS
+#include "audacious.h"
+struct audacious_s {
+       audacious_t items;              /* e.g. items[AUDACIOUS_STATUS] yields char[] */
+       int runnable;                   /* used to signal infopipe thread to stop */
+       pthread_t thread;               /* worker thread for infopipe updating */
+       pthread_attr_t thread_attr;     /* thread attributes */
+       pthread_mutex_t item_mutex;     /* mutex for item array */
+       pthread_mutex_t runnable_mutex; /* mutex for runnable flag */
+};
+#endif
+
 #ifdef BMPX
 void update_bmpx();
 struct bmpx_s {
@@ -194,6 +206,9 @@ enum {
 #ifdef INFOPIPE
        INFO_INFOPIPE = 24,
 #endif
+#ifdef AUDACIOUS
+        INFO_AUDACIOUS = 25,
+#endif
 };
 
 
@@ -237,6 +252,9 @@ struct information {
        struct mpd_s mpd;
        mpd_Connection *conn;
 #endif
+#ifdef AUDACIOUS
+       struct audacious_s audacious;
+#endif
 #ifdef BMPX
        struct bmpx_s bmpx;
 #endif