summaryrefslogtreecommitdiff
path: root/apps/plugins/lib/grey_scroll.c
diff options
context:
space:
mode:
Diffstat (limited to 'apps/plugins/lib/grey_scroll.c')
-rw-r--r--apps/plugins/lib/grey_scroll.c358
1 files changed, 358 insertions, 0 deletions
diff --git a/apps/plugins/lib/grey_scroll.c b/apps/plugins/lib/grey_scroll.c
new file mode 100644
index 0000000000..80496e7706
--- /dev/null
+++ b/apps/plugins/lib/grey_scroll.c
@@ -0,0 +1,358 @@
1/***************************************************************************
2* __________ __ ___.
3* Open \______ \ ____ ____ | | _\_ |__ _______ ___
4* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7* \/ \/ \/ \/ \/
8* $Id$
9*
10* New greyscale framework
11* Scrolling routines
12*
13* This is a generic framework to display 129 shades of grey on low-depth
14* bitmap LCDs (Archos b&w, Iriver & Ipod 4-grey) within plugins.
15*
16* Copyright (C) 2008 Jens Arnold
17*
18* All files in this archive are subject to the GNU General Public License.
19* See the file COPYING in the source tree root for full license agreement.
20*
21* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
22* KIND, either express or implied.
23*
24****************************************************************************/
25
26#include "plugin.h"
27#include "grey.h"
28
29/*** Scrolling ***/
30
31/* Scroll left */
32void grey_scroll_left(int count)
33{
34 unsigned char *data, *data_end;
35 int length, blank;
36
37 if ((unsigned)count >= (unsigned)_grey_info.width)
38 return;
39
40 data = _grey_info.buffer;
41 data_end = data + _GREY_MULUQ(_grey_info.width, _grey_info.height);
42 length = _grey_info.width - count;
43 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
44 _grey_info.fg_val : _grey_info.bg_val;
45
46 do
47 {
48 _grey_rb->memmove(data, data + count, length);
49 _grey_rb->memset(data + length, blank, count);
50 data += _grey_info.width;
51 }
52 while (data < data_end);
53}
54
55/* Scroll right */
56void grey_scroll_right(int count)
57{
58 unsigned char *data, *data_end;
59 int length, blank;
60
61 if ((unsigned)count >= (unsigned)_grey_info.width)
62 return;
63
64 data = _grey_info.buffer;
65 data_end = data + _GREY_MULUQ(_grey_info.width, _grey_info.height);
66 length = _grey_info.width - count;
67 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
68 _grey_info.fg_val : _grey_info.bg_val;
69
70 do
71 {
72 _grey_rb->memmove(data + count, data, length);
73 _grey_rb->memset(data, blank, count);
74 data += _grey_info.width;
75 }
76 while (data < data_end);
77}
78
79/* Scroll up */
80void grey_scroll_up(int count)
81{
82 long shift, length;
83 int blank;
84
85 if ((unsigned)count >= (unsigned)_grey_info.height)
86 return;
87
88 shift = _GREY_MULUQ(_grey_info.width, count);
89 length = _GREY_MULUQ(_grey_info.width, _grey_info.height - count);
90 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
91 _grey_info.fg_val : _grey_info.bg_val;
92
93 _grey_rb->memmove(_grey_info.buffer, _grey_info.buffer + shift, length);
94 _grey_rb->memset(_grey_info.buffer + length, blank, shift);
95}
96
97/* Scroll down */
98void grey_scroll_down(int count)
99{
100 long shift, length;
101 int blank;
102
103 if ((unsigned)count >= (unsigned)_grey_info.height)
104 return;
105
106 shift = _GREY_MULUQ(_grey_info.width, count);
107 length = _GREY_MULUQ(_grey_info.width, _grey_info.height - count);
108 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
109 _grey_info.fg_val : _grey_info.bg_val;
110
111 _grey_rb->memmove(_grey_info.buffer + shift, _grey_info.buffer, length);
112 _grey_rb->memset(_grey_info.buffer, blank, shift);
113}
114
115/*** Unbuffered scrolling functions ***/
116
117#ifdef SIMULATOR
118
119/* Scroll left */
120void grey_ub_scroll_left(int count)
121{
122 grey_scroll_left(count);
123 grey_update();
124}
125
126/* Scroll right */
127void grey_ub_scroll_right(int count)
128{
129 grey_scroll_right(count);
130 grey_update();
131}
132
133/* Scroll up */
134void grey_ub_scroll_up(int count)
135{
136 grey_scroll_up(count);
137 grey_update();
138}
139
140/* Scroll down */
141void grey_ub_scroll_down(int count)
142{
143 grey_scroll_down(count);
144 grey_update();
145}
146
147#else /* !SIMULATOR */
148
149/* Scroll left */
150void grey_ub_scroll_left(int count)
151{
152 unsigned char *dst, *src, *end;
153 int blank, y, idx;
154
155 if ((count == 0) || ((unsigned)count >= (unsigned)_grey_info.width))
156 return;
157
158 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
159 _grey_info.fg_val : _grey_info.bg_val;
160
161 for (y = 0; y < _grey_info.height; y++)
162 {
163#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
164 idx = _GREY_MULUQ(_grey_info.width, y);
165#else
166#if LCD_DEPTH == 1
167 idx = _GREY_MULUQ(_grey_info.width, y & ~7) + (~y & 7);
168#elif LCD_DEPTH == 2
169 idx = _GREY_MULUQ(_grey_info.width, y & ~3) + (~y & 3);
170#endif
171#endif /* LCD_PIXELFORMAT */
172 dst = &_grey_info.data[idx].value;
173 src = dst + count * _GREY_X_ADVANCE;
174 end = dst + _grey_info.width * _GREY_X_ADVANCE;
175
176 do
177 {
178 *dst = *src;
179 dst += _GREY_X_ADVANCE;
180 src += _GREY_X_ADVANCE;
181 }
182 while (src < end);
183
184 do
185 {
186 *dst = blank;
187 dst += _GREY_X_ADVANCE;
188 }
189 while (dst < end);
190 }
191}
192
193/* Scroll right */
194void grey_ub_scroll_right(int count)
195{
196 unsigned char *dst, *src, *start;
197 int blank, y, idx;
198
199 if ((count == 0) || ((unsigned)count >= (unsigned)_grey_info.width))
200 return;
201
202 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
203 _grey_info.fg_val : _grey_info.bg_val;
204
205 for (y = 0; y < _grey_info.height; y++)
206 {
207#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
208 idx = _GREY_MULUQ(_grey_info.width, y);
209#else
210#if LCD_DEPTH == 1
211 idx = _GREY_MULUQ(_grey_info.width, y & ~7) + (~y & 7);
212#elif LCD_DEPTH == 2
213 idx = _GREY_MULUQ(_grey_info.width, y & ~3) + (~y & 3);
214#endif
215#endif /* LCD_PIXELFORMAT */
216 start = &_grey_info.data[idx].value;
217 dst = start + _grey_info.width * _GREY_X_ADVANCE;
218 src = dst - count * _GREY_X_ADVANCE;
219
220 do
221 {
222 dst -= _GREY_X_ADVANCE;
223 src -= _GREY_X_ADVANCE;
224 *dst = *src;
225 }
226 while (src > start);
227
228 do
229 {
230 dst -= _GREY_X_ADVANCE;
231 *dst = blank;
232 }
233 while (dst > start);
234 }
235}
236
237void grey_ub_scroll_up(int count)
238{
239 unsigned char *dst, *dst_end, *src;
240 int blank, ys, yd, is, id;
241
242 if ((unsigned)count >= (unsigned)_grey_info.height)
243 return;
244
245 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
246 _grey_info.fg_val : _grey_info.bg_val;
247
248 for (ys = count, yd = 0; ys < _grey_info.height; ys++, yd++)
249 {
250#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
251 id = _GREY_MULUQ(_grey_info.width, yd);
252 is = _GREY_MULUQ(_grey_info.width, ys);
253#else
254#if LCD_DEPTH == 1
255 id = _GREY_MULUQ(_grey_info.width, yd & ~7) + (~yd & 7);
256 is = _GREY_MULUQ(_grey_info.width, ys & ~7) + (~ys & 7);
257#elif LCD_DEPTH == 2
258 id = _GREY_MULUQ(_grey_info.width, yd & ~3) + (~yd & 3);
259 is = _GREY_MULUQ(_grey_info.width, ys & ~3) + (~ys & 3);
260#endif
261#endif /* LCD_PIXELFORMAT */
262 dst = &_grey_info.data[id].value;
263 src = &_grey_info.data[is].value;
264 dst_end = dst + _grey_info.width * _GREY_X_ADVANCE;
265
266 do
267 {
268 *dst = *src;
269 dst += _GREY_X_ADVANCE;
270 src += _GREY_X_ADVANCE;
271 }
272 while (dst < dst_end);
273 }
274 for (; yd < _grey_info.height; yd++)
275 {
276#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
277 id = _GREY_MULUQ(_grey_info.width, yd);
278#else
279#if LCD_DEPTH == 1
280 id = _GREY_MULUQ(_grey_info.width, yd & ~7) + (~yd & 7);
281#elif LCD_DEPTH == 2
282 id = _GREY_MULUQ(_grey_info.width, yd & ~3) + (~yd & 3);
283#endif
284#endif /* LCD_PIXELFORMAT */
285 dst = &_grey_info.data[id].value;
286 dst_end = dst + _grey_info.width * _GREY_X_ADVANCE;
287
288 do
289 {
290 *dst = blank;
291 dst += _GREY_X_ADVANCE;
292 }
293 while (dst < dst_end);
294 }
295}
296
297void grey_ub_scroll_down(int count)
298{
299 unsigned char *dst, *dst_end, *src;
300 int blank, ys, yd, is, id;
301
302 if ((unsigned)count >= (unsigned)_grey_info.height)
303 return;
304
305 blank = (_grey_info.drawmode & DRMODE_INVERSEVID) ?
306 _grey_info.fg_val : _grey_info.bg_val;
307
308 yd = _grey_info.height - 1;
309 for (ys = yd - count; ys >= 0; ys--, yd--)
310 {
311#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
312 id = _GREY_MULUQ(_grey_info.width, yd);
313 is = _GREY_MULUQ(_grey_info.width, ys);
314#else
315#if LCD_DEPTH == 1
316 id = _GREY_MULUQ(_grey_info.width, yd & ~7) + (~yd & 7);
317 is = _GREY_MULUQ(_grey_info.width, ys & ~7) + (~ys & 7);
318#elif LCD_DEPTH == 2
319 id = _GREY_MULUQ(_grey_info.width, yd & ~3) + (~yd & 3);
320 is = _GREY_MULUQ(_grey_info.width, ys & ~3) + (~ys & 3);
321#endif
322#endif /* LCD_PIXELFORMAT */
323 dst = &_grey_info.data[id].value;
324 src = &_grey_info.data[is].value;
325 dst_end = dst + _grey_info.width * _GREY_X_ADVANCE;
326
327 do
328 {
329 *dst = *src;
330 dst += _GREY_X_ADVANCE;
331 src += _GREY_X_ADVANCE;
332 }
333 while (dst < dst_end);
334 }
335 for (; yd >= 0; yd--)
336 {
337#if LCD_PIXELFORMAT == HORIZONTAL_PACKING
338 id = _GREY_MULUQ(_grey_info.width, yd);
339#else
340#if LCD_DEPTH == 1
341 id = _GREY_MULUQ(_grey_info.width, yd & ~7) + (~yd & 7);
342#elif LCD_DEPTH == 2
343 id = _GREY_MULUQ(_grey_info.width, yd & ~3) + (~yd & 3);
344#endif
345#endif /* LCD_PIXELFORMAT */
346 dst = &_grey_info.data[id].value;
347 dst_end = dst + _grey_info.width * _GREY_X_ADVANCE;
348
349 do
350 {
351 *dst = blank;
352 dst += _GREY_X_ADVANCE;
353 }
354 while (dst < dst_end);
355 }
356}
357
358#endif /* !SIMULATOR */