From 792bd17a089c290a201a811fd64f5a6f5f21ff2f Mon Sep 17 00:00:00 2001 From: Linus Nielsen Feltzing Date: Sat, 21 Aug 2004 23:22:05 +0000 Subject: Patch #1002379 by Lee Pilgrim, New VU meter git-svn-id: svn://svn.rockbox.org/rockbox/trunk@5004 a1c6a512-1295-4272-9138-f99709370657 --- apps/plugins/vu_meter.c | 729 +++++++++++++++++++++--------------------------- 1 file changed, 321 insertions(+), 408 deletions(-) (limited to 'apps/plugins/vu_meter.c') diff --git a/apps/plugins/vu_meter.c b/apps/plugins/vu_meter.c index a9d74da794..c400a4e189 100644 --- a/apps/plugins/vu_meter.c +++ b/apps/plugins/vu_meter.c @@ -15,508 +15,421 @@ * KIND, either express or implied. * **************************************************************************/ - - /****************************************************** - * Quick note: throughout this code you'll see - * comments like this one, inside of a box. They are - * used to indicate new functions, not because I - * think you're blind. Only here to help. - ******************************************************/ - #include "plugin.h" #ifdef HAVE_LCD_BITMAP -static struct plugin_api* rb; - -/* This table is used to define x positions on a logarithmic (dBfs) scale. - There are 112 of them, one for each pixel. - The formula I used to figure these out was log(x)*32.09, - where x was the original x position. */ -static unsigned char db_scale[] = {0,0,10,15,19,22,25,27,29,31,32,33,35,36,37,38,39,39,40,41,42,42, - 43,44,44,45,45,46,46,47,47,48,48,49,49,50,50,50,51,51,51,52,52, - 52,53,53,53,54,54,54,55,55,55,55,56,56,56,56,56,66, 71,75,78,81, - 83,85,87,88,89,91,92,93,94,95,95,96,97,98,98,99,100,100,101,101, - 102,102,103,103,104,104,105,105,106,106,106,107,107,107,108,108, - 108,109,109,109,110,110,110,111,111,111,111,112,112,112}; - -/* Define's y positions, and makes it look like an arch, like a real needle would. */ -static unsigned char y_values[] = {32,31,30,29,28,27,26,25,24,24,23,22,22,21,21,20,19,19,18,18,18,18,18,17,17,17,17,17, - 17,17,17,17,17,18,18,18,18,18,19,19,20,21,21,22,22,23,24,24,25,26,27,28,29,30,31,32, - 32,31,30,29,28,27,26,25,24,24,23,22,22,21,21,20,19,19,18,18,18,18,18,17,17,17,17,17, - 17,17,17,17,17,18,18,18,18,18,19,19,20,21,21,22,22,23,24,24,25,26,27,28,29,30,31,32}; - -/*************************************************** - * LCD Bitmaps/Icons - ***************************************************/ - -/* Linear mode bitmap icon. */ -unsigned char mode_linear[] = {0xDF,0x10,0xD0,0x00,0xDF,0x00,0xDF,0x02,0xC4,0x08,0xDF, - 0x00,0xDF,0x15,0xD1,0x00,0xDE,0x05,0xDE,0x00,0xDF,0x05, - 0xDA}; - -/* Logarithmic (dBfs) mode bitmap icon. */ -unsigned char mode_dbfs[] = {0xC8,0x14,0x14,0x1F,0x00,0xDF,0x15,0x15,0x0A,0xC0,0x1E, - 0x05,0x05,0xC0,0x16,0x15,0xD5,0x09,0xC0,0x00,0xF0,0x00, - 0xFE}; +const struct plugin_api* rb; -/* Channel indicator - no level [4x8] */ -static unsigned char sound_speaker[] = {0x18,0x24,0x42,0xFF}; +/* Defines x positions on a logarithmic (dBfs) scale. */ +const unsigned char analog_db_scale[] = +{0,0,10,15,19,22,25,27,29,31,32,33,35,36,37,38,39,39,40,41,42,42,43,44,44,45,45,46, +46,47,47,48,48,49,49,50,50,50,51,51,51,52,52,52,53,53,53,54,54,54,55,55,55,55,56,56}; -/* Channel indicator - low level [2x8] */ -static unsigned char sound_low_level[] = {0x24,0x18}; +const unsigned char digital_db_scale[] = +{0,2,3,5,5,6,6,6,7,7,7,7,8,8,8,8,8,9,9,9,9,9,9,9,9,10,10, +10,10,10,10,10,10,10,10,10,11,11,11,11,11,11,11,11}; -/* Channel indicator - medium level [2x8] */ -static unsigned char sound_med_level[] = {0x42,0x3C}; +/* Define's y positions, to make the needle arch, like a real needle would. */ +const unsigned char y_values[] = +{34,34,33,33,32,32,31,31,30,30,29,29,28,28,28,27,27,27,26,26,26,26,25,25,25,25,25,25, +25,25,25,25,25,25,26,26,26,26,27,27,27,28,28,28,29,29,30,30,31,31,32,32,33,33,34,34}; -/* Channel indicator - high level [2x8] */ -static unsigned char sound_high_level[] = {0x81,0x7E}; +const unsigned char led[] = {0x0e, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x0e}; -/* Channel indicator - maxed out [3x8] */ -static unsigned char sound_max_level[] = {0x0E,0xDF,0x0E}; +const unsigned char needle_cover[] = +{0x18, 0x1c, 0x1c, 0x1e, 0x1e, 0x1f, 0x1f, 0x1f, 0x1e, 0x1e, 0x1c, 0x1c, 0x18}; -/* Volume level icon [4x7] */ -static unsigned char volume_indicator[] = {0x1C,0x1C,0x22,0x7F}; +const unsigned char sound_speaker[] = {0x18,0x24,0x42,0xFF}; +const unsigned char sound_low_level[] = {0x24,0x18}; +const unsigned char sound_med_level[] = {0x42,0x3C}; +const unsigned char sound_high_level[] = {0x81,0x7E}; +const unsigned char sound_max_level[] = {0x0E,0xDF,0x0E}; -/* RIGHT ARROW icon (from icons.c) [7x8] */ -static unsigned char right_arrow[] = {0x7F,0x3E,0x1C,0x7F,0x3E,0x1C,0x08}; +#define ANALOG 1 /* The two meter types */ +#define DIGITAL 2 -/* LEFT ARROW icon (from icons.c) [7x8] */ -static unsigned char left_arrow[] = {0x08,0x1C,0x3E,0x7F,0x1C,0x3E,0x7F}; - -/************************* - * DEFINES - *************************/ -#define MAX_PEAK 0x7FFF -#define NEEDLE_BOTTOM_Y 54 - -/****************************** - * LEFT NEEDLE ints - ******************************/ -#define LEFT_NEEDLE_BOTTOM_X 28 int left_needle_top_y; int left_needle_top_x; -int old_left_needle_top_x = 0; -int left_needle_top_x_no_log; - -/******************************* - * RIGHT NEEDLE ints - *******************************/ -#define RIGHT_NEEDLE_BOTTOM_X 84 +int last_left_needle_top_x; int right_needle_top_y; int right_needle_top_x; -int old_right_needle_top_x = 56; -int right_needle_top_x_no_log; - -/********************* - * LEFT MINIMETER ints - *********************/ -int mini_left_low; -int mini_left_med; -int mini_left_high; -int mini_left_clip; - -/********************** - * RIGHT MINIMETER ints - **********************/ -int mini_right_low; -int mini_right_med; -int mini_right_high; -int mini_right_clip; - -/************************ - * GENERAL ints - ************************/ -char curr_vol[3]; /* CURRENT VOLUME */ -int vol; /* CURENNT VOLUME int */ -int on = 1; /* MINIMETER OPTIONS int */ -int needle_cover_mode = 1; /* NEEDLE COVER int (defaults to "rounded") */ -int arch = 1; /* ARCH int (defaults to "solid") */ -int decay = 3; /* DECAY int (defaults to "medium") */ - -/************************* - * GENERAL bools - *************************/ -bool quit = false; -bool use_log_scale = true; -bool use_minimeters = true; - -/******************************************** - * Change the volume - derived from VIDEO.C - ********************************************/ -void ChangeVolume(int delta) -{ - vol = rb->global_settings->volume + delta; +int last_right_needle_top_x = 56; - if (vol > 100) vol = 100; - else if (vol < 0) vol = 0; - if (vol != rb->global_settings->volume) - { - rb->mpeg_sound_set(SOUND_VOLUME, vol); - rb->global_settings->volume = vol; - rb->snprintf(curr_vol, sizeof(curr_vol), "%d", vol); - } -} +int num_left_leds; +int num_right_leds; +int last_num_left_leds; +int last_num_right_leds; -/***************************************************** - * Draw the status bar - *****************************************************/ -void draw_status_bar(void) -{ - rb->lcd_setfont(FONT_SYSFIXED); +int i; - rb->lcd_drawline(0, 10, 112, 10); - rb->lcd_putsxy(1, 1, "VU Meter"); - rb->lcd_drawline(52, 1, 52, 8); - rb->lcd_bitmap(volume_indicator, 60, 1, 4, 7, true); - rb->lcd_putsxy(65, 1, curr_vol); - rb->lcd_drawline(85, 1, 85, 8); - - if(use_log_scale) - rb->lcd_bitmap(mode_dbfs, 88, 1, 23, 8, true); - else - rb->lcd_bitmap(mode_linear, 88, 1, 23, 8, true); - - /* The last line under the needle covers. */ - rb->lcd_drawline(0, 54, 111, 54); +#define MAX_PEAK 0x7FFF - rb->lcd_update_rect(0, 0, 112, 10); +struct saved_settings { + int meter_type; + bool analog_use_db_scale; + bool digital_use_db_scale; + bool analog_minimeters; + bool digital_minimeters; + int analog_decay; + int digital_decay; +} settings; + +void reset_settings(void) { + settings.meter_type=ANALOG; + settings.analog_use_db_scale=true; + settings.digital_use_db_scale=true; + settings.analog_minimeters=true; + settings.digital_minimeters=false; + settings.analog_decay=3; + settings.digital_decay=0; } -/****************************** - * DRAW left MiniMeters - ******************************/ +void load_settings(void) { + int fp = rb->open("/.rockbox/rocks/.vu_meter", O_RDONLY); + if(fp>=0) { + rb->read(fp, &settings, sizeof(struct saved_settings)); + rb->close(fp); + } + else { + reset_settings(); + rb->splash(HZ, true, "Press ON for help"); + } +} -void draw_left_minimeters(void) -{ - rb->lcd_bitmap(sound_speaker, 22, 56, 4, 8, true); - - if(5lcd_bitmap(sound_low_level, 27, 56, 2, 8, false); - if(12lcd_bitmap(sound_med_level, 30, 56, 2, 8, false); - if(24lcd_bitmap(sound_high_level, 33, 56, 2, 8, false); - if(40lcd_bitmap(sound_max_level, 36, 56, 3, 8, false); +void save_settings(void) { + int fp = rb->creat("/.rockbox/rocks/.vu_meter", O_WRONLY); + if(fp >= 0) { + rb->write (fp, &settings, sizeof(struct saved_settings)); + rb->close(fp); + } } -/******************************* - * DRAW right MiniMeters - *******************************/ -void draw_right_minimeters(void) -{ - rb->lcd_bitmap(sound_speaker, 79, 56, 4, 8, true); - - if(5<(right_needle_top_x_no_log-56)) - rb->lcd_bitmap(sound_low_level, 84, 56, 2, 8, false); - if(12<(right_needle_top_x_no_log-56)) - rb->lcd_bitmap(sound_med_level, 87, 56, 2, 8, false); - if(24<(right_needle_top_x_no_log-56)) - rb->lcd_bitmap(sound_high_level, 90, 56, 2, 8, false); - if(40<(right_needle_top_x_no_log-56)) - rb->lcd_bitmap(sound_max_level, 93, 56, 3, 8, false); +void change_volume(int delta) { + char curr_vol[4]; + int vol = rb->global_settings->volume + delta; + + if (vol>100) vol = 100; + else if (vol < 0) vol = 0; + if (vol != rb->global_settings->volume) { + rb->mpeg_sound_set(SOUND_VOLUME, vol); + rb->global_settings->volume = vol; + rb->snprintf(curr_vol, sizeof(curr_vol), "%d", vol); + rb->lcd_putsxy(0,0, curr_vol); + rb->lcd_update(); + rb->sleep(HZ/12); + } } -/*************************************** - * GENERAL SETTINGS - F1 - ***************************************/ -void general_settings(void) +void change_settings(void) { - char buf[15]; - int w, h; - + int selected_setting=0; + bool quit=false; while(!quit) { rb->lcd_clear_display(); - /* Left hand side (needle covers) */ - rb->lcd_putsxy(0, 15, "Needle"); - rb->lcd_putsxy(0, 23, "Covers:"); - if(needle_cover_mode == 1) - rb->lcd_putsxy(0, 32, "Rounded"); + rb->lcd_putsxy(33, 0, "Settings"); + + rb->lcd_putsxy(0, 8, "Meter type:"); + if(settings.meter_type==ANALOG) + rb->lcd_putsxy(67, 8, "Analog"); else - rb->lcd_putsxy(0, 32, "Pyramid"); - rb->lcd_bitmap(left_arrow, 43, 23, 7, 8, true); - - /* Right hand side (visible arch) */ - rb->snprintf(buf, sizeof(buf), "Visible"); - rb->lcd_getstringsize(buf, &w, &h); - rb->lcd_putsxy(LCD_WIDTH-w, 15, buf); - rb->snprintf(buf, sizeof(buf), "Arch:"); - rb->lcd_getstringsize(buf, &w, &h); - rb->lcd_putsxy(LCD_WIDTH-w, 23, buf); - rb->lcd_bitmap(right_arrow, 62, 23, 7, 8, true); - if(arch == 1) - { - rb->snprintf(buf, sizeof(buf), "Solid"); - rb->lcd_getstringsize(buf, &w, &h); - rb->lcd_putsxy(LCD_WIDTH-w, 32, buf); + rb->lcd_putsxy(67, 8, "Digital"); + + if(settings.meter_type==ANALOG) { + rb->lcd_putsxy(0, 16, "Scale:"); + if(settings.analog_use_db_scale) + rb->lcd_putsxy(36, 16, "dBfs"); + else + rb->lcd_putsxy(36, 16, "Linear"); + + rb->lcd_putsxy(0, 24, "Minimeters:"); + if(settings.analog_minimeters) + rb->lcd_putsxy(65, 24, "On"); + else + rb->lcd_putsxy(65, 24, "Off"); + + rb->lcd_putsxy(0, 32, "Decay Speed:"); + switch(settings.analog_decay) { + case 0: rb->lcd_putsxy(10, 40, "No Decay"); break; + case 1: rb->lcd_putsxy(10, 40, "Very Fast"); break; + case 2: rb->lcd_putsxy(10, 40, "Fast"); break; + case 3: rb->lcd_putsxy(10, 40, "Medium"); break; + case 4: rb->lcd_putsxy(10, 40, "Medium-Slow"); break; + case 5: rb->lcd_putsxy(10, 40, "Slow"); break; + case 6: rb->lcd_putsxy(10, 40, "Very Slow"); break; + } } - else if(arch == 2) - { - rb->snprintf(buf, sizeof(buf), "Dotted"); - rb->lcd_getstringsize(buf, &w, &h); - rb->lcd_putsxy(LCD_WIDTH-w, 32, buf); + else { + rb->lcd_putsxy(0, 16, "Scale:"); + if(settings.digital_use_db_scale) + rb->lcd_putsxy(36, 16, "dBfs"); + else + rb->lcd_putsxy(36, 16, "Linear"); + + rb->lcd_putsxy(0, 24, "Minimeters:"); + if(settings.digital_minimeters) + rb->lcd_putsxy(65, 24, "On"); + else + rb->lcd_putsxy(65, 24, "Off"); + + rb->lcd_putsxy(0, 32, "Decay Speed:"); + switch(settings.digital_decay) { + case 0: rb->lcd_putsxy(10, 40, "No Decay"); break; + case 1: rb->lcd_putsxy(10, 40, "Very Fast"); break; + case 2: rb->lcd_putsxy(10, 40, "Fast"); break; + case 3: rb->lcd_putsxy(10, 40, "Medium"); break; + case 4: rb->lcd_putsxy(10, 40, "Medium-Slow"); break; + case 5: rb->lcd_putsxy(10, 40, "Slow"); break; + case 6: rb->lcd_putsxy(10, 40, "Very Slow"); break; + } } - else - { - rb->snprintf(buf, sizeof(buf), "Off"); - rb->lcd_getstringsize(buf, &w, &h); - rb->lcd_putsxy(LCD_WIDTH-w, 32, buf); - } + rb->lcd_invertrect(0, selected_setting*8+8,111,8); rb->lcd_update(); - switch(rb->button_get_w_tmo(HZ/4)) + switch(rb->button_get_w_tmo(1)) { case BUTTON_F1: case BUTTON_OFF: quit = true; break; + case BUTTON_LEFT: + if(selected_setting==0) + settings.meter_type == DIGITAL ? settings.meter_type = ANALOG : settings.meter_type++; + if(settings.meter_type==ANALOG) { + if(selected_setting==1) + settings.analog_use_db_scale = !settings.analog_use_db_scale; + if(selected_setting==2) + settings.analog_minimeters = !settings.analog_minimeters; + if(selected_setting==3) + settings.analog_decay == 0 ? settings.analog_decay = 6 : settings.analog_decay--; + } + else { + if(selected_setting==1) + settings.digital_use_db_scale = !settings.digital_use_db_scale; + if(selected_setting==2) + settings.digital_minimeters = !settings.digital_minimeters; + if(selected_setting==3) + settings.digital_decay == 0 ? settings.digital_decay = 6 : settings.digital_decay--; + } + break; + case BUTTON_RIGHT: - arch==3 ? arch=1 : arch++; + if(selected_setting==0) + settings.meter_type == DIGITAL ? settings.meter_type = ANALOG : settings.meter_type++; + if(settings.meter_type==ANALOG) { + if(selected_setting==1) + settings.analog_use_db_scale = !settings.analog_use_db_scale; + if(selected_setting==2) + settings.analog_minimeters = !settings.analog_minimeters; + if(selected_setting==3) + settings.analog_decay == 6 ? settings.analog_decay = 0 : settings.analog_decay++; + } + else { + if(selected_setting==1) + settings.digital_use_db_scale = !settings.digital_use_db_scale; + if(selected_setting==2) + settings.digital_minimeters = !settings.digital_minimeters; + if(selected_setting==3) + settings.digital_decay == 6 ? settings.digital_decay = 0 : settings.digital_decay++; + } break; - case BUTTON_LEFT: - needle_cover_mode==2 ? needle_cover_mode=1 : needle_cover_mode++; + case BUTTON_DOWN: + selected_setting == 3 ? selected_setting=0 : selected_setting++; break; + + case BUTTON_UP: + selected_setting == 0 ? selected_setting=3 : selected_setting--; } } } -/***************************** - * User Decay settings - *****************************/ -void user_decay_settings(void) -{ - while(!quit) - { - rb->lcd_clear_display(); - - rb->lcd_putsxy(2, 0, "User Decay Options"); - rb->lcd_putsxy(5, 15, "Release Speed:"); - - switch(decay) - { - case 0: rb->lcd_putsxy(5, 23, "No Decay"); break; - case 1: rb->lcd_putsxy(5, 23, "Very Fast"); break; - case 2: rb->lcd_putsxy(5, 23, "Fast"); break; - case 3: rb->lcd_putsxy(5, 23, "Medium"); break; - case 4: rb->lcd_putsxy(5, 23, "Medium-Slow"); break; - case 5: rb->lcd_putsxy(5, 23, "Slow"); break; - case 6: rb->lcd_putsxy(5, 23, "Very Slow"); break; - default: break; - } - - rb->lcd_putsxy(2, 48, "UP/DOWN: Change"); - rb->lcd_putsxy(2, 56, "OFF/F2: Back to VU"); - - rb->lcd_update(); - - switch(rb->button_get_w_tmo(HZ/4)) - { - case BUTTON_F2: - case BUTTON_OFF: - quit = true; - break; - - case BUTTON_DOWN: - decay == 6 ? decay = 0 : decay++; - break; - - case BUTTON_UP: - decay == 0 ? decay = 6 : decay--; - break; - } - } +void draw_analog_minimeters(void) { + rb->lcd_bitmap(sound_speaker, 0, 12, 4, 8, true); + if(5lcd_bitmap(sound_low_level, 5, 12, 2, 8, false); + if(12lcd_bitmap(sound_med_level, 7, 12, 2, 8, false); + if(24lcd_bitmap(sound_high_level, 9, 12, 2, 8, false); + if(40lcd_bitmap(sound_max_level, 12, 12, 3, 8, false); + + rb->lcd_bitmap(sound_speaker, 54, 12, 4, 8, true); + if(5<(right_needle_top_x-56)) + rb->lcd_bitmap(sound_low_level, 59, 12, 2, 8, false); + if(12<(right_needle_top_x-56)) + rb->lcd_bitmap(sound_med_level, 61, 12, 2, 8, false); + if(24<(right_needle_top_x-56)) + rb->lcd_bitmap(sound_high_level, 63, 12, 2, 8, false); + if(40<(right_needle_top_x-56)) + rb->lcd_bitmap(sound_max_level, 66, 12, 3, 8, false); } -/*********************************************************************** - * PLUGIN STARTS HERE - ***********************************************************************/ -enum plugin_status plugin_start(struct plugin_api* api, void* parameter) -{ - TEST_PLUGIN_API(api); - (void) parameter; - rb = api; +void draw_digital_minimeters(void) { + rb->lcd_bitmap(sound_speaker, 34, 24, 4, 8, true); + if(1lcd_bitmap(sound_low_level, 39, 24, 2, 8, false); + if(2lcd_bitmap(sound_med_level, 41, 24, 2, 8, false); + if(5lcd_bitmap(sound_high_level, 43, 24, 2, 8, false); + if(8lcd_bitmap(sound_max_level, 46, 24, 3, 8, false); + + rb->lcd_bitmap(sound_speaker, 34, 40, 4, 8, true); + if(1<(num_right_leds)) + rb->lcd_bitmap(sound_low_level, 39, 40, 2, 8, false); + if(2<(num_right_leds)) + rb->lcd_bitmap(sound_med_level, 41, 40, 2, 8, false); + if(5<(num_right_leds)) + rb->lcd_bitmap(sound_high_level, 43, 40, 2, 8, false); + if(8<(num_right_leds)) + rb->lcd_bitmap(sound_max_level, 46, 40, 3, 8, false); +} - /* Calculate the volume right away */ - vol = rb->global_settings->volume; - rb->snprintf(curr_vol, sizeof(curr_vol), "%d", vol); +void analog_meter(void) { + if(settings.analog_use_db_scale) { + left_needle_top_x = analog_db_scale[rb->mas_codec_readreg(0xC)*56/MAX_PEAK]; + right_needle_top_x = analog_db_scale[rb->mas_codec_readreg(0xD)*56/MAX_PEAK]+56; + } - rb->splash(HZ*2, true, "Press [ON] for help"); - while (!PLUGIN_OK) - { - quit = false; + else { + left_needle_top_x = rb->mas_codec_readreg(0xC) * 56 / MAX_PEAK; + right_needle_top_x = (rb->mas_codec_readreg(0xD) * 56 / MAX_PEAK)+56; + } - #ifdef SIMULATOR - left_needle_top_x_no_log = rb->rand()%56; - right_needle_top_x_no_log = (rb->rand()%56)+56; - #else - left_needle_top_x_no_log = - (rb->mas_codec_readreg(0xC) * 56 / MAX_PEAK); + /* Makes a decay on the needle */ + left_needle_top_x = (left_needle_top_x+last_left_needle_top_x*settings.analog_decay)/(settings.analog_decay+1); + right_needle_top_x = (right_needle_top_x+last_right_needle_top_x*settings.analog_decay)/(settings.analog_decay+1); - right_needle_top_x_no_log = - (rb->mas_codec_readreg(0xD) * 56 / MAX_PEAK) + 56; - #endif + last_left_needle_top_x = left_needle_top_x; + last_right_needle_top_x = right_needle_top_x; - rb->lcd_clear_display(); + left_needle_top_y = y_values[left_needle_top_x]; + right_needle_top_y = y_values[right_needle_top_x-56]; - if (use_log_scale) - { - left_needle_top_x = db_scale[left_needle_top_x_no_log]; - right_needle_top_x = db_scale[right_needle_top_x_no_log]; - } + /* Needles */ + rb->lcd_drawline(28, 63, left_needle_top_x, left_needle_top_y); + rb->lcd_drawline(84, 63, right_needle_top_x, right_needle_top_y); - else - { - left_needle_top_x = left_needle_top_x_no_log; - right_needle_top_x = right_needle_top_x_no_log; - } + if(settings.analog_minimeters) + draw_analog_minimeters(); - /* Makes a decay on the needle (Custom Decay is at F2) */ - left_needle_top_x = (left_needle_top_x+old_left_needle_top_x*decay)/(decay+1); - right_needle_top_x = (right_needle_top_x+old_right_needle_top_x*decay)/(decay+1); + /* Needle covers */ + rb->lcd_bitmap(needle_cover, 22, 59, 13, 5, false); + rb->lcd_bitmap(needle_cover, 78, 59, 13, 5, false); - old_left_needle_top_x = left_needle_top_x; - old_right_needle_top_x = right_needle_top_x; + /* Show Left/Right */ + rb->lcd_putsxy(16, 12, "Left"); + rb->lcd_putsxy(70, 12, "Right"); - left_needle_top_y = y_values[left_needle_top_x]; - right_needle_top_y = y_values[right_needle_top_x]; + /* Line above/below the Left/Right text */ + rb->lcd_drawline(0,9,111,9); + rb->lcd_drawline(0,21,111,21); - /* Draws the needles */ - rb->lcd_drawline(LEFT_NEEDLE_BOTTOM_X, NEEDLE_BOTTOM_Y, - left_needle_top_x, left_needle_top_y); + for(i=0; i<56; i++) { + rb->lcd_drawpixel(i, (y_values[i])-2); + rb->lcd_drawpixel(i+56, (y_values[i])-2); + } +} - rb->lcd_drawline(RIGHT_NEEDLE_BOTTOM_X, NEEDLE_BOTTOM_Y, - right_needle_top_x, right_needle_top_y); +void digital_meter(void) { + if(settings.digital_use_db_scale) { + num_left_leds = digital_db_scale[rb->mas_codec_readreg(0xC) * 44 / MAX_PEAK]; + num_right_leds = digital_db_scale[rb->mas_codec_readreg(0xD) * 44 / MAX_PEAK]; + } + else { + num_left_leds = rb->mas_codec_readreg(0xC) * 11 / MAX_PEAK; + num_right_leds = rb->mas_codec_readreg(0xD) * 11 / MAX_PEAK; + } - /* We've got four needle cover modes... */ - if(needle_cover_mode == 1) /* Rounded needle cover. */ - { - /* Left needle cover, top to bottom */ - rb->lcd_drawline(27, 49, 29, 49); - rb->lcd_drawline(25, 50, 31, 50); - rb->lcd_drawline(23, 51, 33, 51); - rb->lcd_drawline(22, 52, 34, 52); - rb->lcd_drawline(22, 53, 34, 53); - - /* Right needle cover, top to bottom */ - rb->lcd_drawline(83, 49, 85, 49); - rb->lcd_drawline(81, 50, 87, 50); - rb->lcd_drawline(79, 51, 89, 51); - rb->lcd_drawline(78, 52, 90, 52); - rb->lcd_drawline(78, 53, 90, 53); - } + num_left_leds = (num_left_leds+last_num_left_leds*settings.digital_decay)/(settings.digital_decay+1); + num_right_leds = (num_right_leds+last_num_right_leds*settings.digital_decay)/(settings.digital_decay+1); + + last_num_left_leds = num_left_leds; + last_num_right_leds = num_right_leds; - else /* Pyramid needle cover. */ - { - /* Left needle cover, top to bottom */ - rb->lcd_drawpixel(28, 49); - rb->lcd_drawline(27, 50, 29, 50); - rb->lcd_drawline(26, 51, 30, 51); - rb->lcd_drawline(25, 52, 31, 52); - rb->lcd_drawline(24, 53, 32, 53); - - /* Right needle cover, top to bottom */ - rb->lcd_drawpixel(84, 49); - rb->lcd_drawline(83, 50, 85, 50); - rb->lcd_drawline(82, 51, 86, 51); - rb->lcd_drawline(81, 52, 87, 52); - rb->lcd_drawline(80, 53, 88, 53); - } + /* LEDS */ + for(i=0; ilcd_bitmap(led, i*9+2+i, 14, 9, 5, false); - if(arch == 1) /* Solid */ - { - int i; - for(i=0; i<=112; i++) - rb->lcd_drawpixel(i, (y_values[i])-2 ); - } - else if(arch == 2) /* Dotted */ - { - int i; - for(i=0; i<=112; i+=2) - rb->lcd_drawpixel(i, y_values[i]); - } + for(i=0; ilcd_bitmap(led, i*9+2+i, 52, 9, 5, false); - if(use_minimeters) - { - draw_left_minimeters(); - draw_right_minimeters(); - } + if(settings.digital_minimeters) + draw_digital_minimeters(); + + /* Lines above/below where the LEDS are */ + rb->lcd_drawline(0,12,111,12); + rb->lcd_drawline(0,20,111,20); + + rb->lcd_drawline(0,50,111,50); + rb->lcd_drawline(0,58,111,58); + + /* Show Left/Right */ + rb->lcd_putsxy(2, 24, "Left"); + rb->lcd_putsxy(2, 40, "Right"); + + /* Line in the middle */ + rb->lcd_drawline(0,35,111,35); +} + +enum plugin_status plugin_start(struct plugin_api* api, void* parameter) { + TEST_PLUGIN_API(api); + (void) parameter; + rb = api; - draw_status_bar(); + load_settings(); + rb->lcd_setfont(FONT_SYSFIXED); + + while (1) + { + rb->lcd_clear_display(); + rb->lcd_putsxy(33, 0, "VU Meter"); + + if(settings.meter_type==ANALOG) + analog_meter(); + else + digital_meter(); + rb->lcd_update(); - /* Using a faster timeout like "1" makes the - * minimeters flicker, HZ/35 looks good. */ - switch (rb->button_get_w_tmo(HZ/35)) + switch (rb->button_get_w_tmo(1)) { - /* EXIT */ case BUTTON_OFF: + save_settings(); return PLUGIN_OK; break; - /* INFO */ case BUTTON_ON: rb->lcd_clear_display(); - while(!quit) - { - rb->lcd_puts(0, 0, "OFF: Exit Plugin"); - rb->lcd_puts(0, 1, "PLAY: Change Scale"); - rb->lcd_puts(0, 2, "F1: Settings"); - rb->lcd_puts(0, 3, "F2: Custom Decay"); - rb->lcd_puts(0, 4, "F3: Mini-Meters"); - rb->lcd_puts(0, 5, "UP/DOWN: Volume"); - rb->lcd_puts(0, 7, "ON to exit..."); - - rb->lcd_update(); - - switch(rb->button_get_w_tmo(HZ/4)) - { - case BUTTON_ON: - quit = true; - break; - } - } + rb->lcd_puts(0, 0, "OFF: Exit"); + rb->lcd_puts(0, 1, "F1: Settings"); + rb->lcd_puts(0, 2, "UP/DOWN: Volume"); + rb->lcd_update(); + rb->sleep(HZ*3); break; - /* SCALE switch */ - case BUTTON_PLAY: - use_log_scale = !use_log_scale; - break; - - /* GENERAL SETTINGS screen */ case BUTTON_F1: - general_settings(); - break; - - /* DECAY SETTINGS screen */ - case BUTTON_F2: - user_decay_settings(); - break; - - /* MINIMETER SETTINGS screen */ - case BUTTON_F3: - use_minimeters = !use_minimeters; + change_settings(); break; - /* VOLUME UP */ case BUTTON_UP: case BUTTON_UP | BUTTON_REPEAT: - ChangeVolume(1); + change_volume(1); break; - /* VOLUME DOWN */ case BUTTON_DOWN: case BUTTON_DOWN | BUTTON_REPEAT: - ChangeVolume(-1); + change_volume(-1); break; - /* USB CONNECTED */ case SYS_USB_CONNECTED: rb->usb_screen(); return PLUGIN_USB_CONNECTED; -- cgit v1.2.3