• Main Page
  • Related Pages
  • Data Structures
  • Files
  • File List
  • Globals

draw.c

Go to the documentation of this file.
00001 /****************** COPYRIGHT (C) 2007-2010 RAISONANCE S.A.S. *****************/
00013 /******************************************************************************/
00014 
00015 /* Includes ------------------------------------------------------------------*/
00016 #include "circle.h"
00017 
00019 
00020 /* Private define ------------------------------------------------------------*/
00021 #define ROTATE_DIVIDER  127
00022 
00023 #define abs(X) ( ( (X) < 0 ) ? -(X) : (X) )
00024 #define sgn(X) ( ( (X) < 0 ) ? -1 : 1 )
00025 
00026 
00027 /* Private variables ---------------------------------------------------------*/
00028 mag_t   CharMagniCoeff = 1;               // !< Current character magnify coefficient
00029 color_t BGndColor = RGB_WHITE;            // !< Current background color
00030 color_t TextColor = RGB_BLACK;            // !< Current text color
00031 
00032 coord_t PosCurX = 0;                      // !< Current cursor X position
00033 coord_t PosCurY = 0;                      // !< Current cursor Y position
00034 
00035 coord_t LeftMarginX = 0;                  // !< Current left margin in X
00036 coord_t RightMarginX = APP_SCREEN_WIDTH; // !< Current right margin in X
00037 coord_t HighMarginY = APP_SCREEN_HEIGHT; // !< Current high margin in Y
00038 coord_t LowMarginY = 0;                   // !< Current low margin in Y
00039 
00040 bool fDisplayTime = 0;
00041 u16 BatState;
00042 u16 OldBatState;
00043 s16 OldTemp = -1;                // Stores current temperature
00044 
00045 coord_t xBat;
00046 coord_t yBat;
00047 coord_t widthBat;
00048 coord_t heightBat;
00049 
00050 divider_t divider_coord = 0;
00051 
00052 /* Screen orientation management*/
00053 divider_t rotate_counter             = 0;
00054 
00055 /*Initialise the direction to +4 at reset (that forces a redraw)*/
00056 Rotate_H12_V_Match_TypeDef previous_orient            = V12;
00057 Rotate_H12_V_Match_TypeDef previous_previous_orient   = V12;
00058 Rotate_H12_V_Match_TypeDef new_orient                 = V12;
00059 Rotate_H12_V_Match_TypeDef CurrentScreenOrientation   = V12;
00060 bool                       CurrentRotateScreen        = 1;
00061 
00062 /* Extern variables ----------------------------------------------------------*/
00063 extern coord_t XInit;
00064 extern coord_t YInit;
00065 
00066 /* Private functions ---------------------------------------------------------*/
00067 void DRAW_Clear_Text( coord_t x, coord_t y, len_t len, bool mode );
00068 
00069 /*******************************************************************************
00070 *
00071 *                                DRAW_Clear_Text
00072 *
00073 *******************************************************************************/
00090 /******************************************************************************/
00091 void DRAW_Clear_Text( coord_t x, coord_t y, len_t len, bool mode )
00092 {
00093     len_t i;
00094     coord_t ref_x = x;
00095 
00096     /* Display each character on LCD */
00097     for ( i = 0 ; i < len ; i++ )
00098     {
00099         /* Display one character on LCD */
00100         LCD_DisplayChar( ref_x, y, ' ', mode ? BGndColor : TextColor,  mode ? TextColor : BGndColor, CharMagniCoeff );
00101 
00102         /* Increment the column position by character width */
00103         ref_x += ( Char_Width * CharMagniCoeff );
00104     }
00105 }
00106 
00107 
00108 /* Public functions for CircleOS ---------------------------------------------*/
00109 
00110 /*******************************************************************************
00111 *
00112 *                                DRAW_Init
00113 *
00114 *******************************************************************************/
00122 /******************************************************************************/
00123 NODEBUG2 void DRAW_Init( void )
00124 {
00125 
00126 #if MEMS_POINTER     // Not necessary if no MEMS menu handling
00127     MEMS_GetRotation( &CurrentScreenOrientation );
00128 #endif
00129 
00130     LCD_SetScreenOrientation( CurrentScreenOrientation );
00131 
00132     xBat        = Screen_Width - 30;
00133     yBat        = 3;
00134     OldBatState = 10;
00135     PosCurY = Screen_Height - Char_Height;
00136     RightMarginX = Screen_Width;
00137     HighMarginY = Screen_Height;
00138 
00139     /* Clear LCD and draw black and white logo*/
00140     DRAW_SetDefaultColor();
00141     DRAW_Clear();
00142     LCD_Batt( xBat, yBat, fDisplayTime, BatState, &OldBatState, divider_coord, &widthBat, &heightBat );
00143     POINTER_Init();
00144 }
00145 
00146 /*******************************************************************************
00147 *
00148 *                                DRAW_Handler
00149 *
00150 *******************************************************************************/
00158 /******************************************************************************/
00159 void DRAW_Handler( void )
00160 {
00161 
00162     BatState = UTIL_GetBat();
00163     LCD_Batt( xBat, yBat, fDisplayTime, BatState, &OldBatState, divider_coord, &widthBat, &heightBat );
00164 
00165 #if MEMS_POINTER     // Not necessary if no MEMS menu handling
00166     /* Rotate LCD screen*/
00167     if ( LCD_GetRotateScreen() )
00168     {
00169         rotate_counter++;
00170 
00171         if ( rotate_counter == ROTATE_DIVIDER )
00172         {
00173             MEMS_GetRotation( &new_orient );
00174 
00175             if ( new_orient != previous_previous_orient )
00176             {
00177                 if ( ( new_orient == previous_orient ) && ( new_orient != CurrentScreenOrientation ) )
00178                 {
00179                     CurrentScreenOrientation = new_orient;
00180                     LCD_SetScreenOrientation( CurrentScreenOrientation );
00181                     MEMS_GetPosition( &XInit, &YInit );
00182 #if TOUCHSCREEN_AVAIL
00183                     TOOLBAR_RedrawToolbar( TOOLBAR_REDRAW );
00184 #endif
00185                     DRAW_Clear();
00186                     if ( CurrentMenu != 0 )
00187                     {
00188                         MENU_Set( CurrentMenu );
00189                     }
00190                 }
00191             }
00192 
00193             previous_previous_orient = previous_orient;
00194             previous_orient          = new_orient;
00195             rotate_counter           = 0;
00196         }
00197     }
00198 #endif
00199 }
00200 
00201 /*******************************************************************************
00202 *
00203 *                                DRAW_Batt
00204 *
00205 *******************************************************************************/
00211 /******************************************************************************/
00212 NODEBUG2 void DRAW_Batt( void )
00213 {
00214     widthBat = 24;
00215     heightBat = 8;
00216 
00217     LCD_FillRect_Circle( xBat, yBat, widthBat, heightBat, RGB_BLUE );
00218     LCD_FillRect_Circle( xBat + 1 , yBat + 1 , widthBat - 2 , heightBat - 2 , RGB_WHITE );
00219 
00220     widthBat = 2;
00221     heightBat = 4;
00222 
00223     LCD_FillRect_Circle( xBat - 2 , yBat + 2 , widthBat , heightBat, RGB_BLUE );
00224     LCD_FillRect_Circle( xBat - 1 , yBat + 3 , widthBat - 1 , heightBat - 2 , RGB_WHITE );
00225 }
00226 
00227 
00228 /*******************************************************************************
00229 *
00230 *                                DRAW_Line_Circle
00231 *
00232 *******************************************************************************/
00246 /******************************************************************************/
00247 NODEBUG2 void DRAW_Line_Circle( coord_t x1, coord_t y1, coord_t x2, coord_t y2, color_t color )
00248 {
00249     s16 i;
00250     coord_t dx,    dy;
00251     coord_t dxabs, dyabs;
00252     coord_t sdx,   sdy;
00253     coord_t x,     y;
00254     coord_t px,    py;
00255 
00256     dx = x2 - x1;       /* the horizontal distance of the line */
00257 
00258     if ( dx == 0 )     /* Vertical Line*/
00259     {
00260         if ( y1 > y2 ) /* We assume y2>y1 and invert if not*/
00261         {
00262             i = y2;
00263             y2 = y1;
00264             y1 = i;
00265         }
00266         LCD_FillRect_Circle( x1, y1, 1, y2 - y1 + 1, color );
00267         return;
00268     }
00269 
00270     dy = y2 - y1;       /* the vertical distance of the line */
00271 
00272     if ( dy == 0 )     /* Horizontal Line*/
00273     {
00274         if ( x1 > x2 ) /* We assume x2>x1 and we swap them if not*/
00275         {
00276             i = x2;
00277             x2 = x1;
00278             x1 = i;
00279         }
00280         LCD_FillRect_Circle( x1, y1, x2 - x1 + 1, 1, color );
00281         return;
00282     }
00283 
00284     dxabs = abs( dx );
00285     dyabs = abs( dy );
00286     sdx = sgn( dx );
00287     sdy = sgn( dy );
00288     x = dyabs >> 1;
00289     y = dxabs >> 1;
00290     px = x1;
00291     py = y1;
00292 
00293     if ( dxabs >= dyabs ) /* the line is more horizontal than vertical */
00294     {
00295         for ( i = 0; i < dxabs; i++ )
00296         {
00297             y += dyabs;
00298             if ( y >= dxabs )
00299             {
00300                 y -= dxabs;
00301                 py += sdy;
00302             }
00303             px += sdx;
00304             LCD_DrawPixel( px, py, color );
00305         }
00306     }
00307     else /* the line is more vertical than horizontal */
00308     {
00309         for ( i = 0; i < dyabs; i++ )
00310         {
00311             x += dxabs;
00312             if ( x >= dyabs )
00313             {
00314                 x -= dyabs;
00315                 px += sdx;
00316             }
00317             py += sdy;
00318             LCD_DrawPixel( px, py, color );
00319         }
00320     }
00321 }
00322 
00323 /******************************************************************************
00324 *
00325 *                                DRAW_RestoreCharMagniCoeff
00326 *
00327 *******************************************************************************/
00333 /******************************************************************************/
00334 NODEBUG2 void DRAW_RestoreCharMagniCoeff( void )
00335 {
00336 #if LCD_HIGH_DEF
00337     DRAW_SetCharMagniCoeff( 2 );
00338 #else
00339     DRAW_SetCharMagniCoeff( 1 );
00340 #endif
00341 }
00342 
00343 /*******************************************************************************
00344 *
00345 *                                DRAW_Cross_Absolute
00346 *
00347 *******************************************************************************/
00355 /******************************************************************************/
00356 NODEBUG2 void DRAW_Cross_Absolute( coord_t x1, coord_t y1, color_t color, u16 CrossSize )
00357 {
00358     DRAW_Line( x1 - CrossSize, y1, x1 + CrossSize, y1, color );
00359     DRAW_Line( x1, y1 - CrossSize, x1, y1 + CrossSize, color );
00360 }
00361 
00362 /*******************************************************************************
00363 *
00364 *                                DRAW_DisplayTemp
00365 *
00366 *******************************************************************************/
00380 /******************************************************************************/
00381 NODEBUG2 void DRAW_DisplayTemp( coord_t x, coord_t y )
00382 {
00383     s16 Temp;
00384     u8 c;
00385     u16 r = 0;
00386     u8 TempTextBuffer[5];
00387     bool firstTime = 0;
00388 
00389     if ( OldTemp == -1 )
00390     {
00391         /* Get the intial value */
00392         Temp = OldTemp = UTIL_GetTemp();
00393         firstTime = 1;
00394     }
00395     else
00396     {
00397         /* Get Time and filter it with the previous value*/
00398         Temp = ( UTIL_GetTemp() + OldTemp * 7 ) / 8;
00399         OldTemp = Temp;
00400     }
00401 
00402     // Display value if changed or first call
00403     if ( ( Temp != OldTemp ) || firstTime )
00404     {
00405         // Display modified temperature
00406         /* 1 000 digit*/
00407         c = ( ( Temp - r ) / 100 );
00408         r = r + ( c * 100 );
00409         TempTextBuffer[0] = c + 0x30;
00410 
00411         /* 100 digit*/
00412         c = ( ( Temp - r ) / 10 );
00413         r = r + ( c * 10 );
00414         TempTextBuffer[1] = c + 0x30;
00415 
00416         /* Dot*/
00417         TempTextBuffer[2] = '.';
00418 
00419         /* 10 digit*/
00420         c = ( ( Temp - r ) );
00421         TempTextBuffer[3] = c + 0x30;
00422 
00423         /* Volt*/
00424         TempTextBuffer[4] = fTemperatureInFahrenheit ? 'F' : 'C';
00425         TempTextBuffer[5] = 0;
00426 
00427         DRAW_DisplayString( x, y, TempTextBuffer, 5 );
00428     }
00429 }
00430 
00431 /*******************************************************************************
00432 *
00433 *                                DRAW_GetIndexedColorBMP
00434 *
00435 *******************************************************************************/
00446 /******************************************************************************/
00447 NODEBUG2 color_t DRAW_GetIndexedColorBMP( u8* color_table, u16 i )
00448 {
00449     color_t color;
00450     color = ( color_table[i] & 0x1c ) << 11;  //green (low)
00451     color |= ( color_table[i + 1] & 0xf8 ) << 5; //blue
00452     color |= ( color_table[i + 3] & 0xf8 );   //red
00453     color |= ( color_table[i] & 0xe0 ) >> 5;  //green (high)
00454     return color;
00455 }
00456 
00457 
00459 
00460 /* Public functions ----------------------------------------------------------*/
00461 
00462 /*******************************************************************************
00463 *
00464 *                                DRAW_SetCharMagniCoeff
00465 *
00466 *******************************************************************************/
00474 /******************************************************************************/
00475 void DRAW_SetCharMagniCoeff( mag_t Coeff )
00476 {
00477     CharMagniCoeff = Coeff;
00478 }
00479 
00480 /******************************************************************************
00481 *
00482 *                                DRAW_GetCharMagniCoeff
00483 *
00484 *******************************************************************************/
00492 /******************************************************************************/
00493 mag_t DRAW_GetCharMagniCoeff( void )
00494 {
00495     return CharMagniCoeff;
00496 }
00497 
00498 /******************************************************************************
00499 *
00500 *                                DRAW_GetTextColor
00501 *
00502 *******************************************************************************/
00510 /******************************************************************************/
00511 color_t DRAW_GetTextColor( void )
00512 {
00513     return TextColor;
00514 }
00515 
00516 /*******************************************************************************
00517 *
00518 *                                DRAW_SetTextColor
00519 *
00520 *******************************************************************************/
00528 /******************************************************************************/
00529 void DRAW_SetTextColor( color_t Color )
00530 {
00531     TextColor = Color ;
00532 }
00533 
00534 /*******************************************************************************
00535 *
00536 *                                DRAW_GetBGndColor
00537 *
00538 *******************************************************************************/
00546 /******************************************************************************/
00547 color_t DRAW_GetBGndColor( void )
00548 {
00549     return BGndColor;
00550 }
00551 
00552 /*******************************************************************************
00553 *
00554 *                                DRAW_SetBGndColor
00555 *
00556 *******************************************************************************/
00564 /******************************************************************************/
00565 void DRAW_SetBGndColor( color_t Color )
00566 {
00567     BGndColor = Color;
00568 }
00569 
00570 /*******************************************************************************
00571 *
00572 *                                DRAW_Clear
00573 *
00574 *******************************************************************************/
00580 /******************************************************************************/
00581 void DRAW_Clear( void )
00582 {
00583     enum POINTER_mode ptr_bak = POINTER_GetMode() ;
00584 
00585     POINTER_SetMode( POINTER_OFF );
00586     if ( ( LCD_GetScreenOrientation() % 2 ) == 1 )
00587         LCD_FillRect_Circle( 0, 0, Screen_Height, Screen_Width, BGndColor );
00588     else
00589         LCD_FillRect_Circle( 0, 0, Screen_Width, Screen_Height, BGndColor );
00590 
00591     if ( ( CurrentMenu == 0 ) && ( CurrentCommand == 0 )
00592             && ( BUTTON_GetMode() == BUTTON_ONOFF_FORMAIN ) )
00593     {
00594         DRAW_SetDefaultColor();
00595         DRAW_SetLogoBW();
00596         LCD_Clear( xBat, yBat );
00597 
00598         OldBatState  = 10;
00599         OldTemp = -1;
00600         fDisplayTime = 1;
00601     }
00602 
00603     POINTER_SetMode( ptr_bak );
00604 }
00605 
00606 /*******************************************************************************
00607 *
00608 *                                DRAW_SetLogoBW
00609 *
00610 *******************************************************************************/
00616 /******************************************************************************/
00617 void DRAW_SetLogoBW( void )
00618 {
00619     LCD_SetLogoBW();
00620 }
00621 
00622 /*******************************************************************************
00623 *
00624 *                                DRAW_SetImage
00625 *
00626 *******************************************************************************/
00642 /******************************************************************************/
00643 void DRAW_SetImage( const color_t* imageptr, coord_t x, coord_t y, coord_t width, coord_t height )
00644 {
00645     DRAW_SetImageSel( imageptr, x, y, width, height, 0xFFFF, 0xFFFF );
00646 }
00647 
00648 /*******************************************************************************
00649 *
00650 *                                DRAW_SetImageSel
00651 *
00652 *******************************************************************************/
00671 /******************************************************************************/
00672 void DRAW_SetImageSel( const color_t* imageptr, coord_t x, coord_t y, coord_t width, coord_t height, color_t oldBgndColor, color_t newBgndColor )
00673 {
00674     s32 j;
00675     coord_t i, k;
00676     color_t color;
00677     color_t* imagetemp;
00678     u8* color_table;
00679     Rotate_H12_V_Match_TypeDef OrientationSave;
00680 
00681     if ( imageptr )
00682     {
00683         j = width * height; // pixel counter
00684         //TODO ASSERT((u32)width * height < 0xFFFF);    // Ensure i can be a short
00685 
00686         // BMP header test
00687         if ( ( imageptr[0] == 0x424D ) && ( imageptr[3] == 0 ) )
00688         {
00689             // Regular BMP file
00690             OrientationSave = LCD_GetScreenOrientation();
00691             imagetemp = ( color_t* )( imageptr ) + ( imageptr[5] >> 9 ) + ( ( imageptr[5] & 0xff ) << 7 ) ; // Offset of the image (header size)
00692 
00693             LCD_SetScreenOrientation( OrientationSave + 4 ); // Change to V*BMP orientation
00694             LCD_SetRect_For_Cmd( x, y, width, height );
00695             LCD_SendLCDCmd_RAM_Access();
00696 
00697             switch ( ( ( imageptr[14] >> 8 ) + ( imageptr[15] & 0xff00 ) ) ) // colour depth + compression methode
00698             {
00699             case 0x0010:    // 16 bits and no compression
00700             case 0x0310:
00701                 imageptr += 0x36;
00702                 for ( i = 0; i < j ; i++ )
00703                 {
00704                     if ( imageptr[i] != oldBgndColor )
00705                     {
00706                         LCD_SendLCDData( imageptr[i] & 0xff );
00707                         LCD_SendLCDData( ( imageptr[i] >> 8 ) & 0xff );
00708                     }
00709                     else
00710                     {
00711                         LCD_SendLCDData( newBgndColor & 0xff );
00712                         LCD_SendLCDData( ( newBgndColor >> 8 ) & 0xff );
00713                     }
00714                 }
00715                 break;
00716 
00717             case 0x0008:    // 8 bits (256 colors) and no compression
00718                 color_table = ( u8* )imageptr + 0x36;
00719                 for ( i = 0; ( 2 * i ) < j ; i++ )
00720                 {
00721                     color = DRAW_GetIndexedColorBMP( color_table, 4 * ( imagetemp[i] >> 8 ) );
00722                     if ( color == oldBgndColor )
00723                         color = newBgndColor;
00724                     LCD_SendLCDData( color & 0xff );
00725                     LCD_SendLCDData( ( color >> 8 ) & 0xff );
00726                     color = DRAW_GetIndexedColorBMP( color_table, 4 * ( imagetemp[i] & 0xff ) );
00727                     LCD_SendLCDData( color & 0xff );
00728                     LCD_SendLCDData( ( color >> 8 ) & 0xff );
00729                 }
00730                 break;
00731 
00732             case 0x0108:    // 8 bits (256 colors) and RLE compression
00733                 color_table = ( u8* )imageptr + 0x36;
00734                 i = 0; // file cursor (in words)
00735                 while ( j > 0 ) // while there is still pixels to write (j : amount of remaining pixels)
00736                 {
00737 
00738                     if ( ( imagetemp[i] >> 8 ) == 0 )
00739                     {
00740                         k = imagetemp[i] & 0xff;
00741                         i++; // move the file cursor
00742 
00743                         if ( k == 0 ) // End of line
00744                         {
00745                             color = newBgndColor;
00746                             while ( ( j % width ) != 0 ) // fill with the background color to the end of line
00747                             {
00748                                 j--; // remove each pixel from the pixel counter
00749                                 LCD_SendLCDData( color & 0xff );
00750                                 LCD_SendLCDData( ( color >> 8 ) & 0xff );
00751                             }
00752                         }
00753 
00754                         else if ( k == 1 ) // End of file
00755                             break;
00756                         else
00757                         {
00758                             // If not either end of file or end of line : streak of single values
00759                             // in this case k is the length of the streak
00760                             j -= k ; // remove the streak length from the pixel counter
00761                             while ( k > 0 )
00762                             {
00763                                 color = DRAW_GetIndexedColorBMP( color_table , 4 * ( imagetemp[i] >> 8 ) );
00764                                 LCD_SendLCDData( color & 0xff );
00765                                 LCD_SendLCDData( ( color >> 8 ) & 0xff );
00766                                 k--;
00767                                 if ( k > 0 )
00768                                 {
00769                                     color = DRAW_GetIndexedColorBMP( color_table , 4 * ( imagetemp[i] & 0xff ) );
00770                                     if ( color == oldBgndColor ) // if the color should be replaced
00771                                         color = newBgndColor;
00772                                     LCD_SendLCDData( color & 0xff );
00773                                     LCD_SendLCDData( ( color >> 8 ) & 0xff );
00774                                     k--;
00775                                 }
00776                                 i++; // move the file cursor
00777                             }
00778                         }
00779                     } // End of : if ( (imagetemp[i]>>8) == 0 )
00780                     else
00781                     {
00782                         // Streak of same values
00783                         color = DRAW_GetIndexedColorBMP( color_table , 4 * ( imagetemp[i] & 0xff ) );
00784                         if ( color == oldBgndColor ) // if the color should be replaced
00785                             color = newBgndColor;
00786                         k = imagetemp[i] >> 8; // length of the streak
00787                         j -= k; // remove the streak length from the pixel counter
00788                         for ( ; k > 0 ; k-- )
00789                         {
00790                             LCD_SendLCDData( color & 0xff );
00791                             LCD_SendLCDData( ( color >> 8 ) & 0xff );
00792                         }
00793                         i++; // move the file cursor
00794                     }
00795                 } // End of : while ( j > 0 )
00796                 break;
00797 
00798             }   // End of : switch( ((imageptr[14]>>8) + (imageptr[15]&0xff00)) )
00799 
00800             /* End of select screen area to access.*/
00801             LCD_SendLCDCmd_RAM_Access_End();
00802 
00803             LCD_SetScreenOrientation( OrientationSave );
00804         }
00805         else
00806             // Non regular BMP file (old Primer format)
00807         {
00808             /* Select screen area to access.*/
00809             LCD_SetRect_For_Cmd( x, y, width, height );
00810             LCD_SendLCDCmd_RAM_Access();
00811 
00812             for ( i = 0; i < j ; i++ )
00813             {
00814                 if ( imageptr[i] != oldBgndColor )
00815                 {
00816                     LCD_SendLCDData( imageptr[i] & 0xff );
00817                     LCD_SendLCDData( ( imageptr[i] >> 8 ) & 0xff );
00818                 }
00819                 else
00820                 {
00821                     LCD_SendLCDData( newBgndColor & 0xff );
00822                     LCD_SendLCDData( ( newBgndColor >> 8 ) & 0xff );
00823                 }
00824             }
00825             /* End of select screen area to access.*/
00826             LCD_SendLCDCmd_RAM_Access_End();
00827         }
00828     }
00829 }
00830 
00831 /*******************************************************************************
00832 *
00833 *                                DRAW_SetImageBW
00834 *
00835 *******************************************************************************/
00852 /******************************************************************************/
00853 void DRAW_SetImageBW( const u8* imageptr, coord_t x, coord_t y, coord_t width, coord_t height )
00854 {
00855     coord_t i, j, k;
00856 
00857     k = ( width * height ) >> 3;
00858 
00859     /* Select screen area to access.*/
00860     LCD_SetRect_For_Cmd( x, y, width, height );
00861 
00862     /* Send command to write data on the LCD screen.*/
00863     LCD_SendLCDCmd_RAM_Access();
00864 
00865     /* Loop on all bitmap bytes.*/
00866     for ( i = 0; i < k; i++ )
00867     {
00868         /* Loop on all byte bits.*/
00869         for ( j = 0; j < 8; j++ )
00870         {
00871             /* Bit set: draw pixel with text color.*/
00872             if ( imageptr && ( ( ( imageptr[i] ) >> ( 7 - j ) ) & 1 ) )
00873             {
00874                 LCD_SendLCDData( TextColor & 0xff );
00875                 LCD_SendLCDData( ( TextColor >> 8 ) & 0xff );
00876             }
00877             else
00878             {
00879                 /* Bit not set: draw pixel with background color.*/
00880                 LCD_SendLCDData( BGndColor & 0xff );
00881                 LCD_SendLCDData( ( BGndColor >> 8 ) & 0xff );
00882             }
00883         }
00884     }
00885 
00886     /* End of select screen area to access.*/
00887     LCD_SendLCDCmd_RAM_Access_End();
00888 }
00889 
00890 /*******************************************************************************
00891 *
00892 *                                DRAW_DisplayVbat
00893 *
00894 *******************************************************************************/
00905 /******************************************************************************/
00906 void DRAW_DisplayVbat( coord_t x, coord_t y )
00907 {
00908     u8 text[17];
00909     u8* p = text;
00910     u16 vbat = UTIL_GetBat();
00911 
00912     *p++ = 'B';
00913     *p++ = 'A';
00914     *p++ = 'T';
00915     *p++ = '=';
00916 
00917     /* Translate vbat into p.*/
00918     vbattoa( p, vbat );
00919 
00920     /* Display text at the provided coordinates.*/
00921     DRAW_DisplayString( x, y, ( u8* )text, 10 );
00922 }
00923 
00924 /*******************************************************************************
00925 *
00926 *                                DRAW_DisplayTime
00927 *
00928 *******************************************************************************/
00939 /******************************************************************************/
00940 void DRAW_DisplayTime( coord_t x, coord_t y )
00941 {
00942     u8 THH;
00943     u8 TMM;
00944     u8 TSS;
00945     static u8 OldTHH = 100;
00946     static u8 OldTMM = 100;
00947     static u8 OldTSS = 100;
00948 
00949     static u8 TimeTextBuffer[9];       // Trailing '\0' is NOT included
00950 
00951     /* Get Time*/
00952     RTC_GetTime( &THH, &TMM, &TSS );
00953 
00954     /* Update time display if seconds have changed */
00955     if ( THH != OldTHH )
00956     {
00957         OldTHH = THH;
00958         UTIL_uint2str( &TimeTextBuffer[0], OldTHH, 2, 1 );
00959         TimeTextBuffer[2] = ':';
00960     }
00961     if ( TMM != OldTMM )
00962     {
00963         OldTMM = TMM;
00964         UTIL_uint2str( &TimeTextBuffer[3], OldTMM, 2, 1 );
00965         TimeTextBuffer[5] = ':';
00966     }
00967     if ( TSS != OldTSS )
00968     {
00969         OldTSS = TSS;
00970         UTIL_uint2str( &TimeTextBuffer[6], OldTSS, 2, 1 );
00971         TimeTextBuffer[8] = '\0';
00972         DRAW_DisplayString( x , y, TimeTextBuffer, 8 );
00973     }
00974 }
00975 
00976 /*******************************************************************************
00977 *
00978 *                                DRAW_DisplayStringWithMode
00979 *
00980 *******************************************************************************/
01004 /******************************************************************************/
01005 void DRAW_DisplayStringWithMode( coord_t x, coord_t y, const u8* ptr, len_t len, bool mode, enumset_t align )
01006 {
01007     coord_t ref_x;
01008     coord_t lx;
01009     len_t i;
01010     len_t lgc;
01011     u8 CharWidth;
01012     u16 Display_Width;
01013 
01014     // Swap the max coordinates according to the orientation
01015     if ( ( LCD_GetScreenOrientation() % 2 ) == 1 )
01016     {
01017         Display_Width = Screen_Height;
01018     }
01019     else
01020     {
01021         Display_Width = Screen_Width;
01022     }
01023 
01024     // Check the length validity
01025     if ( len == 0 )
01026         len = my_strlen( ptr );
01027     if ( len == ALL_SCREEN )
01028         len = Display_Width / ( Char_Width * CharMagniCoeff );
01029 
01030     // Check and limit the length of the string to display
01031     CharWidth = Char_Width * CharMagniCoeff;
01032     lx = x + ( len * CharWidth );
01033     if ( lx > Display_Width )
01034     {
01035         if ( ( ( lx - Display_Width ) % CharWidth ) == 0 )
01036             len -= ( ( lx - Display_Width ) / CharWidth );
01037         else
01038             len -= ( ( ( lx - Display_Width ) / CharWidth ) + 1 );
01039     }
01040 
01041     // Clear the area
01042     if ( ( Transparency == 0 ) || ( CharMagniCoeff > 3 ) )
01043         DRAW_Clear_Text( x, y, len, mode );
01044 
01045     // Locate the string into the area
01046     ref_x = x;
01047     lgc = my_strlen( ptr );
01048     if ( lgc > len )
01049         lgc = len;
01050 
01051     switch ( align )
01052     {
01053     case CENTER:
01054         ref_x += ( ( len - lgc ) * CharWidth ) / 2;
01055         break;
01056     case RIGHT:
01057         ref_x += ( len - lgc ) * CharWidth;
01058         break;
01059     case LEFT:
01060     default:
01061         break;
01062     }
01063 
01064     /* Display each character on LCD */
01065     for ( i = 0 ; i < lgc; i++ )
01066     {
01067         /* Display one character on LCD */
01068         LCD_DisplayChar( ref_x, y, *ptr++, mode ? BGndColor : TextColor,  mode ? TextColor : BGndColor, CharMagniCoeff );
01069 
01070         /* Increment the column position by CharWidth pixels */
01071         ref_x += CharWidth;
01072     }
01073 }
01074 
01075 /*******************************************************************************
01076 *
01077 *                                DRAW_DisplayString
01078 *
01079 *******************************************************************************/
01095 /******************************************************************************/
01096 void DRAW_DisplayString( coord_t x, coord_t y, const u8* ptr, len_t len )
01097 {
01098     DRAW_DisplayStringWithMode( x, y, ptr, len, NORMAL_TEXT, LEFT );
01099 }
01100 
01101 /*******************************************************************************
01102 *
01103 *                                DRAW_DisplayStringInverted
01104 *
01105 *******************************************************************************/
01121 /******************************************************************************/
01122 void DRAW_DisplayStringInverted( coord_t x, coord_t y, const u8* ptr, len_t len )
01123 {
01124     //BackGround and Text Colors are inverted
01125     DRAW_DisplayStringWithMode( x, y, ptr, len, INVERTED_TEXT, LEFT );
01126 }
01127 
01128 /*******************************************************************************
01129 *
01130 *                                DRAW_SetDefaultColor
01131 *
01132 *******************************************************************************/
01138 /******************************************************************************/
01139 void DRAW_SetDefaultColor( void )
01140 {
01141     BGndColor = RGB_WHITE;
01142     TextColor = RGB_BLACK;
01143 }
01144 
01145 
01146 /*******************************************************************************
01147 *
01148 *                                DRAW_Line
01149 *
01150 *******************************************************************************/
01164 /******************************************************************************/
01165 void DRAW_Line( coord_t x1, coord_t y1, coord_t x2, coord_t y2, color_t color )
01166 {
01167     /* Check the x parameters*/
01168     if ( x1 < 0 )
01169         x1 = 0;
01170     if ( x2 < 0 )
01171         x2 = 0;
01172 
01173     if ( x1 > Screen_Width - 1 )
01174         x1 = Screen_Width - 1;
01175     if ( x2 > Screen_Width - 1 )
01176         x2 = Screen_Width - 1;
01177 
01178     /* Check the y parameters*/
01179     if ( y1 < 0 )
01180         y1 = 0;
01181     if ( y2 < 0 )
01182         y2 = 0;
01183 
01184     if ( y1 > Screen_Height - 1 )
01185         y1 = Screen_Height - 1;
01186     if ( y2 > Screen_Height - 1 )
01187         y2 = Screen_Height - 1;
01188 
01189     /* Call the native function*/
01190     DRAW_Line_Circle( x1, y1, x2, y2, color );
01191 }
01192 
01193 /*******************************************************************************
01194 *
01195 *                                DRAW_Putc
01196 *
01197 *******************************************************************************/
01212 /******************************************************************************/
01213 void DRAW_Putc( u8 Ascii )
01214 {
01215     u16 Char_Y = Char_Height * CharMagniCoeff;
01216 
01217     /* CRLF ? */
01218     if ( ( Ascii == '\n' ) )
01219     {
01220         PosCurX = LeftMarginX;
01221         if ( PosCurY >= LowMarginY )
01222         {
01223             PosCurY -= Char_Y;
01224         }
01225         return;
01226     }
01227 
01228     /* Line change, if end of line reached*/
01229     if ( ( PosCurX + ( Char_Width * CharMagniCoeff ) ) > RightMarginX )
01230     {
01231         PosCurX = LeftMarginX;
01232         PosCurY -= Char_Y;
01233     }
01234 
01235     /* Normal print if end of screen not reached*/
01236     if ( PosCurY >= LowMarginY )
01237     {
01238         /* Display the selected bitmap according to the provided ASCII character.*/
01239         LCD_DisplayChar( PosCurX, PosCurY, Ascii, TextColor, BGndColor, CharMagniCoeff );
01240     }
01241     else
01242     {
01243         LCD_Scroll( Ascii, PosCurX, &PosCurY, RightMarginX, LeftMarginX, HighMarginY, LowMarginY, BGndColor, TextColor, CharMagniCoeff );
01244     }
01245 
01246     PosCurX += ( Char_Width * CharMagniCoeff );
01247 }
01248 
01249 /*******************************************************************************
01250 *
01251 *                                DRAW_Puts
01252 *
01253 *******************************************************************************/
01270 /******************************************************************************/
01271 void DRAW_Puts( const u8* ptr )
01272 {
01273     /* Display each character on LCD */
01274     while ( *ptr != 0 )
01275     {
01276         /* Display the character on LCD */
01277         DRAW_Putc( *ptr );
01278 
01279         /* Point to the next character */
01280         ptr++;
01281     }
01282 }
01283 
01284 /*******************************************************************************
01285 *
01286 *                                DRAW_SetCursorPos
01287 *
01288 *******************************************************************************/
01300 /******************************************************************************/
01301 void DRAW_SetCursorPos( coord_t x, coord_t y )
01302 {
01303     if ( x < LeftMarginX )
01304         x = LeftMarginX;
01305     else if ( x > RightMarginX )
01306         x = RightMarginX;
01307     PosCurX = x;
01308 
01309     if ( y < LowMarginY )
01310         y = LowMarginY;
01311     else if ( y > HighMarginY - ( Char_Height * CharMagniCoeff ) )
01312         y = HighMarginY - ( Char_Height * CharMagniCoeff );
01313     PosCurY = y;
01314 }
01315 
01316 /*******************************************************************************
01317 *
01318 *                                DRAW_GetCursorPos
01319 *
01320 *******************************************************************************/
01330 /******************************************************************************/
01331 ret_t DRAW_GetCursorPos( void )
01332 {
01333     return ( PosCurX | ( PosCurY << 8 ) );
01334 }
01335 
01336 /*******************************************************************************
01337 *
01338 *                                DRAW_SetCursorMargin
01339 *
01340 *******************************************************************************/
01354 /******************************************************************************/
01355 void DRAW_SetCursorMargin( coord_t lx, coord_t rx, coord_t hy, coord_t ly )
01356 {
01357     if ( lx < 0 )
01358         lx = 0;
01359 
01360     if ( rx > Screen_Width )
01361         rx = Screen_Width;
01362     else if ( lx > rx )      // else-if necessary in case lx==rx==Screen_Width
01363         lx = rx - 1;
01364 
01365     LeftMarginX = lx;
01366     RightMarginX = rx;
01367 
01368     if ( ly < 0 )
01369         ly = 0;
01370 
01371     if ( hy > Screen_Height )
01372         hy = Screen_Height;
01373     else if ( ly > hy )
01374         ly = hy - 1;
01375 
01376     HighMarginY = hy;
01377     LowMarginY = ly;
01378 }
01379 
01380 /*******************************************************************************
01381 *
01382 *                                DRAW_GetCursorMargin
01383 *
01384 *******************************************************************************/
01398 /******************************************************************************/
01399 void DRAW_GetCursorMargin( coord_t* lx, coord_t* rx, coord_t* hy, coord_t* ly )
01400 {
01401     if ( lx )
01402         *lx = LeftMarginX;
01403 
01404     if ( rx )
01405         *rx = RightMarginX;
01406 
01407     if ( hy )
01408         *hy = HighMarginY;
01409 
01410     if ( ly )
01411         *ly = LowMarginY;
01412 }
01413 
01414 /*******************************************************************************
01415 *
01416 *                                DRAW_Circle
01417 *
01432 void DRAW_Circle( coord_t CENTER_x, coord_t CENTER_y, coord_t RADIUS_r, color_t Color, color_t Fill_Color, bool Fill, bool Circle )
01433 {
01434     int ERROR = 1 - RADIUS_r;
01435     int ddF_x = 0;
01436     int ddF_y = -2 * RADIUS_r;
01437     int x = 0;
01438     int y = RADIUS_r;
01439 
01440     /* Check the x parameters*/
01441     if ( CENTER_x - RADIUS_r < 0 )
01442         CENTER_x = RADIUS_r;
01443 
01444     if ( CENTER_x + RADIUS_r > Screen_Width - 1 )
01445         CENTER_x = Screen_Width - RADIUS_r - 1;
01446 
01447     /* Check the y parameters*/
01448     if ( CENTER_y - RADIUS_r < 0 )
01449         CENTER_y = RADIUS_r;
01450 
01451     if ( CENTER_y + RADIUS_r > Screen_Height - 1 )
01452         CENTER_y = Screen_Height - RADIUS_r - 1;
01453 
01454     if ( Fill )
01455     {
01456         if ( Circle )
01457         {
01458             Fill = 0;
01459             DRAW_Circle( CENTER_x, CENTER_y, RADIUS_r, Color, Fill_Color, 1, 0 );
01460         }
01461     }
01462 
01463     if ( Fill )
01464     {
01465         DRAW_Line( CENTER_x + RADIUS_r, CENTER_y, CENTER_x - RADIUS_r, CENTER_y, Fill_Color );
01466         DRAW_Line( CENTER_x , CENTER_y - RADIUS_r, CENTER_x, CENTER_y + RADIUS_r, Fill_Color );
01467     }
01468 
01469     if ( Circle )
01470     {
01471         LCD_DrawPixel( CENTER_x, CENTER_y + RADIUS_r, Color );
01472         LCD_DrawPixel( CENTER_x, CENTER_y - RADIUS_r, Color );
01473         LCD_DrawPixel( CENTER_x + RADIUS_r, CENTER_y, Color );
01474         LCD_DrawPixel( CENTER_x - RADIUS_r, CENTER_y, Color );
01475     }
01476 
01477     while ( x < y )
01478     {
01479         if ( ERROR >= 0 )
01480         {
01481             y--;
01482             ddF_y += 2;
01483             ERROR += ddF_y;
01484         }
01485         x++;
01486         ddF_x += 2;
01487         ERROR += ddF_x + 1;
01488         if ( Fill )
01489         {
01490             DRAW_Line( CENTER_x + x, CENTER_y + y, CENTER_x + x, CENTER_y - y, Fill_Color );
01491             DRAW_Line( CENTER_x - x, CENTER_y + y, CENTER_x - x, CENTER_y - y, Fill_Color );
01492             DRAW_Line( CENTER_x + y, CENTER_y + x, CENTER_x + y, CENTER_y - x, Fill_Color );
01493             DRAW_Line( CENTER_x - y, CENTER_y + x, CENTER_x - y, CENTER_y - x, Fill_Color );
01494         }
01495 
01496         if ( Circle )
01497         {
01498             LCD_DrawPixel( CENTER_x + x, CENTER_y + y, Color );
01499             LCD_DrawPixel( CENTER_x - x, CENTER_y + y, Color );
01500             LCD_DrawPixel( CENTER_x + x, CENTER_y - y, Color );
01501             LCD_DrawPixel( CENTER_x - x, CENTER_y - y, Color );
01502             LCD_DrawPixel( CENTER_x + y, CENTER_y + x, Color );
01503             LCD_DrawPixel( CENTER_x - y, CENTER_y + x, Color );
01504             LCD_DrawPixel( CENTER_x + y, CENTER_y - x, Color );
01505             LCD_DrawPixel( CENTER_x - y, CENTER_y - x, Color );
01506         }
01507     }
01508 }
01509 
01510 /*******************************************************************************
01511 *
01512 *                                DRAW_Ellipse
01513 *
01529 void DRAW_Ellipse( coord_t CENTER_x, coord_t CENTER_y, coord_t RADIUS_a, coord_t RADIUS_b, color_t Color, color_t Fill_Color, bool Fill, bool Ellipse )
01530 {
01531     int X, Y;
01532     int XChange, YChange;
01533     int EllipseError;
01534     int TwoASquare, TwoBSquare;
01535     int StoppingX, StoppingY;
01536     TwoASquare = 2 * RADIUS_a * RADIUS_a;
01537     TwoBSquare = 2 * RADIUS_b * RADIUS_b;
01538     X = RADIUS_a;
01539     Y = 0;
01540     XChange = RADIUS_b * RADIUS_b * ( 1 - 2 * RADIUS_a );
01541     YChange = RADIUS_a * RADIUS_a;
01542     EllipseError = 0;
01543     StoppingX = TwoBSquare * RADIUS_a;
01544     StoppingY = 0;
01545 
01546     /* Check the x parameters*/
01547     if ( CENTER_x - RADIUS_a < 0 )
01548         CENTER_x = RADIUS_a;
01549 
01550     if ( CENTER_x + RADIUS_a > Screen_Width - 1 )
01551         CENTER_x = Screen_Width - RADIUS_a - 1;
01552 
01553     /* Check the y parameters*/
01554     if ( CENTER_y - RADIUS_b < 0 )
01555         CENTER_y = RADIUS_b;
01556 
01557     if ( CENTER_y + RADIUS_b > Screen_Height - 1 )
01558         CENTER_y = Screen_Height - RADIUS_b - 1;
01559 
01560     if ( Fill )
01561     {
01562         if ( Ellipse )
01563         {
01564             Fill = 0;
01565             DRAW_Ellipse( CENTER_x, CENTER_y, RADIUS_a, RADIUS_b, Color, Fill_Color, 1, 0 );
01566         }
01567     }
01568 
01569     while ( StoppingX >= StoppingY )
01570     {
01571         if ( Fill )
01572         {
01573             DRAW_Line( CENTER_x + X, CENTER_y + Y, CENTER_x - X , CENTER_y + Y, Fill_Color );
01574             DRAW_Line( CENTER_x - X, CENTER_y - Y, CENTER_x + X , CENTER_y - Y, Fill_Color );
01575         }
01576 
01577         if ( Ellipse )
01578         {
01579             LCD_DrawPixel( CENTER_x + X, CENTER_y + Y, Color );
01580             LCD_DrawPixel( CENTER_x - X, CENTER_y + Y, Color );
01581             LCD_DrawPixel( CENTER_x - X, CENTER_y - Y, Color );
01582             LCD_DrawPixel( CENTER_x + X, CENTER_y - Y, Color );
01583         }
01584         Y++;
01585         StoppingY += TwoASquare;
01586         EllipseError += YChange;
01587         YChange += TwoASquare;
01588         if ( ( 2 * EllipseError + XChange ) > 0 )
01589         {
01590             X--;
01591             StoppingX -= TwoBSquare;
01592             EllipseError += XChange;
01593             XChange += TwoBSquare;
01594         }
01595 
01596     } // While (StoppingX >= StoppingY)
01597 
01598     X = 0;
01599     Y = RADIUS_b;
01600     XChange = RADIUS_b * RADIUS_b;
01601     YChange = RADIUS_a * RADIUS_a * ( 1 - 2 * RADIUS_b );
01602     EllipseError = 0;
01603     StoppingX = 0;
01604     StoppingY = TwoASquare * RADIUS_b;
01605 
01606     while ( StoppingX <= StoppingY )
01607     {
01608         if ( Fill )
01609         {
01610             DRAW_Line( CENTER_x + X, CENTER_y + Y, CENTER_x - X , CENTER_y + Y, Fill_Color );
01611             DRAW_Line( CENTER_x - X, CENTER_y - Y, CENTER_x + X , CENTER_y - Y, Fill_Color );
01612         }
01613 
01614         if ( Ellipse )
01615         {
01616             LCD_DrawPixel( CENTER_x + X, CENTER_y + Y, Color );
01617             LCD_DrawPixel( CENTER_x - X, CENTER_y + Y, Color );
01618             LCD_DrawPixel( CENTER_x - X, CENTER_y - Y, Color );
01619             LCD_DrawPixel( CENTER_x + X, CENTER_y - Y, Color );
01620         }
01621 
01622         X++;
01623         StoppingX += TwoBSquare;
01624         EllipseError += XChange;
01625         XChange += TwoBSquare;
01626 
01627         if ( ( 2 * EllipseError + YChange ) > 0 )
01628         {
01629             Y--;
01630             StoppingY -= TwoASquare;
01631             EllipseError += YChange;
01632             YChange += TwoASquare;
01633         }
01634 
01635     } // While (StoppingX <= StoppingY)
01636 }
01637 
01638 
01639 /*******************************************************************************
01640 *
01641 *                                DRAW_Polygon
01642 *
01653 void DRAW_Polygon( coord_t* points, u16 NUM_Points, color_t Line_Color )
01654 {
01655     int i = 1;
01656 
01657     if ( points )
01658     {
01659         for ( i = 1; i < NUM_Points >> 1 ; i++ )
01660         {
01661             DRAW_Line( points[( i - 1 ) * 2], points[1 + ( i - 1 ) * 2], points[( i ) * 2], points[1 + ( i ) * 2], Line_Color );
01662         }
01663     }
01664 }
01665 
01666