Enlightenment CVS committal Author : devilhorns Project : e_modules Module : mixer
Dir : e_modules/mixer Modified Files: alsa_mixer.c alsa_mixer.h e_mod_config.c e_mod_main.c e_mod_main.h mixer.edc Log Message: Start of virtualizing sound stuffs. Should make doing alsa/oss/*bsd easier. =================================================================== RCS file: /cvs/e/e_modules/mixer/alsa_mixer.c,v retrieving revision 1.1 retrieving revision 1.2 diff -u -3 -r1.1 -r1.2 --- alsa_mixer.c 7 Sep 2006 15:26:17 -0000 1.1 +++ alsa_mixer.c 11 Sep 2006 09:06:50 -0000 1.2 @@ -3,7 +3,8 @@ static int _alsa_get_hash (const char *name); static int _alsa_get_system_id (const char *name); -static int _alsa_get_mixer_id (const char *name); +static int _alsa_get_card_id (const char *name); +static int _alsa_get_mixer_id (const char *name); Evas_List * alsa_get_cards() @@ -53,7 +54,7 @@ if (!card) continue; card->name = evas_stringshare_add(buf); card->real = evas_stringshare_add(snd_ctl_card_info_get_name(hw_info)); - card->id = _alsa_get_mixer_id(card->real); + card->id = _alsa_get_card_id(card->real); cards = evas_list_append(cards, card); } @@ -62,8 +63,11 @@ } void -alsa_free_cards(Evas_List *cards) +alsa_free_cards(void *data) { + Evas_List *cards; + + cards = data; if (!cards) return; while (cards) @@ -74,10 +78,163 @@ if (!card) continue; if (card->name) evas_stringshare_del(card->name); if (card->real) evas_stringshare_del(card->real); + while (card->channels) + { + Alsa_Channel *chan; + + chan = card->channels->data; + if (!chan) continue; + if (chan->name) evas_stringshare_del(chan->name); + card->channels = evas_list_remove_list(card->channels, card->channels); + E_FREE(chan); + } + cards = evas_list_remove_list(cards, cards); E_FREE(card); + } +} + +void * +alsa_get_card(int id) +{ + Evas_List *cards = NULL; + snd_mixer_t *handle; + snd_ctl_t *control; + snd_ctl_card_info_t *hw_info; + int err, i; + char buf[1024]; + + if ((err = snd_mixer_open(&handle, 0)) < 0) + { + printf("Cannot open mixer: %s\n", snd_strerror(err)); + return NULL; + } + + snd_ctl_card_info_alloca(&hw_info); + + for (i = 0; i < 32; i++) + { + Alsa_Card *card; - cards = evas_list_remove_list(cards, cards); + snprintf(buf, sizeof(buf), "hw:%d", i); + if ((err = snd_mixer_attach(handle, buf)) < 0) break; + if ((err = snd_mixer_detach(handle, buf)) < 0) + { + snd_mixer_close(handle); + break; + } + if ((err = snd_ctl_open(&control, buf, 0)) < 0) + { + printf("Cannot control: %s: %s\n", buf, snd_strerror(err)); + continue; + } + if ((err = snd_ctl_card_info(control, hw_info)) < 0) + { + printf("Cannot get hardware info: %s: %s\n", buf, snd_strerror(err)); + snd_ctl_close(control); + continue; + } + + snd_ctl_close(control); + + card = E_NEW(Alsa_Card, 1); + if (!card) continue; + card->name = evas_stringshare_add(buf); + card->real = evas_stringshare_add(snd_ctl_card_info_get_name(hw_info)); + card->id = _alsa_get_card_id(card->real); + + if (!_alsa_get_card_id(card->real) == id) continue; + return card; } + return NULL; +} + +Evas_List * +alsa_card_get_channels(void *data) +{ + Alsa_Card *card; + Evas_List *channels; + + snd_mixer_t *handle; + snd_ctl_t *control; + snd_ctl_card_info_t *hw_info; + snd_mixer_selem_id_t *sid; + snd_mixer_elem_t *elem; + int err, i; + + card = data; + if (!card) return NULL; + + channels = NULL; + + snd_mixer_selem_id_alloca(&sid); + snd_ctl_card_info_alloca(&hw_info); + + if ((err = snd_ctl_open(&control, card->name, 0)) < 0) + { + printf("\n\nCannot Open Card: %s %s\n\n", card->name, snd_strerror(err)); + return NULL; + } + + if ((err = snd_ctl_card_info(control, hw_info)) < 0) + { + printf("\n\nCannot get hardware info: %s %s\n\n", card->name, snd_strerror(err)); + snd_ctl_close(control); + return NULL; + } + + snd_ctl_close(control); + + if ((err = snd_mixer_open(&handle, 0)) < 0) + { + printf("\n\nCannot Open Mixer: %s\n\n", snd_strerror(err)); + return NULL; + } + + if ((err = snd_mixer_attach(handle, card->name)) < 0) + { + printf("\n\nCannot Attach Mixer: %s\n\n", snd_strerror(err)); + snd_mixer_close(handle); + return NULL; + } + + if ((err = snd_mixer_selem_register(handle, NULL, NULL)) < 0) + { + printf("\n\nCannot Register Mixer: %s\n\n", snd_strerror(err)); + snd_mixer_close(handle); + return NULL; + } + + if ((err = snd_mixer_load(handle)) < 0) + { + printf("\n\nCannot Load Mixer: %s\n\n", snd_strerror(err)); + snd_mixer_close(handle); + return NULL; + } + + for (i = 0, elem = snd_mixer_first_elem(handle); elem; elem = snd_mixer_elem_next(elem)) + { + snd_mixer_selem_get_id(elem, sid); + if (!snd_mixer_selem_is_active(elem)) continue; + + if (snd_mixer_selem_has_playback_volume(elem)) + { + Alsa_Channel *ac; + const char *name; + + name = snd_mixer_selem_id_get_name(sid); + if ((!strcmp(name, "Master")) || (!strcmp(name, "PCM"))) + { + ac = E_NEW(Alsa_Channel, 1); + if (!ac) continue; + + ac->name = evas_stringshare_add(name); + ac->id = _alsa_get_mixer_id(ac->name); + + channels = evas_list_append(channels, ac); + } + } + } + return channels; } /* Privates */ @@ -104,8 +261,14 @@ } static int -_alsa_get_mixer_id(const char *name) +_alsa_get_card_id(const char *name) { return _alsa_get_hash(name) << 8; +} + +static int +_alsa_get_mixer_id(const char *name) +{ + return _alsa_get_hash(name); } =================================================================== RCS file: /cvs/e/e_modules/mixer/alsa_mixer.h,v retrieving revision 1.1 retrieving revision 1.2 diff -u -3 -r1.1 -r1.2 --- alsa_mixer.h 7 Sep 2006 15:26:17 -0000 1.1 +++ alsa_mixer.h 11 Sep 2006 09:06:50 -0000 1.2 @@ -6,6 +6,7 @@ typedef struct _Alsa_Mixer Alsa_Mixer; typedef struct _Alsa_Card Alsa_Card; +typedef struct _Alsa_Channel Alsa_Channel; struct _Alsa_Mixer { @@ -22,9 +23,21 @@ const char *real; int active; int id; + + Evas_List *channels; +}; + +struct _Alsa_Channel +{ + int id; + int card_id; + + const char *name; }; -Evas_List *alsa_get_cards(); -void alsa_free_cards(Evas_List *cards); +Evas_List *alsa_get_cards (void); +void *alsa_get_card (int id); +Evas_List *alsa_card_get_channels (void *data); +void alsa_free_cards (void *data); #endif =================================================================== RCS file: /cvs/e/e_modules/mixer/e_mod_config.c,v retrieving revision 1.3 retrieving revision 1.4 diff -u -3 -r1.3 -r1.4 --- e_mod_config.c 7 Sep 2006 16:36:34 -0000 1.3 +++ e_mod_config.c 11 Sep 2006 09:06:50 -0000 1.4 @@ -1,12 +1,16 @@ #include <e.h> #include "e_mod_main.h" -#include "alsa_mixer.h" + +#ifdef HAVE_LIBASOUND +# include "alsa_mixer.h" +#endif struct _E_Config_Dialog_Data { Evas_Object *list; int card_id; + int channel_id; }; /* Protos */ @@ -47,6 +51,7 @@ _fill_data(Config_Item *ci, E_Config_Dialog_Data *cfdata) { cfdata->card_id = ci->card_id; + cfdata->channel_id = ci->channel_id; } static void * @@ -72,66 +77,21 @@ static Evas_Object * _basic_create_widgets(E_Config_Dialog *cfd, Evas *evas, E_Config_Dialog_Data *cfdata) { - Evas_Object *o, *ol, *ot, *ob, *of, *icon; - Evas_List *cards, *c; - Config_Item *ci; - int i = 0; + Evas_Object *o, *ob, *of; + Evas_List *cards, *c, *e; + Config_Item *ci; + E_Radio_Group *rg; ci = cfd->data; - - cards = alsa_get_cards(); - - o = e_widget_list_add(evas, 0, 1); - of = e_widget_framelist_add(evas, _("Sound Cards"), 0); - ol = e_widget_ilist_add(evas, 48, 48, NULL); - cfdata->list = ol; - e_widget_min_size_set(ol, 160, 200); - if (cards) - { - for (c = cards; c; c = c->next) - { - Alsa_Card *card; - - card = c->data; - if (!card) continue; - e_widget_ilist_append(ol, NULL, card->real, NULL, NULL, NULL); - if (!ci) continue; - if (ci->card_id == card->id) - e_widget_ilist_selected_set(ol, i); - i++; - } - } - e_widget_ilist_go(ol); - e_widget_framelist_object_append(of, ol); + + o = e_widget_list_add(evas, 0, 1); + of = e_widget_framelist_add(evas, _("Available Mixers"), 0); e_widget_list_object_append(o, of, 1, 1, 0.5); - - ot = e_widget_table_add(evas, 0); - ob = e_widget_button_add(evas, _("Configure"), NULL, NULL, NULL, NULL); - e_widget_disabled_set(ob, 1); - e_widget_table_object_append(ot, ob, 0, 0, 1, 1, 1, 1, 1, 0); - - e_widget_list_object_append(o, ot, 1, 1, 0.0); return o; } static int _basic_apply_data(E_Config_Dialog *cfd, E_Config_Dialog_Data *cfdata) { - Evas_List *cards, *c; - Alsa_Card *card; - Config_Item *ci; - - ci = cfd->data; - if (!ci) return 0; - - cards = alsa_get_cards(); - if (cards) - { - card = evas_list_nth(cards, e_widget_ilist_selected_get(cfdata->list)); - if (!card) return 0; - ci->card_id = card->id; - e_config_save_queue(); - } - return 1; } =================================================================== RCS file: /cvs/e/e_modules/mixer/e_mod_main.c,v retrieving revision 1.8 retrieving revision 1.9 diff -u -3 -r1.8 -r1.9 --- e_mod_main.c 10 Sep 2006 20:00:55 -0000 1.8 +++ e_mod_main.c 11 Sep 2006 09:06:50 -0000 1.9 @@ -1,15 +1,18 @@ #include <e.h> #include "e_mod_main.h" -#include "alsa_mixer.h" + +#ifdef HAVE_LIBASOUND +# include "alsa_mixer.h" +#endif /* Define to 1 for testing alsa code */ -#define DEBUG 0 +#define DEBUG 1 #define SLIDE_LENGTH 0.5 typedef struct _Instance Instance; typedef struct _Mixer Mixer; -typedef struct _Mixer_Win Mixer_Win; typedef struct _Mixer_Win_Simple Mixer_Win_Simple; +typedef struct _Mixer_System Mixer_System; struct _Instance { @@ -19,22 +22,14 @@ struct _Mixer { - Instance *inst; - Evas *evas; - Mixer_Win *win; + Instance *inst; + Evas *evas; + Mixer_System *mix_sys; + Mixer_Win_Simple *simple_win; - Evas_Object *base; }; -struct _Mixer_Win -{ - Mixer *mixer; - E_Win *window; - - Evas_Object *bg_obj; -}; - struct _Mixer_Win_Simple { Mixer *mixer; @@ -44,16 +39,26 @@ Evas_Object *bg_obj; Evas_Object *slider; - int x, y, w, h; - int to_top; - int popped_up; - double start_time; + int x, y, w, h; + int to_top; + int popped_up; + double start_time; + Ecore_Animator *slide_animator; }; + +struct _Mixer_System +{ + Evas_List *(*get_cards) (void); + void *(*get_card) (int id); + Evas_List *(*get_channels) (void *card); + void (*free_cards) (void *cards); + Evas_List *cards; +}; + /* Gadcon Protos */ -static E_Gadcon_Client *_gc_init (E_Gadcon * gc, const char *name, - const char *id, const char *style); +static E_Gadcon_Client *_gc_init (E_Gadcon * gc, const char *name, const char *id, const char *style); static void _gc_shutdown (E_Gadcon_Client * gcc); static void _gc_orient (E_Gadcon_Client * gcc); static char *_gc_label (void); @@ -62,13 +67,11 @@ /* Module Protos */ static Config_Item *_mixer_config_item_get (const char *id); static void _mixer_menu_cb_post (void *data, E_Menu *m); -static void _mixer_menu_cb_configure (void *data, E_Menu *m, - E_Menu_Item *mi); -static void _mixer_cb_mouse_down (void *data, Evas *e, - Evas_Object *obj, - void *event_info); -static void _mixer_menu_cb_configure (void *data, E_Menu *m, - E_Menu_Item *mi); +static void _mixer_menu_cb_configure (void *data, E_Menu *m, E_Menu_Item *mi); +static void _mixer_cb_mouse_down (void *data, Evas *e, Evas_Object *obj, void *event_info); +static void _mixer_menu_cb_configure (void *data, E_Menu *m, E_Menu_Item *mi); +static void _mixer_system_init (void *data); +static void _mixer_system_shutdown (void *data); static void _mixer_window_simple_pop_up (Instance *inst); static void _mixer_window_simple_pop_down (Instance *inst); @@ -100,26 +103,6 @@ Mixer *mixer; E_Gadcon_Client *gcc; char buf[4096]; - -#if DEBUG - Evas_List *c; - - c = alsa_get_cards(); - if (c) - { - Evas_List *l; - - for (l = c; l; l = l->next) - { - Alsa_Card *card; - - card = c->data; - if (!card) continue; - printf("\nFound Card: %s\tId: %i\n\n", card->real, card->id); - } - alsa_free_cards(c); - } -#endif inst = E_NEW(Instance, 1); if (!inst) return NULL; @@ -139,6 +122,8 @@ mixer->base = edje_object_add(gc->evas); edje_object_file_set(mixer->base, buf, "e/modules/mixer/main"); evas_object_show(mixer->base); + + _mixer_system_init(mixer); gcc = e_gadcon_client_new(gc, name, id, style, mixer->base); gcc->data = inst; @@ -162,13 +147,7 @@ mixer = inst->mixer; if (!mixer) return; - if (mixer->win) - { - if (mixer->win->bg_obj) evas_object_del(mixer->win->bg_obj); - e_object_del(E_OBJECT(mixer->win->window)); - E_FREE(mixer->win); - } - + if (mixer->mix_sys) _mixer_system_shutdown(mixer->mix_sys); if (mixer->base) evas_object_del(mixer->base); mixer_config->instances = evas_list_remove(mixer_config->instances, inst); @@ -229,9 +208,8 @@ mi = e_menu_item_new(mn); e_menu_item_label_set(mi, _("Configuration")); e_util_menu_item_edje_icon_set(mi, "enlightenment/configuration"); - #if DEBUG e_menu_item_callback_set(mi, _mixer_menu_cb_configure, inst); - #endif + mi = e_menu_item_new(mn); e_menu_item_separator_set(mi, 1); @@ -293,11 +271,48 @@ ci = E_NEW(Config_Item, 1); ci->id = evas_stringshare_add(id); ci->card_id = 0; - + ci->channel_id = 0; + mixer_config->items = evas_list_append(mixer_config->items, ci); return ci; } +static void +_mixer_system_init(void *data) +{ + Mixer *mixer; + Mixer_System *sys; + + mixer = data; + if (!mixer) return; + + sys = E_NEW(Mixer_System, 1); + if (!sys) return; + + #ifdef HAVE_LIBASOUND + sys->get_cards = alsa_get_cards; + sys->get_card = alsa_get_card; + sys->get_channels = alsa_card_get_channels; + sys->free_cards = alsa_free_cards; + #endif + + mixer->mix_sys = sys; +} + +static void +_mixer_system_shutdown(void *data) +{ + Mixer_System *sys; + + sys = data; + if (!sys) return; + + if (sys->free_cards) + sys->free_cards(sys->cards); + + E_FREE(sys); +} + EAPI E_Module_Api e_modapi = { E_MODULE_API_VERSION, "Mixer" @@ -331,7 +346,8 @@ ci = E_NEW(Config_Item, 1); ci->id = evas_stringshare_add("0"); ci->card_id = 0; - + ci->channel_id = 0; + mixer_config->items = evas_list_append(mixer_config->items, ci); } mixer_config->module = m; =================================================================== RCS file: /cvs/e/e_modules/mixer/e_mod_main.h,v retrieving revision 1.3 retrieving revision 1.4 diff -u -3 -r1.3 -r1.4 --- e_mod_main.h 7 Sep 2006 16:36:59 -0000 1.3 +++ e_mod_main.h 11 Sep 2006 09:06:50 -0000 1.4 @@ -18,6 +18,7 @@ const char *id; int card_id; + int channel_id; }; EAPI extern E_Module_Api e_modapi; =================================================================== RCS file: /cvs/e/e_modules/mixer/mixer.edc,v retrieving revision 1.2 retrieving revision 1.3 diff -u -3 -r1.2 -r1.3 --- mixer.edc 7 Sep 2006 13:46:25 -0000 1.2 +++ mixer.edc 11 Sep 2006 09:06:50 -0000 1.3 @@ -38,6 +38,33 @@ normal: "mixer-volume-high.png"; } } + description + { + state: "low" 0.0; + inherit: "default" 0.0; + image + { + normal: "mixer-volume-low.png"; + } + } + description + { + state: "medium" 0.0; + inherit: "default" 0.0; + image + { + normal: "mixer-volume-medium.png"; + } + } + description + { + state: "mute" 0.0; + inherit: "default" 0.0; + image + { + normal: "mixer-volume-muted.png"; + } + } } /* end icon part */ } /* end parts */ } /* end group */ ------------------------------------------------------------------------- Using Tomcat but need to do more? Need to support web services, security? Get stuff done quickly with pre-integrated technology to make your job easier Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo http://sel.as-us.falkag.net/sel?cmd=lnk&kid=120709&bid=263057&dat=121642 _______________________________________________ enlightenment-cvs mailing list enlightenment-cvs@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/enlightenment-cvs