summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--apps/SOURCES4
-rw-r--r--apps/bookmark.c2
-rw-r--r--apps/database.c1
-rw-r--r--apps/dbtree.c2
-rw-r--r--apps/filetree.c16
-rw-r--r--apps/gui/statusbar.c2
-rw-r--r--apps/lang/english.lang12
-rw-r--r--apps/main.c7
-rw-r--r--apps/onplay.c1
-rw-r--r--apps/playback.c2
-rw-r--r--apps/recorder/peakmeter.c2
-rw-r--r--apps/screen_access.c2
-rw-r--r--apps/screen_access.h2
-rw-r--r--apps/screens.c4
-rw-r--r--apps/settings.c50
-rw-r--r--apps/settings.h5
-rw-r--r--apps/settings_menu.c10
-rw-r--r--apps/status.c2
-rw-r--r--apps/tree.c9
-rw-r--r--apps/tree.h1
-rw-r--r--apps/wps-display.c1841
-rw-r--r--apps/wps-display.h48
-rw-r--r--apps/wps.c882
-rw-r--r--apps/wps.h205
-rw-r--r--docs/CREDITS1
-rw-r--r--wps/rockbox_default.rwps2
26 files changed, 113 insertions, 3002 deletions
diff --git a/apps/SOURCES b/apps/SOURCES
index 2d32156cf8..67e09ed53d 100644
--- a/apps/SOURCES
+++ b/apps/SOURCES
@@ -29,8 +29,6 @@ tree.c
dbtree.c
database.c
filetree.c
-wps-display.c
-wps.c
screen_access.c
gui/buttonbar.c
@@ -40,6 +38,8 @@ gui/scrollbar.c
gui/select.c
gui/splash.c
gui/statusbar.c
+gui/gwps.c
+gui/gwps-common.c
gui/textarea.c
#ifdef HAVE_LCD_CHARCELLS
diff --git a/apps/bookmark.c b/apps/bookmark.c
index 788aebe582..c42f466283 100644
--- a/apps/bookmark.c
+++ b/apps/bookmark.c
@@ -27,7 +27,7 @@
#include "button.h"
#include "usb.h"
#include "audio.h"
-#include "wps.h"
+#include "playlist.h"
#include "settings.h"
#include "tree.h"
#include "bookmark.h"
diff --git a/apps/database.c b/apps/database.c
index 6d74ce88a9..97fb2d70cc 100644
--- a/apps/database.c
+++ b/apps/database.c
@@ -35,7 +35,6 @@
#include "mpeg.h"
#include "misc.h"
#include "ata.h"
-#include "wps.h"
#include "filetypes.h"
#include "applimits.h"
#include "icons.h"
diff --git a/apps/dbtree.c b/apps/dbtree.c
index 9115c5902c..b8a4c4703e 100644
--- a/apps/dbtree.c
+++ b/apps/dbtree.c
@@ -35,7 +35,7 @@
#include "mpeg.h"
#include "misc.h"
#include "ata.h"
-#include "wps.h"
+#include "playlist.h"
#include "filetypes.h"
#include "applimits.h"
#include "dbtree.h"
diff --git a/apps/filetree.c b/apps/filetree.c
index a9670e1be7..6855d3ec5d 100644
--- a/apps/filetree.c
+++ b/apps/filetree.c
@@ -31,7 +31,7 @@
#include "filetypes.h"
#include "talk.h"
#include "playlist.h"
-#include "wps-display.h"
+#include "gwps.h"
#include "lang.h"
#include "language.h"
#include "screens.h"
@@ -273,6 +273,9 @@ int ft_load(struct tree_context* c, const char* tempdir)
(dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_M3U) ||
(*c->dirfilter == SHOW_SUPPORTED && !filetype_supported(dptr->attr)))) ||
(*c->dirfilter == SHOW_WPS && (dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_WPS) ||
+#ifdef HAVE_REMOTE_LCD
+ (*c->dirfilter == SHOW_RWPS && (dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_RWPS) ||
+#endif
(*c->dirfilter == SHOW_CFG && (dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_CFG) ||
(*c->dirfilter == SHOW_LNG && (dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_LNG) ||
(*c->dirfilter == SHOW_MOD && (dptr->attr & TREE_ATTR_MASK) != TREE_ATTR_MOD) ||
@@ -381,11 +384,20 @@ int ft_enter(struct tree_context* c)
/* wps config file */
case TREE_ATTR_WPS:
- wps_load(buf,true);
+ wps_data_load(gui_syncwps.gui_wps[0].data, buf, true, true);
set_file(buf, global_settings.wps_file,
MAX_FILENAME);
break;
+#ifdef HAVE_REMOTE_LCD
+ /* remote-wps config file */
+ case TREE_ATTR_RWPS:
+ wps_data_load(gui_syncwps.gui_wps[1].data, buf, true, true);
+ set_file(buf, global_settings.rwps_file,
+ MAX_FILENAME);
+ break;
+#endif
+
case TREE_ATTR_CFG:
if (!settings_load_config(buf))
break;
diff --git a/apps/gui/statusbar.c b/apps/gui/statusbar.c
index efc74d50af..d279c220cc 100644
--- a/apps/gui/statusbar.c
+++ b/apps/gui/statusbar.c
@@ -34,7 +34,7 @@
#include "led.h"
#include "status.h" /* needed for battery_state global var */
-#include "wps.h" /* for keys_locked */
+#include "gwps.h" /* for keys_locked */
#include "statusbar.h"
diff --git a/apps/lang/english.lang b/apps/lang/english.lang
index d601f7175e..469e4cb033 100644
--- a/apps/lang/english.lang
+++ b/apps/lang/english.lang
@@ -3437,3 +3437,15 @@ eng: "=== Please Wait ==="
voice:
new:
+id: VOICE_EXT_RWPS
+desc: spoken only, for file extension
+eng: ""
+voice: "remote while-playing-screen"
+new:
+
+id: LANG_REMOTE_WHILE_PLAYING
+desc: in settings_menu()
+eng: "Browse .rwps files"
+voice: "Browse remote while-playing-screen files"
+new:
+
diff --git a/apps/main.c b/apps/main.c
index ab802d5e24..d84aa25d0f 100644
--- a/apps/main.c
+++ b/apps/main.c
@@ -49,7 +49,7 @@
#include "sprintf.h"
#include "font.h"
#include "language.h"
-#include "wps-display.h"
+#include "gwps.h"
#include "playlist.h"
#include "buffer.h"
#include "rolo.h"
@@ -138,6 +138,8 @@ void init(void)
settings_reset();
settings_calc_config_sector();
settings_load(SETTINGS_ALL);
+ gui_sync_data_wps_init();
+ gui_sync_wps_init();
settings_apply();
init_dircache();
sleep(HZ/2);
@@ -295,7 +297,8 @@ void init(void)
settings_calc_config_sector();
settings_load(SETTINGS_ALL);
init_dircache();
-
+ gui_sync_data_wps_init();
+ gui_sync_wps_init();
settings_apply();
status_init();
diff --git a/apps/onplay.c b/apps/onplay.c
index 36ea95771a..704e0c04ec 100644
--- a/apps/onplay.c
+++ b/apps/onplay.c
@@ -46,7 +46,6 @@
#include "filetypes.h"
#include "plugin.h"
#include "bookmark.h"
-#include "wps.h"
#include "action.h"
#include "splash.h"
#ifdef HAVE_LCD_BITMAP
diff --git a/apps/playback.c b/apps/playback.c
index b68cb641fe..6a944c9dc8 100644
--- a/apps/playback.c
+++ b/apps/playback.c
@@ -34,8 +34,6 @@
#include "sprintf.h"
#include "settings.h"
#include "codecs.h"
-#include "wps.h"
-#include "wps-display.h"
#include "audio.h"
#include "logf.h"
#include "mp3_playback.h"
diff --git a/apps/recorder/peakmeter.c b/apps/recorder/peakmeter.c
index 2e4cea0704..a93e20ad0e 100644
--- a/apps/recorder/peakmeter.c
+++ b/apps/recorder/peakmeter.c
@@ -24,7 +24,7 @@
#include "ata.h"
#include "lcd.h"
#include "widgets.h"
-#include "wps-display.h"
+#include "gwps.h"
#include "sprintf.h"
#include "button.h"
#include "system.h"
diff --git a/apps/screen_access.c b/apps/screen_access.c
index dfaba4d0f2..b1ae9eb2b8 100644
--- a/apps/screen_access.c
+++ b/apps/screen_access.c
@@ -123,6 +123,8 @@ void screen_init(struct screen * screen, enum screen_type screen_type)
screen->height=2;
screen->double_height=&lcd_double_height;
screen->putc=&lcd_putc;
+ screen->get_locked_pattern=&lcd_get_locked_pattern;
+ screen->define_pattern=&lcd_define_pattern;
#ifdef SIMULATOR
screen->icon=&sim_lcd_icon;
#else
diff --git a/apps/screen_access.h b/apps/screen_access.h
index 6111de9de4..95ddcb9462 100644
--- a/apps/screen_access.h
+++ b/apps/screen_access.h
@@ -99,6 +99,8 @@ struct screen
void (*scroll_delay)(int ms);
void (*stop_scroll)(void);
void (*clear_display)(void);
+ unsigned char (*get_locked_pattern)(void);
+ void (*define_pattern)(int pat, const char *pattern);
#if defined(HAVE_LCD_BITMAP) || defined(SIMULATOR)
void (*update)(void);
#endif
diff --git a/apps/screens.c b/apps/screens.c
index 978d2a12f8..f861bb76c9 100644
--- a/apps/screens.c
+++ b/apps/screens.c
@@ -46,7 +46,7 @@
#include "led.h"
#include "sound.h"
#include "abrepeat.h"
-#include "wps-display.h"
+#include "gwps-common.h"
#include "splash.h"
#if defined(HAVE_LCD_BITMAP)
#include "widgets.h"
@@ -1226,7 +1226,7 @@ bool browse_id3(void)
line = draw_id3_item(line, top, LANG_ID3_YEAR, body);
- wps_format_time(buf, sizeof(buf), id3->length);
+ gui_wps_format_time(buf, sizeof(buf), id3->length);
line = draw_id3_item(line, top, LANG_ID3_LENGHT, buf);
snprintf(buf, sizeof(buf), "%d/%d", playlist_get_display_index(),
diff --git a/apps/settings.c b/apps/settings.c
index 63da47e34b..2e5014fce7 100644
--- a/apps/settings.c
+++ b/apps/settings.c
@@ -59,7 +59,7 @@
#endif
#include "lang.h"
#include "language.h"
-#include "wps-display.h"
+#include "gwps.h"
#include "powermgmt.h"
#include "bookmark.h"
#include "sprintf.h"
@@ -85,7 +85,7 @@ const char rec_base_directory[] = REC_BASE_DIR;
#include "dsp.h"
#endif
-#define CONFIG_BLOCK_VERSION 31
+#define CONFIG_BLOCK_VERSION 32
#define CONFIG_BLOCK_SIZE 512
#define RTC_BLOCK_SIZE 44
@@ -758,10 +758,16 @@ int settings_save( void )
strncpy(&config_block[0xb8], global_settings.wps_file, MAX_FILENAME);
strncpy(&config_block[0xcc], global_settings.lang_file, MAX_FILENAME);
strncpy(&config_block[0xe0], global_settings.font_file, MAX_FILENAME);
+#ifdef HAVE_REMOTE_LCD
+ strncpy(&config_block[0xf4], global_settings.rwps_file, MAX_FILENAME);
+#endif
if(save_config_buffer())
{
lcd_clear_display();
+#ifdef HAVE_REMOTE_LCD
+ lcd_remote_clear_display();
+#endif
#ifdef HAVE_LCD_CHARCELLS
lcd_puts(0, 0, str(LANG_SETTINGS_SAVE_PLAYER));
lcd_puts(0, 1, str(LANG_SETTINGS_BATTERY_PLAYER));
@@ -769,6 +775,11 @@ int settings_save( void )
lcd_puts(4, 2, str(LANG_SETTINGS_SAVE_RECORDER));
lcd_puts(2, 4, str(LANG_SETTINGS_BATTERY_RECORDER));
lcd_update();
+#ifdef HAVE_REMOTE_LCD
+ lcd_remote_puts(4, 2, str(LANG_SETTINGS_SAVE_RECORDER));
+ lcd_remote_puts(2, 4, str(LANG_SETTINGS_BATTERY_RECORDER));
+ lcd_remote_update();
+#endif
#endif
sleep(HZ*2);
return -1;
@@ -879,10 +890,21 @@ void settings_apply(void)
global_settings.wps_file[0] != 0xff ) {
snprintf(buf, sizeof buf, WPS_DIR "/%s.wps",
global_settings.wps_file);
- wps_load(buf, false);
+ wps_data_load(gui_syncwps.gui_wps[0].data, buf, true, false);
}
else
- wps_reset();
+ wps_data_init(gui_syncwps.gui_wps[0].data);
+
+#ifdef HAVE_REMOTE_LCD
+ if ( global_settings.rwps_file[0] &&
+ global_settings.rwps_file[0] != 0xff ) {
+ snprintf(buf, sizeof buf, WPS_DIR "/%s.rwps",
+ global_settings.rwps_file);
+ wps_data_load(gui_syncwps.gui_wps[1].data, buf, true, false);
+ }
+ else
+ wps_data_init(gui_syncwps.gui_wps[1].data);
+#endif
#ifdef HAVE_LCD_BITMAP
if ( global_settings.font_file[0] &&
@@ -1003,6 +1025,9 @@ void settings_load(int which)
strncpy(global_settings.wps_file, &config_block[0xb8], MAX_FILENAME);
strncpy(global_settings.lang_file, &config_block[0xcc], MAX_FILENAME);
strncpy(global_settings.font_file, &config_block[0xe0], MAX_FILENAME);
+#ifdef HAVE_REMOTE_LCD
+ strncpy(global_settings.rwps_file, &config_block[0xf4], MAX_FILENAME);
+#endif
}
}
@@ -1141,9 +1166,15 @@ bool settings_load_config(const char* file)
/* check for the string values */
if (!strcasecmp(name, "wps")) {
- if (wps_load(value,false))
+ if (wps_data_load(gui_syncwps.gui_wps[0].data,value,true, false))
set_file(value, global_settings.wps_file, MAX_FILENAME);
}
+#ifdef HAVE_REMOTE_LCD
+ else if (!strcasecmp(name, "rwps")) {
+ if (wps_data_load(gui_syncwps.gui_wps[1].data,value,true, false))
+ set_file(value, global_settings.rwps_file, MAX_FILENAME);
+ }
+#endif
else if (!strcasecmp(name, "lang")) {
if (!lang_load(value))
{
@@ -1283,6 +1314,12 @@ bool settings_save_config(void)
fdprintf(fd, "wps: %s/%s.wps\r\n", WPS_DIR,
global_settings.wps_file);
+#ifdef HAVE_REMOTE_LCD
+ if (global_settings.rwps_file[0] != 0)
+ fdprintf(fd, "rwps: %s/%s.rwps\r\n", WPS_DIR,
+ global_settings.rwps_file);
+#endif
+
if (global_settings.lang_file[0] != 0)
fdprintf(fd, "lang: %s/%s.lng\r\n", ROCKBOX_DIR LANG_DIR,
global_settings.lang_file);
@@ -1365,6 +1402,9 @@ void settings_reset(void) {
#endif
global_settings.contrast = lcd_default_contrast();
global_settings.wps_file[0] = '\0';
+#ifdef HAVE_REMOTE_LCD
+ global_settings.rwps_file[0] = '\0';
+#endif
global_settings.font_file[0] = '\0';
global_settings.lang_file[0] = '\0';
diff --git a/apps/settings.h b/apps/settings.h
index 50f38cab50..20b0408dfd 100644
--- a/apps/settings.h
+++ b/apps/settings.h
@@ -359,6 +359,9 @@ struct user_settings
bool dircache; /* enable directory cache */
int dircache_size; /* directory cache structure last size, 22 bits */
#endif
+#ifdef HAVE_REMOTE_LCD
+ unsigned char rwps_file[MAX_FILENAME+1]; /* last remote-wps */
+#endif
};
enum optiontype { INT, BOOL };
@@ -443,7 +446,7 @@ enum
* must be added after NUM_FILTER_MODES. */
enum { SHOW_ALL, SHOW_SUPPORTED, SHOW_MUSIC, SHOW_PLAYLIST, SHOW_ID3DB,
NUM_FILTER_MODES,
- SHOW_WPS, SHOW_CFG, SHOW_LNG, SHOW_MOD, SHOW_FONT, SHOW_PLUGINS};
+ SHOW_WPS, SHOW_RWPS, SHOW_CFG, SHOW_LNG, SHOW_MOD, SHOW_FONT, SHOW_PLUGINS};
/* recursive dir insert options */
enum { RECURSE_OFF, RECURSE_ON, RECURSE_ASK };
diff --git a/apps/settings_menu.c b/apps/settings_menu.c
index 4aea853f82..8695177a00 100644
--- a/apps/settings_menu.c
+++ b/apps/settings_menu.c
@@ -996,6 +996,13 @@ static bool custom_wps_browse(void)
return rockbox_browse(WPS_DIR, SHOW_WPS);
}
+#ifdef HAVE_REMOTE_LCD
+static bool custom_remote_wps_browse(void)
+{
+ return rockbox_browse(WPS_DIR, SHOW_RWPS);
+}
+#endif
+
static bool custom_cfg_browse(void)
{
return rockbox_browse(ROCKBOX_DIR, SHOW_CFG);
@@ -1602,6 +1609,9 @@ static bool display_settings_menu(void)
{ ID2P(LANG_CUSTOM_FONT), font_browse },
#endif
{ ID2P(LANG_WHILE_PLAYING), custom_wps_browse },
+#ifdef HAVE_REMOTE_LCD
+ { ID2P(LANG_REMOTE_WHILE_PLAYING), custom_remote_wps_browse },
+#endif
{ ID2P(LANG_LCD_MENU), lcd_settings_menu },
#ifdef HAVE_REMOTE_LCD
{ ID2P(LANG_LCD_REMOTE_MENU), lcd_remote_settings_menu },
diff --git a/apps/status.c b/apps/status.c
index 9f43c6551d..978341d1db 100644
--- a/apps/status.c
+++ b/apps/status.c
@@ -26,7 +26,7 @@
#include "status.h"
#include "mp3_playback.h"
#include "audio.h"
-#include "wps.h"
+#include "gwps.h"
#include "abrepeat.h"
#ifdef HAVE_RTC
#include "timefuncs.h"
diff --git a/apps/tree.c b/apps/tree.c
index bfeac6c545..39980b1b81 100644
--- a/apps/tree.c
+++ b/apps/tree.c
@@ -36,8 +36,7 @@
#include "audio.h"
#include "playlist.h"
#include "menu.h"
-#include "wps.h"
-#include "wps-display.h"
+#include "gwps.h"
#include "settings.h"
#include "status.h"
#include "debug.h"
@@ -97,6 +96,9 @@ const struct filetype filetypes[] = {
{ "m3u", TREE_ATTR_M3U, Icon_Playlist, LANG_PLAYLIST },
{ "cfg", TREE_ATTR_CFG, Icon_Config, VOICE_EXT_CFG },
{ "wps", TREE_ATTR_WPS, Icon_Wps, VOICE_EXT_WPS },
+#ifdef HAVE_REMOTE_LCD
+ { "rwps", TREE_ATTR_RWPS, Icon_Wps, VOICE_EXT_RWPS },
+#endif
{ "lng", TREE_ATTR_LNG, Icon_Language, LANG_LANGUAGE },
{ "rock",TREE_ATTR_ROCK,Icon_Plugin, VOICE_EXT_ROCK },
#ifdef HAVE_LCD_BITMAP
@@ -212,6 +214,7 @@ void browse_root(void)
{
/* essential to all programs that wants to display things */
screen_access_init();
+ gui_sync_wps_screen_init();
filetype_init();
check_rockboxdir();
@@ -885,7 +888,7 @@ static bool dirbrowse(void)
int i;
FOR_NB_SCREENS(i)
screens[i].stop_scroll();
- if (wps_show() == SYS_USB_CONNECTED)
+ if (gui_wps_show() == SYS_USB_CONNECTED)
reload_dir = true;
#ifdef HAVE_HOTSWAP
else
diff --git a/apps/tree.h b/apps/tree.h
index 86e95931d1..55dfc562b9 100644
--- a/apps/tree.h
+++ b/apps/tree.h
@@ -213,6 +213,7 @@ struct tree_context {
#define TREE_ATTR_LNG 0x0700 /* binary lang file */
#define TREE_ATTR_ROCK 0x0800 /* binary rockbox plugin */
#define TREE_ATTR_MOD 0x0900 /* firmware file */
+#define TREE_ATTR_RWPS 0x1000 /* remote-wps config file */
#define TREE_ATTR_MASK 0xFF00 /* which bits tree.c uses for file types */
void tree_get_filetypes(const struct filetype**, int*);
diff --git a/apps/wps-display.c b/apps/wps-display.c
deleted file mode 100644
index 58a953e4c0..0000000000
--- a/apps/wps-display.c
+++ /dev/null
@@ -1,1841 +0,0 @@
-/***************************************************************************
- * __________ __ ___.
- * Open \______ \ ____ ____ | | _\_ |__ _______ ___
- * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
- * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
- * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
- * \/ \/ \/ \/ \/
- * $Id$
- *
- * Copyright (C) 2002 Björn Stenberg
- *
- * All files in this archive are subject to the GNU General Public License.
- * See the file COPYING in the source tree root for full license agreement.
- *
- * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
- * KIND, either express or implied.
- *
- ****************************************************************************/
-
-/* ID3 formatting based on code from the MAD Winamp plugin (in_mad.dll),
- * Copyright (C) 2000-2001 Robert Leslie.
- * See http://www.mars.org/home/rob/proj/mpeg/ for more information.
- */
-
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-
-#include "lcd.h"
-#include "hwcompat.h"
-#include "font.h"
-#include "audio.h"
-#include "id3.h"
-#include "settings.h"
-#include "playlist.h"
-#include "kernel.h"
-#include "system.h"
-#include "status.h"
-#include "wps-display.h"
-#include "debug.h"
-#include "mas.h"
-#include "lang.h"
-#include "powermgmt.h"
-#include "power.h"
-#include "sprintf.h"
-#include "backlight.h"
-#include "button.h"
-#include "abrepeat.h"
-#include "screens.h"
-#include "splash.h"
-#ifdef HAVE_LCD_BITMAP
-#include <ctype.h>
-#include "icons.h"
-#include "widgets.h"
-#include "peakmeter.h"
-
-/* Image stuff */
-#include "bmp.h"
-#include "atoi.h"
-#define MAX_IMAGES (26*2) /* a-z and A-Z */
-#define IMG_BUFSIZE (LCD_HEIGHT * LCD_WIDTH * MAX_IMAGES / 25 ) / 8
-static unsigned char img_buf[IMG_BUFSIZE]; /* image buffer */
-static unsigned char* img_buf_ptr = img_buf; /* where are in image buffer? */
-
-static int img_buf_free = IMG_BUFSIZE; /* free space in image buffer */
-
-struct {
- unsigned char* ptr; /* pointer */
- int x; /* x-pos */
- int y; /* y-pos */
- int w; /* width */
- int h; /* height */
- bool loaded; /* load state */
- bool display; /* is to be displayed */
- bool always_display; /* not using the preload/display mechanism */
-} img[MAX_IMAGES] ;
-
-
-#endif
-
-#define WPS_DEFAULTCFG WPS_DIR "/rockbox_default.wps"
-
-#ifdef HAVE_LCD_BITMAP
-#define MAX_LINES (LCD_HEIGHT/5+1)
-#define FORMAT_BUFFER_SIZE 3072
-#else
-#define MAX_LINES 2
-#define FORMAT_BUFFER_SIZE 400
-#endif
-#define MAX_SUBLINES 12
-#define DEFAULT_SUBLINE_TIME_MULTIPLIER 20 /* (10ths of sec) */
-#define BASE_SUBLINE_TIME 10 /* base time that multiplier is applied to
- (1/HZ sec, or 100ths of sec) */
-#define SUBLINE_RESET -1
-
-#ifdef HAVE_LCD_CHARCELLS
-static unsigned char wps_progress_pat[8]={0,0,0,0,0,0,0,0};
-static bool full_line_progressbar=0;
-static bool draw_player_progress(const struct mp3entry* id3,
- int ff_rewwind_count);
-static void draw_player_fullbar(char* buf, int buf_size,
- const struct mp3entry* id3,
- int ff_rewwind_count);
-static char map_fullbar_char(char ascii_val);
-#endif
-
-struct align_pos {
- char* left;
- char* center;
- char* right;
-};
-static char format_buffer[FORMAT_BUFFER_SIZE];
-static char* format_lines[MAX_LINES][MAX_SUBLINES];
-static struct align_pos format_align[MAX_LINES][MAX_SUBLINES];
-static unsigned char line_type[MAX_LINES][MAX_SUBLINES];
-static unsigned short time_mult[MAX_LINES][MAX_SUBLINES];
-static long subline_expire_time[MAX_LINES];
-static int curr_subline[MAX_LINES];
-
-static int ff_rewind_count;
-bool wps_time_countup = true;
-static bool wps_loaded = false;
-
-#ifdef HAVE_LCD_BITMAP
-/* Display images */
-static void wps_display_images(void) {
- int n;
- for (n = 0; n < MAX_IMAGES; n++) {
- if (img[n].loaded && img[n].display) {
- if(img[n].always_display)
- lcd_set_drawmode(DRMODE_FG);
- else
- lcd_set_drawmode(DRMODE_SOLID);
-
- lcd_mono_bitmap(img[n].ptr, img[n].x, img[n].y, img[n].w, img[n].h);
- lcd_update_rect(img[n].x, img[n].y, img[n].w, img[n].h);
- }
- }
- lcd_set_drawmode(DRMODE_SOLID);
-}
-#endif
-
-/* Set format string to use for WPS, splitting it into lines */
-static void wps_format(const char* fmt, char *bmpdir, size_t bmpdirlen)
-{
- char* buf = format_buffer;
- char* start_of_line = format_buffer;
- int line = 0;
- int subline;
-#ifndef HAVE_LCD_BITMAP
- /* no bitmap lcd == no bitmap loading */
- (void)bmpdir;
- (void)bmpdirlen;
-#endif
-
- strncpy(format_buffer, fmt, sizeof(format_buffer));
- format_buffer[sizeof(format_buffer) - 1] = 0;
-
- for (line=0; line<MAX_LINES; line++)
- {
- for (subline=0; subline<MAX_SUBLINES; subline++)
- {
- format_lines[line][subline] = 0;
- time_mult[line][subline] = 0;
- }
- subline_expire_time[line] = 0;
- curr_subline[line] = SUBLINE_RESET;
- }
-
- line = 0;
- subline = 0;
- format_lines[line][subline] = buf;
-
- while ((*buf) && (line < MAX_LINES))
- {
- switch (*buf)
- {
- /*
- * skip % sequences so "%;" doesn't start a new subline
- * don't skip %x lines (pre-load bitmaps)
- */
- case '%':
- if (*(buf+1) != 'x')
- buf++;
- break;
-
- case '\r': /* CR */
- *buf = 0;
- break;
-
- case '\n': /* LF */
- *buf = 0;
-
- if (*start_of_line != '#') /* A comment? */
- line++;
-
- if (line < MAX_LINES)
- {
- /* the next line starts on the next byte */
- subline = 0;
- format_lines[line][subline] = buf+1;
- start_of_line = format_lines[line][subline];
- }
- break;
-
- case ';': /* start a new subline */
- *buf = 0;
- subline++;
- if (subline < MAX_SUBLINES)
- {
- format_lines[line][subline] = buf+1;
- }
- else /* exceeded max sublines, skip rest of line */
- {
- while (*(++buf))
- {
- if ((*buf == '\r') || (*buf == '\n'))
- {
- break;
- }
- }
- buf--;
- subline = 0;
- }
- break;
-
- case 'x':
-#ifdef HAVE_LCD_BITMAP
- /* Preload images so the %xd# tag can display it */
- {
- int ret = 0;
- int n;
- char *ptr = buf+1;
- char *pos = NULL;
- char imgname[MAX_PATH];
- char qual = *ptr;
- if (qual == 'l' || qual == '|') /* format:
- %x|n|filename.bmp|x|y|
- or
- %xl|n|filename.bmp|x|y|
- */
- {
- ptr = strchr(ptr, '|') + 1;
- pos = strchr(ptr, '|');
- if (pos)
- {
- /* get the image ID */
- n = *ptr;
- if(n >= 'a' && n <= 'z')
- n -= 'a';
- if(n >= 'A' && n <= 'Z')
- n = n - 'A' + 26;
-
- if(n < 0 || n >= MAX_IMAGES)
- {
- /* Skip the rest of the line */
- while(*buf != '\n')
- buf++;
- break;
- }
- ptr = pos+1;
-
- /* check the image number and load state */
- if (!img[n].loaded)
- {
- /* get filename */
- pos = strchr(ptr, '|');
- if ((pos - ptr) <
- (int)sizeof(imgname)-ROCKBOX_DIR_LEN-2)
- {
- memcpy(imgname, bmpdir, bmpdirlen);
- imgname[bmpdirlen] = '/';
- memcpy(&imgname[bmpdirlen+1],
- ptr, pos - ptr);
- imgname[bmpdirlen+1+pos-ptr] = 0;
- }
- else
- /* filename too long */
- imgname[0] = 0;
-
- ptr = pos+1;
-
- /* get x-position */
- pos = strchr(ptr, '|');
- if (pos)
- img[n].x = atoi(ptr);
- else
- {
- /* weird syntax, bail out */
- buf++;
- break;
- }
-
- /* get y-position */
- ptr = pos+1;
- pos = strchr(ptr, '|');
- if (pos)
- img[n].y = atoi(ptr);
- else
- {
- /* weird syntax, bail out */
- buf++;
- break;
- }
-
- pos++;
-
- /* reposition buf pointer to next WPS element */
- while (*pos && *pos != ';' &&
- *pos != '\r' && *pos != '\n')
- pos++;
-
- buf = pos;
-
- /* load the image */
- ret = read_bmp_file(imgname, &img[n].w, &img[n].h,
- img_buf_ptr, img_buf_free);
- if (ret > 0)
- {
- img[n].ptr = img_buf_ptr;
- img_buf_ptr += ret;
- img_buf_free -= ret;
- img[n].loaded = true;
- if(qual == '|')
- img[n].always_display = true;
- }
- }
- buf++;
- }
- }
- }
-#endif
- break;
- }
- buf++;
- }
-}
-
-/* Clear the WPS image cache */
-static void wps_clear(void)
-{
-#ifdef HAVE_LCD_BITMAP
- int i;
-
- /* reset image buffer */
- img_buf_ptr = img_buf;
- img_buf_free = IMG_BUFSIZE;
-
- /* set images to unloaded and not displayed */
- for (i = 0; i < MAX_IMAGES; i++) {
- img[i].loaded = false;
- img[i].display = false;
- img[i].always_display = false;
- }
-#endif
-
-}
-
-void wps_reset(void)
-{
- wps_loaded = false;
- memset(&format_buffer, 0, sizeof format_buffer);
- wps_clear();
-}
-
-bool wps_load(const char* file, bool display)
-{
- int i,s;
- char buffer[FORMAT_BUFFER_SIZE];
- int fd;
- size_t bmpdirlen;
-
- char *bmpdir = strrchr(file, '.');
- bmpdirlen = bmpdir - file;
-
- /*
- * Hardcode loading WPS_DEFAULTCFG to cause a reset ideally this
- * wants to be a virtual file. Feel free to modify dirbrowse()
- * if you're feeling brave.
- */
- if (! strcmp(file, WPS_DEFAULTCFG) ) {
- wps_reset();
- return(false);
- }
-
- fd = open(file, O_RDONLY);
-
- if (fd >= 0)
- {
- int numread = read(fd, buffer, sizeof(buffer) - 1);
-
- if (numread > 0)
- {
- wps_clear();
- buffer[numread] = 0;
- wps_format(buffer, (char *)file, bmpdirlen);
- }
-
- close(fd);
-
- if ( display ) {
- bool any_defined_line;
- lcd_clear_display();
-#ifdef HAVE_LCD_BITMAP
- lcd_setmargins(0,0);
-#endif
- for (s=0; s<MAX_SUBLINES; s++)
- {
- any_defined_line = false;
- for (i=0; i<MAX_LINES; i++)
- {
- if (format_lines[i][s])
- {
- if (*format_lines[i][s] == 0)
- lcd_puts(0,i," ");
- else
- lcd_puts(0,i,format_lines[i][s]);
- any_defined_line = true;
- }
- else
- {
- lcd_puts(0,i," ");
- }
- }
- if (any_defined_line)
- {
-#ifdef HAVE_LCD_BITMAP
- wps_display_images();
-#endif
- lcd_update();
- sleep(HZ/2);
- }
- }
- }
- wps_loaded = true;
-
- return numread > 0;
- }
-
- return false;
-}
-
-/* Format time into buf.
- *
- * buf - buffer to format to.
- * buf_size - size of buffer.
- * time - time to format, in milliseconds.
- */
-void wps_format_time(char* buf, int buf_size, long time)
-{
- if ( time < 3600000 ) {
- snprintf(buf, buf_size, "%d:%02d",
- (int) (time % 3600000 / 60000), (int) (time % 60000 / 1000));
- } else {
- snprintf(buf, buf_size, "%d:%02d:%02d",
- (int) (time / 3600000), (int) (time % 3600000 / 60000),
- (int) (time % 60000 / 1000));
- }
-}
-
-/* Extract a part from a path.
- *
- * buf - buffer extract part to.
- * buf_size - size of buffer.
- * path - path to extract from.
- * level - what to extract. 0 is file name, 1 is parent of file, 2 is
- * parent of parent, etc.
- *
- * Returns buf if the desired level was found, NULL otherwise.
- */
-static char* get_dir(char* buf, int buf_size, const char* path, int level)
-{
- const char* sep;
- const char* last_sep;
- int len;
-
- sep = path + strlen(path);
- last_sep = sep;
-
- while (sep > path)
- {
- if ('/' == *(--sep))
- {
- if (!level)
- {
- break;
- }
-
- level--;
- last_sep = sep - 1;
- }
- }
-
- if (level || (last_sep <= sep))
- {
- return NULL;
- }
-
- len = MIN(last_sep - sep, buf_size - 1);
- strncpy(buf, sep + 1, len);
- buf[len] = 0;
- return buf;
-}
-
-/* Get the tag specified by the two characters at fmt.
- *
- * cid3 - ID3 data to get tag values from.
- * nid3 - next-song ID3 data to get tag values from.
- * tag - string (of two characters) specifying the tag to get.
- * buf - buffer to certain tags, such as track number, play time or
- * directory name.
- * buf_size - size of buffer.
- * flags - returns the type of the line. See constants i wps-display.h
- *
- * Returns the tag. NULL indicates the tag wasn't available.
- */
-static char* get_tag(struct mp3entry* cid3,
- struct mp3entry* nid3,
- const char* tag,
- char* buf,
- int buf_size,
- unsigned char* tag_len,
- unsigned short* subline_time_mult,
- unsigned char* flags,
- int *intval)
-{
- struct mp3entry *id3 = cid3; /* default to current song */
-
- if ((0 == tag[0]) || (0 == tag[1]))
- {
- *tag_len = 0;
- return NULL;
- }
-
- *tag_len = 2;
-
- *intval = 0;
-
- switch (tag[0])
- {
- case 'I': /* ID3 Information */
- id3 = nid3; /* display next-song data */
- *flags |= WPS_REFRESH_DYNAMIC;
- if(!id3)
- return NULL; /* no such info (yet) */
- /* fall-through */
- case 'i': /* ID3 Information */
- *flags |= WPS_REFRESH_STATIC;
- switch (tag[1])
- {
- case 't': /* ID3 Title */
- return id3->title;
-
- case 'a': /* ID3 Artist */
- return id3->artist;
-
- case 'n': /* ID3 Track Number */
- if (id3->track_string)
- return id3->track_string;
-
- if (id3->tracknum) {
- snprintf(buf, buf_size, "%d", id3->tracknum);
- return buf;
- }
- return NULL;
-
- case 'd': /* ID3 Album/Disc */
- return id3->album;
-
- case 'c': /* ID3 Composer */
- return id3->composer;
-
- case 'y': /* year */
- if( id3->year_string )
- return id3->year_string;
-
- if (id3->year) {
- snprintf(buf, buf_size, "%d", id3->year);
- return buf;
- }
- return NULL;
-
- case 'g': /* genre */
- return id3_get_genre(id3);
-
- case 'v': /* id3 version */
- switch (id3->id3version) {
- case ID3_VER_1_0:
- return "1";
-
- case ID3_VER_1_1:
- return "1.1";
-
- case ID3_VER_2_2:
- return "2.2";
-
- case ID3_VER_2_3:
- return "2.3";
-
- case ID3_VER_2_4:
- return "2.4";
-
- default:
- return NULL;
- }
- }
- break;
-
- case 'F': /* File Information */
- id3 = nid3;
- *flags |= WPS_REFRESH_DYNAMIC;
- if(!id3)
- return NULL; /* no such info (yet) */
- /* fall-through */
- case 'f': /* File Information */
- *flags |= WPS_REFRESH_STATIC;
- switch(tag[1])
- {
- case 'v': /* VBR file? */
- return id3->vbr ? "(avg)" : NULL;
-
- case 'b': /* File Bitrate */
- if(id3->bitrate)
- snprintf(buf, buf_size, "%d", id3->bitrate);
- else
- snprintf(buf, buf_size, "?");
- return buf;
-
- case 'f': /* File Frequency */
- snprintf(buf, buf_size, "%ld", id3->frequency);
- return buf;
-
- case 'p': /* File Path */
- return id3->path;
-
- case 'm': /* File Name - With Extension */
- return get_dir(buf, buf_size, id3->path, 0);
-
- case 'n': /* File Name */
- if (get_dir(buf, buf_size, id3->path, 0))
- {
- /* Remove extension */
- char* sep = strrchr(buf, '.');
-
- if (NULL != sep)
- {
- *sep = 0;
- }
-
- return buf;
- }
- else
- {
- return NULL;
- }
-
- case 's': /* File Size (in kilobytes) */
- snprintf(buf, buf_size, "%ld", id3->filesize / 1024);
- return buf;
-
- case 'c': /* File Codec */
- if(id3->codectype == AFMT_UNKNOWN)
- *intval = AFMT_NUM_CODECS;
- else
- *intval = id3->codectype;
- return id3_get_codec(id3);
- }
- break;
-
- case 'p': /* Playlist/Song Information */
- switch(tag[1])
- {
- case 'b': /* progress bar */
- *flags |= WPS_REFRESH_PLAYER_PROGRESS;
-#ifdef HAVE_LCD_CHARCELLS
- snprintf(buf, buf_size, "%c", wps_progress_pat[0]);
- full_line_progressbar=0;
- return buf;
-#else
- return "\x01";
-#endif
- case 'f': /* full-line progress bar */
-#ifdef HAVE_LCD_CHARCELLS
- if(is_new_player()) {
- *flags |= WPS_REFRESH_PLAYER_PROGRESS;
- *flags |= WPS_REFRESH_DYNAMIC;
- full_line_progressbar=1;
- /* we need 11 characters (full line) for
- progress-bar */
- snprintf(buf, buf_size, " ");
- }
- else
- {
- /* Tell the user if we have an OldPlayer */
- snprintf(buf, buf_size, " <Old LCD> ");
- }
- return buf;
-#endif
- case 'p': /* Playlist Position */
- *flags |= WPS_REFRESH_STATIC;
- snprintf(buf, buf_size, "%d", playlist_get_display_index());
- return buf;
-
- case 'n': /* Playlist Name (without path) */
- *flags |= WPS_REFRESH_STATIC;
- return playlist_name(NULL, buf, buf_size);
-
- case 'e': /* Playlist Total Entries */
- *flags |= WPS_REFRESH_STATIC;
- snprintf(buf, buf_size, "%d", playlist_amount());
- return buf;
-
- case 'c': /* Current Time in Song */
- *flags |= WPS_REFRESH_DYNAMIC;
- wps_format_time(buf, buf_size,
- id3->elapsed + ff_rewind_count);
- return buf;
-
- case 'r': /* Remaining Time in Song */
- *flags |= WPS_REFRESH_DYNAMIC;
- wps_format_time(buf, buf_size,
- id3->length - id3->elapsed - ff_rewind_count);
- return buf;
-
- case 't': /* Total Time */
- *flags |= WPS_REFRESH_STATIC;
- wps_format_time(buf, buf_size, id3->length);
- return buf;
-
-#ifdef HAVE_LCD_BITMAP
- case 'm': /* Peak Meter */
- *flags |= WPS_REFRESH_PEAK_METER;
- return "\x01";
-#endif
- case 's': /* shuffle */
- *flags |= WPS_REFRESH_DYNAMIC;
- if ( global_settings.playlist_shuffle )
- return "s";
- else
- return NULL;
- break;
-
- case 'v': /* volume */
- *flags |= WPS_REFRESH_DYNAMIC;
- snprintf(buf, buf_size, "%d%%", global_settings.volume);
- *intval = global_settings.volume / 10 + 1;
- return buf;
-
- }
- break;
-
- case 'm':
- switch (tag[1])
- {
- case 'm': /* playback repeat mode */
- *flags |= WPS_REFRESH_DYNAMIC;
- *intval = global_settings.repeat_mode + 1;
- snprintf(buf, buf_size, "%d", *intval);
- return buf;
-
- /* playback status */
- case 'p': /* play */
- *flags |= WPS_REFRESH_DYNAMIC;
- int status = audio_status();
- *intval = 1;
- if (status == AUDIO_STATUS_PLAY && \
- !(status & AUDIO_STATUS_PAUSE))
- *intval = 2;
- if (audio_status() & AUDIO_STATUS_PAUSE && \
- (! status_get_ffmode()))
- *intval = 3;
- if (status_get_ffmode() == STATUS_FASTFORWARD)
- *intval = 4;
- if (status_get_ffmode() == STATUS_FASTBACKWARD)
- *intval = 5;
- snprintf(buf, buf_size, "%d", *intval);
- return buf;
-
-#if CONFIG_KEYPAD == IRIVER_H100_PAD
- case 'h': /* hold */
- *flags |= WPS_REFRESH_DYNAMIC;
- if (button_hold())
- return "h";
- else
- return NULL;
- case 'r': /* remote hold */
- *flags |= WPS_REFRESH_DYNAMIC;
- if (remote_button_hold())
- return "r";
- else
- return NULL;
-#endif
- }
- break;
-
- case 'b': /* battery info */
- *flags |= WPS_REFRESH_DYNAMIC;
- switch (tag[1]) {
- case 'l': /* battery level */
- {
- int l = battery_level();
- if (l > -1)
- {
- snprintf(buf, buf_size, "%d%%", l);
- *intval = l / 20 + 1;
- }
- else
- {
- *intval = 6;
- return "?%";
- }
- return buf;
- }
-
- case 't': /* estimated battery time */
- {
- int t = battery_time();
- if (t >= 0)
- snprintf(buf, buf_size, "%dh %dm", t / 60, t % 60);
- else
- strncpy(buf, "?h ?m", buf_size);
- return buf;
- }
-
- case 'p': /* External power plugged in? */
- {
- if(charger_inserted())
- return "p";
- else
- return NULL;
- }
- }
- break;
-
- case 'D': /* Directory path information */
- id3 = nid3; /* next song please! */
- *flags |= WPS_REFRESH_DYNAMIC;
- if(!id3)
- return NULL; /* no such info (yet) */
- /* fall-through */
- case 'd': /* Directory path information */
- {
- int level = tag[1] - '0';
- *flags |= WPS_REFRESH_STATIC;
- /* d1 through d9 */
- if ((0 < level) && (9 > level))
- {
- return get_dir(buf, buf_size, id3->path, level);
- }
- }
- break;
-
- case 't': /* set sub line time multiplier */
- {
- int d = 1;
- int time_mult = 0;
- bool have_point = false;
- bool have_tenth = false;
-
- while (((tag[d] >= '0') &&
- (tag[d] <= '9')) ||
- (tag[d] == '.'))
- {
- if (tag[d] != '.')
- {
- time_mult = time_mult * 10;
- time_mult = time_mult + tag[d] - '0';
- if (have_point)
- {
- have_tenth = true;
- d++;
- break;
- }
- }
- else
- {
- have_point = true;
- }
- d++;
- }
-
- if (have_tenth == false)
- time_mult *= 10;
-
- *subline_time_mult = time_mult;
- *tag_len = d;
-
- buf[0] = 0;
- return buf;
- }
- break;
- case 'r': /* Runtime database Information */
- switch(tag[1])
- {
- case 'p': /* Playcount */
- *flags |= WPS_REFRESH_STATIC;
- snprintf(buf, buf_size, "%ld", cid3->playcount);
- return buf;
- case 'r': /* Rating */
- *flags |= WPS_REFRESH_STATIC;
- *intval = cid3->rating+1;
- snprintf(buf, buf_size, "%d", cid3->rating);
- return buf;
- }
- break;
- }
- return NULL;
-}
-
-/* Skip to the end of the current %? conditional.
- *
- * fmt - string to skip it. Should point to somewhere after the leading
- * "<" char (and before or at the last ">").
- * num - number of |'s to skip, or 0 to skip to the end (the ">").
- *
- * Returns the new position in fmt.
- */
-static const char* skip_conditional(const char* fmt, int num)
-{
- int level = 1;
- int count = num;
- const char *last_alternative = NULL;
-
- while (*fmt)
- {
- switch (*fmt++)
- {
- case '%':
- break;
-
- case '|':
- if(1 == level) {
- last_alternative = fmt;
- if(num) {
- count--;
- if(count == 0)
- return fmt;
- continue;
- }
- }
- continue;
-
- case '>':
- if (0 == --level)
- {
- /* We're just skipping to the end */
- if(num == 0)
- return fmt;
-
- /* If we are parsing an enum, we'll return the selected
- item. If there weren't enough items in the enum, we'll
- return the last one found. */
- if(count && last_alternative)
- {
- return last_alternative;
- }
- return fmt - 1;
- }
- continue;
-
- default:
- continue;
- }
-
- switch (*fmt++)
- {
- case 0:
- case '%':
- case '|':
- case '<':
- case '>':
- break;
-
- case '?':
- while (*fmt && ('<' != *fmt))
- fmt++;
-
- if ('<' == *fmt)
- fmt++;
-
- level++;
- break;
-
- default:
- break;
- }
- }
-
- return fmt;
-}
-
-/* Generate the display based on id3 information and format string.
- *
- * buf - char buffer to write the display to.
- * buf_size - the size of buffer.
- * id3 - the ID3 data to format with.
- * nid3 - the ID3 data of the next song (might by NULL)
- * fmt - format description.
- * flags - returns the type of the line. See constants i wps-display.h
- */
-static void format_display(char* buf,
- int buf_size,
- struct mp3entry* id3,
- struct mp3entry* nid3, /* next song's id3 */
- const char* fmt,
- struct align_pos* align,
- unsigned short* subline_time_mult,
- unsigned char* flags)
-{
- char temp_buf[128];
- char* buf_start = buf;
- char* buf_end = buf + buf_size - 1; /* Leave room for end null */
- char* value = NULL;
- int level = 0;
- unsigned char tag_length;
- int intval;
- int cur_align;
- char* cur_align_start;
-#ifdef HAVE_LCD_BITMAP
- int n;
-#endif
-
- cur_align_start = buf;
- cur_align = WPS_ALIGN_LEFT;
- *subline_time_mult = DEFAULT_SUBLINE_TIME_MULTIPLIER;
-
- align->left = 0;
- align->center = 0;
- align->right = 0;
-
- while (fmt && *fmt && buf < buf_end)
- {
- switch (*fmt)
- {
- case '%':
- ++fmt;
- break;
-
- case '|':
- case '>':
- if (level > 0)
- {
- fmt = skip_conditional(fmt, 0);
- level--;
- continue;
- }
- /* Else fall through */
-
- default:
- *buf++ = *fmt++;
- continue;
- }
-
- switch (*fmt)
- {
- case 0:
- *buf++ = '%';
- break;
- case 'a':
- ++fmt;
- /* remember where the current aligned text started */
- switch (cur_align)
- {
- case WPS_ALIGN_LEFT:
- align->left = cur_align_start;
- break;
-
- case WPS_ALIGN_CENTER:
- align->center = cur_align_start;
- break;
-
- case WPS_ALIGN_RIGHT:
- align->right = cur_align_start;
- break;
- }
- /* start a new alignment */
- switch (*fmt)
- {
- case 'l':
- cur_align = WPS_ALIGN_LEFT;
- break;
- case 'c':
- cur_align = WPS_ALIGN_CENTER;
- break;
- case 'r':
- cur_align = WPS_ALIGN_RIGHT;
- break;
- }
- *buf++=0;
- cur_align_start = buf;
- ++fmt;
- break;
- case 's':
- *flags |= WPS_REFRESH_SCROLL;
- ++fmt;
- break;
-
- case 'x': /* image support */
-#ifdef HAVE_LCD_BITMAP
- /* skip preload or regular image tag */
- if ('l' == *(fmt+1) || '|' == *(fmt+1))
- {
- while (*fmt && *fmt != '\n')
- fmt++;
- }
- else if ('d' == *(fmt+1))
- {
- fmt+=2;
-
- /* get the image ID */
- n = *fmt;
- if(n >= 'a' && n <= 'z')
- n -= 'a';
- if(n >= 'A' && n <= 'Z')
- n = n - 'A' + 26;
-
- if (n >= 0 && n < MAX_IMAGES && img[n].loaded) {
- img[n].display = true;
- }
- }
-#endif
- fmt++;
- break;
-
-
- case '%':
- case '|':
- case '<':
- case '>':
- case ';':
- *buf++ = *fmt++;
- break;
-
- case '?':
- fmt++;
- value = get_tag(id3, nid3, fmt, temp_buf, sizeof(temp_buf),
- &tag_length, subline_time_mult, flags,
- &intval);
-
- while (*fmt && ('<' != *fmt))
- fmt++;
-
- if ('<' == *fmt)
- fmt++;
-
- /* No value, so skip to else part, using a sufficiently high
- value to "hit" the last part of the conditional */
- if ((!value) || (!strlen(value)))
- fmt = skip_conditional(fmt, 1000);
- else
- if(intval > 1) /* enum */
- fmt = skip_conditional(fmt, intval - 1);
-
- level++;
- break;
-
- default:
- value = get_tag(id3, nid3, fmt, temp_buf, sizeof(temp_buf),
- &tag_length, subline_time_mult, flags,
- &intval);
- fmt += tag_length;
-
- if (value)
- {
- while (*value && (buf < buf_end))
- *buf++ = *value++;
- }
- }
- }
-
- /* remember where the current aligned text started */
- switch (cur_align)
- {
- case WPS_ALIGN_LEFT:
- align->left = cur_align_start;
- break;
-
- case WPS_ALIGN_CENTER:
- align->center = cur_align_start;
- break;
-
- case WPS_ALIGN_RIGHT:
- align->right = cur_align_start;
- break;
- }
-
- *buf = 0;
-
- /* if resulting line is an empty line, set the subline time to 0 */
- if (buf - buf_start == 0)
- *subline_time_mult = 0;
-
- /* If no flags have been set, the line didn't contain any format codes.
- We still want to refresh it. */
- if(*flags == 0)
- *flags = WPS_REFRESH_STATIC;
-}
-
-bool wps_refresh(struct mp3entry* id3,
- struct mp3entry* nid3,
- int ffwd_offset,
- unsigned char refresh_mode)
-{
- char buf[MAX_PATH];
- unsigned char flags;
- int i;
- bool update_line;
- bool only_one_subline;
- bool new_subline_refresh;
- int search;
- int search_start;
-#ifdef HAVE_LCD_BITMAP
- int h = font_get(FONT_UI)->height;
- int offset = global_settings.statusbar ? STATUSBAR_HEIGHT : 0;
- /* to find out wether the peak meter is enabled we
- assume it wasn't until we find a line that contains
- the peak meter. We can't use peak_meter_enabled itself
- because that would mean to turn off the meter thread
- temporarily. (That shouldn't matter unless yield
- or sleep is called but who knows...)
- */
- bool enable_pm = false;
-
- /* Set images to not to be displayed */
- for (i = 0; i < MAX_IMAGES; i++) {
- img[i].display = false;
- }
-#endif
-
- /* reset to first subline if refresh all flag is set */
- if (refresh_mode == WPS_REFRESH_ALL)
- {
- for (i=0; i<MAX_LINES; i++)
- {
- curr_subline[i] = SUBLINE_RESET;
- }
- }
-
-#ifdef HAVE_LCD_CHARCELLS
- for (i=0; i<8; i++) {
- if (wps_progress_pat[i]==0)
- wps_progress_pat[i]=lcd_get_locked_pattern();
- }
-#endif
-
- if (!id3)
- {
- lcd_stop_scroll();
- return false;
- }
-
- ff_rewind_count = ffwd_offset;
-
- for (i = 0; i < MAX_LINES; i++)
- {
- new_subline_refresh = false;
- only_one_subline = false;
-
- /* if time to advance to next sub-line */
- if (TIME_AFTER(current_tick, subline_expire_time[i] - 1) ||
- (curr_subline[i] == SUBLINE_RESET))
- {
- /* search all sublines until the next subline with time > 0
- is found or we get back to the subline we started with */
- if (curr_subline[i] == SUBLINE_RESET)
- search_start = 0;
- else
- search_start = curr_subline[i];
- for (search=0; search<MAX_SUBLINES; search++)
- {
- curr_subline[i]++;
-
- /* wrap around if beyond last defined subline or MAX_SUBLINES */
- if ((!format_lines[i][curr_subline[i]]) ||
- (curr_subline[i] == MAX_SUBLINES))
- {
- if (curr_subline[i] == 1)
- only_one_subline = true;
- curr_subline[i] = 0;
- }
-
- /* if back where we started after search or
- only one subline is defined on the line */
- if (((search > 0) && (curr_subline[i] == search_start)) ||
- only_one_subline)
- {
- /* no other subline with a time > 0 exists */
- subline_expire_time[i] = current_tick + 100 * HZ;
- break;
- }
- else
- {
- /* get initial time multiplier and
- line type flags for this subline */
- format_display(buf, sizeof(buf), id3, nid3,
- format_lines[i][curr_subline[i]],
- &format_align[i][curr_subline[i]],
- &time_mult[i][curr_subline[i]],
- &line_type[i][curr_subline[i]]);
-
- /* only use this subline if subline time > 0 */
- if (time_mult[i][curr_subline[i]] > 0)
- {
- new_subline_refresh = true;
- subline_expire_time[i] = current_tick +
- BASE_SUBLINE_TIME * time_mult[i][curr_subline[i]];
- break;
- }
- }
- }
-
- }
-
- update_line = false;
-
- if ( !format_lines[i][curr_subline[i]] )
- break;
-
- if ((line_type[i][curr_subline[i]] & refresh_mode) ||
- (refresh_mode == WPS_REFRESH_ALL) ||
- new_subline_refresh)
- {
- flags = 0;
-#ifdef HAVE_LCD_BITMAP
- int left_width, left_xpos;
- int center_width, center_xpos;
- int right_width, right_xpos;
- int space_width;
- int string_height;
- int ypos;
-#endif
-
- format_display(buf, sizeof(buf), id3, nid3,
- format_lines[i][curr_subline[i]],
- &format_align[i][curr_subline[i]],
- &time_mult[i][curr_subline[i]],
- &flags);
- line_type[i][curr_subline[i]] = flags;
-
-#ifdef HAVE_LCD_BITMAP
- /* progress */
- if (flags & refresh_mode & WPS_REFRESH_PLAYER_PROGRESS)
- {
-#define PROGRESS_BAR_HEIGHT 6 /* this should probably be defined elsewhere; config-*.h perhaps? */
- int sby = i*h + offset + (h > 7 ? (h - 6) / 2 : 1);
- scrollbar(0, sby, LCD_WIDTH, PROGRESS_BAR_HEIGHT,
- id3->length?id3->length:1, 0,
- id3->length?id3->elapsed + ff_rewind_count:0,
- HORIZONTAL);
-#ifdef AB_REPEAT_ENABLE
- if ( ab_repeat_mode_enabled() )
- ab_draw_markers(id3->length, 0, sby, LCD_WIDTH, PROGRESS_BAR_HEIGHT);
-#endif
- update_line = true;
- }
- if (flags & refresh_mode & WPS_REFRESH_PEAK_METER) {
- /* peak meter */
- int peak_meter_y;
-
- update_line = true;
- peak_meter_y = i * h + offset;
-
- /* The user might decide to have the peak meter in the last
- line so that it is only displayed if no status bar is
- visible. If so we neither want do draw nor enable the
- peak meter. */
- if (peak_meter_y + h <= LCD_HEIGHT) {
- /* found a line with a peak meter -> remember that we must
- enable it later */
- enable_pm = true;
- peak_meter_draw(0, peak_meter_y, LCD_WIDTH,
- MIN(h, LCD_HEIGHT - peak_meter_y));
- }
- }
-#else
- /* progress */
- if (flags & refresh_mode & WPS_REFRESH_PLAYER_PROGRESS) {
- if (full_line_progressbar)
- draw_player_fullbar(buf, sizeof(buf),
- id3, ff_rewind_count);
- else
- draw_player_progress(id3, ff_rewind_count);
- }
-#endif
-#ifdef HAVE_LCD_BITMAP
- /* calculate different string sizes and positions */
- lcd_getstringsize(" ", &space_width, &string_height);
- if (format_align[i][curr_subline[i]].left != 0) {
- lcd_getstringsize(format_align[i][curr_subline[i]].left,
- &left_width, &string_height);
- }
- else {
- left_width = 0;
- }
- left_xpos = 0;
-
- if (format_align[i][curr_subline[i]].center != 0) {
- lcd_getstringsize(format_align[i][curr_subline[i]].center,
- &center_width, &string_height);
- }
- else {
- center_width = 0;
- }
- center_xpos=(LCD_WIDTH - center_width) / 2;
-
- if (format_align[i][curr_subline[i]].right != 0) {
- lcd_getstringsize(format_align[i][curr_subline[i]].right,
- &right_width, &string_height);
- }
- else {
- right_width = 0;
- }
- right_xpos = (LCD_WIDTH - right_width);
-
- /* Checks for overlapping strings.
- If needed the overlapping strings will be merged, separated by a
- space */
-
- /* CASE 1: left and centered string overlap */
- /* there is a left string, need to merge left and center */
- if ((left_width != 0 && center_width != 0) &&
- (left_xpos + left_width + space_width > center_xpos)) {
- /* replace the former separator '\0' of left and
- center string with a space */
- *(--format_align[i][curr_subline[i]].center) = ' ';
- /* calculate the new width and position of the merged string */
- left_width = left_width + space_width + center_width;
- left_xpos = 0;
- /* there is no centered string anymore */
- center_width = 0;
- }
- /* there is no left string, move center to left */
- if ((left_width == 0 && center_width != 0) &&
- (left_xpos + left_width > center_xpos)) {
- /* move the center string to the left string */
- format_align[i][curr_subline[i]].left = format_align[i][curr_subline[i]].center;
- /* calculate the new width and position of the string */
- left_width = center_width;
- left_xpos = 0;
- /* there is no centered string anymore */
- center_width = 0;
- }
-
- /* CASE 2: centered and right string overlap */
- /* there is a right string, need to merge center and right */
- if ((center_width != 0 && right_width != 0) &&
- (center_xpos + center_width + space_width > right_xpos)) {
- /* replace the former separator '\0' of center and
- right string with a space */
- *(--format_align[i][curr_subline[i]].right) = ' ';
- /* move the center string to the right after merge */
- format_align[i][curr_subline[i]].right = format_align[i][curr_subline[i]].center;
- /* calculate the new width and position of the merged string */
- right_width = center_width + space_width + right_width;
- right_xpos = (LCD_WIDTH - right_width);
- /* there is no centered string anymore */
- center_width = 0;
- }
- /* there is no right string, move center to right */
- if ((center_width != 0 && right_width == 0) &&
- (center_xpos + center_width > right_xpos)) {
- /* move the center string to the right string */
- format_align[i][curr_subline[i]].right = format_align[i][curr_subline[i]].center;
- /* calculate the new width and position of the string */
- right_width = center_width;
- right_xpos = (LCD_WIDTH - right_width);
- /* there is no centered string anymore */
- center_width = 0;
- }
-
- /* CASE 3: left and right overlap
- There is no center string anymore, either there never
- was one or it has been merged in case 1 or 2 */
- /* there is a left string, need to merge left and right */
- if ((left_width != 0 && center_width == 0 && right_width != 0) &&
- (left_xpos + left_width + space_width > right_xpos)) {
- /* replace the former separator '\0' of left and
- right string with a space */
- *(--format_align[i][curr_subline[i]].right) = ' ';
- /* calculate the new width and position of the string */
- left_width = left_width + space_width + right_width;
- left_xpos = 0;
- /* there is no right string anymore */
- right_width = 0;
- }
- /* there is no left string, move right to left */
- if ((left_width == 0 && center_width == 0 && right_width != 0) &&
- (left_xpos + left_width > right_xpos)) {
- /* move the right string to the left string */
- format_align[i][curr_subline[i]].left = format_align[i][curr_subline[i]].right;
- /* calculate the new width and position of the string */
- left_width = right_width;
- left_xpos = 0;
- /* there is no right string anymore */
- right_width = 0;
- }
-
-#endif
-
- if (flags & WPS_REFRESH_SCROLL) {
-
- /* scroll line */
- if ((refresh_mode & WPS_REFRESH_SCROLL) ||
- new_subline_refresh) {
-#ifdef HAVE_LCD_BITMAP
- ypos = (i*string_height)+lcd_getymargin();
- update_line = true;
-
- if (left_width>LCD_WIDTH) {
- lcd_puts_scroll(0, i, format_align[i][curr_subline[i]].left);
- } else {
- /* clear the line first */
- lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
- lcd_fillrect(0, ypos, LCD_WIDTH, string_height);
- lcd_set_drawmode(DRMODE_SOLID);
-
- /* Nasty hack: we output an empty scrolling string,
- which will reset the scroller for that line */
- lcd_puts_scroll(0, i, "");
-
- /* print aligned strings */
- if (left_width != 0)
- {
- lcd_putsxy(left_xpos, ypos, format_align[i][curr_subline[i]].left);
- }
- if (center_width != 0)
- {
- lcd_putsxy(center_xpos, ypos, format_align[i][curr_subline[i]].center);
- }
- if (right_width != 0)
- {
- lcd_putsxy(right_xpos, ypos, format_align[i][curr_subline[i]].right);
- }
- }
-#else
- lcd_puts_scroll(0, i, buf);
- update_line = true;
-#endif
- }
- }
- else if (flags & (WPS_REFRESH_DYNAMIC | WPS_REFRESH_STATIC))
- {
- /* dynamic / static line */
- if ((refresh_mode & (WPS_REFRESH_DYNAMIC|WPS_REFRESH_STATIC)) ||
- new_subline_refresh)
- {
-#ifdef HAVE_LCD_BITMAP
- ypos = (i*string_height)+lcd_getymargin();
- update_line = true;
-
- /* clear the line first */
- lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
- lcd_fillrect(0, ypos, LCD_WIDTH, string_height);
- lcd_set_drawmode(DRMODE_SOLID);
-
- /* Nasty hack: we output an empty scrolling string,
- which will reset the scroller for that line */
- lcd_puts_scroll(0, i, "");
-
- /* print aligned strings */
- if (left_width != 0)
- {
- lcd_putsxy(left_xpos, ypos, format_align[i][curr_subline[i]].left);
- }
- if (center_width != 0)
- {
- lcd_putsxy(center_xpos, ypos, format_align[i][curr_subline[i]].center);
- }
- if (right_width != 0)
- {
- lcd_putsxy(right_xpos, ypos, format_align[i][curr_subline[i]].right);
- }
-#else
- update_line = true;
- lcd_puts(0, i, buf);
-#endif
- }
- }
- }
-#ifdef HAVE_LCD_BITMAP
- if (update_line) {
- lcd_update_rect(0, i*h + offset, LCD_WIDTH, h);
- }
-#endif
- }
-
-#ifdef HAVE_LCD_BITMAP
- /* Display all images */
- for (i = 0; i < MAX_IMAGES; i++) {
- if(img[i].always_display)
- img[i].display = img[i].always_display;
- }
- wps_display_images();
-
- /* Now we know wether the peak meter is used.
- So we can enable / disable the peak meter thread */
- peak_meter_enabled = enable_pm;
-#endif
-
-#if defined(CONFIG_BACKLIGHT) && !defined(SIMULATOR)
- if (global_settings.caption_backlight && id3) {
- /* turn on backlight n seconds before track ends, and turn it off n
- seconds into the new track. n == backlight_timeout, or 5s */
- int n =
- backlight_timeout_value[global_settings.backlight_timeout] * 1000;
-
- if ( n < 1000 )
- n = 5000; /* use 5s if backlight is always on or off */
-
- if ((id3->elapsed < 1000) ||
- ((id3->length - id3->elapsed) < (unsigned)n))
- backlight_on();
- }
-#endif
- return true;
-}
-
-bool wps_display(struct mp3entry* id3,
- struct mp3entry* nid3)
-{
- if (!id3 && !(audio_status() & AUDIO_STATUS_PLAY))
- {
- global_settings.resume_index = -1;
-#ifdef HAVE_LCD_CHARCELLS
- gui_syncsplash(HZ, true, str(LANG_END_PLAYLIST_PLAYER));
-#else
- status_draw(true);
- gui_syncsplash(HZ, true, str(LANG_END_PLAYLIST_RECORDER));
-#endif
- return true;
- }
- else
- {
- lcd_clear_display();
-
- if (!wps_loaded) {
- if ( !format_buffer[0] ) {
-#ifdef HAVE_LCD_BITMAP
- wps_format("%s%?it<%?in<%in. |>%it|%fn>\n"
- "%s%?ia<%ia|%?d2<%d2|(root)>>\n"
- "%s%?id<%id|%?d1<%d1|(root)>> %?iy<(%iy)|>\n"
- "\n"
- "%al%pc/%pt%ar[%pp:%pe]\n"
- "%fbkBit %?fv<avg|> %?iv<(id3v%iv)|(no id3)>\n"
- "%pb\n"
- "%pm\n", NULL, 0);
-#else
- wps_format("%s%pp/%pe: %?it<%it|%fn> - %?ia<%ia|%d2> - %?id<%id|%d1>\n"
- "%pc%?ps<*|/>%pt\n", NULL, 0);
-#endif
- }
- }
- }
- yield();
- wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
- status_draw(true);
-#ifdef HAVE_LCD_BITMAP
- wps_display_images();
-#endif
- lcd_update();
- return false;
-}
-
-#ifdef HAVE_LCD_CHARCELLS
-static bool draw_player_progress(const struct mp3entry* id3,
- int ff_rewwind_count)
-{
- char player_progressbar[7];
- char binline[36];
- int songpos = 0;
- int i,j;
-
- if (!id3)
- return false;
-
- memset(binline, 1, sizeof binline);
- memset(player_progressbar, 1, sizeof player_progressbar);
-
- if(id3->elapsed >= id3->length)
- songpos = 0;
- else
- {
- if(wps_time_countup == false)
- songpos = ((id3->elapsed - ff_rewwind_count) * 36) / id3->length;
- else
- songpos = ((id3->elapsed + ff_rewwind_count) * 36) / id3->length;
- }
- for (i=0; i < songpos; i++)
- binline[i] = 0;
-
- for (i=0; i<=6; i++) {
- for (j=0;j<5;j++) {
- player_progressbar[i] <<= 1;
- player_progressbar[i] += binline[i*5+j];
- }
- }
- lcd_define_pattern(wps_progress_pat[0], player_progressbar);
- return true;
-}
-
-static void draw_player_fullbar(char* buf, int buf_size,
- const struct mp3entry* id3,
- int ff_rewwind_count)
-{
- int i,j,lcd_char_pos;
-
- char player_progressbar[7];
- char binline[36];
- static const char numbers[12][4][3]={
- {{1,1,1},{1,0,1},{1,0,1},{1,1,1}},/*0*/
- {{0,1,0},{1,1,0},{0,1,0},{0,1,0}},/*1*/
- {{1,1,1},{0,0,1},{0,1,0},{1,1,1}},/*2*/
- {{1,1,1},{0,0,1},{0,1,1},{1,1,1}},/*3*/
- {{1,0,0},{1,1,0},{1,1,1},{0,1,0}},/*4*/
- {{1,1,1},{1,1,0},{0,0,1},{1,1,0}},/*5*/
- {{1,1,1},{1,0,0},{1,1,1},{1,1,1}},/*6*/
- {{1,1,1},{0,0,1},{0,1,0},{1,0,0}},/*7*/
- {{1,1,1},{1,1,1},{1,0,1},{1,1,1}},/*8*/
- {{1,1,1},{1,1,1},{0,0,1},{1,1,1}},/*9*/
- {{0,0,0},{0,1,0},{0,0,0},{0,1,0}},/*:*/
- {{0,0,0},{0,0,0},{0,0,0},{0,0,0}} /*<blank>*/
- };
-
- int songpos = 0;
- int digits[6];
- int time;
- char timestr[7];
-
- for (i=0; i < buf_size; i++)
- buf[i] = ' ';
-
- if(id3->elapsed >= id3->length)
- songpos = 55;
- else {
- if(wps_time_countup == false)
- songpos = ((id3->elapsed - ff_rewwind_count) * 55) / id3->length;
- else
- songpos = ((id3->elapsed + ff_rewwind_count) * 55) / id3->length;
- }
-
- time=(id3->elapsed + ff_rewind_count);
-
- memset(timestr, 0, sizeof(timestr));
- wps_format_time(timestr, sizeof(timestr), time);
- for(lcd_char_pos=0; lcd_char_pos<6; lcd_char_pos++) {
- digits[lcd_char_pos] = map_fullbar_char(timestr[lcd_char_pos]);
- }
-
- /* build the progressbar-icons */
- for (lcd_char_pos=0; lcd_char_pos<6; lcd_char_pos++) {
- memset(binline, 0, sizeof binline);
- memset(player_progressbar, 0, sizeof player_progressbar);
-
- /* make the character (progressbar & digit)*/
- for (i=0; i<7; i++) {
- for (j=0;j<5;j++) {
- /* make the progressbar */
- if (lcd_char_pos==(songpos/5)) {
- /* partial */
- if ((j<(songpos%5))&&(i>4))
- binline[i*5+j] = 1;
- else
- binline[i*5+j] = 0;
- }
- else {
- if (lcd_char_pos<(songpos/5)) {
- /* full character */
- if (i>4)
- binline[i*5+j] = 1;
- }
- }
- /* insert the digit */
- if ((j<3)&&(i<4)) {
- if (numbers[digits[lcd_char_pos]][i][j]==1)
- binline[i*5+j] = 1;
- }
- }
- }
-
- for (i=0; i<=6; i++) {
- for (j=0;j<5;j++) {
- player_progressbar[i] <<= 1;
- player_progressbar[i] += binline[i*5+j];
- }
- }
-
- lcd_define_pattern(wps_progress_pat[lcd_char_pos+1],player_progressbar);
- buf[lcd_char_pos]=wps_progress_pat[lcd_char_pos+1];
-
- }
-
- /* make rest of the progressbar if necessary */
- if (songpos/5>5) {
-
- /* set the characters positions that use the full 5 pixel wide bar */
- for (lcd_char_pos=6; lcd_char_pos < (songpos/5); lcd_char_pos++)
- buf[lcd_char_pos] = 0x86; /* '_' */
-
- /* build the partial bar character for the tail character position */
- memset(binline, 0, sizeof binline);
- memset(player_progressbar, 0, sizeof player_progressbar);
-
- for (i=5; i<7; i++) {
- for (j=0;j<5;j++) {
- if (j<(songpos%5)) {
- binline[i*5+j] = 1;
- }
- }
- }
-
- for (i=0; i<7; i++) {
- for (j=0;j<5;j++) {
- player_progressbar[i] <<= 1;
- player_progressbar[i] += binline[i*5+j];
- }
- }
-
- lcd_define_pattern(wps_progress_pat[7],player_progressbar);
-
- buf[songpos/5]=wps_progress_pat[7];
- }
-}
-
-static char map_fullbar_char(char ascii_val)
-{
- if (ascii_val >= '0' && ascii_val <= '9') {
- return(ascii_val - '0');
- }
- else if (ascii_val == ':') {
- return(10);
- }
- else
- return(11); /* anything besides a number or ':' is mapped to <blank> */
-}
-
-
-#endif
-
-/* -----------------------------------------------------------------
- * vim: et sw=4 ts=8 sts=4 tw=78
- */
diff --git a/apps/wps-display.h b/apps/wps-display.h
deleted file mode 100644
index b23c0d603d..0000000000
--- a/apps/wps-display.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/***************************************************************************
- * __________ __ ___.
- * Open \______ \ ____ ____ | | _\_ |__ _______ ___
- * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
- * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
- * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
- * \/ \/ \/ \/ \/
- * $Id$
- *
- * Copyright (C) 2002 Björn Stenberg
- *
- * All files in this archive are subject to the GNU General Public License.
- * See the file COPYING in the source tree root for full license agreement.
- *
- * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
- * KIND, either express or implied.
- *
- ****************************************************************************/
-#ifndef WPS_DISPLAY
-#define WPS_DISPLAY
-
-#include <stdbool.h>
-#include "id3.h"
-
-/* constants used in line_type and as refresh_mode for wps_refresh */
-#define WPS_REFRESH_STATIC 1 /* line doesn't change over time */
-#define WPS_REFRESH_DYNAMIC 2 /* line may change (e.g. time flag) */
-#define WPS_REFRESH_SCROLL 4 /* line scrolls */
-#define WPS_REFRESH_PLAYER_PROGRESS 8 /* line contains a progress bar */
-#define WPS_REFRESH_PEAK_METER 16 /* line contains a peak meter */
-#define WPS_REFRESH_ALL 0xff /* to refresh all line types */
-/* to refresh only those lines that change over time */
-#define WPS_REFRESH_NON_STATIC (WPS_REFRESH_ALL & ~WPS_REFRESH_STATIC & ~WPS_REFRESH_SCROLL)
-
-/* alignments */
-#define WPS_ALIGN_RIGHT 32
-#define WPS_ALIGN_CENTER 64
-#define WPS_ALIGN_LEFT 128
-
-
-void wps_format_time(char* buf, int buf_size, long time);
-bool wps_refresh(struct mp3entry* id3, struct mp3entry* nid3,
- int ffwd_offset, unsigned char refresh_mode);
-bool wps_display(struct mp3entry* id3, struct mp3entry* nid3);
-bool wps_load(const char* file, bool display);
-void wps_reset(void);
-
-#endif
diff --git a/apps/wps.c b/apps/wps.c
deleted file mode 100644
index 573444fdc4..0000000000
--- a/apps/wps.c
+++ /dev/null
@@ -1,882 +0,0 @@
-/***************************************************************************
- * __________ __ ___.
- * Open \______ \ ____ ____ | | _\_ |__ _______ ___
- * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
- * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
- * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
- * \/ \/ \/ \/ \/
- * $Id$
- *
- * Copyright (C) 2002 Jerome Kuptz
- *
- * All files in this archive are subject to the GNU General Public License.
- * See the file COPYING in the source tree root for full license agreement.
- *
- * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
- * KIND, either express or implied.
- *
- ****************************************************************************/
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-
-#include "system.h"
-#include "file.h"
-#include "lcd.h"
-#include "font.h"
-#include "backlight.h"
-#include "button.h"
-#include "kernel.h"
-#include "tree.h"
-#include "debug.h"
-#include "sprintf.h"
-#include "settings.h"
-#include "wps.h"
-#include "wps-display.h"
-#include "audio.h"
-#include "mp3_playback.h"
-#include "usb.h"
-#include "status.h"
-#include "main_menu.h"
-#include "ata.h"
-#include "screens.h"
-#include "playlist.h"
-#ifdef HAVE_LCD_BITMAP
-#include "icons.h"
-#include "peakmeter.h"
-#endif
-#include "action.h"
-#include "lang.h"
-#include "bookmark.h"
-#include "misc.h"
-#include "sound.h"
-#include "onplay.h"
-#include "abrepeat.h"
-#include "playback.h"
-#include "splash.h"
-
-#define FF_REWIND_MAX_PERCENT 3 /* cap ff/rewind step size at max % of file */
- /* 3% of 30min file == 54s step size */
-#define MIN_FF_REWIND_STEP 500
-
-bool keys_locked = false;
-static bool ff_rewind = false;
-static bool paused = false;
-static struct mp3entry* id3 = NULL;
-static struct mp3entry* nid3 = NULL;
-static char current_track_path[MAX_PATH+1];
-
-/* set volume
- return true if screen restore is needed
- return false otherwise
-*/
-static bool setvol(void)
-{
- if (global_settings.volume < sound_min(SOUND_VOLUME))
- global_settings.volume = sound_min(SOUND_VOLUME);
- if (global_settings.volume > sound_max(SOUND_VOLUME))
- global_settings.volume = sound_max(SOUND_VOLUME);
- sound_set_volume(global_settings.volume);
- status_draw(false);
- wps_refresh(id3, nid3, 0, WPS_REFRESH_NON_STATIC);
- settings_save();
-#ifdef HAVE_LCD_CHARCELLS
- gui_syncsplash(0, false, "Vol: %d %% ",
- sound_val2phys(SOUND_VOLUME, global_settings.volume));
- return true;
-#endif
- return false;
-}
-
-static bool ffwd_rew(int button)
-{
- static const int ff_rew_steps[] = {
- 1000, 2000, 3000, 4000,
- 5000, 6000, 8000, 10000,
- 15000, 20000, 25000, 30000,
- 45000, 60000
- };
-
- unsigned int step = 0; /* current ff/rewind step */
- unsigned int max_step = 0; /* maximum ff/rewind step */
- int ff_rewind_count = 0; /* current ff/rewind count (in ticks) */
- int direction = -1; /* forward=1 or backward=-1 */
- long accel_tick = 0; /* next time at which to bump the step size */
- bool exit = false;
- bool usb = false;
-
- while (!exit) {
- switch ( button ) {
- case WPS_FFWD:
-#ifdef WPS_RC_FFWD
- case WPS_RC_FFWD:
-#endif
- direction = 1;
- case WPS_REW:
-#ifdef WPS_RC_REW
- case WPS_RC_REW:
-#endif
- if (ff_rewind)
- {
- if (direction == 1)
- {
- /* fast forwarding, calc max step relative to end */
- max_step =
- (id3->length - (id3->elapsed + ff_rewind_count)) *
- FF_REWIND_MAX_PERCENT / 100;
- }
- else
- {
- /* rewinding, calc max step relative to start */
- max_step = (id3->elapsed + ff_rewind_count) *
- FF_REWIND_MAX_PERCENT / 100;
- }
-
- max_step = MAX(max_step, MIN_FF_REWIND_STEP);
-
- if (step > max_step)
- step = max_step;
-
- ff_rewind_count += step * direction;
-
- if (global_settings.ff_rewind_accel != 0 &&
- current_tick >= accel_tick)
- {
- step *= 2;
- accel_tick = current_tick +
- global_settings.ff_rewind_accel*HZ;
- }
- }
- else
- {
- if ( (audio_status() & AUDIO_STATUS_PLAY) &&
- id3 && id3->length )
- {
- if (!paused)
- audio_pause();
-#if CONFIG_KEYPAD == PLAYER_PAD
- lcd_stop_scroll();
-#endif
- if (direction > 0)
- status_set_ffmode(STATUS_FASTFORWARD);
- else
- status_set_ffmode(STATUS_FASTBACKWARD);
-
- ff_rewind = true;
-
- step = ff_rew_steps[global_settings.ff_rewind_min_step];
-
- accel_tick = current_tick +
- global_settings.ff_rewind_accel*HZ;
- }
- else
- break;
- }
-
- if (direction > 0) {
- if ((id3->elapsed + ff_rewind_count) > id3->length)
- ff_rewind_count = id3->length - id3->elapsed;
- }
- else {
- if ((int)(id3->elapsed + ff_rewind_count) < 0)
- ff_rewind_count = -id3->elapsed;
- }
-
- if(wps_time_countup == false)
- wps_refresh(id3, nid3, -ff_rewind_count,
- WPS_REFRESH_PLAYER_PROGRESS |
- WPS_REFRESH_DYNAMIC);
- else
- wps_refresh(id3, nid3, ff_rewind_count,
- WPS_REFRESH_PLAYER_PROGRESS |
- WPS_REFRESH_DYNAMIC);
-
- break;
-
- case WPS_PREV:
- case WPS_NEXT:
-#ifdef WPS_RC_PREV
- case WPS_RC_PREV:
- case WPS_RC_NEXT:
-#endif
- audio_ff_rewind(id3->elapsed+ff_rewind_count);
- ff_rewind_count = 0;
- ff_rewind = false;
- status_set_ffmode(0);
- if (!paused)
- audio_resume();
-#ifdef HAVE_LCD_CHARCELLS
- wps_display(id3, nid3);
-#endif
- exit = true;
- break;
-
- default:
- if(default_event_handler(button) == SYS_USB_CONNECTED) {
- status_set_ffmode(0);
- usb = true;
- exit = true;
- }
- break;
- }
- if (!exit)
- button = button_get(true);
- }
-
- /* let audio thread update id3->elapsed before calling wps_refresh */
- yield();
- wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
- return usb;
-}
-
-static bool update(void)
-{
- bool track_changed = audio_has_changed_track();
- bool retcode = false;
-
- nid3 = audio_next_track();
- if (track_changed)
- {
- lcd_stop_scroll();
- id3 = audio_current_track();
- if (wps_display(id3, nid3))
- retcode = true;
- else
- wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
-
- if (id3)
- memcpy(current_track_path, id3->path, sizeof(current_track_path));
- }
-
- if (id3)
- wps_refresh(id3, nid3, 0, WPS_REFRESH_NON_STATIC);
-
- status_draw(false);
-
- return retcode;
-}
-
-static void fade(bool fade_in)
-{
- unsigned fp_global_vol = global_settings.volume << 8;
- unsigned fp_step = fp_global_vol / 30;
-
- if (fade_in) {
- /* fade in */
- unsigned fp_volume = 0;
-
- /* zero out the sound */
- sound_set_volume(0);
-
- sleep(HZ/10); /* let audio thread run */
- audio_resume();
-
- while (fp_volume < fp_global_vol) {
- fp_volume += fp_step;
- sleep(1);
- sound_set_volume(fp_volume >> 8);
- }
- sound_set_volume(global_settings.volume);
- }
- else {
- /* fade out */
- unsigned fp_volume = fp_global_vol;
-
- while (fp_volume > fp_step) {
- fp_volume -= fp_step;
- sleep(1);
- sound_set_volume(fp_volume >> 8);
- }
- audio_pause();
-#ifndef SIMULATOR
- /* let audio thread run and wait for the mas to run out of data */
- while (!mp3_pause_done())
-#endif
- sleep(HZ/10);
-
- /* reset volume to what it was before the fade */
- sound_set_volume(global_settings.volume);
- }
-}
-
-
-#ifdef WPS_KEYLOCK
-static void display_keylock_text(bool locked)
-{
- char* s;
- lcd_stop_scroll();
-#ifdef HAVE_LCD_CHARCELLS
- if(locked)
- s = str(LANG_KEYLOCK_ON_PLAYER);
- else
- s = str(LANG_KEYLOCK_OFF_PLAYER);
-#else
- if(locked)
- s = str(LANG_KEYLOCK_ON_RECORDER);
- else
- s = str(LANG_KEYLOCK_OFF_RECORDER);
-#endif
- gui_syncsplash(HZ, true, s);
-}
-
-static void waitfor_nokey(void)
-{
- /* wait until all keys are released */
- while (button_get(false) != BUTTON_NONE)
- yield();
-}
-#endif
-
-/* demonstrates showing different formats from playtune */
-long wps_show(void)
-{
- long button = 0, lastbutton = 0;
- bool ignore_keyup = true;
- bool restore = false;
- long restoretimer = 0; /* timer to delay screen redraw temporarily */
- bool exit = false;
- bool update_track = false;
- unsigned long right_lastclick = 0;
- unsigned long left_lastclick = 0;
-
- id3 = nid3 = NULL;
- current_track_path[0] = '\0';
-
-#ifdef HAVE_LCD_CHARCELLS
- status_set_audio(true);
- status_set_param(false);
-#else
- if(global_settings.statusbar)
- lcd_setmargins(0, STATUSBAR_HEIGHT);
- else
- lcd_setmargins(0, 0);
-#endif
-
-#ifdef AB_REPEAT_ENABLE
- ab_repeat_init();
- ab_reset_markers();
-#endif
-
- ff_rewind = false;
-
- if(audio_status() & AUDIO_STATUS_PLAY)
- {
- id3 = audio_current_track();
- nid3 = audio_next_track();
- if (id3) {
- if (wps_display(id3, nid3))
- return 0;
- wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
-
- memcpy(current_track_path, id3->path, sizeof(current_track_path));
- }
-
- restore = true;
- }
-
- while ( 1 )
- {
- bool audio_paused = (audio_status() & AUDIO_STATUS_PAUSE)?true:false;
-
- /* did someone else (i.e power thread) change audio pause mode? */
- if (paused != audio_paused) {
- paused = audio_paused;
-
- /* if another thread paused audio, we are probably in car mode,
- about to shut down. lets save the settings. */
- if (paused) {
- settings_save();
-#if !defined(HAVE_RTC) && !defined(HAVE_SW_POWEROFF)
- ata_flush();
-#endif
- }
- }
-
-#ifdef HAVE_LCD_BITMAP
- /* when the peak meter is enabled we want to have a
- few extra updates to make it look smooth. On the
- other hand we don't want to waste energy if it
- isn't displayed */
- if (peak_meter_enabled) {
- long next_refresh = current_tick;
- long next_big_refresh = current_tick + HZ / 5;
- button = BUTTON_NONE;
- while (TIME_BEFORE(current_tick, next_big_refresh)) {
- button = button_get(false);
- if (button != BUTTON_NONE) {
- break;
- }
- peak_meter_peek();
- sleep(0); /* Sleep until end of current tick. */
-
- if (TIME_AFTER(current_tick, next_refresh)) {
- wps_refresh(id3, nid3, 0, WPS_REFRESH_PEAK_METER);
- next_refresh += HZ / PEAK_METER_FPS;
- }
- }
-
- }
-
- /* The peak meter is disabled
- -> no additional screen updates needed */
- else {
- button = button_get_w_tmo(HZ/5);
- }
-#else
- button = button_get_w_tmo(HZ/5);
-#endif
-
- /* discard first event if it's a button release */
- if (button && ignore_keyup)
- {
- ignore_keyup = false;
- /* Negative events are system events */
- if (button >= 0 && button & BUTTON_REL )
- continue;
- }
-
-#ifdef WPS_KEYLOCK
- /* ignore non-remote buttons when keys are locked */
- if (keys_locked &&
- ! ((button < 0) ||
- (button == BUTTON_NONE) ||
- ((button & WPS_KEYLOCK) == WPS_KEYLOCK) ||
- (button & BUTTON_REMOTE)
- ))
- {
- if (!(button & BUTTON_REL))
- display_keylock_text(true);
- restore = true;
- button = BUTTON_NONE;
- }
-#endif
-
- /* Exit if audio has stopped playing. This can happen if using the
- sleep timer with the charger plugged or if starting a recording
- from F1 */
- if (!audio_status())
- exit = true;
-
- switch(button)
- {
-#ifdef WPS_CONTEXT
- case WPS_CONTEXT:
- onplay(id3->path, TREE_ATTR_MPA, CONTEXT_WPS);
- restore = true;
- break;
-#endif
-
-#ifdef WPS_RC_BROWSE
- case WPS_RC_BROWSE:
-#endif
- case WPS_BROWSE:
-#ifdef WPS_BROWSE_PRE
- if ((lastbutton != WPS_BROWSE_PRE)
-#ifdef WPS_RC_BROWSE_PRE
- && (lastbutton != WPS_RC_BROWSE_PRE)
-#endif
- )
- break;
-#endif
-#ifdef HAVE_LCD_CHARCELLS
- status_set_record(false);
- status_set_audio(false);
-#endif
- lcd_stop_scroll();
-
- /* set dir browser to current playing song */
- if (global_settings.browse_current &&
- current_track_path[0] != '\0')
- set_current_file(current_track_path);
-
- return 0;
- break;
-
- /* play/pause */
- case WPS_PAUSE:
-#ifdef WPS_PAUSE_PRE
- if (lastbutton != WPS_PAUSE_PRE)
- break;
-#endif
-#ifdef WPS_RC_PAUSE
- case WPS_RC_PAUSE:
-#ifdef WPS_RC_PAUSE_PRE
- if ((button == WPS_RC_PAUSE) && (lastbutton != WPS_RC_PAUSE_PRE))
- break;
-#endif
-#endif
- if ( paused )
- {
- paused = false;
- if ( global_settings.fade_on_stop )
- fade(1);
- else
- audio_resume();
- }
- else
- {
- paused = true;
- if ( global_settings.fade_on_stop )
- fade(0);
- else
- audio_pause();
- settings_save();
-#if !defined(HAVE_RTC) && !defined(HAVE_SW_POWEROFF)
- ata_flush(); /* make sure resume info is saved */
-#endif
- }
- break;
-
- /* volume up */
- case WPS_INCVOL:
- case WPS_INCVOL | BUTTON_REPEAT:
-#ifdef WPS_RC_INCVOL
- case WPS_RC_INCVOL:
- case WPS_RC_INCVOL | BUTTON_REPEAT:
-#endif
- global_settings.volume++;
- if (setvol()) {
- restore = true;
- restoretimer = current_tick + HZ;
- }
- break;
-
- /* volume down */
- case WPS_DECVOL:
- case WPS_DECVOL | BUTTON_REPEAT:
-#ifdef WPS_RC_DECVOL
- case WPS_RC_DECVOL:
- case WPS_RC_DECVOL | BUTTON_REPEAT:
-#endif
- global_settings.volume--;
- if (setvol()) {
- restore = true;
- restoretimer = current_tick + HZ;
- }
- break;
-
- /* fast forward / rewind */
-#ifdef WPS_RC_FFWD
- case WPS_RC_FFWD:
-#endif
- case WPS_FFWD:
-#ifdef WPS_NEXT_DIR
- if (current_tick - right_lastclick < HZ)
- {
- audio_next_dir();
- right_lastclick = 0;
- break;
- }
-#endif
-#ifdef WPS_RC_REW
- case WPS_RC_REW:
-#endif
- case WPS_REW:
-#ifdef WPS_PREV_DIR
- if (current_tick - left_lastclick < HZ)
- {
- audio_prev_dir();
- left_lastclick = 0;
- break;
- }
-#endif
- ffwd_rew(button);
- break;
-
- /* prev / restart */
- case WPS_PREV:
-#ifdef WPS_PREV_PRE
- if (lastbutton != WPS_PREV_PRE)
- break;
-#endif
-#ifdef WPS_RC_PREV
- case WPS_RC_PREV:
-#ifdef WPS_RC_PREV_PRE
- if ((button == WPS_RC_PREV) && (lastbutton != WPS_RC_PREV_PRE))
- break;
-#endif
-#endif
- left_lastclick = current_tick;
- update_track = true;
-
-#ifdef AB_REPEAT_ENABLE
- /* if we're in A/B repeat mode and the current position
- is past the A marker, jump back to the A marker... */
- if ( ab_repeat_mode_enabled() && ab_after_A_marker(id3->elapsed) )
- {
- ab_jump_to_A_marker();
- break;
- }
- /* ...otherwise, do it normally */
-#endif
-
- if (!id3 || (id3->elapsed < 3*1000)) {
- audio_prev();
- }
- else {
- if (!paused)
- audio_pause();
-
- audio_ff_rewind(0);
-
- if (!paused)
- audio_resume();
- }
- break;
-
-#ifdef WPS_NEXT_DIR
-#ifdef WPS_RC_NEXT_DIR
- case WPS_RC_NEXT_DIR:
-#endif
- case WPS_NEXT_DIR:
- audio_next_dir();
- break;
-#endif
-#ifdef WPS_PREV_DIR
-#ifdef WPS_RC_PREV_DIR
- case WPS_RC_PREV_DIR:
-#endif
- case WPS_PREV_DIR:
- audio_prev_dir();
- break;
-#endif
-
- /* next */
- case WPS_NEXT:
-#ifdef WPS_NEXT_PRE
- if (lastbutton != WPS_NEXT_PRE)
- break;
-#endif
-#ifdef WPS_RC_NEXT
- case WPS_RC_NEXT:
-#ifdef WPS_RC_NEXT_PRE
- if ((button == WPS_RC_NEXT) && (lastbutton != WPS_RC_NEXT_PRE))
- break;
-#endif
-#endif
- right_lastclick = current_tick;
- update_track = true;
-
-#ifdef AB_REPEAT_ENABLE
- /* if we're in A/B repeat mode and the current position is
- before the A marker, jump to the A marker... */
- if ( ab_repeat_mode_enabled() && ab_before_A_marker(id3->elapsed) )
- {
- ab_jump_to_A_marker();
- break;
- }
- /* ...otherwise, do it normally */
-#endif
-
- audio_next();
- break;
-
-#ifdef WPS_MENU
- /* menu key functions */
- case WPS_MENU:
-#ifdef WPS_MENU_PRE
- if (lastbutton != WPS_MENU_PRE)
- break;
-#endif
-#ifdef WPS_RC_MENU
- case WPS_RC_MENU:
-#ifdef WPS_RC_MENU_PRE
- if ((button == WPS_RC_MENU) && (lastbutton != WPS_RC_MENU_PRE))
- break;
-#endif
-#endif
- lcd_stop_scroll();
-
- if (main_menu())
- return true;
-#ifdef HAVE_LCD_BITMAP
- if (global_settings.statusbar)
- lcd_setmargins(0, STATUSBAR_HEIGHT);
- else
- lcd_setmargins(0, 0);
-#endif
- restore = true;
- break;
-#endif /* WPS_MENU */
-
-#ifdef WPS_KEYLOCK
- /* key lock */
- case WPS_KEYLOCK:
- case WPS_KEYLOCK | BUTTON_REPEAT:
- keys_locked = !keys_locked;
- display_keylock_text(keys_locked);
- restore = true;
- waitfor_nokey();
- break;
-#endif
-
-#if (CONFIG_KEYPAD == RECORDER_PAD) || (CONFIG_KEYPAD == IRIVER_H100_PAD)
- /* play settings */
- case WPS_QUICK:
- if (quick_screen(CONTEXT_WPS, WPS_QUICK))
- return SYS_USB_CONNECTED;
- restore = true;
- lastbutton = 0;
- break;
-
- /* screen settings */
-#ifdef BUTTON_F3
- case BUTTON_F3:
- if (quick_screen(CONTEXT_WPS, BUTTON_F3))
- return SYS_USB_CONNECTED;
- restore = true;
- break;
-#endif
-
- /* pitch screen */
-#if CONFIG_KEYPAD == RECORDER_PAD
- case BUTTON_ON | BUTTON_UP:
- case BUTTON_ON | BUTTON_DOWN:
- if (2 == pitch_screen())
- return SYS_USB_CONNECTED;
- restore = true;
- break;
-#endif
-#endif
-
-#ifdef AB_REPEAT_ENABLE
-
-#ifdef WPS_AB_SET_A_MARKER
- /* set A marker for A-B repeat */
- case WPS_AB_SET_A_MARKER:
- if (ab_repeat_mode_enabled())
- ab_set_A_marker(id3->elapsed);
- break;
-#endif
-
-#ifdef WPS_AB_SET_B_MARKER
- /* set B marker for A-B repeat and jump to A */
- case WPS_AB_SET_B_MARKER:
- if (ab_repeat_mode_enabled())
- {
- ab_set_B_marker(id3->elapsed);
- ab_jump_to_A_marker();
- update_track = true;
- }
- break;
-#endif
-
-#ifdef WPS_AB_RESET_AB_MARKERS
- /* reset A&B markers */
- case WPS_AB_RESET_AB_MARKERS:
- if (ab_repeat_mode_enabled())
- {
- ab_reset_markers();
- update_track = true;
- }
- break;
-#endif
-
-#endif /* AB_REPEAT_ENABLE */
-
- /* stop and exit wps */
-#ifdef WPS_EXIT
- case WPS_EXIT:
-# ifdef WPS_EXIT_PRE
- if (lastbutton != WPS_EXIT_PRE)
- break;
-# endif
- exit = true;
-
-# ifdef WPS_RC_EXIT
- case WPS_RC_EXIT:
-# ifdef WPS_RC_EXIT_PRE
- if (lastbutton != WPS_RC_EXIT_PRE)
- break;
-# endif
- exit = true;
-# endif
- break;
-#endif
-
-#ifdef WPS_ID3
- case WPS_ID3:
- browse_id3();
- restore = true;
- break;
-#endif
-
- case BUTTON_NONE: /* Timeout */
- update_track = true;
- break;
-
- default:
- if(default_event_handler(button) == SYS_USB_CONNECTED)
- return SYS_USB_CONNECTED;
- update_track = true;
- break;
- }
-
- if (update_track)
- {
- if (update())
- {
- /* set dir browser to current playing song */
- if (global_settings.browse_current &&
- current_track_path[0] != '\0')
- set_current_file(current_track_path);
-
- return 0;
- }
- update_track = false;
- }
-
- if (exit) {
-#ifdef HAVE_LCD_CHARCELLS
- status_set_record(false);
- status_set_audio(false);
-#endif
- if (global_settings.fade_on_stop)
- fade(0);
-
- lcd_stop_scroll();
- bookmark_autobookmark();
- audio_stop();
-#ifdef AB_REPEAT_ENABLE
- ab_reset_markers();
-#endif
-
- /* Keys can be locked when exiting, so either unlock here
- or implement key locking in tree.c too */
- keys_locked=false;
-
- /* set dir browser to current playing song */
- if (global_settings.browse_current &&
- current_track_path[0] != '\0')
- set_current_file(current_track_path);
-
- return 0;
- }
-
- if ( button )
- ata_spin();
-
- if (restore &&
- ((restoretimer == 0) ||
- (restoretimer < current_tick)))
- {
- restore = false;
- restoretimer = 0;
- if (wps_display(id3, nid3))
- {
- /* set dir browser to current playing song */
- if (global_settings.browse_current &&
- current_track_path[0] != '\0')
- set_current_file(current_track_path);
-
- return 0;
- }
-
- if (id3)
- wps_refresh(id3, nid3, 0, WPS_REFRESH_NON_STATIC);
- }
- if (button != BUTTON_NONE)
- lastbutton = button;
- }
- return 0; /* unreachable - just to reduce compiler warnings */
-}
diff --git a/apps/wps.h b/apps/wps.h
deleted file mode 100644
index 61b3d002fc..0000000000
--- a/apps/wps.h
+++ /dev/null
@@ -1,205 +0,0 @@
-/***************************************************************************
- * __________ __ ___.
- * Open \______ \ ____ ____ | | _\_ |__ _______ ___
- * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
- * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
- * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
- * \/ \/ \/ \/ \/
- * $Id$
- *
- * Copyright (C) 2002 Jerome Kuptz
- *
- * All files in this archive are subject to the GNU General Public License.
- * See the file COPYING in the source tree root for full license agreement.
- *
- * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
- * KIND, either express or implied.
- *
- ****************************************************************************/
-#ifndef _WPS_H
-#define _WPS_H
-#include "id3.h"
-#include "playlist.h"
-
-/* button definitions */
-#if (CONFIG_KEYPAD == IRIVER_H100_PAD) || \
- (CONFIG_KEYPAD == IRIVER_H300_PAD)
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL BUTTON_UP
-#define WPS_DECVOL BUTTON_DOWN
-#define WPS_PAUSE (BUTTON_ON | BUTTON_REL)
-#define WPS_PAUSE_PRE BUTTON_ON
-#define WPS_MENU (BUTTON_MODE | BUTTON_REL)
-#define WPS_MENU_PRE BUTTON_MODE
-#define WPS_BROWSE (BUTTON_SELECT | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_SELECT
-#define WPS_EXIT (BUTTON_OFF | BUTTON_REL)
-#define WPS_EXIT_PRE BUTTON_OFF
-#define WPS_ID3 (BUTTON_MODE | BUTTON_ON)
-#define WPS_CONTEXT (BUTTON_SELECT | BUTTON_REPEAT)
-#define WPS_QUICK (BUTTON_MODE | BUTTON_REPEAT)
-#define WPS_NEXT_DIR (BUTTON_RIGHT | BUTTON_ON)
-#define WPS_PREV_DIR (BUTTON_LEFT | BUTTON_ON)
-
-#define WPS_RC_NEXT_DIR (BUTTON_RC_BITRATE | BUTTON_REL)
-#define WPS_RC_PREV_DIR (BUTTON_RC_SOURCE | BUTTON_REL)
-#define WPS_RC_NEXT (BUTTON_RC_FF | BUTTON_REL)
-#define WPS_RC_NEXT_PRE BUTTON_RC_FF
-#define WPS_RC_PREV (BUTTON_RC_REW | BUTTON_REL)
-#define WPS_RC_PREV_PRE BUTTON_RC_REW
-#define WPS_RC_FFWD (BUTTON_RC_FF | BUTTON_REPEAT)
-#define WPS_RC_REW (BUTTON_RC_REW | BUTTON_REPEAT)
-#define WPS_RC_PAUSE BUTTON_RC_ON
-#define WPS_RC_INCVOL BUTTON_RC_VOL_UP
-#define WPS_RC_DECVOL BUTTON_RC_VOL_DOWN
-#define WPS_RC_EXIT (BUTTON_RC_STOP | BUTTON_REL)
-#define WPS_RC_EXIT_PRE BUTTON_RC_STOP
-#define WPS_RC_MENU (BUTTON_RC_MODE | BUTTON_REL)
-#define WPS_RC_MENU_PRE BUTTON_RC_MODE
-#define WPS_RC_BROWSE (BUTTON_RC_MENU | BUTTON_REL)
-#define WPS_RC_BROWSE_PRE BUTTON_RC_MENU
-
-#elif CONFIG_KEYPAD == RECORDER_PAD
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL BUTTON_UP
-#define WPS_DECVOL BUTTON_DOWN
-#define WPS_PAUSE_PRE BUTTON_PLAY
-#define WPS_PAUSE (BUTTON_PLAY | BUTTON_REL)
-#define WPS_MENU (BUTTON_F1 | BUTTON_REL)
-#define WPS_MENU_PRE BUTTON_F1
-#define WPS_BROWSE (BUTTON_ON | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_ON
-#define WPS_EXIT BUTTON_OFF
-#define WPS_KEYLOCK (BUTTON_F1 | BUTTON_DOWN)
-#define WPS_ID3 (BUTTON_F1 | BUTTON_ON)
-#define WPS_CONTEXT (BUTTON_PLAY | BUTTON_REPEAT)
-#define WPS_QUICK BUTTON_F2
-
-#ifdef AB_REPEAT_ENABLE
-#define WPS_AB_SET_A_MARKER (BUTTON_ON | BUTTON_LEFT)
-#define WPS_AB_SET_B_MARKER (BUTTON_ON | BUTTON_RIGHT)
-#define WPS_AB_RESET_AB_MARKERS (BUTTON_ON | BUTTON_OFF)
-#endif
-
-#define WPS_RC_NEXT BUTTON_RC_RIGHT
-#define WPS_RC_PREV BUTTON_RC_LEFT
-#define WPS_RC_PAUSE BUTTON_RC_PLAY
-#define WPS_RC_INCVOL BUTTON_RC_VOL_UP
-#define WPS_RC_DECVOL BUTTON_RC_VOL_DOWN
-#define WPS_RC_EXIT BUTTON_RC_STOP
-
-#elif CONFIG_KEYPAD == PLAYER_PAD
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL (BUTTON_MENU | BUTTON_RIGHT)
-#define WPS_DECVOL (BUTTON_MENU | BUTTON_LEFT)
-#define WPS_PAUSE_PRE BUTTON_PLAY
-#define WPS_PAUSE (BUTTON_PLAY | BUTTON_REL)
-#define WPS_MENU (BUTTON_MENU | BUTTON_REL)
-#define WPS_MENU_PRE BUTTON_MENU
-#define WPS_BROWSE (BUTTON_ON | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_ON
-#define WPS_EXIT BUTTON_STOP
-#define WPS_KEYLOCK (BUTTON_MENU | BUTTON_STOP)
-#define WPS_ID3 (BUTTON_MENU | BUTTON_ON)
-#define WPS_CONTEXT (BUTTON_PLAY | BUTTON_REPEAT)
-
-#ifdef AB_REPEAT_ENABLE
-#define WPS_AB_SET_A_MARKER (BUTTON_ON | BUTTON_LEFT)
-#define WPS_AB_SET_B_MARKER (BUTTON_ON | BUTTON_RIGHT)
-#define WPS_AB_RESET_AB_MARKERS (BUTTON_ON | BUTTON_STOP)
-#endif
-
-#define WPS_RC_NEXT BUTTON_RC_RIGHT
-#define WPS_RC_PREV BUTTON_RC_LEFT
-#define WPS_RC_PAUSE BUTTON_RC_PLAY
-#define WPS_RC_INCVOL BUTTON_RC_VOL_UP
-#define WPS_RC_DECVOL BUTTON_RC_VOL_DOWN
-#define WPS_RC_EXIT BUTTON_RC_STOP
-
-#elif CONFIG_KEYPAD == ONDIO_PAD
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL BUTTON_UP
-#define WPS_DECVOL BUTTON_DOWN
-#define WPS_PAUSE BUTTON_OFF
-/* #define WPS_MENU Ondio can't have both main menu and context menu in wps */
-#define WPS_BROWSE (BUTTON_MENU | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_MENU
-#define WPS_KEYLOCK (BUTTON_MENU | BUTTON_DOWN)
-#define WPS_EXIT (BUTTON_OFF | BUTTON_REPEAT)
-#define WPS_CONTEXT (BUTTON_MENU | BUTTON_REPEAT)
-
-#elif CONFIG_KEYPAD == GMINI100_PAD
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL BUTTON_UP
-#define WPS_DECVOL BUTTON_DOWN
-#define WPS_PAUSE BUTTON_PLAY
-#define WPS_MENU (BUTTON_MENU | BUTTON_REL)
-#define WPS_MENU_PRE BUTTON_MENU
-#define WPS_BROWSE (BUTTON_ON | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_ON
-#define WPS_EXIT BUTTON_OFF
-#define WPS_KEYLOCK (BUTTON_MENU | BUTTON_DOWN)
-#define WPS_ID3 (BUTTON_MENU | BUTTON_ON)
-
-#elif (CONFIG_KEYPAD == IPOD_4G_PAD) || (CONFIG_KEYPAD == IPOD_NANO_PAD)
-
-/* TODO: Check WPS button assignments */
-
-#define WPS_NEXT (BUTTON_RIGHT | BUTTON_REL)
-#define WPS_NEXT_PRE BUTTON_RIGHT
-#define WPS_PREV (BUTTON_LEFT | BUTTON_REL)
-#define WPS_PREV_PRE BUTTON_LEFT
-#define WPS_FFWD (BUTTON_RIGHT | BUTTON_REPEAT)
-#define WPS_REW (BUTTON_LEFT | BUTTON_REPEAT)
-#define WPS_INCVOL BUTTON_UP
-#define WPS_DECVOL BUTTON_DOWN
-#define WPS_PAUSE BUTTON_OFF
-/* #define WPS_MENU iPod can't have both main menu and context menu in wps */
-#define WPS_BROWSE (BUTTON_MENU | BUTTON_REL)
-#define WPS_BROWSE_PRE BUTTON_MENU
-#define WPS_KEYLOCK (BUTTON_MENU | BUTTON_DOWN)
-#define WPS_EXIT (BUTTON_OFF | BUTTON_REPEAT)
-#define WPS_CONTEXT (BUTTON_MENU | BUTTON_REPEAT)
-
-
-#endif
-
-extern bool keys_locked;
-extern bool wps_time_countup;
-
-long wps_show(void);
-bool refresh_wps(bool refresh_scroll);
-void handle_usb(void);
-
-#if CONFIG_KEYPAD == RECORDER_PAD
-bool f2_screen(void);
-bool f3_screen(void);
-#endif
-
-#endif
-
diff --git a/docs/CREDITS b/docs/CREDITS
index 2877fd2156..9380a0e321 100644
--- a/docs/CREDITS
+++ b/docs/CREDITS
@@ -139,3 +139,4 @@ Alyssa Milburn
Kevin Ferrare
Anton Oleynikov
Mark Arigo
+Magnus Westerlund
diff --git a/wps/rockbox_default.rwps b/wps/rockbox_default.rwps
new file mode 100644
index 0000000000..b1427cab84
--- /dev/null
+++ b/wps/rockbox_default.rwps
@@ -0,0 +1,2 @@
+# Dummy file to allow Rockbox to reset to the default WPS config.
+# Do not edit this file. It's never actually loaded by Rockbox.