#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <ctype.h>
#include <string.h>
#include "vu.h"


STATS stats;
void usage(void);

main(int argc, char *argv[])
{
void get_sound_stats(void), parse_args(int argc, char *argv[]);
void do_vu(void), init_sound_stats();

	init_sound_stats();
	get_sound_stats();

	parse_args(argc, argv);


//	fprintf(stderr, "stats.sample_width: %d\n",stats.sample_width);
//	fprintf(stderr, "stats.num_channels: %d\n",stats.num_channels);
//	fprintf(stderr, "stats.sample_rate: %d\n",stats.sample_rate);
//	fprintf(stderr, "stats.display_rate: %g\n",stats.display_rate);
//	fprintf(stderr, "stats.show_graph: %d\n",stats.show_graph);
//	fprintf(stderr, "stats.show_percent: %d\n",stats.show_percent);
//	fprintf(stderr, "stats.show_raw	: %d\n",stats.show_raw	);
//	fprintf(stderr, "stats.show_time	: %d\n",stats.show_time	);
//	fprintf(stderr, "stats.invert_channel[0]: %d\n",stats.invert_channel[0]);
//	fprintf(stderr, "stats.invert_channel[1]: %d\n",stats.invert_channel[1]);
//	fprintf(stderr, "stats.threshold:%d\n", stats.threshold);
//	fprintf(stderr, "stats.decay_length:%d\n", stats.decay_length);


	do_vu();

	exit(0);

}

void 
init_sound_stats()
{
int x;
	stats.sample_width	= 16;
	stats.num_channels	= 1;
	stats.sample_rate	= 44100;
	stats.display_rate	= 2;
	stats.graph_gain	= 1;
	stats.show_graph	= YES;
	stats.show_percent	= YES;
	stats.show_raw		= YES;
	stats.show_time		= YES;
	stats.threshold		= 0;
	stats.decay_length	= 0;

	for(x = 0; x < MAX_CHANNELS; ++x){
		stats.invert_channel[x] = 1;
	}
}

void
parse_args(int argc, char *argv[]){
unsigned char index1;
int c;
char ch;
char emessage[256];
float optval;
void die(char *);

	while( (c = getopt(argc, argv, "m:g:b:s:d:c:i::GTPR")) != EOF){
		if( (c == 'b') | (c == 's') | (c == 'd') | (c == 'c') | (c == 'm') ){
			optval = atof(optarg);
		}
		switch(c){
			case 'm':
				if((optval < 1.0) || (optval > 16384.0)){
					fprintf(stderr, "%f -m gain must be between 1 and 16384\n", optval);
					usage();
				}
				stats.graph_gain = (int)optval;
				break;
			case 'b':
				if((optval != 8.0) && (optval != 16.0)){
					usage();
				}
				stats.sample_width = (int)optval;
				break;
			case 's':
				if(optval < 0.0){
					usage();
				}
				stats.sample_rate = (int)optval;
				break;
			case 'd':
				if(optval < 0.0){
					usage();
				}
				stats.display_rate = optval;
				break;
			case 'c':
				if( (optval < 1) || (optval > 8) ){
					sprintf(emessage, "Number of channels must be between 1 an %d", MAX_CHANNELS);
					die(emessage);
				}
				stats.num_channels = (int)optval;
				break;
			case 'g':
				stats.threshold = atoi(strtok(optarg, ":"));
				stats.decay_length = atoi(strtok(NULL, ":"));
				break;

			/***** CHANNEL INVERSION *****/
			case 'i':
				if( optarg != 0 ){
					for(index1 = 0; index1 < strlen(optarg); ++index1){
						ch = *(optarg + index1);
						if(isdigit( ch )){
							stats.invert_channel[ch] = -stats.invert_channel[ch];
						} else {
							switch(*(optarg + index1)){
								case 'l' :
									stats.invert_channel[0] = -stats.invert_channel[0];
									break;
								case 'r' :
									stats.invert_channel[1] = -stats.invert_channel[1];
									break;
								default:
									usage();
							}
						}
					}
				} else {
					stats.invert_channel[0] = -stats.invert_channel[0];
				}
				break;

			case 'G':
				stats.show_graph = !stats.show_graph;	
				break;
			case 'T':
				stats.show_time = !stats.show_time;	
				break;
			case 'P':
				stats.show_percent = !stats.show_percent;	
				break;
			case 'R':
				stats.show_raw = !stats.show_raw;	
				break;

		
		}
	}

	stats.decay_length = stats.decay_length * stats.sample_rate;

}

void
usage()
{
	fprintf(stderr, "vu: usage: vu [-b:s:c:r:GTPR]");
	exit(-1);
}

void
die(char *message)
{
	fprintf(stderr, "\n\nvu: %s\n\n", message);
	exit(-1);
	
}
