status

statusbar program for dwm
git clone anongit@rnpnr.xyz:status.git
Log | Files | Refs | Feed | README | LICENSE

volume.c (1330B)


      1 /* See LICENSE for license details. */
      2 #include <alsa/asoundlib.h>
      3 #include <alsa/mixer.h>
      4 #include <limits.h>
      5 
      6 struct vol_arg {
      7 	const char *card;
      8 	const char *sink;
      9 };
     10 
     11 static size_t
     12 volume(struct Block *b)
     13 {
     14 	snd_mixer_t *handle;
     15 	snd_mixer_selem_id_t *sid;
     16 	snd_mixer_elem_t *elem;
     17 	struct vol_arg *va = b->arg;
     18 	const char *str = "muted";
     19 
     20 	int notmuted;
     21 	long vol = 0, min, max;
     22 
     23 	snd_mixer_open(&handle, 0);
     24 	snd_mixer_attach(handle, va->card);
     25 	snd_mixer_selem_register(handle, NULL, NULL);
     26 	snd_mixer_load(handle);
     27 
     28 	snd_mixer_selem_id_malloc(&sid);
     29 	snd_mixer_selem_id_set_index(sid, 0);
     30 	snd_mixer_selem_id_set_name(sid, va->sink);
     31 	elem = snd_mixer_find_selem(handle, sid);
     32 
     33 	snd_mixer_selem_get_playback_switch(elem, 0, &notmuted);
     34 
     35 	if (snd_mixer_selem_has_playback_volume(elem)) {
     36 		snd_mixer_selem_get_playback_volume(elem, SND_MIXER_SCHN_MONO, &vol);
     37 		snd_mixer_selem_get_playback_volume_range(elem, &min, &max);
     38 
     39 		/* covert from raw value to percent */
     40 		vol = (double)(vol - min) / (double)(max - min) * 100;
     41 	}
     42 
     43 	/* don't change to snd_mixer_elem_free() it leaks memory */
     44 	snd_mixer_close(handle);
     45 	snd_mixer_selem_id_free(sid);
     46 
     47 	if (notmuted) {
     48 		if (vol) {
     49 			snprintf(buf, sizeof(buf), "%ld%%", vol);
     50 			str = buf;
     51 		} else
     52 			str = "on";
     53 	}
     54 
     55 	return snprintf(b->curstr, LEN(b->curstr), b->fmt, str);
     56 }