594 lines
13 KiB
C
594 lines
13 KiB
C
/* E-SD.c
|
|
*
|
|
* Copyright (C) 1999-2000 Tom Gilbert
|
|
*
|
|
* This program is free software; you can redistribute it and/or
|
|
* modify it under the terms of the GNU General Public License as
|
|
* published by the Free Software Foundation; either version 2 of the
|
|
* License, or (at your option) any later version.
|
|
*
|
|
* This program 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 General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
* USA
|
|
*/
|
|
#include <esd.h>
|
|
#include <fcntl.h>
|
|
|
|
#include "config.h"
|
|
#include "epplet.h"
|
|
#include "esdcloak.h"
|
|
#include "utils.h"
|
|
|
|
extern int load_val;
|
|
extern int load_r;
|
|
extern int load_l;
|
|
|
|
RGB_buf rgbbuf;
|
|
|
|
static Epplet_gadget btn_conf, btn_close, btn_help, btn_ctimer;
|
|
static Epplet_gadget p, ctimer_p;
|
|
static Window win;
|
|
static Epplet_gadget da;
|
|
static int cloaked = 0;
|
|
|
|
static const int cloak_anims[] = {
|
|
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16
|
|
};
|
|
static const int cloak_delays[] = {
|
|
1, 2, 3, 4, 5, 10, 15, 20, 30, 60, 120
|
|
};
|
|
|
|
struct {
|
|
int fd;
|
|
int vol_l;
|
|
int vol_r;
|
|
int vol_ave;
|
|
int standby;
|
|
} esd;
|
|
|
|
static Epplet_gadget lbar, rbar, standby;
|
|
|
|
struct {
|
|
int cloak_anim;
|
|
int do_cloak;
|
|
double cloak_delay;
|
|
double draw_interval;
|
|
char *dir;
|
|
} opt;
|
|
|
|
/* RATE is sample rate (samples/sec) */
|
|
#define BUFS 8 /* number of audio buffers (lag compensation) */
|
|
#define RATE 44100
|
|
|
|
static int nsamp; /* number of samples */
|
|
|
|
static void cb_in(void *data, Window w);
|
|
|
|
/*
|
|
short *incoming_buf[BUFS];
|
|
int last_is_full;
|
|
volatile int curbuf;
|
|
int pos;
|
|
int to_get;
|
|
int lag;
|
|
*/
|
|
|
|
static void
|
|
save_config(void)
|
|
{
|
|
char buf[10];
|
|
|
|
Esnprintf(buf, sizeof(buf), "%f", opt.cloak_delay);
|
|
Epplet_modify_config("CLOAK_DELAY", buf);
|
|
Esnprintf(buf, sizeof(buf), "%f", opt.draw_interval);
|
|
Epplet_modify_config("DRAW_INTERVAL", buf);
|
|
Esnprintf(buf, sizeof(buf), "%d", opt.do_cloak);
|
|
Epplet_modify_config("DO_CLOAK", buf);
|
|
Esnprintf(buf, sizeof(buf), "%d", opt.cloak_anim);
|
|
Epplet_modify_config("CLOAK_ANIM", buf);
|
|
Epplet_modify_config("DIRECTORY", opt.dir);
|
|
}
|
|
|
|
static void
|
|
load_config(void)
|
|
{
|
|
opt.do_cloak = atoi(Epplet_query_config_def("DO_CLOAK", "1"));
|
|
opt.cloak_anim = atoi(Epplet_query_config_def("CLOAK_ANIM", "4"));
|
|
opt.cloak_delay = atof(Epplet_query_config_def("CLOAK_DELAY", "3"));
|
|
opt.draw_interval = atof(Epplet_query_config_def("DRAW_INTERVAL", "0.05"));
|
|
if (opt.dir)
|
|
free(opt.dir);
|
|
opt.dir = _Strdup(Epplet_query_config_def("DIRECTORY", "~/"));
|
|
}
|
|
|
|
static void
|
|
cb_close(void *data __UNUSED__)
|
|
{
|
|
save_config();
|
|
Epplet_unremember();
|
|
esd_close(esd.fd);
|
|
Esync();
|
|
exit(0);
|
|
}
|
|
|
|
static void
|
|
cb_help(void *data __UNUSED__)
|
|
{
|
|
Epplet_show_about("E-SD");
|
|
}
|
|
|
|
static void
|
|
cloak_draw(void *data __UNUSED__)
|
|
{
|
|
switch (opt.cloak_anim)
|
|
{
|
|
case 0:
|
|
{
|
|
blank_buf();
|
|
break;
|
|
}
|
|
case 1:
|
|
{
|
|
draw_flame();
|
|
break;
|
|
}
|
|
case 2:
|
|
{
|
|
draw_aa_triangle();
|
|
break;
|
|
}
|
|
case 3:
|
|
{
|
|
draw_aa_star();
|
|
break;
|
|
}
|
|
case 4:
|
|
{
|
|
draw_scanner();
|
|
break;
|
|
}
|
|
case 5:
|
|
{
|
|
draw_colorwarp();
|
|
break;
|
|
}
|
|
case 6:
|
|
{
|
|
draw_ball();
|
|
break;
|
|
}
|
|
case 7:
|
|
{
|
|
draw_atoms();
|
|
break;
|
|
}
|
|
case 8:
|
|
{
|
|
draw_text();
|
|
break;
|
|
}
|
|
case 9:
|
|
{
|
|
draw_history();
|
|
break;
|
|
}
|
|
case 10:
|
|
{
|
|
draw_history_bar();
|
|
break;
|
|
}
|
|
default:
|
|
{
|
|
blank_buf();
|
|
break;
|
|
}
|
|
}
|
|
Epplet_paste_buf(rgbbuf, win, 0, 0);
|
|
Epplet_timer(cloak_draw, NULL, opt.draw_interval, "DRAW_TIMER");
|
|
}
|
|
|
|
static void
|
|
cloak_epplet(void *data __UNUSED__)
|
|
{
|
|
if (!cloaked)
|
|
{
|
|
Epplet_gadget_hide(btn_close);
|
|
Epplet_gadget_hide(btn_conf);
|
|
Epplet_gadget_hide(btn_help);
|
|
Epplet_gadget_show(da);
|
|
cloak_draw(NULL);
|
|
cloaked = 1;
|
|
}
|
|
}
|
|
|
|
static void
|
|
cb_cloak_anim(void *data)
|
|
{
|
|
cb_in(NULL, 0);
|
|
opt.do_cloak = 1;
|
|
opt.cloak_anim = *((int *)data);
|
|
Epplet_timer(cloak_epplet, NULL, opt.cloak_delay, "CLOAK_TIMER");
|
|
}
|
|
|
|
static void
|
|
cb_dont_cloak(void *data __UNUSED__)
|
|
{
|
|
opt.do_cloak = 0;
|
|
Epplet_remove_timer("CLOAK_TIMER");
|
|
if (cloaked)
|
|
{
|
|
Epplet_gadget_hide(da);
|
|
cloaked = 0;
|
|
Epplet_gadget_show(btn_close);
|
|
Epplet_gadget_show(btn_conf);
|
|
Epplet_gadget_show(btn_help);
|
|
}
|
|
}
|
|
|
|
static void
|
|
cb_in(void *data __UNUSED__, Window w __UNUSED__)
|
|
{
|
|
if (cloaked)
|
|
{
|
|
Epplet_gadget_hide(da);
|
|
cloaked = 0;
|
|
Epplet_gadget_show(btn_close);
|
|
Epplet_gadget_show(btn_conf);
|
|
Epplet_gadget_show(btn_help);
|
|
}
|
|
Epplet_remove_timer("CLOAK_TIMER");
|
|
Epplet_remove_timer("DRAW_TIMER");
|
|
}
|
|
|
|
static void
|
|
cb_out(void *data __UNUSED__, Window w __UNUSED__)
|
|
{
|
|
Epplet_remove_timer("CLOAK_TIMER");
|
|
if ((!cloaked) && (opt.do_cloak))
|
|
Epplet_timer(cloak_epplet, NULL, opt.cloak_delay, "CLOAK_TIMER");
|
|
}
|
|
|
|
static void
|
|
cb_cloak_delay(void *data)
|
|
{
|
|
Epplet_remove_timer("CLOAK_TIMER");
|
|
opt.cloak_delay = *(int *)data;
|
|
Epplet_timer(cloak_epplet, NULL, opt.cloak_delay, "CLOAK_TIMER");
|
|
}
|
|
|
|
/* This method was *really* laggy */
|
|
|
|
/*
|
|
static void
|
|
handle_data (void)
|
|
{
|
|
int buf;
|
|
short *ptr;
|
|
int count;
|
|
register int i;
|
|
register short val_l = 0, val_r = 0;
|
|
unsigned short bigl = 0, bigr = 0;
|
|
|
|
if (last_is_full)
|
|
{
|
|
curbuf++;
|
|
if (curbuf >= BUFS)
|
|
curbuf = 0;
|
|
}
|
|
count = read (esd.fd, incoming_buf[curbuf] + pos, to_get);
|
|
if (count < 0)
|
|
{
|
|
printf ("count < 0\n");
|
|
exit (1);
|
|
}
|
|
else
|
|
{
|
|
pos += count;
|
|
to_get -= count;
|
|
}
|
|
if (to_get <= 0)
|
|
{
|
|
to_get = nsamp;
|
|
pos = 0;
|
|
last_is_full = 1;
|
|
buf = ((BUFS * 2) + curbuf - lag) % BUFS;
|
|
|
|
bigl = bigr = 0;
|
|
for (i = 0; i < nsamp; i++)
|
|
{
|
|
val_l = abs (*(incoming_buf[buf] + i));
|
|
i++;
|
|
val_r = abs (*(incoming_buf[buf] + i));
|
|
bigl = (val_l > bigl) ? val_l : bigl;
|
|
bigr = (val_r > bigr) ? val_r : bigr;
|
|
}
|
|
bigl /= (nsamp / 8);
|
|
bigr /= (nsamp / 8);
|
|
|
|
esd.vol_l = bigl;
|
|
esd.vol_r = bigr;
|
|
esd.vol_ave = (bigl + bigr) / 2;
|
|
|
|
if (!cloaked)
|
|
{
|
|
Epplet_gadget_data_changed (lbar);
|
|
Epplet_gadget_data_changed (rbar);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
last_is_full = 0;
|
|
}
|
|
}
|
|
*/
|
|
|
|
static void
|
|
esd_timer(void *data __UNUSED__)
|
|
{
|
|
fd_set rfds;
|
|
struct timeval tv;
|
|
int retval;
|
|
|
|
register short val_l = 0, val_r = 0;
|
|
unsigned short bigl = 0, bigr = 0;
|
|
int count, i;
|
|
short aubuf[8192] = { 0 };
|
|
FD_ZERO(&rfds);
|
|
FD_SET(esd.fd, &rfds);
|
|
tv.tv_sec = 0;
|
|
tv.tv_usec = 0;
|
|
|
|
/* tv is basically 0, so this should be a non-blocking select() */
|
|
/* It should immediately return whether there is anything in the stream */
|
|
retval = select(esd.fd + 1, &rfds, NULL, NULL, &tv);
|
|
|
|
if (retval)
|
|
{
|
|
count = read(esd.fd, aubuf, nsamp * 2);
|
|
if (count < 0)
|
|
{
|
|
printf("WARNING: Couldn't read EsounD monitor stream!\n");
|
|
return;
|
|
}
|
|
for (i = 0; i < count;)
|
|
{
|
|
val_r = abs(aubuf[i++]);
|
|
val_l = abs(aubuf[i++]);
|
|
bigl = (val_l > bigl) ? val_l : bigl;
|
|
bigr = (val_r > bigr) ? val_r : bigr;
|
|
}
|
|
bigl /= 327;
|
|
bigr /= 327;
|
|
|
|
esd.vol_l = bigl;
|
|
esd.vol_r = bigr;
|
|
esd.vol_ave = (bigl + bigr) / 2;
|
|
load_val = esd.vol_ave;
|
|
load_r = esd.vol_r;
|
|
load_l = esd.vol_l;
|
|
|
|
if (!cloaked)
|
|
{
|
|
Epplet_gadget_data_changed(lbar);
|
|
Epplet_gadget_data_changed(rbar);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (esd.vol_ave != 0)
|
|
{
|
|
esd.vol_r = 0;
|
|
esd.vol_l = 0;
|
|
esd.vol_ave = 0;
|
|
load_val = esd.vol_ave;
|
|
load_r = esd.vol_r;
|
|
load_l = esd.vol_l;
|
|
|
|
if (!cloaked)
|
|
{
|
|
Epplet_gadget_data_changed(lbar);
|
|
Epplet_gadget_data_changed(rbar);
|
|
}
|
|
}
|
|
}
|
|
|
|
/*
|
|
if (retval)
|
|
{
|
|
handle_data ();
|
|
}
|
|
else
|
|
{
|
|
if (esd.vol_ave != 0)
|
|
{
|
|
esd.vol_r = 0;
|
|
esd.vol_l = 0;
|
|
esd.vol_ave = 0;
|
|
Epplet_gadget_data_changed (lbar);
|
|
Epplet_gadget_data_changed (rbar);
|
|
}
|
|
}
|
|
*/
|
|
Epplet_timer(esd_timer, NULL, 0.05, "ESD_TIMER");
|
|
}
|
|
|
|
static void
|
|
standby_cb(void *data __UNUSED__)
|
|
{
|
|
int fd = esd_open_sound(NULL);
|
|
|
|
if (esd.standby)
|
|
{
|
|
esd_resume(fd);
|
|
}
|
|
else
|
|
{
|
|
esd_standby(fd);
|
|
}
|
|
|
|
esd_close(fd);
|
|
}
|
|
|
|
static void
|
|
create_epplet_layout(void)
|
|
{
|
|
Epplet_gadget_show(btn_close = Epplet_create_button(NULL, NULL,
|
|
2, 2, 0, 0, "CLOSE",
|
|
0, NULL, cb_close,
|
|
NULL));
|
|
Epplet_gadget_show(btn_help =
|
|
Epplet_create_button(NULL, NULL, 18, 2, 0, 0, "HELP",
|
|
0, NULL, cb_help, NULL));
|
|
|
|
Epplet_gadget_show(lbar = Epplet_create_vbar(2, 18, 12, 28, 1, &esd.vol_l));
|
|
Epplet_gadget_show(rbar = Epplet_create_vbar(34, 18, 12, 28, 1, &esd.vol_r));
|
|
Epplet_gadget_show(standby =
|
|
Epplet_create_togglebutton(NULL, "E-SD_standby.png",
|
|
18, 18, 12, 12,
|
|
&esd.standby, standby_cb,
|
|
NULL));
|
|
|
|
p = Epplet_create_popup();
|
|
Epplet_add_popup_entry(p, "Don't Cloak", NULL, cb_dont_cloak, NULL);
|
|
Epplet_add_popup_entry(p, "Blank Epplet", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[0])));
|
|
Epplet_add_popup_entry(p, "RasterFire", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[1])));
|
|
Epplet_add_popup_entry(p, "AA Triangle", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[2])));
|
|
Epplet_add_popup_entry(p, "AA Star", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[3])));
|
|
Epplet_add_popup_entry(p, "Scanner", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[4])));
|
|
Epplet_add_popup_entry(p, "ColorShift", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[5])));
|
|
Epplet_add_popup_entry(p, "Bouncy Ball", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[6])));
|
|
Epplet_add_popup_entry(p, "Atoms", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[7])));
|
|
Epplet_add_popup_entry(p, "Banner", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[8])));
|
|
Epplet_add_popup_entry(p, "History", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[9])));
|
|
Epplet_add_popup_entry(p, "History Bar", NULL, cb_cloak_anim,
|
|
(void *)(&(cloak_anims[10])));
|
|
|
|
ctimer_p = Epplet_create_popup();
|
|
Epplet_add_popup_entry(ctimer_p, "Cloak Delay", NULL, NULL, NULL);
|
|
Epplet_add_popup_entry(ctimer_p, "1 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[0])));
|
|
Epplet_add_popup_entry(ctimer_p, "2 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[1])));
|
|
Epplet_add_popup_entry(ctimer_p, "3 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[2])));
|
|
Epplet_add_popup_entry(ctimer_p, "4 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[3])));
|
|
Epplet_add_popup_entry(ctimer_p, "5 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[4])));
|
|
Epplet_add_popup_entry(ctimer_p, "10 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[5])));
|
|
Epplet_add_popup_entry(ctimer_p, "15 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[6])));
|
|
Epplet_add_popup_entry(ctimer_p, "20 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[7])));
|
|
Epplet_add_popup_entry(ctimer_p, "30 Sec", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[8])));
|
|
Epplet_add_popup_entry(ctimer_p, "1 min", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[9])));
|
|
Epplet_add_popup_entry(ctimer_p, "2 mins", NULL, cb_cloak_delay,
|
|
(void *)(&(cloak_delays[10])));
|
|
|
|
Epplet_gadget_show(btn_ctimer =
|
|
Epplet_create_popupbutton(NULL, "E-SD_minitime.png",
|
|
18, 31, 12, 12, NULL,
|
|
ctimer_p));
|
|
|
|
Epplet_gadget_show(btn_conf = Epplet_create_popupbutton(NULL, NULL,
|
|
34, 2, 12, 12,
|
|
"CONFIGURE", p));
|
|
|
|
da = Epplet_create_drawingarea(2, 2, 44, 44);
|
|
win = Epplet_get_drawingarea_window(da);
|
|
rgbbuf = Epplet_make_rgb_buf(40, 40);
|
|
|
|
cloaked = 0;
|
|
if (opt.do_cloak)
|
|
Epplet_timer(cloak_epplet, NULL, opt.cloak_delay, "CLOAK_TIMER");
|
|
|
|
Epplet_timer(esd_timer, NULL, 0.05, "ESD_TIMER");
|
|
|
|
Epplet_register_mouse_enter_handler(cb_in, (void *)win);
|
|
Epplet_register_mouse_leave_handler(cb_out, NULL);
|
|
}
|
|
|
|
static void
|
|
clean_exit(void)
|
|
{
|
|
save_config();
|
|
Epplet_cleanup();
|
|
}
|
|
|
|
int
|
|
main(int argc, char **argv)
|
|
{
|
|
Epplet_adjust_priority(10);
|
|
|
|
atexit(clean_exit);
|
|
|
|
/* Initialise random numbers */
|
|
srand(time(0));
|
|
|
|
Epplet_Init("E-SD", "0.4", "Enlightenment ESD Monitor", 3, 3, argc, argv, 0);
|
|
Epplet_load_config();
|
|
|
|
esd.fd =
|
|
esd_monitor_stream(ESD_BITS16 | ESD_STEREO | ESD_STREAM | ESD_PLAY,
|
|
RATE, NULL, "E-SD");
|
|
if (esd.fd < 0)
|
|
{
|
|
printf("No ESD - exiting!\n");
|
|
exit(1);
|
|
}
|
|
|
|
fcntl(esd.fd, F_SETFL, O_NONBLOCK);
|
|
|
|
if (esd_get_standby_mode(esd.fd) == ESM_RUNNING)
|
|
esd.standby = 0;
|
|
else
|
|
esd.standby = 1;
|
|
|
|
nsamp = 4096;
|
|
/*
|
|
last_is_full = 1;
|
|
pos = 0;
|
|
to_get = nsamp;
|
|
lag = 0;
|
|
for (i = 0; i < BUFS; i++)
|
|
{
|
|
incoming_buf[i] = malloc (nsamp * sizeof (short));
|
|
if (incoming_buf[i] == NULL)
|
|
{
|
|
printf
|
|
("Audio Buffer Memory could NOT be allocated!!!!, Exiting now!\n");
|
|
exit (2);
|
|
}
|
|
}
|
|
*/
|
|
|
|
set_flame_col(0);
|
|
|
|
load_config();
|
|
create_epplet_layout();
|
|
|
|
Epplet_show();
|
|
Epplet_Loop();
|
|
|
|
return 0;
|
|
}
|