?lang_form? ?lang_select? ?lang_submit? ?lang_endform?
{HEADER END}
{BLAME START}

library

?curdirlinks? -

Blame information for rev 32

Line No. Rev Author Line
1 32 kaklik /*****************************************************************************
2 * Module for Microchip Graphics Library
3 * Custom display controller driver template
4 *****************************************************************************
5 * FileName: MicrochipGraphicsModule.c
6 * Dependencies: Graphics.h
7 * Processor: PIC24
8 * Compiler: MPLAB C30
9 * Linker: MPLAB LINK30
10 * Company: Microchip Technology Incorporated
11 *
12 * Software License Agreement
13 *
14 * Copyright © 2008 Microchip Technology Inc. All rights reserved.
15 * Microchip licenses to you the right to use, modify, copy and distribute
16 * Software only when embedded on a Microchip microcontroller or digital
17 * signal controller, which is integrated into your product or third party
18 * product (pursuant to the sublicense terms in the accompanying license
19 * agreement).
20 *
21 * You should refer to the license agreement accompanying this Software
22 * for additional information regarding your rights and obligations.
23 *
24 * SOFTWARE AND DOCUMENTATION ARE PROVIDED “AS IS” WITHOUT WARRANTY OF ANY
25 * KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION, ANY WARRANTY
26 * OF MERCHANTABILITY, TITLE, NON-INFRINGEMENT AND FITNESS FOR A PARTICULAR
27 * PURPOSE. IN NO EVENT SHALL MICROCHIP OR ITS LICENSORS BE LIABLE OR
28 * OBLIGATED UNDER CONTRACT, NEGLIGENCE, STRICT LIABILITY, CONTRIBUTION,
29 * BREACH OF WARRANTY, OR OTHER LEGAL EQUITABLE THEORY ANY DIRECT OR INDIRECT
30 * DAMAGES OR EXPENSES INCLUDING BUT NOT LIMITED TO ANY INCIDENTAL, SPECIAL,
31 * INDIRECT, PUNITIVE OR CONSEQUENTIAL DAMAGES, LOST PROFITS OR LOST DATA,
32 * COST OF PROCUREMENT OF SUBSTITUTE GOODS, TECHNOLOGY, SERVICES, OR ANY
33 * CLAIMS BY THIRD PARTIES (INCLUDING BUT NOT LIMITED TO ANY DEFENSE THEREOF),
34 * OR OTHER SIMILAR COSTS.
35 *
36 * Author Date Comment
37 *~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
38 * Pradeep Budagutta 20 Aug 2009 Initial Version
39 * Pradeep Budagutta 03 Dec 2009 Added Double Buffering Support
40 * PAT 29 Mar 2010 Fixed EPMP base address programming
41 *****************************************************************************/
42 #include "Graphics\Graphics.h"
43  
44 #if (DISPLAY_PANEL == TFT_G240320LTSW_118W_E)
45  
46 #include "TCON_SSD1289.c"
47  
48 #elif (DISPLAY_PANEL == TFT_G320240DTSW_69W_TP_E)
49  
50 #include "TCON_HX8238.c"
51  
52 #elif (DISPLAY_PANEL == PH480272T_005_I06Q)
53  
54 #include "TCON_HX8257.c"
55  
56 #else
57  
58 #include "TCON_Custom.c"
59  
60 #endif
61  
62 #ifdef USE_PALETTE
63  
64 #include "Graphics\Palette.h"
65  
66 extern void *_palette;
67 extern BYTE PaletteBpp;
68 extern BYTE blPaletteChangeError;
69 extern void *pPendingPalette;
70 extern WORD PendingStartEntry;
71 extern WORD PendingLength;
72  
73 #endif
74  
75 // Color
76 WORD_VAL _color;
77 WORD_VAL _chrcolor;
78  
79 // Clipping region control
80 SHORT _clipRgn;
81  
82 // Clipping region borders
83 SHORT _clipLeft;
84 SHORT _clipTop;
85 SHORT _clipRight;
86 SHORT _clipBottom;
87  
88 // work areas base addresses
89 volatile DWORD _workArea1BaseAddr;
90 volatile DWORD _workArea2BaseAddr;
91  
92 // display buffer base address
93 volatile DWORD _displayAreaBaseAddr;
94  
95 #ifdef USE_DOUBLE_BUFFERING
96  
97 volatile DWORD _drawbuffer;
98 volatile BYTE blDisplayUpdatePending;
99  
100 #endif //USE_DOUBLE_BUFFERING
101  
102 #define GFX_FLIP(a,b) { SHORT t=a; a=b; b=t; }
103  
104 #if defined (GFX_EPMP_CS1_BASE_ADDRESS) || defined (GFX_EPMP_CS2_BASE_ADDRESS)
105  
106 void EPMP_Init(void)
107 {
108 /* Note: When using the EPMP to access external RAM or Flash, PMA0-PMA16 will only access a range of
109 256K RAM. To increase this range enable higher Address lines.
110 */
111 ANSDbits.ANSD7 = 0; // PMD15
112 ANSDbits.ANSD6 = 0; // PMD14
113 ANSFbits.ANSF0 = 0; // PMD11
114  
115 ANSBbits.ANSB15 = 0; // PMA0
116 ANSBbits.ANSB14 = 0; // PMA1
117 ANSGbits.ANSG9 = 0; // PMA2
118 ANSBbits.ANSB13 = 0; // PMA10
119 ANSBbits.ANSB12 = 0; // PMA11
120 ANSBbits.ANSB11 = 0; // PMA12
121 ANSBbits.ANSB10 = 0; // PMA13
122 ANSAbits.ANSA7 = 0; // PMA17
123 ANSGbits.ANSG6 = 0; // PMA18
124  
125 PMCON1bits.ADRMUX = 0; // address is not multiplexed
126 PMCON1bits.MODE = 3; // master mode
127 PMCON1bits.CSF = 0; // PMCS1 pin used for chip select 1, PMCS2 pin used for chip select 2
128 PMCON1bits.ALP = 1; // set address latch strobes to high active level (for sn74lvc16373)
129 PMCON1bits.ALMODE = 1; // "smart" address strobes are not used
130 PMCON1bits.BUSKEEP = 0; // bus keeper is not used
131  
132 #if defined (GFX_EPMP_CS1_BASE_ADDRESS)
133 #ifdef USE_DOUBLE_BUFFERING
134 PMCS1BS = ((DWORD)GFX_BUFFER1>>8); // CS1 start address
135 PMCON3 |= 0x0003; // PMA16 - PMA17 address lines are enabled
136 #else
137 PMCS1BS = (GFX_EPMP_CS1_BASE_ADDRESS>>8); // CS1 start address
138 PMCON3 |= 0x0001; // PMA16 address line is enabled
139 #endif //USE_DOUBLE_BUFFERING
140  
141 PMCS1CFbits.CSDIS = 0; // enable CS
142 PMCS1CFbits.CSP = EPMPCS1_CS_POLARITY; // CS1 polarity
143 PMCS1CFbits.BEP = EPMPCS1_BE_POLARITY; // byte enable polarity
144 PMCS1CFbits.WRSP = EPMPCS1_WR_POLARITY; // write strobe polarity
145 PMCS1CFbits.RDSP = EPMPCS1_RD_POLARITY; // read strobe polarity
146 PMCS1CFbits.CSPTEN = 1; // enable CS port
147 PMCS1CFbits.SM = 0; // read and write strobes on separate lines
148 PMCS1CFbits.PTSZ = 2; // data bus width is 16-bit
149  
150 PMCS1MDbits.ACKM = 0; // PMACK is not used
151  
152 // The device timing parameters. Set the proper timing
153 // according to the device used (the timing macros are defined in the hardware profile)
154 PMCS1MDbits.DWAITB = EPMPCS1_DWAITB; // access time 1 Tcy
155 PMCS1MDbits.DWAITM = EPMPCS1_DWAITM;
156 PMCS1MDbits.DWAITE = EPMPCS1_DWAITE;
157 PMCS1MDbits.AMWAIT = EPMPCS1_AMWAIT; // Note: adjust this delay for slower devices
158  
159 #else
160 PMCS1CFbits.CSDIS = 1; // disable CS1 functionality
161 #endif //#if defined (GFX_EPMP_CS1_BASE_ADDRESS)
162  
163 #if defined (GFX_EPMP_CS2_BASE_ADDRESS)
164  
165 PMCS2BS = (GFX_EPMP_CS2_BASE_ADDRESS>>8); // CS2 start address
166  
167 PMCS2CFbits.CSDIS = 0; // enable CS
168  
169 PMCS2CFbits.CSP = EPMPCS2_CS_POLARITY; // CS2 polarity
170 PMCS2CFbits.BEP = EPMPCS2_BE_POLARITY; // byte enable polarity
171 PMCS2CFbits.WRSP = EPMPCS2_WR_POLARITY; // write strobe polarity
172 PMCS2CFbits.RDSP = EPMPCS2_RD_POLARITY; // read strobe polarity
173 PMCS2CFbits.CSPTEN = 1; // enable CS port
174 PMCS2CFbits.SM = 0; // read and write strobes on separate lines
175 PMCS2CFbits.PTSZ = 2; // data bus width is 16-bit
176  
177 PMCS2MDbits.ACKM = 0; // PMACK is not used
178  
179 // The device timing parameters. Set the proper timing
180 // according to the device used (the timing macros are defined in the hardware profile)
181 PMCS2MDbits.DWAITB = EPMPCS2_DWAITB; // access time 1 Tcy
182 PMCS2MDbits.DWAITM = EPMPCS2_DWAITM;
183 PMCS2MDbits.DWAITE = EPMPCS2_DWAITE;
184 PMCS2MDbits.AMWAIT = EPMPCS2_AMWAIT; // Note: adjust this delay for slower devices
185  
186  
187 #else
188 PMCS2CFbits.CSDIS = 1; // disable CS2 functionality
189 #endif //#if defined (GFX_EPMP_CS2_BASE_ADDRESS)
190  
191 PMCON2bits.RADDR = 0xFF; // set CS2 end address
192 PMCON4 = 0xFFFF; // PMA0 - PMA15 address lines are enabled
193  
194  
195 PMCON3bits.PTWREN = 1; // enable write strobe port
196 PMCON3bits.PTRDEN = 1; // enable read strobe port
197 PMCON3bits.PTBE0EN = 1; // enable byte enable port
198 PMCON3bits.PTBE1EN = 1; // enable byte enable port
199 PMCON3bits.AWAITM = 0; // set address latch pulses width to 1/2 Tcy
200 PMCON3bits.AWAITE = 0; // set address hold time to 1/4 Tcy
201  
202 DelayMs(100);
203  
204 PMCON2bits.MSTSEL = 3; // select EPMP bypass mode (for Graphics operation)
205 PMCON1bits.PMPEN = 1; // enable the module
206  
207 DelayMs(100);
208  
209 }
210  
211 #endif //#if defined (GFX_EPMP_CS1_BASE_ADDRESS) || defined (GFX_EPMP_CS2_BASE_ADDRESS)
212  
213 /*********************************************************************
214 * Function: void ResetDevice()
215 *
216 * PreCondition: none
217 *
218 * Input: none
219 *
220 * Output: none
221 *
222 * Side Effects: none
223 *
224 * Overview: Resets LCD, initializes PMP. FRM Section 43. Graphics
225 * Controller Module (GFX) (Document #:DS39731) for details.
226 *
227 * Note: none
228 *
229 ********************************************************************/
230 void ResetDevice(void)
231 {
232 #ifdef USE_DOUBLE_BUFFERING
233  
234 blInvalidateAll = 1;
235 blDisplayUpdatePending = 0;
236 NoOfInvalidatedRectangleAreas = 0;
237 _drawbuffer = GFX_BUFFER1;
238 SwitchOnDoubleBuffering();
239  
240 #endif //USE_DOUBLE_BUFFERING
241  
242  
243 #if defined (POWERON_LAT_BIT)
244  
245 /* Switch On display if IO controlled; if controlled
246 by the Graphics Module, hook up the power-on signal of the display to
247 GPWR pin of the Graphics Module and this code should not compile */
248  
249 POWERON_LAT_BIT = 1;
250 POWERON_TRIS_BIT = 0;
251  
252 #endif
253  
254 #if defined (GFX_EPMP_CS1_BASE_ADDRESS) || defined (GFX_EPMP_CS2_BASE_ADDRESS)
255  
256 EPMP_Init();
257  
258 #endif
259  
260 /************ End - Project Specific Code - Relocate ************/
261  
262  
263 G1CON1 = 0; /* Switch off the module */
264 G1CON2 = 0;
265 G1CON3 = 0;
266 G1IE = 0;
267 G1IR = 0;
268 G1CLUT = 0;
269 G1MRGN = 0;
270 G1CLUTWR = 0;
271 G1CHRX = 0;
272 G1CHRY = 0;
273 G1CMDL = 0;
274 G1CMDH = 0;
275  
276 // set the processing unit bit per pixel
277 _PUBPP = GFX_BITS_PER_PIXEL;
278 // set the display controller bit per pixel
279 _DPBPP = GFX_BITS_PER_PIXEL;
280 // set the LCD type used (TFT, MSTN or CSTN)
281 _DPMODE = GFX_LCD_TYPE;
282  
283 #if (GFX_LCD_TYPE == GFX_LCD_MSTN) || (GFX_LCD_TYPE == GFX_LCD_CSTN)
284 // set the display width
285 _DPGWDTH = STN_DISPLAY_WIDTH;
286  
287 #endif
288  
289 /* Port configurations */
290 #ifdef GFX_DISPLAYENABLE_ENABLE
291 // set the display enable polarity
292 _DPENPOL = GFX_DISPLAYENABLE_POLARITY;
293 _DPENOE = 1;
294  
295 #endif
296  
297 #ifdef GFX_HSYNC_ENABLE
298 // set the HSYNC signal polarity
299 _DPHSPOL = GFX_HSYNC_POLARITY;
300 _DPHSOE = 1;
301  
302 #endif
303  
304 #ifdef GFX_VSYNC_ENABLE
305 // set the VSYNC signal polarity
306 _DPVSPOL = GFX_VSYNC_POLARITY;
307 _DPVSOE = 1;
308  
309 #endif
310  
311 #ifdef GFX_DISPLAYPOWER_ENABLE
312 // set the display power (GPWR) signal polarity
313 _DPPOWER = GFX_DISPLAYPOWER_POLARITY;
314 _DPPWROE = 1;
315  
316 #endif
317  
318 /* Display timing signal configurations */
319 // set the clock polarity
320 _DPCLKPOL = GFX_CLOCK_POLARITY;
321  
322 // set the display buffer dimension
323 G1DPW = DISP_HOR_RESOLUTION;
324 G1DPH = DISP_VER_RESOLUTION;
325  
326 // set the work area dimension
327 G1PUW = DISP_HOR_RESOLUTION;
328 G1PUH = DISP_VER_RESOLUTION;
329  
330 /* Note:
331 In some display panel the definition of porches (front and back porches) varies.
332 Example TFT display definitions (for horizontal timing):
333 1. Horizontal Cycle = horizontal front porch + horizontal back porch + horizontal display period
334 2. Horizontal Cycle = horizontal front porch + horizontal back porch + horizontal display period + horizontal sync pulse width
335 In example (1) the horizontal sync pulse width must not exceed the horizontal back porch.
336 For the vertical timing, the equations are the same (replace horizontal with vertical).
337  
338 For the Microchip graphics controller: the definition follows example (2). To accomodate displays like
339 example (1), adjust the back porches and pulse widths accordingly. Refer to
340 FRM Section 43. Graphics Controller Module (GFX) (Document #:DS39731).
341 */
342 #define HT (DISP_HOR_PULSE_WIDTH + DISP_HOR_BACK_PORCH + DISP_HOR_FRONT_PORCH + DISP_HOR_RESOLUTION)
343 #define VT (DISP_VER_PULSE_WIDTH + DISP_VER_BACK_PORCH + DISP_VER_FRONT_PORCH + DISP_VER_RESOLUTION)
344  
345 G1DPWT = HT;
346 G1DPHT = VT;
347  
348 // set the horizontal pulse width
349 _HSLEN = DISP_HOR_PULSE_WIDTH;
350 _HSST = 0;
351  
352 // set the verrizontal pulse width
353 _VSLEN = DISP_VER_PULSE_WIDTH;
354 _VSST = 0;
355  
356 // set the horizontal & vertical start position
357 _HENST = _HSST + DISP_HOR_PULSE_WIDTH + DISP_HOR_BACK_PORCH;
358 _VENST = _VSST + DISP_VER_PULSE_WIDTH + DISP_VER_BACK_PORCH;
359  
360 // set the active pixel and active line start position
361 _ACTPIX = _HENST;
362 _ACTLINE = _VENST;
363  
364 // initialize the work areas and display buffer base addresses global variables
365 _workArea1BaseAddr = GFX_DISPLAY_BUFFER_START_ADDRESS;
366 _workArea2BaseAddr = GFX_DISPLAY_BUFFER_START_ADDRESS;
367 _displayAreaBaseAddr = GFX_DISPLAY_BUFFER_START_ADDRESS;
368  
369 // Set the display buffer base address (SFR) (or the start addresses in RAM)
370 GFX_SetDisplayArea(_displayAreaBaseAddr);
371  
372 /* Switch On the Graphics Module */
373 _GDBEN = 0xFFFF;
374 _DPPINOE = 1;
375  
376 #ifdef USE_PALETTE
377 // initialize the color look up table (CLUT) if enabled
378 PaletteInit();
379  
380 #endif
381  
382 _G1CLKSEL = 1; // 96MHz Enable
383 _GCLKDIV = GFX_GCLK_DIVIDER; // value used is dependent on the display panel specification
384 _DPSTGER = 0; // display data stagger (set to none)
385 _GFX1IF = 0; // clear graphics interrupt flag
386 _GFX1IE = 0; // graphics interrupt are not enabled
387 _G1EN = 1; // turn on the graphics module
388  
389 DelayMs(100);
390  
391 _DPPWROE = 1; // enable the display power sequencer port to function as GPWR
392 _DPPOWER = 1; // turn on the display power sequencer
393  
394 // clear the screen to all black first to remove the noise screen
395 SetColor(0);
396 Bar(0,0,GetMaxX(),GetMaxY());
397  
398 TCON_Init(); // Panel Timing Controller (TCON) Programming
399  
400 DelayMs(100);
401  
402 // disable clipping (default setting)
403 SetClip(0);
404 }
405  
406 /*********************************************************************
407 * Function: SetClip(control)
408 *
409 * Overview: Enables/disables clipping.
410 *
411 * PreCondition: none
412 *
413 * Input: control - Enables or disables the clipping.
414 * - 0: Disable clipping
415 * - 1: Enable clipping
416 *
417 * Output: none
418 *
419 * Side Effects: none
420 *
421 ********************************************************************/
422 void SetClip(BYTE control)
423 {
424 _clipRgn=control;
425  
426 if(_clipRgn)
427 {
428 GFX_WaitForCommandQueue(2);
429 GFX_SetStartXY(_clipLeft, _clipTop);
430 GFX_SetEndXY(_clipRight, _clipBottom) ;
431 }
432 else
433 {
434 GFX_WaitForCommandQueue(2);
435 GFX_SetStartXY(0, 0);
436 GFX_SetEndXY(GetMaxX(), GetMaxY());
437 }
438 }
439  
440 /*********************************************************************
441 * Function: SetClipRgn(left, top, right, bottom)
442 *
443 * Overview: Sets clipping region.
444 *
445 * PreCondition: none
446 *
447 * Input: left - Defines the left clipping region border.
448 * top - Defines the top clipping region border.
449 * right - Defines the right clipping region border.
450 * bottom - Defines the bottom clipping region border.
451 *
452 * Output: none
453 *
454 * Side Effects: none
455 *
456 ********************************************************************/
457 void SetClipRgn(SHORT left, SHORT top, SHORT right, SHORT bottom)
458 {
459 _clipLeft=left;
460 _clipTop=top;
461 _clipRight=right;
462 _clipBottom=bottom;
463  
464 if(_clipRgn)
465 {
466 SetClip(_clipRgn);
467 }
468 }
469  
470 /*********************************************************************
471 * Function: WORD MoveBlock(DWORD srcAddr, DWORD dstAddr,
472 * DWORD srcOffset, DWORD dstOffset,
473 * WORD srcType, WORD dstType,
474 * WORD width, WORD height)
475 *
476 * PreCondition: none
477 *
478 * Input: srcAddr - the base address of the data to be moved
479 * dstAddr - the base address of the new location of the moved data
480 * srcOffset - offset of the data to be moved with respect to the
481 * source base address.
482 * dstOffset - offset of the new location of the moved data respect
483 * to the source base address.
484 * srcType - sets the source type (1 - continuous or 0 - discontinuous)
485 * dstType - sets the source type (1 - continuous or 0 - discontinuous)
486 * width - width of the block of data to be moved
487 * height - height of the block of data to be moved
488 *
489 * Output: none
490 *
491 * Side Effects: none
492 *
493 * Overview: puts pixel
494 *
495 * Note: none
496 *
497 ********************************************************************/
498 WORD MoveBlock(DWORD srcAddr, DWORD dstAddr, DWORD srcOffset, DWORD dstOffset,
499 WORD srcType, WORD dstType, WORD width, WORD height)
500 {
501 // make sure there are no pending RCC GPU commands
502 if(GFX_GetFreeCommandSpace() < 16)
503 {
504 #ifndef USE_NONBLOCKING_CONFIG
505 GFX_WaitForCommandQueue(16);
506 #else
507 return (0);
508 #endif
509 }
510  
511 // make sure the GPUs are not operating since changing the base addresses
512 // will break the currently executing GPU command.
513 #ifndef USE_NONBLOCKING_CONFIG
514 GFX_WaitForGpu();
515 #else
516 if (GFX_IsPuGpuBusy() == 1)
517 return (0);
518 #endif
519  
520 GFX_SetWorkArea1(srcAddr);
521 GFX_SetWorkArea2(dstAddr);
522  
523 GFX_SetSrcAddress(srcOffset);
524 GFX_SetDestAddress(dstOffset);
525  
526 GFX_SetRectSize(width, height);
527  
528 GFX_StartCopy(RCC_COPY, RCC_ROP_C, srcType, dstType);
529  
530 return (1);
531  
532 }
533  
534 /*********************************************************************
535 * Function: WORD ScrollLeft(SHORT left, SHORT top,
536 * SHORT right, SHORT bottom, SHORT delta)
537 *
538 * PreCondition: none
539 *
540 * Input: left - left position of the scrolled rectangle
541 * top - top position of the scrolled rectangle
542 * right - right position of the scrolled rectangle
543 * bottom - bottom position of the scrolled rectangle
544 * delta - defines the scroll delta
545 *
546 * Output: none
547 *
548 * Side Effects: none
549 *
550 * Overview: Scrolls the rectangular area defined by left, top, right, bottom by delta pixels.
551 *
552 * Note: none
553 *
554 ********************************************************************/
555 WORD ScrollLeft(SHORT left, SHORT top, SHORT right, SHORT bottom, SHORT delta)
556 {
557 DWORD address;
558 SHORT width, height;
559  
560 // make sure there are no pending RCC GPU commands
561 if(GFX_GetFreeCommandSpace() < 16)
562 {
563 #ifndef USE_NONBLOCKING_CONFIG
564 GFX_WaitForCommandQueue(16);
565 #else
566 return (0);
567 #endif
568 }
569  
570  
571 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
572  
573 width = right - left + 1;
574 height = bottom - top + 1;
575  
576 #elif (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
577  
578 height = right - left + 1;
579 width = bottom - top + 1;
580 #endif
581  
582 GFX_SetWorkArea1(_workArea1BaseAddr);
583 GFX_SetWorkArea2(_workArea2BaseAddr);
584  
585 address = (top * (DWORD)_PUW) + left;
586 GFX_SetSrcAddress(address);
587  
588 address = (top * (DWORD)_PUW) + left - delta;
589 GFX_SetDestAddress(address);
590  
591 GFX_SetRectSize(width, height);
592 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_DEST_ADDR_DISCONTINUOUS,RCC_DEST_ADDR_DISCONTINUOUS);
593  
594 return (1);
595 }
596  
597  
598 /*********************************************************************
599 * Function: void PutPixel(SHORT x, SHORT y)
600 *
601 * PreCondition: none
602 *
603 * Input: x,y - pixel coordinates
604 *
605 * Output: none
606 *
607 * Side Effects: none
608 *
609 * Overview: puts pixel
610 *
611 * Note: none
612 *
613 ********************************************************************/
614 void PutPixel(SHORT x, SHORT y)
615 {
616  
617 if(_clipRgn)
618 {
619 if(x < _clipLeft)
620 return;
621 if(x > _clipRight)
622 return;
623 if(y < _clipTop)
624 return;
625 if(y > _clipBottom)
626 return;
627 }
628  
629 #if (DISP_ORIENTATION == 90)
630 {
631 SHORT t = x;
632 x = y;
633 y = GetMaxX() - t;
634 }
635 #elif (DISP_ORIENTATION == 180)
636 {
637 x = GetMaxX() - x;
638 y = GetMaxY() - y;
639 }
640 #elif (DISP_ORIENTATION == 270)
641 {
642 SHORT t = x;
643 x = GetMaxY() - y;
644 y = t;
645 }
646 #endif
647  
648 #ifndef USE_DOUBLE_BUFFERING
649 GFX_SetWorkArea2(_workArea2BaseAddr);
650 #else
651 GFX_SetWorkArea2(_drawbuffer);
652 #endif
653  
654 GFX_WaitForCommandQueue(4);
655  
656 GFX_SetColor(_color.Val);
657 GFX_SetDestAddress((y * (DWORD)DISP_HOR_RESOLUTION) + x);
658 GFX_SetRectSize(1, 1);
659 GFX_StartCopy(RCC_SOLID_FILL, RCC_ROP_C, RCC_SRC_ADDR_DISCONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
660  
661 /* Note: No need to wait for complete execution of the command even for Blocking Mode. The next commands will be in the queue & hence will execute only after the completion of this command. */
662 }
663  
664 /*********************************************************************
665 * Function: WORD GetPixel(SHORT x, SHORT y)
666 *
667 * PreCondition: none
668 *
669 * Input: x,y - pixel coordinates
670 *
671 * Output: pixel color
672 *
673 * Side Effects: none
674 *
675 * Overview: returns pixel color at x,y position
676 *
677 * Note: none
678 *
679 ********************************************************************/
680 WORD GetPixel(SHORT x, SHORT y)
681 {
682 volatile WORD getcolor = 0;
683  
684 if(x < 0 || y < 0 || x > GetMaxX() || y > GetMaxY())
685 {
686 return 1; /* Don't draw but return 1 */
687 }
688  
689 #if (DISP_ORIENTATION == 90)
690 {
691 SHORT t = x;
692 x = y;
693 y = GetMaxX() - t;
694 }
695 #elif (DISP_ORIENTATION == 180)
696 {
697 x = GetMaxX() - x;
698 y = GetMaxY() - y;
699 }
700 #elif (DISP_ORIENTATION == 270)
701 {
702 SHORT t = x;
703 x = GetMaxY() - y;
704 y = t;
705 }
706 #endif
707  
708 /* Wait till previous commands are fully executed */
709 GFX_WaitForCommandQueue(GFX_COMMAND_QUEUE_LENGTH);
710 GFX_WaitForGpu();
711  
712 #ifndef USE_DOUBLE_BUFFERING
713 GFX_SetWorkArea1(_workArea1BaseAddr);
714 #else
715 GFX_SetWorkArea1(_drawbuffer);
716 #endif
717  
718 GFX_SetWorkArea2((WORD)&getcolor);
719  
720 GFX_WaitForCommandQueue(4);
721  
722 GFX_SetSrcAddress((y * (DWORD)DISP_HOR_RESOLUTION) + x);
723 GFX_SetDestAddress(0);
724 GFX_SetRectSize(1, 1);
725 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_DISCONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
726  
727 /* Wait till the command is fully executed */
728 GFX_WaitForCommandQueue(GFX_COMMAND_QUEUE_LENGTH);
729 GFX_WaitForGpu();
730  
731 return (getcolor);
732 }
733  
734 #ifdef USE_DRV_BAR
735 /*********************************************************************
736 * Function: WORD Bar(SHORT left, SHORT top, SHORT right, SHORT bottom)
737 *
738 * PreCondition: none
739 *
740 * Input: left,top - top left corner coordinates,
741 * right,bottom - bottom right corner coordinates
742 *
743 * Output: For NON-Blocking configuration:
744 * - Returns 0 when device is busy and the shape is not yet completely drawn.
745 * - Returns 1 when the shape is completely drawn.
746 * For Blocking configuration:
747 * - Always return 1.
748 *
749 * Side Effects: none
750 *
751 * Overview: draws rectangle filled with current color
752 *
753 * Note: none
754 *
755 ********************************************************************/
756 WORD Bar(SHORT left, SHORT top, SHORT right, SHORT bottom)
757 {
758 DWORD address;
759 SHORT width, height;
760  
761 if(left > right)
762 {
763 return (1); /* Don't draw but return 1 */
764 }
765  
766 if(top > bottom)
767 {
768 return (1); /* Don't draw but return 1 */
769 }
770  
771 if(_clipRgn)
772 {
773 if(left<_clipLeft)
774 left = _clipLeft;
775 if(right>_clipRight)
776 right= _clipRight;
777 if(top<_clipTop)
778 top = _clipTop;
779 if(bottom>_clipBottom)
780 bottom = _clipBottom;
781 }
782 else
783 {
784 left = (left < 0) ? 0: (left > GetMaxX()) ? GetMaxX(): left;
785 top = (top < 0) ? 0: (top > GetMaxY()) ? GetMaxY(): top;
786 right = (right < 0) ? 0: (right > GetMaxX()) ? GetMaxX(): right;
787 bottom = (bottom < 0) ? 0: (bottom > GetMaxY())? GetMaxY(): bottom;
788 }
789  
790 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
791  
792 width = right - left + 1;
793 height = bottom - top + 1;
794  
795 #elif (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
796  
797 height = right - left + 1;
798 width = bottom - top + 1;
799  
800 #endif
801  
802 #if (DISP_ORIENTATION == 90)
803  
804 bottom = DISP_VER_RESOLUTION - left;
805 left = top;
806 right = left + width;
807 top = bottom - height;
808  
809 #elif (DISP_ORIENTATION == 180)
810  
811 right = DISP_HOR_RESOLUTION - left;
812 bottom = DISP_VER_RESOLUTION - top;
813 left = right - width;
814 top = bottom - height;
815  
816 #elif (DISP_ORIENTATION == 270)
817  
818 right = DISP_HOR_RESOLUTION - top;
819 top = left;
820 bottom = top + height;
821 left = right - width;
822  
823 #endif
824  
825 if(GFX_GetFreeCommandSpace() < 4)
826 {
827 #ifndef USE_NONBLOCKING_CONFIG
828 GFX_WaitForCommandQueue(4);
829 #else
830 return (0);
831 #endif
832 }
833  
834 address = (top * (DWORD)DISP_HOR_RESOLUTION) + left;
835  
836 #ifndef USE_DOUBLE_BUFFERING
837 GFX_SetWorkArea2(_workArea2BaseAddr);
838 #else
839 GFX_SetWorkArea2(_drawbuffer);
840 #endif
841  
842 GFX_SetColor(_color.Val);
843 GFX_SetDestAddress(address);
844 GFX_SetRectSize(width, height);
845 GFX_StartCopy(RCC_SOLID_FILL, RCC_ROP_C, RCC_SRC_ADDR_DISCONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
846  
847 /* Note: No need to wait for complete execution of the command even for Blocking Mode. The next commands will be in the queue & hence will execute only after the completion of this command. */
848 return (1);
849 }
850 #endif
851  
852 #ifdef USE_DRV_CLEARDEVICE
853 /*********************************************************************
854 * Function: void ClearDevice(void)
855 *
856 * PreCondition: none
857 *
858 * Input: none
859 *
860 * Output: none
861 *
862 * Side Effects: none
863 *
864 * Overview: clears screen with current color
865 *
866 * Note: none
867 *
868 ********************************************************************/
869 void ClearDevice(void)
870 {
871 GFX_WaitForCommandQueue(4);
872  
873 #ifndef USE_DOUBLE_BUFFERING
874 GFX_SetWorkArea2(_workArea2BaseAddr);
875 #else
876 GFX_SetWorkArea2(_drawbuffer);
877 #endif
878  
879 GFX_SetColor(_color.Val);
880 GFX_SetDestAddress(0);
881 GFX_SetRectSize(DISP_HOR_RESOLUTION, DISP_VER_RESOLUTION);
882 GFX_StartCopy(RCC_SOLID_FILL, RCC_ROP_C, RCC_SRC_ADDR_DISCONTINUOUS, RCC_DEST_ADDR_CONTINUOUS);
883  
884 /* Note: No need to wait for complete execution of the command even for Blocking Mode. The next commands will be in the queue & hence will execute only after the completion of this command. */
885 }
886 #endif
887  
888 #ifdef USE_DRV_LINE
889 /*********************************************************************
890 * Function: WORD Line(SHORT x1, SHORT y1, SHORT x2, SHORT y2)
891 *
892 * PreCondition: none
893 *
894 * Input: x1,y1 - starting coordinates, x2,y2 - ending coordinates
895 *
896 * Output: For NON-Blocking configuration:
897 * - Returns 0 when device is busy and the shape is not yet completely drawn.
898 * - Returns 1 when the shape is completely drawn.
899 * For Blocking configuration:
900 * - Always return 1.
901 *
902 * Side Effects: none
903 *
904 * Overview: draws line
905 *
906 * Note: none
907 *
908 ********************************************************************/
909  
910 WORD Line(SHORT x1, SHORT y1, SHORT x2, SHORT y2)
911 {
912 SHORT deltaX, deltaY;
913 SHORT error, stepErrorLT, stepErrorGE;
914 SHORT stepX, stepY;
915 SHORT steep;
916 SHORT temp;
917 SHORT style, type;
918  
919 if((_lineType == 0) && ((x1 == x2) || (y1 == y2)))
920 {
921 if(x1 > x2)
922 {
923 temp = x1;
924 x1 = x2;
925 x2 = temp;
926 }
927 else if(y1 > y2)
928 {
929 temp = y1;
930 y1 = y2;
931 y2 = temp;
932 }
933  
934 if(_lineThickness)
935 {
936 if(x1 == x2)
937 {
938 if(!Bar(x1 - 1, y1, x2 + 1, y2)) return (0);
939 }
940 else
941 {
942 if(!Bar(x1, y1 - 1, x2, y2 + 1)) return (0);
943 }
944 }
945 else
946 {
947 if(!Bar(x1, y1, x2, y2)) return (0);
948 }
949  
950 return (1);
951 }
952  
953 // Move cursor
954 MoveTo(x2, y2);
955  
956 if(x1 == x2)
957 {
958 if(y1 > y2)
959 {
960 temp = y1;
961 y1 = y2;
962 y2 = temp;
963 }
964  
965 style = 0;
966 type = 1;
967 for(temp = y1; temp < y2 + 1; temp++)
968 {
969 if((++style) == _lineType)
970 {
971 type ^= 1;
972 style = 0;
973 }
974  
975 if(type)
976 {
977 PutPixel(x1, temp);
978 if(_lineThickness)
979 {
980 PutPixel(x1 + 1, temp);
981 PutPixel(x1 - 1, temp);
982 }
983 }
984 }
985  
986 return (1);
987 }
988  
989 if(y1 == y2)
990 {
991 if(x1 > x2)
992 {
993 temp = x1;
994 x1 = x2;
995 x2 = temp;
996 }
997  
998 style = 0;
999 type = 1;
1000 for(temp = x1; temp < x2 + 1; temp++)
1001 {
1002 if((++style) == _lineType)
1003 {
1004 type ^= 1;
1005 style = 0;
1006 }
1007  
1008 if(type)
1009 {
1010 PutPixel(temp, y1);
1011 if(_lineThickness)
1012 {
1013 PutPixel(temp, y1 + 1);
1014 PutPixel(temp, y1 - 1);
1015 }
1016 }
1017 }
1018  
1019 return (1);
1020 }
1021  
1022 stepX = 0;
1023 deltaX = x2 - x1;
1024 if(deltaX < 0)
1025 {
1026 deltaX = -deltaX;
1027 --stepX;
1028 }
1029 else
1030 {
1031 ++stepX;
1032 }
1033  
1034 stepY = 0;
1035 deltaY = y2 - y1;
1036 if(deltaY < 0)
1037 {
1038 deltaY = -deltaY;
1039 --stepY;
1040 }
1041 else
1042 {
1043 ++stepY;
1044 }
1045  
1046 steep = 0;
1047 if(deltaX < deltaY)
1048 {
1049 ++steep;
1050 temp = deltaX;
1051 deltaX = deltaY;
1052 deltaY = temp;
1053 temp = x1;
1054 x1 = y1;
1055 y1 = temp;
1056 temp = stepX;
1057 stepX = stepY;
1058 stepY = temp;
1059 PutPixel(y1, x1);
1060 }
1061 else
1062 {
1063 PutPixel(x1, y1);
1064 }
1065  
1066 // If the current error greater or equal zero
1067 stepErrorGE = deltaX << 1;
1068  
1069 // If the current error less than zero
1070 stepErrorLT = deltaY << 1;
1071  
1072 // Error for the first pixel
1073 error = stepErrorLT - deltaX;
1074  
1075 style = 0;
1076 type = 1;
1077  
1078 while(--deltaX >= 0)
1079 {
1080 if(error >= 0)
1081 {
1082 y1 += stepY;
1083 error -= stepErrorGE;
1084 }
1085  
1086 x1 += stepX;
1087 error += stepErrorLT;
1088  
1089 if((++style) == _lineType)
1090 {
1091 type ^= 1;
1092 style = 0;
1093 }
1094  
1095 if(type)
1096 {
1097 if(steep)
1098 {
1099 PutPixel(y1, x1);
1100 if(_lineThickness)
1101 {
1102 PutPixel(y1 + 1, x1);
1103 PutPixel(y1 - 1, x1);
1104 }
1105 }
1106 else
1107 {
1108 PutPixel(x1, y1);
1109 if(_lineThickness)
1110 {
1111 PutPixel(x1, y1 + 1);
1112 PutPixel(x1, y1 - 1);
1113 }
1114 }
1115 }
1116 } // end of while
1117  
1118 return (1);
1119 }
1120  
1121 #endif
1122  
1123 #ifdef USE_DRV_FONT
1124  
1125 /*********************************************************************
1126 * Function: void SetFont(void* font)
1127 *
1128 * PreCondition: none
1129 *
1130 * Input: pointer to the font image
1131 *
1132 * Output: none
1133 *
1134 * Side Effects: none
1135 *
1136 * Overview: defines current font
1137 *
1138 * Note: none
1139 *
1140 ********************************************************************/
1141 void SetFont(void *font)
1142 {
1143 FONT_HEADER *pHeader;
1144  
1145 #ifdef USE_FONT_EXTERNAL
1146 FONT_HEADER header;
1147 #endif
1148  
1149 if(_font == font)
1150 {
1151 return;
1152 }
1153  
1154 _font = font;
1155 switch(*((SHORT *)font))
1156 {
1157 #ifdef USE_FONT_RAM
1158 case RAM:
1159 pHeader = (FONT_HEADER *) ((FONT_RAM *)font)->address;
1160 GFX_WaitForCommandQueue(1);
1161 GFX_SetFont((WORD)pHeader);
1162 break;
1163 #endif
1164  
1165 #ifdef USE_FONT_FLASH
1166 case FLASH:
1167 pHeader = (FONT_HEADER *) ((FONT_FLASH *)font)->address;
1168 break;
1169 #endif
1170  
1171 #ifdef USE_FONT_EXTERNAL
1172  
1173 case EXTERNAL:
1174 pHeader = &header;
1175 ExternalMemoryCallback(font, 0, sizeof(FONT_HEADER), pHeader);
1176 break;
1177 #endif
1178  
1179 default:
1180 return;
1181 }
1182  
1183 _fontFirstChar = pHeader->firstChar;
1184 _fontLastChar = pHeader->lastChar;
1185 _fontHeight = pHeader->height;
1186 }
1187  
1188 /*********************************************************************
1189 * Function: WORD OutChar(XCHAR ch)
1190 *
1191 * PreCondition: none
1192 *
1193 * Input: character code
1194 *
1195 * Output: For NON-Blocking configuration:
1196 * - Returns 0 when device is busy and the character is not yet completely drawn.
1197 * - Returns 1 when the character is completely drawn.
1198 * For Blocking configuration:
1199 * - Always return 1.
1200 *
1201 * Side Effects: none
1202 *
1203 * Overview: outputs a character
1204 *
1205 * Note: none
1206 *
1207 ********************************************************************/
1208 WORD OutChar(XCHAR ch)
1209 {
1210 GLYPH_ENTRY *pChTable = NULL;
1211 BYTE *pChImage = NULL;
1212  
1213 #ifdef USE_FONT_EXTERNAL
1214 GLYPH_ENTRY chTable;
1215 BYTE chImage[EXTERNAL_FONT_BUFFER_SIZE];
1216 WORD imageSize;
1217 DWORD_VAL glyphOffset;
1218 #endif
1219 SHORT chWidth = 0;
1220 SHORT xCnt, yCnt, x = 0, y;
1221 BYTE temp = 0, mask;
1222  
1223 if(GFX_GetFreeCommandSpace() < 2)
1224 {
1225 #ifndef USE_NONBLOCKING_CONFIG
1226 GFX_WaitForCommandQueue(2);
1227 #else
1228 return (0);
1229 #endif
1230 }
1231  
1232 if((unsigned XCHAR)ch < (unsigned XCHAR)_fontFirstChar)
1233 return (-1);
1234 if((unsigned XCHAR)ch > (unsigned XCHAR)_fontLastChar)
1235 return (-1);
1236  
1237 switch(*((SHORT *)_font))
1238 {
1239  
1240 case RAM:
1241 if(_fontOrientation == ORIENT_HOR)
1242 {
1243 pChTable = (GLYPH_ENTRY *) (((FONT_RAM *)_font)->address + sizeof(FONT_HEADER)) + ((unsigned XCHAR)ch - (unsigned XCHAR)_fontFirstChar);
1244  
1245 pChImage = (BYTE *) (((FONT_RAM *)_font)->address + pChTable->offsetLSB);
1246  
1247 chWidth = pChTable->width;
1248  
1249 if(_chrcolor.Val != _color.Val)
1250 {
1251 GFX_WaitForCommandQueue(3); /* Already 2 commands space will be available */
1252 GFX_SetCharFgColor(_color.Val);
1253 }
1254  
1255 #ifndef USE_DOUBLE_BUFFERING
1256 GFX_SetWorkArea1(_workArea1BaseAddr);
1257 #else
1258 GFX_SetWorkArea1(_drawbuffer);
1259 #endif
1260  
1261 GFX_SetPrintXY(GetX(), GetY());
1262 GFX_PrintChar(ch, CHR_TRANSPARENT);
1263  
1264 MoveTo(GetX() + chWidth, GetY());
1265 }
1266 else
1267 {
1268 // if orientation is vertical, process the font using PutPixel.
1269 pChTable = (GLYPH_ENTRY *) (((FONT_FLASH *)_font)->address + sizeof(FONT_HEADER)) + ((unsigned XCHAR)ch - (unsigned XCHAR)_fontFirstChar);
1270 pChImage = (BYTE *) (((FONT_FLASH *)_font)->address + ((DWORD)(pChTable->offsetMSB) << 8) + pChTable->offsetLSB);
1271 chWidth = pChTable->width;
1272 break;
1273 }
1274  
1275 return (1);
1276  
1277  
1278 #ifdef USE_FONT_FLASH
1279  
1280 case FLASH:
1281  
1282 // if font is from FLASH process the font using PutPixel.
1283 pChTable = (GLYPH_ENTRY *) (((FONT_FLASH *)_font)->address + sizeof(FONT_HEADER)) + ((unsigned XCHAR)ch - (unsigned XCHAR)_fontFirstChar);
1284 pChImage = (BYTE *) (((FONT_FLASH *)_font)->address + ((DWORD)(pChTable->offsetMSB) << 8) + pChTable->offsetLSB);
1285 chWidth = pChTable->width;
1286 break;
1287 #endif
1288  
1289 #ifdef USE_FONT_EXTERNAL
1290  
1291 case EXTERNAL:
1292  
1293 // get glyph entry
1294 ExternalMemoryCallback
1295 (
1296 _font,
1297 sizeof(FONT_HEADER) + ((unsigned XCHAR)ch - (unsigned XCHAR)_fontFirstChar) * sizeof(GLYPH_ENTRY),
1298 sizeof(GLYPH_ENTRY),
1299 &chTable
1300 );
1301  
1302 chWidth = chTable.width;
1303  
1304 // width of glyph in bytes
1305 imageSize = 0;
1306 if(chWidth & 0x0007)
1307 imageSize = 1;
1308 imageSize += (chWidth >> 3);
1309  
1310 // glyph image size
1311 imageSize *= _fontHeight;
1312  
1313 // get glyph image
1314 glyphOffset.w[1] = chTable.offsetMSB;
1315 glyphOffset.w[0] = chTable.offsetLSB;
1316  
1317 ExternalMemoryCallback(_font, glyphOffset.Val, imageSize, &chImage);
1318 pChImage = (BYTE *) &chImage;
1319  
1320 break;
1321 #endif
1322  
1323 default:
1324 break;
1325 }
1326  
1327 if(_fontOrientation == ORIENT_HOR)
1328 {
1329 y = GetY();
1330 for(yCnt = 0; yCnt < _fontHeight; yCnt++)
1331 {
1332 x = GetX();
1333 mask = 0;
1334 for(xCnt = 0; xCnt < chWidth; xCnt++)
1335 {
1336 if(mask == 0)
1337 {
1338 temp = *pChImage++;
1339 mask = 0x01;
1340 }
1341  
1342 if(temp & mask)
1343 {
1344 PutPixel(x, y);
1345 }
1346  
1347 x++;
1348 mask <<= 1;
1349 }
1350  
1351 y++;
1352 }
1353  
1354 // move cursor
1355 _cursorX = x;
1356 }
1357 else
1358 {
1359 y = GetX();
1360 for(yCnt = 0; yCnt < _fontHeight; yCnt++)
1361 {
1362 x = GetY();
1363 mask = 0;
1364 for(xCnt = 0; xCnt < chWidth; xCnt++)
1365 {
1366 if(mask == 0)
1367 {
1368 temp = *pChImage++;
1369 mask = 0x01;
1370 }
1371  
1372 if(temp & mask)
1373 {
1374 PutPixel(y, x);
1375 }
1376  
1377 x--;
1378 mask <<= 1;
1379 }
1380  
1381 y++;
1382 }
1383  
1384 // move cursor
1385 _cursorY = x;
1386 }
1387  
1388 return (1);
1389 }
1390  
1391 #endif
1392  
1393 #ifdef USE_DRV_PUTIMAGE
1394  
1395 #ifdef USE_BITMAP_FLASH
1396  
1397 /*********************************************************************
1398 * Function: void PutImage1BPP(SHORT left, SHORT top, FLASH_BYTE* bitmap, BYTE stretch)
1399 *
1400 * PreCondition: none
1401 *
1402 * Input: left,top - left top image corner,
1403 * bitmap - image pointer,
1404 * stretch - image stretch factor
1405 *
1406 * Output: none
1407 *
1408 * Side Effects: none
1409 *
1410 * Overview: outputs monochrome image starting from left,top coordinates
1411 *
1412 * Note: image must be located in flash
1413 *
1414 ********************************************************************/
1415 void PutImage1BPP(SHORT left, SHORT top, FLASH_BYTE *bitmap, BYTE stretch)
1416 {
1417 register FLASH_BYTE *flashAddress;
1418 register FLASH_BYTE *tempFlashAddress;
1419 BYTE temp = 0;
1420 WORD sizeX, sizeY;
1421 WORD x, y;
1422 WORD xc, yc;
1423 BYTE stretchX, stretchY;
1424 WORD palette[2], color;
1425 BYTE mask;
1426 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1427 WORD outputSize;
1428 WORD lineBuffer[(GetMaxX() + (DWORD) 1)];
1429 WORD *pData;
1430  
1431 GFX_WaitForCommandQueue(16);
1432 GFX_WaitForGpu();
1433  
1434 #endif
1435  
1436 // Move pointer to size information
1437 flashAddress = bitmap + 2;
1438  
1439 // Read image size
1440 sizeY = *((FLASH_WORD *)flashAddress);
1441 flashAddress += 2;
1442 sizeX = *((FLASH_WORD *)flashAddress);
1443 flashAddress += 2;
1444 palette[0] = *((FLASH_WORD *)flashAddress);
1445 flashAddress += 2;
1446 palette[1] = *((FLASH_WORD *)flashAddress);
1447 flashAddress += 2;
1448  
1449 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1450 if (stretch == IMAGE_X2) {
1451 outputSize = sizeX << 1;
1452 }
1453 else //if (stretch == IMAGE_NORMAL)
1454 {
1455 outputSize = sizeX;
1456 }
1457 GFX_SetWorkArea1((WORD)lineBuffer);
1458 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
1459 GFX_SetRectSize(outputSize, 1);
1460 GFX_SetSrcAddress(0);
1461 #endif
1462  
1463 yc = top;
1464 for(y = 0; y < sizeY; y++)
1465 {
1466 tempFlashAddress = flashAddress;
1467 for(stretchY = 0; stretchY < stretch; stretchY++)
1468 {
1469 flashAddress = tempFlashAddress;
1470 mask = 0;
1471 xc = left;
1472  
1473 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1474 pData = lineBuffer;
1475 #endif
1476  
1477 for(x = 0; x < sizeX; x++)
1478 {
1479  
1480 // Read 8 pixels from flash
1481 if(mask == 0)
1482 {
1483 temp = *flashAddress;
1484 flashAddress++;
1485 mask = 0x80;
1486 }
1487  
1488 // Set color
1489 if(mask & temp)
1490 {
1491 // Set color
1492 #ifdef USE_PALETTE
1493 color = 1;
1494 #else
1495 color = palette[1];
1496 #endif
1497 }
1498 else
1499 {
1500 // Set color
1501 #ifdef USE_PALETTE
1502 color = 0;
1503 #else
1504 color = palette[0];
1505 #endif
1506 }
1507 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1508 SetColor(color);
1509 #endif
1510  
1511 // Write pixel to screen
1512 for(stretchX = 0; stretchX < stretch; stretchX++)
1513 {
1514 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1515 PutPixel(xc++, yc);
1516 #else
1517 *pData++ = color;
1518 #endif
1519 }
1520  
1521 // Shift to the next pixel
1522 mask >>= 1;
1523 }
1524 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1525 GFX_WaitForCommandQueue(2);
1526 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
1527 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
1528 #endif
1529 yc++;
1530 }
1531 }
1532 }
1533  
1534 /*********************************************************************
1535 * Function: void PutImage4BPP(SHORT left, SHORT top, FLASH_BYTE* bitmap, BYTE stretch)
1536 *
1537 * PreCondition: none
1538 *
1539 * Input: left,top - left top image corner, bitmap - image pointer,
1540 * stretch - image stretch factor
1541 *
1542 * Output: none
1543 *
1544 * Side Effects: none
1545 *
1546 * Overview: outputs 16 color image starting from left,top coordinates
1547 *
1548 * Note: image must be located in flash
1549 *
1550 ********************************************************************/
1551 #if (COLOR_DEPTH >= 4)
1552  
1553 void PutImage4BPP(SHORT left, SHORT top, FLASH_BYTE *bitmap, BYTE stretch)
1554 {
1555 register FLASH_BYTE *flashAddress;
1556 register FLASH_BYTE *tempFlashAddress;
1557 WORD sizeX, sizeY;
1558 register WORD x, y;
1559 WORD xc, yc;
1560 BYTE temp = 0;
1561 register BYTE stretchX, stretchY;
1562 WORD palette[16], color;
1563 WORD counter;
1564  
1565 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1566 WORD outputSize;
1567 WORD lineBuffer[(GetMaxX() + (DWORD) 1)];
1568 WORD *pData;
1569  
1570 GFX_WaitForCommandQueue(16);
1571 GFX_WaitForGpu();
1572  
1573 #endif
1574 // Move pointer to size information
1575 flashAddress = bitmap + 2;
1576  
1577 // Read image size
1578 sizeY = *((FLASH_WORD *)flashAddress);
1579 flashAddress += 2;
1580 sizeX = *((FLASH_WORD *)flashAddress);
1581 flashAddress += 2;
1582  
1583 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1584 if (stretch == IMAGE_X2) {
1585 outputSize = sizeX << 1;
1586 }
1587 else //if (stretch == IMAGE_NORMAL)
1588 {
1589 outputSize = sizeX;
1590 }
1591 GFX_SetWorkArea1((WORD)lineBuffer);
1592 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
1593 GFX_SetRectSize(outputSize, 1);
1594 GFX_SetSrcAddress(0);
1595 #endif
1596  
1597 // Read palette
1598 for(counter = 0; counter < 16; counter++)
1599 {
1600 palette[counter] = *((FLASH_WORD *)flashAddress);
1601 flashAddress += 2;
1602 }
1603  
1604 yc = top;
1605 for(y = 0; y < sizeY; y++)
1606 {
1607 tempFlashAddress = flashAddress;
1608 for(stretchY = 0; stretchY < stretch; stretchY++)
1609 {
1610 flashAddress = tempFlashAddress;
1611 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1612 pData = lineBuffer;
1613 #endif
1614 xc = left;
1615 for(x = 0; x < sizeX; x++)
1616 {
1617  
1618 // Read 2 pixels from flash
1619 if((x & 0x0001) == 0)
1620 {
1621 temp = *flashAddress;
1622 flashAddress++;
1623 }
1624  
1625 #ifdef USE_PALETTE
1626 color = temp >> ((x&0x0001)*4) & 0x000F;
1627 #else
1628 color = palette[(temp >> ((x&0x0001)*4)) & 0x000F];
1629 #endif
1630  
1631 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1632 SetColor(color);
1633 #endif
1634  
1635 // Write pixel to screen
1636 for(stretchX = 0; stretchX < stretch; stretchX++)
1637 {
1638 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1639 PutPixel(xc++, yc);
1640 #else
1641 *pData++ = color;
1642 #endif
1643 }
1644 }
1645 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1646 GFX_WaitForCommandQueue(2);
1647 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
1648 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
1649 #endif
1650 yc++;
1651 }
1652 }
1653 }
1654  
1655 #endif //#if (COLOR_DEPTH >= 4)
1656  
1657 /*********************************************************************
1658 * Function: void PutImage8BPP(SHORT left, SHORT top, FLASH_BYTE* bitmap, BYTE stretch)
1659 *
1660 * PreCondition: none
1661 *
1662 * Input: left,top - left top image corner, bitmap - image pointer,
1663 * stretch - image stretch factor
1664 *
1665 * Output: none
1666 *
1667 * Side Effects: none
1668 *
1669 * Overview: outputs 256 color image starting from left,top coordinates
1670 *
1671 * Note: image must be located in flash
1672 *
1673 ********************************************************************/
1674 #if (COLOR_DEPTH >= 8)
1675  
1676 void PutImage8BPP(SHORT left, SHORT top, FLASH_BYTE *bitmap, BYTE stretch)
1677 {
1678 register FLASH_BYTE *flashAddress;
1679 register FLASH_BYTE *tempFlashAddress;
1680 WORD sizeX, sizeY;
1681 WORD x, y;
1682 WORD xc, yc;
1683 BYTE temp;
1684 BYTE stretchX, stretchY;
1685 WORD palette[256], color;
1686 WORD counter;
1687  
1688 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1689 WORD outputSize;
1690 WORD lineBuffer[(GetMaxX() + (DWORD) 1)];
1691 WORD *pData;
1692  
1693 GFX_WaitForCommandQueue(16);
1694 GFX_WaitForGpu();
1695  
1696 #endif
1697  
1698 // Move pointer to size information
1699 flashAddress = bitmap + 2;
1700  
1701 // Read image size
1702 sizeY = *((FLASH_WORD *)flashAddress);
1703 flashAddress += 2;
1704 sizeX = *((FLASH_WORD *)flashAddress);
1705 flashAddress += 2;
1706  
1707 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1708 if (stretch == IMAGE_X2) {
1709 outputSize = sizeX << 1;
1710 }
1711 else //if (stretch == IMAGE_NORMAL)
1712 {
1713 outputSize = sizeX;
1714 }
1715 GFX_SetWorkArea1((WORD)lineBuffer);
1716 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
1717 GFX_SetRectSize(outputSize, 1);
1718 GFX_SetSrcAddress(0);
1719 #endif
1720  
1721 // Read palette
1722 for(counter = 0; counter < 256; counter++)
1723 {
1724 palette[counter] = *((FLASH_WORD *)flashAddress);
1725 flashAddress += 2;
1726 }
1727  
1728 yc = top;
1729 for(y = 0; y < sizeY; y++)
1730 {
1731 tempFlashAddress = flashAddress;
1732 for(stretchY = 0; stretchY < stretch; stretchY++)
1733 {
1734 flashAddress = tempFlashAddress;
1735 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1736 pData = lineBuffer;
1737 #endif
1738 xc = left;
1739  
1740 for(x = 0; x < sizeX; x++)
1741 {
1742 // Read pixels from flash
1743 temp = *flashAddress;
1744 flashAddress++;
1745  
1746 #ifdef USE_PALETTE
1747 color = temp;
1748 #else
1749 color = palette[temp];
1750 #endif
1751 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1752 SetColor(color);
1753 #endif
1754  
1755 // Write pixel to buffer
1756 for(stretchX = 0; stretchX < stretch; stretchX++)
1757 {
1758 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1759 PutPixel(xc++, yc);
1760 #else
1761 *pData++ = color;
1762 #endif
1763 }
1764 }
1765 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1766 GFX_WaitForCommandQueue(2);
1767 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
1768 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
1769 #endif
1770 yc++;
1771 }
1772 }
1773 }
1774  
1775 #endif //#if (COLOR_DEPTH >= 8)
1776  
1777 /*********************************************************************
1778 * Function: void PutImage16BPP(SHORT left, SHORT top, FLASH_BYTE* bitmap, BYTE stretch)
1779 *
1780 * PreCondition: none
1781 *
1782 * Input: left,top - left top image corner, bitmap - image pointer,
1783 * stretch - image stretch factor
1784 *
1785 * Output: none
1786 *
1787 * Side Effects: none
1788 *
1789 * Overview: outputs hicolor image starting from left,top coordinates
1790 *
1791 * Note: image must be located in flash
1792 *
1793 ********************************************************************/
1794 #if (COLOR_DEPTH == 16)
1795 void PutImage16BPP(SHORT left, SHORT top, FLASH_BYTE *bitmap, BYTE stretch)
1796 {
1797 register FLASH_WORD *flashAddress;
1798 register FLASH_WORD *tempFlashAddress;
1799 WORD sizeX, sizeY;
1800 register WORD x, y;
1801 WORD xc, yc;
1802 WORD temp;
1803 register BYTE stretchX, stretchY;
1804  
1805 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1806 WORD outputSize;
1807 WORD lineBuffer[(GetMaxX() + (DWORD) 1)];
1808 WORD *pData;
1809  
1810  
1811 GFX_WaitForCommandQueue(16);
1812 GFX_WaitForGpu();
1813  
1814 #endif
1815  
1816  
1817 // Move pointer to size information
1818 flashAddress = (FLASH_WORD *)bitmap + 1;
1819  
1820 // Read image size
1821 sizeY = *flashAddress;
1822 flashAddress++;
1823 sizeX = *flashAddress;
1824 flashAddress++;
1825  
1826 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1827 if (stretch == IMAGE_X2) {
1828 outputSize = sizeX << 1;
1829 }
1830 else
1831 {
1832 outputSize = sizeX;
1833 }
1834 GFX_SetWorkArea1((WORD)lineBuffer);
1835 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
1836 GFX_SetRectSize(outputSize, 1);
1837 GFX_SetSrcAddress(0);
1838 #endif
1839  
1840 yc = top;
1841 for(y = 0; y < sizeY; y++)
1842 {
1843 tempFlashAddress = flashAddress;
1844 for(stretchY = 0; stretchY < stretch; stretchY++)
1845 {
1846 flashAddress = tempFlashAddress;
1847 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1848 pData = lineBuffer;
1849 #endif
1850 xc = left;
1851  
1852 for(x = 0; x < sizeX; x++)
1853 {
1854 temp = *flashAddress;
1855 flashAddress++;
1856 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1857 SetColor(temp);
1858 #endif
1859  
1860 // Write pixel to buffer
1861 for(stretchX = 0; stretchX < stretch; stretchX++)
1862 {
1863 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1864 PutPixel(xc++, yc);
1865 #else
1866 *pData++ = temp;
1867 #endif
1868 }
1869 }
1870 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1871 GFX_WaitForCommandQueue(2);
1872 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
1873 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
1874 #endif
1875 yc++;
1876 }
1877 }
1878 }
1879 #endif // #if (COLOR_DEPTH == 16)
1880 #endif //USE_BITMAP_FLASH
1881  
1882 #ifdef USE_BITMAP_EXTERNAL
1883  
1884 /*********************************************************************
1885 * Function: void PutImage1BPPExt(SHORT left, SHORT top, void* bitmap, BYTE stretch)
1886 *
1887 * PreCondition: none
1888 *
1889 * Input: left,top - left top image corner, bitmap - image pointer,
1890 * stretch - image stretch factor
1891 *
1892 * Output: none
1893 *
1894 * Side Effects: none
1895 *
1896 * Overview: outputs monochrome image starting from left,top coordinates
1897 *
1898 * Note: image must be located in external memory
1899 *
1900 ********************************************************************/
1901 void PutImage1BPPExt(SHORT left, SHORT top, void *bitmap, BYTE stretch)
1902 {
1903 register DWORD memOffset;
1904 BITMAP_HEADER bmp;
1905 BYTE lineBuffer[((GetMaxX() + (DWORD) 1) / 8) + 1];
1906 WORD palette[2], color;
1907 BYTE *pData;
1908 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1909 WORD *pBufAddr, *pData2;
1910 WORD lineBuffer2[(GetMaxX() + (DWORD) 1)];
1911 WORD outputSize;
1912 #endif
1913 SHORT byteWidth;
1914 BYTE mask, temp = 0;
1915 WORD sizeX, sizeY;
1916 WORD x, y;
1917 WORD xc, yc;
1918 BYTE stretchX, stretchY;
1919  
1920 // Get bitmap header
1921 ExternalMemoryCallback(bitmap, 0, sizeof(BITMAP_HEADER), &bmp);
1922 // Get palette (2 entries)
1923 ExternalMemoryCallback(bitmap, sizeof(BITMAP_HEADER), 2 * sizeof(WORD), palette);
1924 // Set offset to the image data
1925 memOffset = sizeof(BITMAP_HEADER) + 2 * sizeof(WORD);
1926  
1927 // Get size
1928 sizeX = bmp.width;
1929 sizeY = bmp.height;
1930  
1931 // Line width in bytes
1932 byteWidth = sizeX >> 3;
1933 if(sizeX & 0x0007)
1934 byteWidth++;
1935  
1936 yc = top;
1937  
1938 GFX_WaitForCommandQueue(16);
1939 GFX_WaitForGpu();
1940  
1941 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1942 if (stretch == IMAGE_X2) {
1943 outputSize = sizeX << 1;
1944 }
1945 else //if (stretch == IMAGE_NORMAL)
1946 {
1947 outputSize = sizeX;
1948 }
1949 pBufAddr = lineBuffer2;
1950 GFX_SetWorkArea1((WORD)pBufAddr);
1951 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
1952 GFX_SetRectSize(outputSize, 1);
1953 GFX_SetSrcAddress(0);
1954 #endif
1955  
1956 for(y = 0; y < sizeY; y++)
1957 {
1958 // Get line
1959 ExternalMemoryCallback(bitmap, memOffset, byteWidth, lineBuffer);
1960 memOffset += byteWidth;
1961 for(stretchY = 0; stretchY < stretch; stretchY++)
1962 {
1963 pData = lineBuffer;
1964 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
1965 pData2 = lineBuffer2;
1966 #endif
1967  
1968 mask = 0;
1969 xc = left;
1970 for(x = 0; x < sizeX; x++)
1971 {
1972  
1973 if (mask == 0)
1974 {
1975 temp = *pData++;
1976 mask = 0x80;
1977 }
1978 if (mask & temp)
1979 {
1980 #ifdef USE_PALETTE
1981 color = 1;
1982 #else
1983 color = palette[1];
1984 #endif
1985 }
1986 else
1987 {
1988 #ifdef USE_PALETTE
1989 color = 0;
1990 #else
1991 color = palette[0];
1992 #endif
1993 }
1994 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
1995 SetColor(color);
1996 #endif
1997  
1998 // Write pixel to buffer
1999 for(stretchX = 0; stretchX < stretch; stretchX++)
2000 {
2001 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2002 PutPixel(xc++, yc);
2003 #else
2004 *pData2++ = color;
2005 #endif
2006 }
2007 mask >>= 1;
2008 }
2009 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2010 GFX_WaitForCommandQueue(2);
2011 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
2012 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
2013 #endif
2014 yc++;
2015 }
2016 }
2017  
2018 }
2019  
2020  
2021 /*********************************************************************
2022 * Function: void PutImage4BPPExt(SHORT left, SHORT top, void* bitmap, BYTE stretch)
2023 *
2024 * PreCondition: none
2025 *
2026 * Input: left,top - left top image corner, bitmap - image pointer,
2027 * stretch - image stretch factor
2028 *
2029 * Output: none
2030 *
2031 * Side Effects: none
2032 *
2033 * Overview: outputs monochrome image starting from left,top coordinates
2034 *
2035 * Note: image must be located in external memory
2036 *
2037 ********************************************************************/
2038 #if (COLOR_DEPTH >= 4)
2039  
2040 void PutImage4BPPExt(SHORT left, SHORT top, void *bitmap, BYTE stretch)
2041 {
2042 register DWORD memOffset;
2043 BITMAP_HEADER bmp;
2044 BYTE lineBuffer[((GetMaxX() + (DWORD) 1) / 2) + 1];
2045 WORD palette[16], color;
2046 BYTE *pData;
2047 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2048 WORD *pBufAddr, *pData2;
2049 WORD lineBuffer2[(GetMaxX() + (DWORD) 1)];
2050 WORD outputSize;
2051 #endif
2052 SHORT byteWidth;
2053 BYTE temp = 0;
2054 WORD sizeX, sizeY;
2055 WORD x, y;
2056 WORD xc, yc;
2057 BYTE stretchX, stretchY;
2058  
2059 // Get bitmap header
2060 ExternalMemoryCallback(bitmap, 0, sizeof(BITMAP_HEADER), &bmp);
2061 // Get palette (16 entries)
2062 ExternalMemoryCallback(bitmap, sizeof(BITMAP_HEADER), 16 * sizeof(WORD), palette);
2063 // Set offset to the image data
2064 memOffset = sizeof(BITMAP_HEADER) + 16 * sizeof(WORD);
2065  
2066 // Get size
2067 sizeX = bmp.width;
2068 sizeY = bmp.height;
2069  
2070 // Line width in bytes
2071 byteWidth = sizeX >> 1;
2072 if(sizeX & 0x0001)
2073 byteWidth++;
2074  
2075 yc = top;
2076  
2077 GFX_WaitForCommandQueue(16);
2078 GFX_WaitForGpu();
2079  
2080 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2081 if (stretch == IMAGE_X2) {
2082 outputSize = sizeX << 1;
2083 }
2084 else //if (stretch == IMAGE_NORMAL)
2085 {
2086 outputSize = sizeX;
2087 }
2088 pBufAddr = lineBuffer2;
2089 GFX_SetWorkArea1((WORD)pBufAddr);
2090 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
2091 GFX_SetRectSize(outputSize, 1);
2092 GFX_SetSrcAddress(0);
2093 #endif
2094  
2095 for(y = 0; y < sizeY; y++)
2096 {
2097 // Get line
2098 ExternalMemoryCallback(bitmap, memOffset, byteWidth, lineBuffer);
2099 memOffset += byteWidth;
2100 for(stretchY = 0; stretchY < stretch; stretchY++)
2101 {
2102 pData = lineBuffer;
2103 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2104 pData2 = lineBuffer2;
2105 #endif
2106  
2107 xc = left;
2108 for(x = 0; x < sizeX; x++)
2109 {
2110 if ((x & 0x0001) == 0)
2111 temp = *pData++;
2112  
2113 #ifdef USE_PALETTE
2114 color = temp >> ((x&0x0001)*4)) & 0x000F;
2115 #else
2116 color = palette[(temp >> ((x&0x0001)*4)) & 0x000F];
2117 #endif
2118 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2119 SetColor(color);
2120 #endif
2121  
2122 // Write pixel to buffer
2123 for(stretchX = 0; stretchX < stretch; stretchX++)
2124 {
2125 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2126 PutPixel(xc++, yc);
2127 #else
2128 *pData2++ = color;
2129 #endif
2130 }
2131 }
2132 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2133 GFX_WaitForCommandQueue(2);
2134 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
2135 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
2136 #endif
2137 yc++;
2138 }
2139 }
2140 }
2141  
2142 #endif //#if (COLOR_DEPTH >= 4)
2143  
2144 /*********************************************************************
2145 * Function: void PutImage8BPPExt(SHORT left, SHORT top, void* bitmap, BYTE stretch)
2146 *
2147 * PreCondition: none
2148 *
2149 * Input: left,top - left top image corner, bitmap - image pointer,
2150 * stretch - image stretch factor
2151 *
2152 * Output: none
2153 *
2154 * Side Effects: none
2155 *
2156 * Overview: outputs monochrome image starting from left,top coordinates
2157 *
2158 * Note: image must be located in external memory
2159 *
2160 ********************************************************************/
2161 #if (COLOR_DEPTH >= 8)
2162  
2163 void PutImage8BPPExt(SHORT left, SHORT top, void *bitmap, BYTE stretch)
2164 {
2165 register DWORD memOffset;
2166 BITMAP_HEADER bmp;
2167 BYTE lineBuffer[(GetMaxX() + (DWORD) 1)];
2168 WORD palette[256], color;
2169 BYTE *pData;
2170 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2171 WORD *pBufAddr, *pData2;
2172 WORD lineBuffer2[(GetMaxX() + (DWORD) 1)];
2173 WORD outputSize;
2174 #endif
2175  
2176 BYTE temp;
2177 WORD sizeX, sizeY;
2178 WORD x, y;
2179 WORD xc, yc;
2180 BYTE stretchX, stretchY;
2181  
2182 // Get bitmap header
2183 ExternalMemoryCallback(bitmap, 0, sizeof(BITMAP_HEADER), &bmp);
2184 // Get palette (256 entries)
2185 ExternalMemoryCallback(bitmap, sizeof(BITMAP_HEADER), 256 * sizeof(WORD), palette);
2186 // Set offset to the image data
2187 memOffset = sizeof(BITMAP_HEADER) + 256 * sizeof(WORD);
2188  
2189 // Get size
2190 sizeX = bmp.width;
2191 sizeY = bmp.height;
2192  
2193 yc = top;
2194  
2195 GFX_WaitForCommandQueue(16);
2196 GFX_WaitForGpu();
2197  
2198 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2199 if (stretch == IMAGE_X2) {
2200 outputSize = sizeX << 1;
2201 }
2202 else //if (stretch == IMAGE_NORMAL)
2203 {
2204 outputSize = sizeX;
2205 }
2206 pBufAddr = lineBuffer2;
2207 GFX_SetWorkArea1((WORD)pBufAddr);
2208 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
2209 GFX_SetRectSize(outputSize, 1);
2210 GFX_SetSrcAddress(0);
2211 #endif
2212  
2213 for(y = 0; y < sizeY; y++)
2214 {
2215 // Get line
2216 ExternalMemoryCallback(bitmap, memOffset, sizeX, lineBuffer);
2217 memOffset += sizeX;
2218 for(stretchY = 0; stretchY < stretch; stretchY++)
2219 {
2220 pData = lineBuffer;
2221 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2222 pData2 = lineBuffer2;
2223 #endif
2224  
2225 xc = left;
2226 for(x = 0; x < sizeX; x++)
2227 {
2228 temp = *pData++;
2229 #ifdef USE_PALETTE
2230 color = temp;
2231 #else
2232 color = palette[temp];
2233 #endif
2234 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2235 SetColor(color);
2236 #endif
2237  
2238 // Write pixel to buffer
2239 for(stretchX = 0; stretchX < stretch; stretchX++)
2240 {
2241 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2242 PutPixel(xc++, yc);
2243 #else
2244 *pData2++ = color;
2245 #endif
2246 }
2247 }
2248 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2249 GFX_WaitForCommandQueue(2);
2250 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
2251 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
2252 #endif
2253 yc++;
2254 }
2255 }
2256 }
2257  
2258 #endif //#if (COLOR_DEPTH >= 8)
2259  
2260 /*********************************************************************
2261 * Function: void PutImage16BPPExt(SHORT left, SHORT top, void* bitmap, BYTE stretch)
2262 *
2263 * PreCondition: none
2264 *
2265 * Input: left,top - left top image corner, bitmap - image pointer,
2266 * stretch - image stretch factor
2267 *
2268 * Output: none
2269 *
2270 * Side Effects: none
2271 *
2272 * Overview: outputs monochrome image starting from left,top coordinates
2273 *
2274 * Note: image must be located in external memory
2275 *
2276 ********************************************************************/
2277 #if (COLOR_DEPTH == 16)
2278  
2279 void PutImage16BPPExt(SHORT left, SHORT top, void *bitmap, BYTE stretch)
2280 {
2281 register DWORD memOffset;
2282 BITMAP_HEADER bmp;
2283 WORD lineBuffer[(GetMaxX() + (DWORD) 1)];
2284 WORD *pData;
2285 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2286 WORD *pBufAddr, *pData2;
2287 WORD lineBuffer2[(GetMaxX() + (DWORD) 1)];
2288 WORD outputSize;
2289 #endif
2290 WORD byteWidth;
2291  
2292 WORD temp;
2293 WORD sizeX, sizeY;
2294 WORD x, y;
2295 WORD xc, yc;
2296 BYTE stretchX, stretchY;
2297  
2298 GFX_WaitForCommandQueue(16);
2299 GFX_WaitForGpu();
2300  
2301 // Get bitmap header
2302 ExternalMemoryCallback(bitmap, 0, sizeof(BITMAP_HEADER), &bmp);
2303  
2304 // Set offset to the image data
2305 memOffset = sizeof(BITMAP_HEADER);
2306  
2307 // Get size
2308 sizeX = bmp.width;
2309 sizeY = bmp.height;
2310  
2311 // calculate how many bytes to fetch
2312 byteWidth = sizeX << 1;
2313  
2314 yc = top;
2315  
2316 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2317 if (stretch == IMAGE_X2) {
2318 outputSize = sizeX << 1;
2319 }
2320 else //if (stretch == IMAGE_NORMAL)
2321 {
2322 outputSize = sizeX;
2323 }
2324 pBufAddr = lineBuffer2;
2325 GFX_SetWorkArea1((WORD)pBufAddr);
2326 GFX_SetWorkArea2(GFX_DISPLAY_BUFFER_START_ADDRESS);
2327 GFX_SetRectSize(outputSize, 1);
2328 GFX_SetSrcAddress(0);
2329 #endif
2330  
2331 for(y = 0; y < sizeY; y++)
2332 {
2333 // Get line
2334 ExternalMemoryCallback(bitmap, memOffset, byteWidth, lineBuffer);
2335 memOffset += byteWidth;
2336 for(stretchY = 0; stretchY < stretch; stretchY++)
2337 {
2338 pData = lineBuffer;
2339 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2340 pData2 = lineBuffer2;
2341 #endif
2342  
2343 xc = left;
2344 for(x = 0; x < sizeX; x++)
2345 {
2346 temp = *pData++;
2347 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2348 SetColor(temp);
2349 #endif
2350  
2351 // Write pixel to buffer
2352 for(stretchX = 0; stretchX < stretch; stretchX++)
2353 {
2354 #if (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2355 PutPixel(xc++, yc);
2356 #else
2357 *pData2++ = temp;
2358 #endif
2359 }
2360 }
2361 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2362 GFX_WaitForCommandQueue(2);
2363 GFX_SetDestAddress((yc * (DWORD)DISP_HOR_RESOLUTION) + left);
2364 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
2365 #endif
2366 yc++;
2367 }
2368 }
2369 }
2370 #endif //#if (COLOR_DEPTH == 16)
2371 #endif //#ifdef USE_BITMAP_EXTERNAL
2372  
2373 /*********************************************************************
2374 * Function: WORD PutImage(SHORT left, SHORT top, void* bitmap, BYTE stretch)
2375 *
2376 * PreCondition: none
2377 *
2378 * Input: left,top - left top image corner,
2379 * bitmap - image pointer,
2380 * stretch - image stretch factor
2381 *
2382 * Output: For NON-Blocking configuration:
2383 * - Returns 0 when device is busy and the image is not yet completely drawn.
2384 * - Returns 1 when the image is completely drawn.
2385 * For Blocking configuration:
2386 * - Always return 1.
2387 *
2388 * Side Effects: none
2389 *
2390 * Overview: outputs image starting from left,top coordinates
2391 *
2392 * Note: image must be located in flash
2393 *
2394 ********************************************************************/
2395 WORD PutImage(SHORT left, SHORT top, void *bitmap, BYTE stretch)
2396 {
2397 #if defined (USE_BITMAP_FLASH) || defined (USE_BITMAP_EXTERNAL)
2398 FLASH_BYTE *flashAddress;
2399 BYTE colorDepth;
2400 #endif
2401 WORD colorTemp;
2402  
2403 if(GFX_GetFreeCommandSpace() < 4)
2404 {
2405 #ifndef USE_NONBLOCKING_CONFIG
2406 GFX_WaitForCommandQueue(4);
2407 #else
2408 return (0);
2409 #endif
2410 }
2411  
2412 // Save current color
2413 colorTemp = GetColor();
2414  
2415 switch(*((SHORT *)bitmap))
2416 {
2417 #ifdef USE_BITMAP_FLASH
2418  
2419 case FLASH:
2420  
2421 // Image address
2422 flashAddress = ((BITMAP_FLASH *)bitmap)->address;
2423  
2424 // Read color depth
2425 colorDepth = *(flashAddress + 1);
2426  
2427 // Draw picture
2428 switch(colorDepth)
2429 {
2430 case 1: PutImage1BPP(left, top, flashAddress, stretch); break;
2431  
2432 #if (COLOR_DEPTH >= 4)
2433 case 4: PutImage4BPP(left, top, flashAddress, stretch); break;
2434 #endif
2435  
2436 #if (COLOR_DEPTH >= 8)
2437 case 8: PutImage8BPP(left, top, flashAddress, stretch); break;
2438 #endif
2439  
2440 #if (COLOR_DEPTH == 16)
2441 case 16: PutImage16BPP(left, top, flashAddress, stretch); break;
2442 #endif
2443  
2444 default: break;
2445 }
2446  
2447 break;
2448 #endif
2449 #ifdef USE_BITMAP_EXTERNAL
2450  
2451 case EXTERNAL:
2452  
2453 // Get color depth
2454 ExternalMemoryCallback(bitmap, 1, 1, &colorDepth);
2455  
2456 // Draw picture
2457 switch(colorDepth)
2458 {
2459 case 1: PutImage1BPPExt(left, top, bitmap, stretch); break;
2460  
2461 #if (COLOR_DEPTH >= 4)
2462 case 4: PutImage4BPPExt(left, top, bitmap, stretch); break;
2463 #endif
2464  
2465 #if (COLOR_DEPTH >= 8)
2466 case 8: PutImage8BPPExt(left, top, bitmap, stretch); break;
2467 #endif
2468  
2469 #if (COLOR_DEPTH == 16)
2470 case 16: PutImage16BPPExt(left, top, bitmap, stretch); break;
2471 #endif
2472  
2473 default: break;
2474 }
2475  
2476 break;
2477 #endif
2478  
2479 default:
2480 break;
2481 }
2482  
2483 // Restore current color
2484 SetColor(colorTemp);
2485 return (1);
2486 }
2487  
2488 #endif // USE_DRV_PUTIMAGE
2489  
2490 /*********************************************************************
2491 * Function: BYTE Decompress(DWORD SrcAddress, DWORD DestAddress, DWORD nbytes);
2492 *
2493 * Overview: Decompresses the nbytes number of data at SrcAddress and
2494 * places starting from DestAddress. (Blocking)
2495 *
2496 * PreCondition: SrcAddress must point to the start of a compressed block.
2497 *
2498 * Input: SrcAddress - Source address
2499 * DestAddress - Destination address
2500 * nbytes - Number of bytes to be decompressed
2501 *
2502 * Output: error flag
2503 *
2504 * Side Effects: Modifies workarea_1 & workarea_2 registers.
2505 *
2506 ********************************************************************/
2507 BYTE Decompress(DWORD SrcAddress, DWORD DestAddress, DWORD nbytes)
2508 {
2509 GFX_WaitForCommandQueue(GFX_COMMAND_QUEUE_LENGTH);
2510 while(GFX_IsPuGpuBusy());
2511  
2512 GFX_SetWorkArea1(SrcAddress);
2513 GFX_SetCompressedSource(0);
2514 GFX_SetWorkArea2(DestAddress);
2515 GFX_SetDecompressionDest(0);
2516 GFX_SetDecompressSize(nbytes);
2517  
2518 while(!GFX_DecomperssionDone())
2519 {
2520 if(GFX_DecompressionError())
2521 {
2522 return GFX_DecompressionError();
2523 }
2524 }
2525  
2526 return GFX_DecompressionError();
2527 }
2528  
2529 /*********************************************************************
2530 * Function: void __GFX1Interrupt(void)
2531 *
2532 * Overview: This is an ISR to handle VMRGN Interrupt
2533 *
2534 * PreCondition: Interrupts must be enabled
2535 *
2536 * Input: none
2537 *
2538 * Output: none
2539 *
2540 * Side Effects: Sets the error flag blPaletteChangeError
2541 *
2542 ********************************************************************/
2543 void __attribute__((interrupt, shadow, no_auto_psv)) _GFX1Interrupt(void)
2544 {
2545 _GFX1IF = 0;
2546 if(_VMRGNIF != 0)
2547 {
2548 _VMRGNIF = 0;
2549  
2550 #ifdef USE_PALETTE
2551  
2552 if(pPendingPalette != NULL)
2553 {
2554 blPaletteChangeError = SetPalette(pPendingPalette, PendingStartEntry, PendingLength);
2555 if(!blPaletteChangeError)
2556 {
2557 _palette = pPendingPalette;
2558 pPendingPalette = NULL;
2559 }
2560 }
2561  
2562 #endif
2563  
2564 #ifdef USE_DOUBLE_BUFFERING
2565  
2566 if(blDisplayUpdatePending)
2567 {
2568 UpdateDisplayNow();
2569 blDisplayUpdatePending = 0;
2570 }
2571  
2572 #endif
2573 }
2574 }
2575  
2576 /*********************************************************************
2577 * Function: void StartVBlankInterrupt(void)
2578 *
2579 * Overview: Sets up the Vertical Blanking Interrupt
2580 *
2581 * PreCondition: Interrupts must be enabled
2582 *
2583 * Input: none
2584 *
2585 * Output: none
2586 *
2587 * Side Effects: none
2588 *
2589 ********************************************************************/
2590 void StartVBlankInterrupt(void)
2591 {
2592 #if (GFX_LCD_TYPE == GFX_LCD_TFT)
2593  
2594 _VMRGNIF = 0;
2595 _VMRGNIE = 1;
2596 _GFX1IE = 1;
2597  
2598 #else
2599  
2600 #ifdef USE_PALETTE
2601  
2602 if(pPendingPalette != NULL)
2603 {
2604 blPaletteChangeError = SetPalette(pPendingPalette, PendingStartEntry, PendingLength);
2605  
2606 if(!blPaletteChangeError)
2607 {
2608 _palette = pPendingPalette;
2609 pPendingPalette = NULL;
2610 }
2611  
2612 #endif
2613  
2614 #ifdef USE_DOUBLE_BUFFERING
2615  
2616 if(blDisplayUpdatePending)
2617 {
2618 UpdateDisplayNow();
2619 blDisplayUpdatePending = 0;
2620 }
2621  
2622 #endif
2623  
2624 }
2625  
2626 #endif
2627 }
2628  
2629 #ifdef USE_DOUBLE_BUFFERING
2630  
2631 BYTE blInvalidateAll;
2632 BYTE blEnableDoubleBuffering;
2633 BYTE NoOfInvalidatedRectangleAreas;
2634 RectangleArea InvalidatedArea[GFX_MAX_INVALIDATE_AREAS];
2635  
2636 /*********************************************************************
2637 * Function: void InvalidateRectangle(WORD left, WORD top, WORD right, WORD bottom)
2638 *
2639 * Overview: Invalidates the specified rectangular area and if the
2640 * invalidated areas exceed the GFX_MAX_INVALIDATE_AREAS,
2641 * whole area is marked as invalidate
2642 *
2643 * PreCondition: None
2644 *
2645 * Input: left,top - top left corner coordinates,
2646 * right,bottom - bottom right corner coordinates
2647 *
2648 * Output: None
2649 *
2650 * Side Effects: Only copies back the invalidated areas to the draw -
2651 * buffer after the exchange of draw and frame buffers
2652 *
2653 ********************************************************************/
2654 void InvalidateRectangle(WORD left, WORD top, WORD right, WORD bottom)
2655 {
2656 if(blInvalidateAll == 1 || blEnableDoubleBuffering == 0)
2657 {
2658 return;
2659 }
2660  
2661 if(NoOfInvalidatedRectangleAreas >= GFX_MAX_INVALIDATE_AREAS)
2662 {
2663 blInvalidateAll = 1;
2664 return;
2665 }
2666 else
2667 {
2668 WORD width, height;
2669  
2670 #if (DISP_ORIENTATION == 0) || (DISP_ORIENTATION == 180)
2671  
2672 width = right - left + 1;
2673 height = bottom - top + 1;
2674  
2675 #elif (DISP_ORIENTATION == 90) || (DISP_ORIENTATION == 270)
2676  
2677 height = right - left + 1;
2678 width = bottom - top + 1;
2679  
2680 #endif
2681  
2682 #if (DISP_ORIENTATION == 90)
2683  
2684 bottom = DISP_VER_RESOLUTION - left;
2685 left = top;
2686 right = left + width;
2687 top = bottom - height;
2688  
2689 #elif (DISP_ORIENTATION == 180)
2690  
2691 right = DISP_HOR_RESOLUTION - left;
2692 bottom = DISP_VER_RESOLUTION - top;
2693 left = right - width;
2694 top = bottom - height;
2695  
2696 #elif (DISP_ORIENTATION == 270)
2697  
2698 right = DISP_HOR_RESOLUTION - top;
2699 top = left;
2700 bottom = top + height;
2701 left = right - width;
2702  
2703 #endif
2704  
2705 InvalidatedArea[NoOfInvalidatedRectangleAreas].X = left;
2706 InvalidatedArea[NoOfInvalidatedRectangleAreas].Y = top;
2707 InvalidatedArea[NoOfInvalidatedRectangleAreas].W = width;
2708 InvalidatedArea[NoOfInvalidatedRectangleAreas].H = height;
2709 NoOfInvalidatedRectangleAreas++;
2710 }
2711 }
2712  
2713 /*********************************************************************
2714 * Function: static void ExchangeDrawAndFrameBuffers(void);
2715 *
2716 * Overview: Interchanges Draw and Frame buffers and copies the contents
2717 * of current frame buffer to the draw buffer
2718 *
2719 * PreCondition: The graphical frame must be completely drawn.
2720 *
2721 * Input: None
2722 *
2723 * Output: None
2724 *
2725 * Side Effects: Always draw on draw buffer & not on frame buffer
2726 *
2727 ********************************************************************/
2728 static void ExchangeDrawAndFrameBuffers(void)
2729 {
2730 DWORD SourceBuffer, DestBuffer;
2731  
2732 if(blEnableDoubleBuffering == 0)
2733 {
2734 return;
2735 }
2736  
2737 if(_drawbuffer == GFX_BUFFER1)
2738 {
2739 SourceBuffer = GFX_BUFFER1;
2740 DestBuffer = GFX_BUFFER2;
2741 }
2742 else
2743 {
2744 SourceBuffer = GFX_BUFFER2;
2745 DestBuffer = GFX_BUFFER1;
2746 }
2747  
2748 _drawbuffer = DestBuffer;
2749 GFX_SetDisplayArea(SourceBuffer);
2750  
2751 GFX_WaitForCommandQueue(GFX_COMMAND_QUEUE_LENGTH);
2752 while(GFX_IsPuGpuBusy());
2753  
2754 GFX_SetWorkArea1(SourceBuffer);
2755 GFX_SetWorkArea2(DestBuffer);
2756  
2757 if(blInvalidateAll == 1 || NoOfInvalidatedRectangleAreas > GFX_MAX_INVALIDATE_AREAS)
2758 {
2759 blInvalidateAll = 0;
2760 NoOfInvalidatedRectangleAreas = 0;
2761 GFX_SetSrcAddress(0);
2762 GFX_SetDestAddress(0);
2763 GFX_SetRectSize((WORD)DISP_HOR_RESOLUTION, (WORD)DISP_VER_RESOLUTION);
2764 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_CONTINUOUS, RCC_DEST_ADDR_CONTINUOUS);
2765 }
2766 else if(NoOfInvalidatedRectangleAreas)
2767 {
2768 while(NoOfInvalidatedRectangleAreas)
2769 {
2770 DWORD address;
2771 NoOfInvalidatedRectangleAreas--;
2772 address = ((DWORD)InvalidatedArea[NoOfInvalidatedRectangleAreas].Y * DISP_HOR_RESOLUTION) + InvalidatedArea[NoOfInvalidatedRectangleAreas].X;
2773 GFX_WaitForCommandQueue(4);
2774 GFX_SetSrcAddress(address);
2775 GFX_SetDestAddress(address);
2776 GFX_SetRectSize(InvalidatedArea[NoOfInvalidatedRectangleAreas].W, InvalidatedArea[NoOfInvalidatedRectangleAreas].H);
2777 GFX_StartCopy(RCC_COPY, RCC_ROP_C, RCC_SRC_ADDR_DISCONTINUOUS, RCC_DEST_ADDR_DISCONTINUOUS);
2778 }
2779 }
2780 }
2781  
2782 /*********************************************************************
2783 * Function: void UpdateDisplayNow(void)
2784 *
2785 * Overview: Synchronizes the draw and frame buffers immediately
2786 *
2787 * PreCondition: none
2788 *
2789 * Input: none
2790 *
2791 * Output: none
2792 *
2793 * Side Effects: none
2794 *
2795 ********************************************************************/
2796 void UpdateDisplayNow(void)
2797 {
2798 ExchangeDrawAndFrameBuffers();
2799 }
2800  
2801 /*********************************************************************
2802 * Function: void RequestDisplayUpdate(void)
2803 *
2804 * Overview: Synchronizes the draw and frame buffers at next VBlank
2805 *
2806 * PreCondition: none
2807 *
2808 * Input: none
2809 *
2810 * Output: none
2811 *
2812 * Side Effects: none
2813 *
2814 ********************************************************************/
2815 void RequestDisplayUpdate(void)
2816 {
2817 if(blInvalidateAll == 1 || NoOfInvalidatedRectangleAreas > 0)
2818 {
2819 blDisplayUpdatePending = 1;
2820 StartVBlankInterrupt();
2821 }
2822 }
2823  
2824 #endif //USE_DOUBLE_BUFFERING
2825  
2826 #ifdef USE_PALETTE
2827  
2828 /*********************************************************************
2829 * Function: void PaletteInit(void)
2830 *
2831 * Overview: Initializes the CLUT.
2832 *
2833 * PreCondition: none
2834 *
2835 * Input: none
2836 *
2837 * Output: none
2838 *
2839 * Side Effects: none
2840 *
2841 ********************************************************************/
2842 void PaletteInit(void)
2843 {
2844 while(_CLUTBUSY != 0)
2845 {
2846 Nop();
2847 }
2848 _CLUTRWEN = 0;
2849 _CLUTEN = 0;
2850 }
2851  
2852 /*********************************************************************
2853 * Function: void EnablePalette(void)
2854 *
2855 * Overview: Enables the Palette mode
2856 *
2857 * PreCondition: A system palette has been set using RequestPaletteChange()
2858 * or SetPalette() and SetPaletteBpp() must have been called
2859 *
2860 * Input: none
2861 *
2862 * Output: none
2863 *
2864 * Side Effects: There may be a little flicker with SetPalette() which
2865 * can be avoided for TFT with RequestPaletteChange()
2866 *
2867 ********************************************************************/
2868 void EnablePalette(void)
2869 {
2870 if(PaletteBpp <= GFX_16_BPP)
2871 {
2872 _PUBPP = PaletteBpp;
2873 _DPBPP = PaletteBpp;
2874 _CLUTEN = 1;
2875 }
2876 }
2877  
2878 /*********************************************************************
2879 * Function: void DisablePalette(void)
2880 *
2881 * Overview: Disables the Palette mode
2882 *
2883 * PreCondition: none
2884 *
2885 * Input: none
2886 *
2887 * Output: none
2888 *
2889 * Side Effects: There may be a little flicker which can be avoided for TFT
2890 * by preceding with a dummy RequestPaletteChange()
2891 *
2892 ********************************************************************/
2893 void DisablePalette(void)
2894 {
2895 _CLUTEN = 0;
2896 _PUBPP = GFX_BITS_PER_PIXEL;
2897 _DPBPP = GFX_BITS_PER_PIXEL;
2898 }
2899  
2900 /*********************************************************************
2901 * Function: BYTE IsPaletteEnabled(void)
2902 *
2903 * Overview: Returns if the Palette mode is enabled or not
2904 *
2905 * PreCondition: none
2906 *
2907 * Input: none
2908 *
2909 * Output: Enabled -> 1, Disabled -> 0
2910 *
2911 * Side Effects:
2912 *
2913 ********************************************************************/
2914 BYTE IsPaletteEnabled(void)
2915 {
2916 return _CLUTEN;
2917 }
2918  
2919 /*********************************************************************
2920 * Function: BYTE SetPaletteBpp(BYTE bpp)
2921 *
2922 * Overview: Sets the CLUT's number of valid entries.
2923 *
2924 * PreCondition: PaletteInit() must be called before.
2925 *
2926 * Input: bpp -> Bits per pixel
2927 *
2928 * Output: Status: Zero -> Success, Non-zero -> Error.
2929 *
2930 * Side Effects: Drawing mode will change to support palettes
2931 *
2932 ********************************************************************/
2933 BYTE SetPaletteBpp(BYTE bpp)
2934 {
2935 switch(bpp)
2936 {
2937 case 1: PaletteBpp = GFX_1_BPP;
2938 break;
2939  
2940 case 2: PaletteBpp = GFX_2_BPP;
2941 break;
2942  
2943 case 4: PaletteBpp = GFX_4_BPP;
2944 break;
2945  
2946 case 8: PaletteBpp = GFX_8_BPP;
2947 break;
2948  
2949 default: PaletteBpp = GFX_16_BPP;
2950 return -1;
2951 }
2952  
2953 return 0;
2954 }
2955  
2956 /*********************************************************************
2957 * Function: BYTE SetPaletteFlash(PALETTE_ENTRY *pPaletteEntry, WORD startEntry, WORD length)
2958 *
2959 * Overview: Loads the palettes from the flash immediately.
2960 *
2961 * PreCondition: PaletteInit() must be called before.
2962 *
2963 * Input: pPaletteEntry - Pointer to the palette table in ROM
2964 * startEntry - Start entry to load (inclusive)
2965 * length - Number of entries
2966 *
2967 * Output: Status: Zero -> Success, Non-zero -> Error.
2968 *
2969 * Side Effects: There may be a slight flicker when the Palette entries
2970 * are getting loaded one by one.
2971 *
2972 ********************************************************************/
2973 BYTE SetPaletteFlash(PALETTE_ENTRY *pPaletteEntry, WORD startEntry, WORD length)
2974 {
2975 WORD counter;
2976  
2977 if((pPaletteEntry == NULL) || ((startEntry + length) > 256))
2978 {
2979 return -1;
2980 }
2981  
2982 _CLUTRWEN = 1;
2983 for(counter = 0; counter < length; counter++)
2984 {
2985 _CLUTADR = counter;
2986 _CLUTWR = pPaletteEntry[counter].value;
2987 while(_CLUTBUSY)
2988 {
2989 Nop();
2990 }
2991 }
2992 _CLUTRWEN = 0;
2993  
2994 return 0;
2995 }
2996  
2997 #endif // USE_PALETTE
{BLAME END}
{FOOTER START}

Powered by WebSVN v2.8.3