Adapt the remaining plugins to put the greyscale isr on cop. Now they can be used...
[Rockbox.git] / apps / plugins / credits.c
blobc0967c6235ca8e5041b27f8fe20bcfa5f8f7313d
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2002 by Robert Hak <rhak at ramapo.edu>
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
18 ****************************************************************************/
19 #include "plugin.h"
20 #include "helper.h"
22 PLUGIN_HEADER
24 static struct plugin_api* rb;
26 const char* const credits[] = {
27 #include "credits.raw" /* generated list of names from docs/CREDITS */
30 bool STOP_AUTOSCROLL(int action)
32 switch (action)
34 case ACTION_STD_CANCEL:
35 case ACTION_STD_OK:
36 case ACTION_STD_NEXT:
37 case ACTION_STD_NEXTREPEAT:
38 case ACTION_STD_PREV:
39 case ACTION_STD_PREVREPEAT:
40 return true;
41 default:
42 return false;
44 return false;
47 #ifdef HAVE_LCD_CHARCELLS
49 void roll_credits(void)
51 int numnames = sizeof(credits)/sizeof(char*);
52 int curr_name = 0;
53 int curr_len = rb->utf8length(credits[0]);
54 int curr_index = 0;
55 int curr_line = 0;
56 int name, len, new_len, line, x;
58 while (1)
60 rb->lcd_clear_display();
62 name = curr_name;
63 x = -curr_index;
64 len = curr_len;
65 line = curr_line;
67 while (x < 11)
69 int x2;
71 if (x < 0)
72 rb->lcd_puts(0, line,
73 credits[name] + rb->utf8seek(credits[name], -x));
74 else
75 rb->lcd_puts(x, line, credits[name]);
77 if (++name >= numnames)
78 break;
80 line ^= 1;
82 x2 = x + len/2;
83 if ((unsigned)x2 < 11)
84 rb->lcd_putc(x2, line, '*');
86 new_len = rb->utf8length(credits[name]);
87 x += MAX(len/2 + 2, len - new_len/2 + 1);
88 len = new_len;
90 rb->lcd_update();
92 /* abort on keypress */
93 if(rb->action_userabort(HZ/8))
94 return;
96 if (++curr_index >= curr_len)
98 if (++curr_name >= numnames)
99 break;
100 new_len = rb->utf8length(credits[curr_name]);
101 curr_index -= MAX(curr_len/2 + 2, curr_len - new_len/2 + 1);
102 curr_len = new_len;
103 curr_line ^= 1;
108 #else
110 int update_rowpos(int action, int cur_pos, int rows_per_screen, int tot_rows)
112 switch(action)
114 case ACTION_STD_PREV:
115 case ACTION_STD_PREVREPEAT:
116 cur_pos--;
117 break;
118 case ACTION_STD_NEXT:
119 case ACTION_STD_NEXTREPEAT:
120 cur_pos++;
121 break;
124 if(cur_pos > tot_rows - rows_per_screen)
125 cur_pos = 0;
126 if(cur_pos < 0)
127 cur_pos = tot_rows - rows_per_screen;
129 return cur_pos;
132 void roll_credits(void)
134 /* to do: use target defines iso keypads to set animation timings */
135 #if (CONFIG_KEYPAD == RECORDER_PAD)
136 #define PAUSE_TIME 1.2
137 #define ANIM_SPEED 35
138 #elif (CONFIG_KEYPAD == IPOD_4G_PAD) || (CONFIG_KEYPAD == IPOD_3G_PAD) || \
139 (CONFIG_KEYPAD == IPOD_1G2G_PAD)
140 #define PAUSE_TIME 0
141 #define ANIM_SPEED 100
142 #elif (CONFIG_KEYPAD == IRIVER_H100_PAD) || (CONFIG_KEYPAD == IRIVER_H300_PAD)
143 #define PAUSE_TIME 0
144 #define ANIM_SPEED 35
145 #elif (CONFIG_KEYPAD == GIGABEAT_PAD)
146 #define PAUSE_TIME 0
147 #define ANIM_SPEED 100
148 #else
149 #define PAUSE_TIME 1
150 #define ANIM_SPEED 40
151 #endif
153 #define NUM_VISIBLE_LINES (LCD_HEIGHT/font_h - 1)
154 #define CREDITS_TARGETPOS ((LCD_WIDTH/2)-(credits_w/2))
156 int i=0, j=0, namepos=0, offset_dummy;
157 int name_w, name_h, name_targetpos=1, font_h;
158 int credits_w, credits_pos;
159 int numnames = (sizeof(credits)/sizeof(char*));
160 char name[40], elapsednames[32];
161 int action = ACTION_NONE;
163 /* control if scrolling is automatic (with animation) or manual */
164 bool manual_scroll = false;
166 rb->lcd_setfont(FONT_UI);
167 rb->lcd_clear_display();
168 rb->lcd_update();
170 rb->lcd_getstringsize("A", NULL, &font_h);
172 /* snprintf "credits" text, and save the width and height */
173 rb->snprintf(elapsednames, sizeof(elapsednames), "[Credits] %d/%d",
174 j+1, numnames);
175 rb->lcd_getstringsize(elapsednames, &credits_w, NULL);
177 /* fly in "credits" text from the left */
178 for(credits_pos = 0 - credits_w; credits_pos <= CREDITS_TARGETPOS;
179 credits_pos += (CREDITS_TARGETPOS-credits_pos + 14) / 7)
181 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
182 rb->lcd_fillrect(0, 0, LCD_WIDTH, font_h);
183 rb->lcd_set_drawmode(DRMODE_SOLID);
184 rb->lcd_putsxy(credits_pos, 0, elapsednames);
185 rb->lcd_update_rect(0, 0, LCD_WIDTH, font_h);
186 rb->sleep(HZ/ANIM_SPEED);
189 /* first screen's worth of lines fly in */
190 for(i=0; i<NUM_VISIBLE_LINES; i++)
192 rb->snprintf(name, sizeof(name), "%s", credits[i]);
193 rb->lcd_getstringsize(name, &name_w, &name_h);
195 rb->snprintf(elapsednames, sizeof(elapsednames), "[Credits] %d/%d",
196 i+1, numnames);
197 rb->lcd_getstringsize(elapsednames, &credits_w, NULL);
198 rb->lcd_putsxy(CREDITS_TARGETPOS, 0, elapsednames);
199 rb->lcd_update_rect(CREDITS_TARGETPOS, 0, credits_w, font_h);
201 for(namepos = 0-name_w; namepos <= name_targetpos;
202 namepos += (name_targetpos - namepos + 14) / 7)
204 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
205 /* clear any trails left behind */
206 rb->lcd_fillrect(0, font_h*(i+1), LCD_WIDTH, font_h);
207 rb->lcd_set_drawmode(DRMODE_SOLID);
208 rb->lcd_putsxy(namepos, font_h*(i+1), name);
209 rb->lcd_update_rect(0, font_h*(i+1), LCD_WIDTH, font_h);
211 /* exit on abort, switch to manual on up/down */
212 action = rb->get_action(CONTEXT_LIST, HZ/ANIM_SPEED);
213 if(STOP_AUTOSCROLL(action))
214 break;
216 if(STOP_AUTOSCROLL(action))
217 break;
220 /* process user actions (if any) */
221 if(ACTION_STD_CANCEL == action)
222 return;
223 if(STOP_AUTOSCROLL(action))
224 manual_scroll = true; /* up/down - abort was catched above */
226 if(!manual_scroll)
228 j+= i;
230 /* pause for a bit if needed */
231 action = rb->get_action(CONTEXT_LIST, HZ*PAUSE_TIME);
232 if(ACTION_STD_CANCEL == action)
233 return;
234 if(STOP_AUTOSCROLL(action))
235 manual_scroll = true;
238 if(!manual_scroll)
240 while(j < numnames)
242 /* just a screen's worth at a time */
243 for(i=0; i<NUM_VISIBLE_LINES; i++)
245 if(j+i >= numnames)
246 break;
247 offset_dummy=1;
249 rb->snprintf(name, sizeof(name), "%s",
250 credits[j+i-NUM_VISIBLE_LINES]);
251 rb->lcd_getstringsize(name, &name_w, &name_h);
253 /* fly out an existing line.. */
254 while(namepos<LCD_WIDTH+offset_dummy)
256 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
257 /* clear trails */
258 rb->lcd_fillrect(0, font_h*(i+1), LCD_WIDTH, font_h);
259 rb->lcd_set_drawmode(DRMODE_SOLID);
260 rb->lcd_putsxy(namepos, font_h*(i+1), name);
261 rb->lcd_update_rect(0, font_h*(i+1), LCD_WIDTH, font_h);
263 /* exit on keypress, react to scrolling */
264 action = rb->get_action(CONTEXT_LIST, HZ/ANIM_SPEED);
265 if(STOP_AUTOSCROLL(action))
266 break;
268 namepos += offset_dummy;
269 offset_dummy++;
270 } /* while(namepos<LCD_WIDTH+offset_dummy) */
271 if(STOP_AUTOSCROLL(action))
272 break;
274 rb->snprintf(name, sizeof(name), "%s", credits[j+i]);
275 rb->lcd_getstringsize(name, &name_w, &name_h);
277 rb->snprintf(elapsednames, sizeof(elapsednames),
278 "[Credits] %d/%d", j+i+1, numnames);
279 rb->lcd_getstringsize(elapsednames, &credits_w, NULL);
280 rb->lcd_putsxy(CREDITS_TARGETPOS, 0, elapsednames);
281 if (j+i < NUM_VISIBLE_LINES) /* takes care of trail on loop */
282 rb->lcd_update_rect(0, 0, LCD_WIDTH, font_h);
284 for(namepos = 0-name_w; namepos <= name_targetpos;
285 namepos += (name_targetpos - namepos + 14) / 7)
287 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
288 rb->lcd_fillrect(0, font_h*(i+1), LCD_WIDTH, font_h);
289 rb->lcd_set_drawmode(DRMODE_SOLID);
290 rb->lcd_putsxy(namepos, font_h*(i+1), name);
291 rb->lcd_update_rect(0, font_h*(i+1), LCD_WIDTH, font_h);
292 rb->lcd_update_rect(CREDITS_TARGETPOS, 0, credits_w,font_h);
294 /* stop on keypress */
295 action = rb->get_action(CONTEXT_LIST, HZ/ANIM_SPEED);
296 if(STOP_AUTOSCROLL(action))
297 break;
299 if(STOP_AUTOSCROLL(action))
300 break;
301 namepos = name_targetpos;
302 } /* for(i=0; i<NUM_VISIBLE_LINES; i++) */
303 if(STOP_AUTOSCROLL(action))
304 break;
306 action = rb->get_action(CONTEXT_LIST, HZ*PAUSE_TIME);
307 if(STOP_AUTOSCROLL(action))
308 break;
310 j+=i; /* no user intervention, draw the next screen-full */
311 } /* while(j < numnames) */
313 /* handle the keypress that we intercepted during autoscroll */
314 if(ACTION_STD_CANCEL == action)
315 return;
316 if(STOP_AUTOSCROLL(action))
317 manual_scroll = true;
318 } /* if(!manual_scroll) */
320 if(manual_scroll)
322 /* user went into manual scrolling, handle it here */
323 rb->lcd_set_drawmode(DRMODE_SOLID);
324 while(ACTION_STD_CANCEL != action)
326 rb->lcd_clear_display();
327 rb->snprintf(elapsednames, sizeof(elapsednames),
328 "[Credits] %d-%d/%d", j+1,
329 j+NUM_VISIBLE_LINES, numnames);
330 rb->lcd_getstringsize(elapsednames, &credits_w, NULL);
331 rb->lcd_putsxy(CREDITS_TARGETPOS, 0, elapsednames);
333 for(i=0; i<NUM_VISIBLE_LINES; i++)
335 rb->snprintf(name, sizeof(name), "%s", credits[j+i]);
336 rb->lcd_putsxy(0, font_h*(i+1), name);
338 rb->lcd_update();
340 /* wait for user action */
341 action = rb->get_action(CONTEXT_LIST, TIMEOUT_BLOCK);
342 if(ACTION_STD_CANCEL == action)
343 return;
344 j = update_rowpos(action, j, NUM_VISIBLE_LINES, numnames);
346 return; /* exit without animation */
349 action = rb->get_action(CONTEXT_LIST, HZ*3);
350 if(ACTION_STD_CANCEL == action)
351 return;
353 offset_dummy = 1;
355 /* now make the text exit to the right */
356 for(credits_pos = (LCD_WIDTH/2)-(credits_w/2);
357 credits_pos <= LCD_WIDTH+offset_dummy;
358 credits_pos += offset_dummy, offset_dummy++)
360 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
361 rb->lcd_fillrect(0, 0, LCD_WIDTH, font_h);
362 rb->lcd_set_drawmode(DRMODE_SOLID);
363 rb->lcd_putsxy(credits_pos, 0, elapsednames);
364 rb->lcd_update();
368 #endif
370 enum plugin_status plugin_start(struct plugin_api* api, void* parameter)
372 (void)parameter;
373 rb = api;
375 /* Turn off backlight timeout */
376 backlight_force_on(rb); /* backlight control in lib/helper.c */
378 rb->show_logo();
379 #ifdef HAVE_LCD_CHARCELLS
380 rb->lcd_double_height(false);
381 #endif
383 /* Show the logo for about 3 secs allowing the user to stop */
384 if(!rb->action_userabort(3*HZ))
385 roll_credits();
387 /* Turn on backlight timeout (revert to settings) */
388 backlight_use_settings(rb); /* backlight control in lib/helper.c */
390 return PLUGIN_OK;