summaryrefslogtreecommitdiff
path: root/apps
diff options
context:
space:
mode:
Diffstat (limited to 'apps')
-rw-r--r--apps/wps-display.c224
-rw-r--r--apps/wps-display.h5
-rw-r--r--apps/wps.c37
3 files changed, 147 insertions, 119 deletions
diff --git a/apps/wps-display.c b/apps/wps-display.c
index c45008ef93..e11ec8a520 100644
--- a/apps/wps-display.c
+++ b/apps/wps-display.c
@@ -17,8 +17,8 @@
17 * 17 *
18 ****************************************************************************/ 18 ****************************************************************************/
19 19
20/* ID3 formatting based on code from the MAD Winamp plugin (in_mad.dll), 20/* ID3 formatting based on code from the MAD Winamp plugin (in_mad.dll),
21 * Copyright (C) 2000-2001 Robert Leslie. 21 * Copyright (C) 2000-2001 Robert Leslie.
22 * See http://www.mars.org/home/rob/proj/mpeg/ for more information. 22 * See http://www.mars.org/home/rob/proj/mpeg/ for more information.
23 */ 23 */
24 24
@@ -61,7 +61,7 @@
61#endif 61#endif
62#define MAX_SUBLINES 12 62#define MAX_SUBLINES 12
63#define DEFAULT_SUBLINE_TIME_MULTIPLIER 20 /* (10ths of sec) */ 63#define DEFAULT_SUBLINE_TIME_MULTIPLIER 20 /* (10ths of sec) */
64#define BASE_SUBLINE_TIME 10 /* base time that multiplier is applied to 64#define BASE_SUBLINE_TIME 10 /* base time that multiplier is applied to
65 (1/HZ sec, or 100ths of sec) */ 65 (1/HZ sec, or 100ths of sec) */
66#define SUBLINE_RESET -1 66#define SUBLINE_RESET -1
67 67
@@ -78,7 +78,7 @@ static char format_buffer[FORMAT_BUFFER_SIZE];
78static char* format_lines[MAX_LINES][MAX_SUBLINES]; 78static char* format_lines[MAX_LINES][MAX_SUBLINES];
79static unsigned char line_type[MAX_LINES][MAX_SUBLINES]; 79static unsigned char line_type[MAX_LINES][MAX_SUBLINES];
80static unsigned char time_mult[MAX_LINES][MAX_SUBLINES]; 80static unsigned char time_mult[MAX_LINES][MAX_SUBLINES];
81static long subline_expire_time[MAX_LINES]; 81static long subline_expire_time[MAX_LINES];
82static int curr_subline[MAX_LINES]; 82static int curr_subline[MAX_LINES];
83 83
84static int ff_rewind_count; 84static int ff_rewind_count;
@@ -115,7 +115,7 @@ char* wps_get_genre(struct mp3entry* id3)
115{ 115{
116 if( id3->genre_string ) 116 if( id3->genre_string )
117 return id3->genre_string ; 117 return id3->genre_string ;
118 118
119 if (id3->genre < sizeof(genres)/sizeof(char*)) 119 if (id3->genre < sizeof(genres)/sizeof(char*))
120 return (char*)genres[id3->genre]; 120 return (char*)genres[id3->genre];
121 return NULL; 121 return NULL;
@@ -128,10 +128,10 @@ static void wps_format(char* fmt)
128 char* start_of_line = format_buffer; 128 char* start_of_line = format_buffer;
129 int line = 0; 129 int line = 0;
130 int subline; 130 int subline;
131 131
132 strncpy(format_buffer, fmt, sizeof(format_buffer)); 132 strncpy(format_buffer, fmt, sizeof(format_buffer));
133 format_buffer[sizeof(format_buffer) - 1] = 0; 133 format_buffer[sizeof(format_buffer) - 1] = 0;
134 134
135 for (line=0; line<MAX_LINES; line++) 135 for (line=0; line<MAX_LINES; line++)
136 { 136 {
137 for (subline=0; subline<MAX_SUBLINES; subline++) 137 for (subline=0; subline<MAX_SUBLINES; subline++)
@@ -152,7 +152,7 @@ static void wps_format(char* fmt)
152 switch (*buf) 152 switch (*buf)
153 { 153 {
154 /* skip % sequences so "%;" doesn't start a new subline */ 154 /* skip % sequences so "%;" doesn't start a new subline */
155 case '%': 155 case '%':
156 buf++; 156 buf++;
157 break; 157 break;
158 158
@@ -165,7 +165,7 @@ static void wps_format(char* fmt)
165 165
166 if (*start_of_line != '#') /* A comment? */ 166 if (*start_of_line != '#') /* A comment? */
167 line++; 167 line++;
168 168
169 if (line < MAX_LINES) 169 if (line < MAX_LINES)
170 { 170 {
171 /* the next line starts on the next byte */ 171 /* the next line starts on the next byte */
@@ -184,7 +184,7 @@ static void wps_format(char* fmt)
184 } 184 }
185 else /* exceeded max sublines, skip rest of line */ 185 else /* exceeded max sublines, skip rest of line */
186 { 186 {
187 while (*(++buf)) 187 while (*(++buf))
188 { 188 {
189 if ((*buf == '\r') || (*buf == '\n')) 189 if ((*buf == '\r') || (*buf == '\n'))
190 { 190 {
@@ -213,17 +213,17 @@ bool wps_load(char* file, bool display)
213 int fd; 213 int fd;
214 214
215 fd = open(file, O_RDONLY); 215 fd = open(file, O_RDONLY);
216 216
217 if (fd >= 0) 217 if (fd >= 0)
218 { 218 {
219 int numread = read(fd, buffer, sizeof(buffer) - 1); 219 int numread = read(fd, buffer, sizeof(buffer) - 1);
220 220
221 if (numread > 0) 221 if (numread > 0)
222 { 222 {
223 buffer[numread] = 0; 223 buffer[numread] = 0;
224 wps_format(buffer); 224 wps_format(buffer);
225 } 225 }
226 226
227 close(fd); 227 close(fd);
228 228
229 if ( display ) { 229 if ( display ) {
@@ -237,7 +237,7 @@ bool wps_load(char* file, bool display)
237 any_defined_line = false; 237 any_defined_line = false;
238 for (i=0; i<MAX_LINES; i++) 238 for (i=0; i<MAX_LINES; i++)
239 { 239 {
240 if (format_lines[i][s]) 240 if (format_lines[i][s])
241 { 241 {
242 if (*format_lines[i][s] == 0) 242 if (*format_lines[i][s] == 0)
243 lcd_puts(0,i," "); 243 lcd_puts(0,i," ");
@@ -261,7 +261,7 @@ bool wps_load(char* file, bool display)
261 261
262 return numread > 0; 262 return numread > 0;
263 } 263 }
264 264
265 return false; 265 return false;
266} 266}
267 267
@@ -281,7 +281,7 @@ static void format_time(char* buf, int buf_size, int time)
281 * buf - buffer extract part to. 281 * buf - buffer extract part to.
282 * buf_size - size of buffer. 282 * buf_size - size of buffer.
283 * path - path to extract from. 283 * path - path to extract from.
284 * level - what to extract. 0 is file name, 1 is parent of file, 2 is 284 * level - what to extract. 0 is file name, 1 is parent of file, 2 is
285 * parent of parent, etc. 285 * parent of parent, etc.
286 * 286 *
287 * Returns buf if the desired level was found, NULL otherwise. 287 * Returns buf if the desired level was found, NULL otherwise.
@@ -303,7 +303,7 @@ static char* get_dir(char* buf, int buf_size, char* path, int level)
303 { 303 {
304 break; 304 break;
305 } 305 }
306 306
307 level--; 307 level--;
308 last_sep = sep - 1; 308 last_sep = sep - 1;
309 } 309 }
@@ -323,32 +323,41 @@ static char* get_dir(char* buf, int buf_size, char* path, int level)
323/* Get the tag specified by the two characters at fmt. 323/* Get the tag specified by the two characters at fmt.
324 * 324 *
325 * id3 - ID3 data to get tag values from. 325 * id3 - ID3 data to get tag values from.
326 * nid3 - next-song ID3 data to get tag values from.
326 * tag - string (of two characters) specifying the tag to get. 327 * tag - string (of two characters) specifying the tag to get.
327 * buf - buffer to certain tags, such as track number, play time or 328 * buf - buffer to certain tags, such as track number, play time or
328 * directory name. 329 * directory name.
329 * buf_size - size of buffer. 330 * buf_size - size of buffer.
330 * flags - returns the type of the line. See constants i wps-display.h 331 * flags - returns the type of the line. See constants i wps-display.h
331 * 332 *
332 * Returns the tag. NULL indicates the tag wasn't available. 333 * Returns the tag. NULL indicates the tag wasn't available.
333 */ 334 */
334static char* get_tag(struct mp3entry* id3, 335static char* get_tag(struct mp3entry* cid3,
335 char* tag, 336 struct mp3entry* nid3,
336 char* buf, 337 char* tag,
338 char* buf,
337 int buf_size, 339 int buf_size,
338 unsigned char* tag_len, 340 unsigned char* tag_len,
339 unsigned char* subline_time_mult, 341 unsigned char* subline_time_mult,
340 unsigned char* flags) 342 unsigned char* flags)
341{ 343{
344 struct mp3entry *id3 = cid3; /* default to current song */
345
342 if ((0 == tag[0]) || (0 == tag[1])) 346 if ((0 == tag[0]) || (0 == tag[1]))
343 { 347 {
344 *tag_len = 0; 348 *tag_len = 0;
345 return NULL; 349 return NULL;
346 } 350 }
347 351
348 *tag_len = 2; 352 *tag_len = 2;
349 353
350 switch (tag[0]) 354 switch (tag[0])
351 { 355 {
356 case 'I': /* ID3 Information */
357 id3 = nid3; /* display next-song data */
358 if(!id3)
359 return NULL; /* no such info (yet) */
360 /* fall-through */
352 case 'i': /* ID3 Information */ 361 case 'i': /* ID3 Information */
353 *flags |= WPS_REFRESH_STATIC; 362 *flags |= WPS_REFRESH_STATIC;
354 switch (tag[1]) 363 switch (tag[1])
@@ -358,7 +367,7 @@ static char* get_tag(struct mp3entry* id3,
358 367
359 case 'a': /* ID3 Artist */ 368 case 'a': /* ID3 Artist */
360 return id3->artist; 369 return id3->artist;
361 370
362 case 'n': /* ID3 Track Number */ 371 case 'n': /* ID3 Track Number */
363 if (id3->track_string) 372 if (id3->track_string)
364 return id3->track_string; 373 return id3->track_string;
@@ -368,13 +377,13 @@ static char* get_tag(struct mp3entry* id3,
368 return buf; 377 return buf;
369 } 378 }
370 return NULL; 379 return NULL;
371 380
372 case 'd': /* ID3 Album/Disc */ 381 case 'd': /* ID3 Album/Disc */
373 return id3->album; 382 return id3->album;
374 383
375 case 'c': /* ID3 Composer */ 384 case 'c': /* ID3 Composer */
376 return id3->composer; 385 return id3->composer;
377 386
378 case 'y': /* year */ 387 case 'y': /* year */
379 if( id3->year_string ) 388 if( id3->year_string )
380 return id3->year_string; 389 return id3->year_string;
@@ -411,6 +420,11 @@ static char* get_tag(struct mp3entry* id3,
411 } 420 }
412 break; 421 break;
413 422
423 case 'F': /* File Information */
424 id3 = nid3;
425 if(!id3)
426 return NULL; /* no such info (yet) */
427 /* fall-through */
414 case 'f': /* File Information */ 428 case 'f': /* File Information */
415 *flags |= WPS_REFRESH_STATIC; 429 *flags |= WPS_REFRESH_STATIC;
416 switch(tag[1]) 430 switch(tag[1])
@@ -511,7 +525,7 @@ static char* get_tag(struct mp3entry* id3,
511 525
512 case 'r': /* Remaining Time in Song */ 526 case 'r': /* Remaining Time in Song */
513 *flags |= WPS_REFRESH_DYNAMIC; 527 *flags |= WPS_REFRESH_DYNAMIC;
514 format_time(buf, buf_size, 528 format_time(buf, buf_size,
515 id3->length - id3->elapsed - ff_rewind_count); 529 id3->length - id3->elapsed - ff_rewind_count);
516 return buf; 530 return buf;
517 531
@@ -565,6 +579,11 @@ static char* get_tag(struct mp3entry* id3,
565 } 579 }
566 break; 580 break;
567 581
582 case 'D': /* Directory path information */
583 id3 = nid3; /* next song please! */
584 if(!id3)
585 return NULL; /* no such info (yet) */
586 /* fall-through */
568 case 'd': /* Directory path information */ 587 case 'd': /* Directory path information */
569 { 588 {
570 int level = tag[1] - '0'; 589 int level = tag[1] - '0';
@@ -578,38 +597,38 @@ static char* get_tag(struct mp3entry* id3,
578 break; 597 break;
579 598
580 case 't': /* set sub line time multiplier */ 599 case 't': /* set sub line time multiplier */
581 { 600 {
582 int d = 1; 601 int d = 1;
583 int time_mult = 0; 602 int time_mult = 0;
584 bool have_point = false; 603 bool have_point = false;
585 bool have_tenth = false; 604 bool have_tenth = false;
586 605
587 while (((tag[d] >= '0') && 606 while (((tag[d] >= '0') &&
588 (tag[d] <= '9')) || 607 (tag[d] <= '9')) ||
589 (tag[d] == '.')) 608 (tag[d] == '.'))
590 { 609 {
591 if (tag[d] != '.') 610 if (tag[d] != '.')
592 { 611 {
593 time_mult = time_mult * 10; 612 time_mult = time_mult * 10;
594 time_mult = time_mult + tag[d] - '0'; 613 time_mult = time_mult + tag[d] - '0';
595 if (have_point) 614 if (have_point)
596 { 615 {
597 have_tenth = true; 616 have_tenth = true;
598 d++; 617 d++;
599 break; 618 break;
600 } 619 }
601 } 620 }
602 else 621 else
603 { 622 {
604 have_point = true; 623 have_point = true;
605 } 624 }
606 d++; 625 d++;
607 } 626 }
608 627
609 if (have_tenth == false) 628 if (have_tenth == false)
610 time_mult *= 10; 629 time_mult *= 10;
611 630
612 *subline_time_mult = time_mult; 631 *subline_time_mult = time_mult;
613 *tag_len = d; 632 *tag_len = d;
614 633
615 buf[0] = 0; 634 buf[0] = 0;
@@ -617,13 +636,13 @@ static char* get_tag(struct mp3entry* id3,
617 } 636 }
618 break; 637 break;
619 } 638 }
620 639
621 return NULL; 640 return NULL;
622} 641}
623 642
624/* Skip to the end of the current %? conditional. 643/* Skip to the end of the current %? conditional.
625 * 644 *
626 * fmt - string to skip it. Should point to somewhere after the leading 645 * fmt - string to skip it. Should point to somewhere after the leading
627 * "<" char (and before or at the last ">"). 646 * "<" char (and before or at the last ">").
628 * to_else - if true, skip to the else part (after the "|", if any), else skip 647 * to_else - if true, skip to the else part (after the "|", if any), else skip
629 * to the end (the ">"). 648 * to the end (the ">").
@@ -640,19 +659,19 @@ static char* skip_conditional(char* fmt, bool to_else)
640 { 659 {
641 case '%': 660 case '%':
642 break; 661 break;
643 662
644 case '|': 663 case '|':
645 if (to_else && (1 == level)) 664 if (to_else && (1 == level))
646 return fmt; 665 return fmt;
647 666
648 continue; 667 continue;
649 668
650 case '>': 669 case '>':
651 if (0 == --level) 670 if (0 == --level)
652 { 671 {
653 if (to_else) 672 if (to_else)
654 fmt--; 673 fmt--;
655 674
656 return fmt; 675 return fmt;
657 } 676 }
658 continue; 677 continue;
@@ -660,7 +679,7 @@ static char* skip_conditional(char* fmt, bool to_else)
660 default: 679 default:
661 continue; 680 continue;
662 } 681 }
663 682
664 switch (*fmt++) 683 switch (*fmt++)
665 { 684 {
666 case 0: 685 case 0:
@@ -669,22 +688,22 @@ static char* skip_conditional(char* fmt, bool to_else)
669 case '<': 688 case '<':
670 case '>': 689 case '>':
671 break; 690 break;
672 691
673 case '?': 692 case '?':
674 while (*fmt && ('<' != *fmt)) 693 while (*fmt && ('<' != *fmt))
675 fmt++; 694 fmt++;
676 695
677 if ('<' == *fmt) 696 if ('<' == *fmt)
678 fmt++; 697 fmt++;
679 698
680 level++; 699 level++;
681 break; 700 break;
682 701
683 default: 702 default:
684 break; 703 break;
685 } 704 }
686 } 705 }
687 706
688 return fmt; 707 return fmt;
689} 708}
690 709
@@ -693,14 +712,16 @@ static char* skip_conditional(char* fmt, bool to_else)
693 * buf - char buffer to write the display to. 712 * buf - char buffer to write the display to.
694 * buf_size - the size of buffer. 713 * buf_size - the size of buffer.
695 * id3 - the ID3 data to format with. 714 * id3 - the ID3 data to format with.
715 * nid3 - the ID3 data of the next song (might by NULL)
696 * fmt - format description. 716 * fmt - format description.
697 * flags - returns the type of the line. See constants i wps-display.h 717 * flags - returns the type of the line. See constants i wps-display.h
698 */ 718 */
699static void format_display(char* buf, 719static void format_display(char* buf,
700 int buf_size, 720 int buf_size,
701 struct mp3entry* id3, 721 struct mp3entry* id3,
702 char* fmt, 722 struct mp3entry* nid3, /* next song's id3 */
703 unsigned char* subline_time_mult, 723 char* fmt,
724 unsigned char* subline_time_mult,
704 unsigned char* flags) 725 unsigned char* flags)
705{ 726{
706 char temp_buf[128]; 727 char temp_buf[128];
@@ -719,10 +740,10 @@ static void format_display(char* buf,
719 case '%': 740 case '%':
720 ++fmt; 741 ++fmt;
721 break; 742 break;
722 743
723 case '|': 744 case '|':
724 case '>': 745 case '>':
725 if (level > 0) 746 if (level > 0)
726 { 747 {
727 fmt = skip_conditional(fmt, false); 748 fmt = skip_conditional(fmt, false);
728 level--; 749 level--;
@@ -734,18 +755,18 @@ static void format_display(char* buf,
734 *buf++ = *fmt++; 755 *buf++ = *fmt++;
735 continue; 756 continue;
736 } 757 }
737 758
738 switch (*fmt) 759 switch (*fmt)
739 { 760 {
740 case 0: 761 case 0:
741 *buf++ = '%'; 762 *buf++ = '%';
742 break; 763 break;
743 764
744 case 's': 765 case 's':
745 *flags |= WPS_REFRESH_SCROLL; 766 *flags |= WPS_REFRESH_SCROLL;
746 ++fmt; 767 ++fmt;
747 break; 768 break;
748 769
749 case '%': 770 case '%':
750 case '|': 771 case '|':
751 case '<': 772 case '<':
@@ -753,30 +774,30 @@ static void format_display(char* buf,
753 case ';': 774 case ';':
754 *buf++ = *fmt++; 775 *buf++ = *fmt++;
755 break; 776 break;
756 777
757 case '?': 778 case '?':
758 fmt++; 779 fmt++;
759 value = get_tag(id3, fmt, temp_buf, sizeof(temp_buf), 780 value = get_tag(id3, nid3, fmt, temp_buf, sizeof(temp_buf),
760 &tag_length, subline_time_mult, flags); 781 &tag_length, subline_time_mult, flags);
761 782
762 while (*fmt && ('<' != *fmt)) 783 while (*fmt && ('<' != *fmt))
763 fmt++; 784 fmt++;
764 785
765 if ('<' == *fmt) 786 if ('<' == *fmt)
766 fmt++; 787 fmt++;
767 788
768 /* No value, so skip to else part */ 789 /* No value, so skip to else part */
769 if ((!value) || (!strlen(value))) 790 if ((!value) || (!strlen(value)))
770 fmt = skip_conditional(fmt, true); 791 fmt = skip_conditional(fmt, true);
771 792
772 level++; 793 level++;
773 break; 794 break;
774 795
775 default: 796 default:
776 value = get_tag(id3, fmt, temp_buf, sizeof(temp_buf), 797 value = get_tag(id3, nid3, fmt, temp_buf, sizeof(temp_buf),
777 &tag_length, subline_time_mult, flags); 798 &tag_length, subline_time_mult, flags);
778 fmt += tag_length; 799 fmt += tag_length;
779 800
780 if (value) 801 if (value)
781 { 802 {
782 while (*value && (buf < buf_end)) 803 while (*value && (buf < buf_end))
@@ -784,7 +805,7 @@ static void format_display(char* buf,
784 } 805 }
785 } 806 }
786 } 807 }
787 808
788 *buf = 0; 809 *buf = 0;
789 810
790 /* if resulting line is an empty line, set the subline time to 0 */ 811 /* if resulting line is an empty line, set the subline time to 0 */
@@ -797,7 +818,9 @@ static void format_display(char* buf,
797 *flags = WPS_REFRESH_STATIC; 818 *flags = WPS_REFRESH_STATIC;
798} 819}
799 820
800bool wps_refresh(struct mp3entry* id3, int ffwd_offset, 821bool wps_refresh(struct mp3entry* id3,
822 struct mp3entry* nid3,
823 int ffwd_offset,
801 unsigned char refresh_mode) 824 unsigned char refresh_mode)
802{ 825{
803 char buf[MAX_PATH]; 826 char buf[MAX_PATH];
@@ -814,8 +837,8 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
814 /* to find out wether the peak meter is enabled we 837 /* to find out wether the peak meter is enabled we
815 assume it wasn't until we find a line that contains 838 assume it wasn't until we find a line that contains
816 the peak meter. We can't use peak_meter_enabled itself 839 the peak meter. We can't use peak_meter_enabled itself
817 because that would mean to turn off the meter thread 840 because that would mean to turn off the meter thread
818 temporarily. (That shouldn't matter unless yield 841 temporarily. (That shouldn't matter unless yield
819 or sleep is called but who knows...) 842 or sleep is called but who knows...)
820 */ 843 */
821 bool enable_pm = false; 844 bool enable_pm = false;
@@ -852,7 +875,7 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
852 875
853 /* if time to advance to next sub-line */ 876 /* if time to advance to next sub-line */
854 if (TIME_AFTER(current_tick, subline_expire_time[i] - 1) || 877 if (TIME_AFTER(current_tick, subline_expire_time[i] - 1) ||
855 (curr_subline[i] == SUBLINE_RESET)) 878 (curr_subline[i] == SUBLINE_RESET))
856 { 879 {
857 /* search all sublines until the next subline with time > 0 880 /* search all sublines until the next subline with time > 0
858 is found or we get back to the subline we started with */ 881 is found or we get back to the subline we started with */
@@ -860,7 +883,7 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
860 search_start = 0; 883 search_start = 0;
861 else 884 else
862 search_start = curr_subline[i]; 885 search_start = curr_subline[i];
863 for (search=0; search<MAX_SUBLINES; search++) 886 for (search=0; search<MAX_SUBLINES; search++)
864 { 887 {
865 curr_subline[i]++; 888 curr_subline[i]++;
866 889
@@ -884,37 +907,37 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
884 } 907 }
885 else 908 else
886 { 909 {
887 /* get initial time multiplier and 910 /* get initial time multiplier and
888 line type flags for this subline */ 911 line type flags for this subline */
889 format_display(buf, sizeof(buf), id3, 912 format_display(buf, sizeof(buf), id3, nid3,
890 format_lines[i][curr_subline[i]], 913 format_lines[i][curr_subline[i]],
891 &time_mult[i][curr_subline[i]], 914 &time_mult[i][curr_subline[i]],
892 &line_type[i][curr_subline[i]]); 915 &line_type[i][curr_subline[i]]);
893 916
894 /* only use this subline if subline time > 0 */ 917 /* only use this subline if subline time > 0 */
895 if (time_mult[i][curr_subline[i]] > 0) 918 if (time_mult[i][curr_subline[i]] > 0)
896 { 919 {
897 new_subline_refresh = true; 920 new_subline_refresh = true;
898 subline_expire_time[i] = current_tick + 921 subline_expire_time[i] = current_tick +
899 BASE_SUBLINE_TIME * time_mult[i][curr_subline[i]]; 922 BASE_SUBLINE_TIME * time_mult[i][curr_subline[i]];
900 break; 923 break;
901 } 924 }
902 } 925 }
903 } 926 }
904 927
905 } 928 }
906 929
907 update_line = false; 930 update_line = false;
908 931
909 if ( !format_lines[i][curr_subline[i]] ) 932 if ( !format_lines[i][curr_subline[i]] )
910 break; 933 break;
911 934
912 if ((line_type[i][curr_subline[i]] & refresh_mode) || 935 if ((line_type[i][curr_subline[i]] & refresh_mode) ||
913 (refresh_mode == WPS_REFRESH_ALL) || 936 (refresh_mode == WPS_REFRESH_ALL) ||
914 new_subline_refresh) 937 new_subline_refresh)
915 { 938 {
916 flags = 0; 939 flags = 0;
917 format_display(buf, sizeof(buf), id3, 940 format_display(buf, sizeof(buf), id3, nid3,
918 format_lines[i][curr_subline[i]], 941 format_lines[i][curr_subline[i]],
919 &time_mult[i][curr_subline[i]], 942 &time_mult[i][curr_subline[i]],
920 &flags); 943 &flags);
@@ -926,7 +949,7 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
926 int percent= 949 int percent=
927 id3->length? 950 id3->length?
928 (id3->elapsed + ff_rewind_count) * 100 / id3->length:0; 951 (id3->elapsed + ff_rewind_count) * 100 / id3->length:0;
929 slidebar(0, i*h + offset + 1, LCD_WIDTH, 6, 952 slidebar(0, i*h + offset + 1, LCD_WIDTH, 6,
930 percent, Grow_Right); 953 percent, Grow_Right);
931 update_line = true; 954 update_line = true;
932 } 955 }
@@ -937,8 +960,8 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
937 update_line = true; 960 update_line = true;
938 peak_meter_y = i * h + offset; 961 peak_meter_y = i * h + offset;
939 962
940 /* The user might decide to have the peak meter in the last 963 /* The user might decide to have the peak meter in the last
941 line so that it is only displayed if no status bar is 964 line so that it is only displayed if no status bar is
942 visible. If so we neither want do draw nor enable the 965 visible. If so we neither want do draw nor enable the
943 peak meter. */ 966 peak meter. */
944 if (peak_meter_y + h <= LCD_HEIGHT) { 967 if (peak_meter_y + h <= LCD_HEIGHT) {
@@ -987,7 +1010,7 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
987#endif 1010#endif
988 } 1011 }
989#ifdef HAVE_LCD_BITMAP 1012#ifdef HAVE_LCD_BITMAP
990 /* Now we know wether the peak meter is used. 1013 /* Now we know wether the peak meter is used.
991 So we can enable / disable the peak meter thread */ 1014 So we can enable / disable the peak meter thread */
992 peak_meter_enabled = enable_pm; 1015 peak_meter_enabled = enable_pm;
993#endif 1016#endif
@@ -996,12 +1019,12 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
996 if (global_settings.caption_backlight && id3) { 1019 if (global_settings.caption_backlight && id3) {
997 /* turn on backlight n seconds before track ends, and turn it off n 1020 /* turn on backlight n seconds before track ends, and turn it off n
998 seconds into the new track. n == backlight_timeout, or 5s */ 1021 seconds into the new track. n == backlight_timeout, or 5s */
999 int n = 1022 int n =
1000 backlight_timeout_value[global_settings.backlight_timeout] * 1000; 1023 backlight_timeout_value[global_settings.backlight_timeout] * 1000;
1001 1024
1002 if ( n < 1000 ) 1025 if ( n < 1000 )
1003 n = 5000; /* use 5s if backlight is always on or off */ 1026 n = 5000; /* use 5s if backlight is always on or off */
1004 1027
1005 if ((id3->elapsed < 1000) || 1028 if ((id3->elapsed < 1000) ||
1006 ((id3->length - id3->elapsed) < (unsigned)n)) 1029 ((id3->length - id3->elapsed) < (unsigned)n))
1007 backlight_on(); 1030 backlight_on();
@@ -1010,7 +1033,8 @@ bool wps_refresh(struct mp3entry* id3, int ffwd_offset,
1010 return true; 1033 return true;
1011} 1034}
1012 1035
1013bool wps_display(struct mp3entry* id3) 1036bool wps_display(struct mp3entry* id3,
1037 struct mp3entry* nid3)
1014{ 1038{
1015 lcd_clear_display(); 1039 lcd_clear_display();
1016 1040
@@ -1049,7 +1073,7 @@ bool wps_display(struct mp3entry* id3)
1049 } 1073 }
1050 } 1074 }
1051 yield(); 1075 yield();
1052 wps_refresh(id3, 0, WPS_REFRESH_ALL); 1076 wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
1053 status_draw(true); 1077 status_draw(true);
1054 lcd_update(); 1078 lcd_update();
1055 return false; 1079 return false;
@@ -1115,10 +1139,10 @@ static void draw_player_fullbar(char* buf, int buf_size,
1115 int digits[6]; 1139 int digits[6];
1116 int time; 1140 int time;
1117 char timestr[7]; 1141 char timestr[7];
1118 1142
1119 for (i=0; i < buf_size; i++) 1143 for (i=0; i < buf_size; i++)
1120 buf[i] = ' '; 1144 buf[i] = ' ';
1121 1145
1122 if(id3->elapsed >= id3->length) 1146 if(id3->elapsed >= id3->length)
1123 songpos = 55; 1147 songpos = 55;
1124 else { 1148 else {
@@ -1129,7 +1153,7 @@ static void draw_player_fullbar(char* buf, int buf_size,
1129 } 1153 }
1130 1154
1131 time=(id3->elapsed + ff_rewind_count); 1155 time=(id3->elapsed + ff_rewind_count);
1132 1156
1133 memset(timestr, 0, sizeof(timestr)); 1157 memset(timestr, 0, sizeof(timestr));
1134 format_time(timestr, sizeof(timestr), time); 1158 format_time(timestr, sizeof(timestr), time);
1135 for(lcd_char_pos=0; lcd_char_pos<6; lcd_char_pos++) { 1159 for(lcd_char_pos=0; lcd_char_pos<6; lcd_char_pos++) {
@@ -1166,22 +1190,22 @@ static void draw_player_fullbar(char* buf, int buf_size,
1166 } 1190 }
1167 } 1191 }
1168 } 1192 }
1169 1193
1170 for (i=0; i<=6; i++) { 1194 for (i=0; i<=6; i++) {
1171 for (j=0;j<5;j++) { 1195 for (j=0;j<5;j++) {
1172 player_progressbar[i] <<= 1; 1196 player_progressbar[i] <<= 1;
1173 player_progressbar[i] += binline[i*5+j]; 1197 player_progressbar[i] += binline[i*5+j];
1174 } 1198 }
1175 } 1199 }
1176 1200
1177 lcd_define_pattern(wps_progress_pat[lcd_char_pos+1],player_progressbar); 1201 lcd_define_pattern(wps_progress_pat[lcd_char_pos+1],player_progressbar);
1178 buf[lcd_char_pos]=wps_progress_pat[lcd_char_pos+1]; 1202 buf[lcd_char_pos]=wps_progress_pat[lcd_char_pos+1];
1179 1203
1180 } 1204 }
1181 1205
1182 /* make rest of the progressbar if necessary */ 1206 /* make rest of the progressbar if necessary */
1183 if (songpos/5>5) { 1207 if (songpos/5>5) {
1184 1208
1185 /* set the characters positions that use the full 5 pixel wide bar */ 1209 /* set the characters positions that use the full 5 pixel wide bar */
1186 for (lcd_char_pos=6; lcd_char_pos < (songpos/5); lcd_char_pos++) 1210 for (lcd_char_pos=6; lcd_char_pos < (songpos/5); lcd_char_pos++)
1187 buf[lcd_char_pos] = 0x86; /* '_' */ 1211 buf[lcd_char_pos] = 0x86; /* '_' */
@@ -1197,16 +1221,16 @@ static void draw_player_fullbar(char* buf, int buf_size,
1197 } 1221 }
1198 } 1222 }
1199 } 1223 }
1200 1224
1201 for (i=0; i<7; i++) { 1225 for (i=0; i<7; i++) {
1202 for (j=0;j<5;j++) { 1226 for (j=0;j<5;j++) {
1203 player_progressbar[i] <<= 1; 1227 player_progressbar[i] <<= 1;
1204 player_progressbar[i] += binline[i*5+j]; 1228 player_progressbar[i] += binline[i*5+j];
1205 } 1229 }
1206 } 1230 }
1207 1231
1208 lcd_define_pattern(wps_progress_pat[7],player_progressbar); 1232 lcd_define_pattern(wps_progress_pat[7],player_progressbar);
1209 1233
1210 buf[songpos/5]=wps_progress_pat[7]; 1234 buf[songpos/5]=wps_progress_pat[7];
1211 } 1235 }
1212} 1236}
diff --git a/apps/wps-display.h b/apps/wps-display.h
index 12eed07c8f..7e5df59b5e 100644
--- a/apps/wps-display.h
+++ b/apps/wps-display.h
@@ -33,8 +33,9 @@
33#define WPS_REFRESH_NON_STATIC (WPS_REFRESH_ALL & ~WPS_REFRESH_STATIC & ~WPS_REFRESH_SCROLL) 33#define WPS_REFRESH_NON_STATIC (WPS_REFRESH_ALL & ~WPS_REFRESH_STATIC & ~WPS_REFRESH_SCROLL)
34 34
35 35
36bool wps_refresh(struct mp3entry* id3, int ffwd_offset, unsigned char refresh_mode); 36bool wps_refresh(struct mp3entry* id3, struct mp3entry* nid3,
37bool wps_display(struct mp3entry* id3); 37 int ffwd_offset, unsigned char refresh_mode);
38bool wps_display(struct mp3entry* id3, struct mp3entry* nid3);
38bool wps_load(char* file, bool display); 39bool wps_load(char* file, bool display);
39void wps_reset(void); 40void wps_reset(void);
40char* wps_get_genre(struct mp3entry* id3); 41char* wps_get_genre(struct mp3entry* id3);
diff --git a/apps/wps.c b/apps/wps.c
index 858a93c934..18de01956c 100644
--- a/apps/wps.c
+++ b/apps/wps.c
@@ -54,6 +54,7 @@ bool keys_locked = false;
54static bool ff_rewind = false; 54static bool ff_rewind = false;
55static bool paused = false; 55static bool paused = false;
56static struct mp3entry* id3 = NULL; 56static struct mp3entry* id3 = NULL;
57static struct mp3entry* nid3 = NULL;
57static char current_track_path[MAX_PATH+1]; 58static char current_track_path[MAX_PATH+1];
58 59
59#if defined(HAVE_PLAYER_KEYPAD) || defined(HAVE_NEO_KEYPAD) 60#if defined(HAVE_PLAYER_KEYPAD) || defined(HAVE_NEO_KEYPAD)
@@ -383,11 +384,11 @@ static bool ffwd_rew(int button)
383 } 384 }
384 385
385 if(wps_time_countup == false) 386 if(wps_time_countup == false)
386 wps_refresh(id3, -ff_rewind_count, 387 wps_refresh(id3, nid3, -ff_rewind_count,
387 WPS_REFRESH_PLAYER_PROGRESS | 388 WPS_REFRESH_PLAYER_PROGRESS |
388 WPS_REFRESH_DYNAMIC); 389 WPS_REFRESH_DYNAMIC);
389 else 390 else
390 wps_refresh(id3, ff_rewind_count, 391 wps_refresh(id3, nid3, ff_rewind_count,
391 WPS_REFRESH_PLAYER_PROGRESS | 392 WPS_REFRESH_PLAYER_PROGRESS |
392 WPS_REFRESH_DYNAMIC); 393 WPS_REFRESH_DYNAMIC);
393 394
@@ -423,7 +424,7 @@ static bool ffwd_rew(int button)
423 424
424 /* let mpeg thread update id3->elapsed before calling wps_refresh */ 425 /* let mpeg thread update id3->elapsed before calling wps_refresh */
425 yield(); 426 yield();
426 wps_refresh(id3, 0, WPS_REFRESH_ALL); 427 wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
427 return usb; 428 return usb;
428} 429}
429 430
@@ -436,17 +437,18 @@ static bool update(void)
436 { 437 {
437 lcd_stop_scroll(); 438 lcd_stop_scroll();
438 id3 = mpeg_current_track(); 439 id3 = mpeg_current_track();
439 if (wps_display(id3)) 440 nid3 = mpeg_next_track();
441 if (wps_display(id3, nid3))
440 retcode = true; 442 retcode = true;
441 else 443 else
442 wps_refresh(id3, 0, WPS_REFRESH_ALL); 444 wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
443 445
444 if (id3) 446 if (id3)
445 memcpy(current_track_path, id3->path, sizeof(current_track_path)); 447 memcpy(current_track_path, id3->path, sizeof(current_track_path));
446 } 448 }
447 449
448 if (id3) 450 if (id3)
449 wps_refresh(id3, 0, WPS_REFRESH_NON_STATIC); 451 wps_refresh(id3, nid3, 0, WPS_REFRESH_NON_STATIC);
450 452
451 status_draw(false); 453 status_draw(false);
452 454
@@ -632,7 +634,7 @@ int wps_show(void)
632 bool exit = false; 634 bool exit = false;
633 bool update_track = false; 635 bool update_track = false;
634 636
635 id3 = NULL; 637 id3 = nid3 = NULL;
636 current_track_path[0] = '\0'; 638 current_track_path[0] = '\0';
637 639
638#ifdef HAVE_LCD_CHARCELLS 640#ifdef HAVE_LCD_CHARCELLS
@@ -650,10 +652,11 @@ int wps_show(void)
650 if(mpeg_status() & MPEG_STATUS_PLAY) 652 if(mpeg_status() & MPEG_STATUS_PLAY)
651 { 653 {
652 id3 = mpeg_current_track(); 654 id3 = mpeg_current_track();
655 nid3 = mpeg_next_track();
653 if (id3) { 656 if (id3) {
654 if (wps_display(id3)) 657 if (wps_display(id3, nid3))
655 return 0; 658 return 0;
656 wps_refresh(id3, 0, WPS_REFRESH_ALL); 659 wps_refresh(id3, nid3, 0, WPS_REFRESH_ALL);
657 660
658 memcpy(current_track_path, id3->path, sizeof(current_track_path)); 661 memcpy(current_track_path, id3->path, sizeof(current_track_path));
659 } 662 }
@@ -703,7 +706,7 @@ int wps_show(void)
703 sleep(1); 706 sleep(1);
704 707
705 if (TIME_AFTER(current_tick, next_refresh)) { 708 if (TIME_AFTER(current_tick, next_refresh)) {
706 wps_refresh(id3, 0, WPS_REFRESH_PEAK_METER); 709 wps_refresh(id3, nid3, 0, WPS_REFRESH_PEAK_METER);
707 next_refresh = current_tick + HZ / peak_meter_fps; 710 next_refresh = current_tick + HZ / peak_meter_fps;
708 } 711 }
709 } 712 }
@@ -712,12 +715,12 @@ int wps_show(void)
712 /* In energy saver mode the cpu may sleep a 715 /* In energy saver mode the cpu may sleep a
713 little bit while waiting for buttons */ 716 little bit while waiting for buttons */
714 else { 717 else {
715 for (i = 0; i < 4; i++) { 718 for (i = 0; i < 4; i++) {
716 button = button_get_w_tmo(HZ / peak_meter_fps); 719 button = button_get_w_tmo(HZ / peak_meter_fps);
717 if (button != 0) { 720 if (button != 0) {
718 break; 721 break;
719 } 722 }
720 wps_refresh(id3, 0, WPS_REFRESH_PEAK_METER); 723 wps_refresh(id3, nid3, 0, WPS_REFRESH_PEAK_METER);
721 } 724 }
722 } 725 }
723 } 726 }
@@ -1008,7 +1011,7 @@ int wps_show(void)
1008 1011
1009 if (restore) { 1012 if (restore) {
1010 restore = false; 1013 restore = false;
1011 if (wps_display(id3)) 1014 if (wps_display(id3, nid3))
1012 { 1015 {
1013 /* set dir browser to current playing song */ 1016 /* set dir browser to current playing song */
1014 if (global_settings.browse_current && 1017 if (global_settings.browse_current &&
@@ -1019,7 +1022,7 @@ int wps_show(void)
1019 } 1022 }
1020 1023
1021 if (id3) 1024 if (id3)
1022 wps_refresh(id3, 0, WPS_REFRESH_NON_STATIC); 1025 wps_refresh(id3, nid3, 0, WPS_REFRESH_NON_STATIC);
1023 } 1026 }
1024 if(button != BUTTON_NONE) 1027 if(button != BUTTON_NONE)
1025 lastbutton = button; 1028 lastbutton = button;