From 2c7cbc1dd733d6835da7b49019e512d6eb06f8fa Mon Sep 17 00:00:00 2001 From: Tectu Date: Tue, 28 Aug 2012 16:24:00 +0200 Subject: [PATCH 01/10] implemented gdispDrawArc() by noether --- src/gdisp.c | 99 ++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 91 insertions(+), 8 deletions(-) diff --git a/src/gdisp.c b/src/gdisp.c index f5da45b9..2b8989e6 100644 --- a/src/gdisp.c +++ b/src/gdisp.c @@ -659,6 +659,84 @@ void gdispDrawBox(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { } } +void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { + if (start >= 0 && start <= 180) + { + float x_maxI = x + radius*cos(start*M_PI/180); + float x_minI; + + if (end > 180) + x_minI = x - radius; + else + x_minI = x + radius*cos(end*M_PI/180); + + int a = 0; + int b = radius; + int P = 1 - radius; + + do + { + if(x-a <= x_maxI && x-a >= x_minI) + gdispDrawPixel(x-a, y+b, color); + if(x+a <= x_maxI && x+a >= x_minI) + gdispDrawPixel(x+a, y+b, color); + if(x-b <= x_maxI && x-b >= x_minI) + gdispDrawPixel(x-b, y+a, color); + if(x+b <= x_maxI && x+b >= x_minI) + gdispDrawPixel(x+b, y+a, color); + + if (P < 0) + { + P = P + 3 + 2*a; + a = a + 1; + }else + { + P = P + 5 + 2*(a - b); + a = a + 1; + b = b - 1; + } + }while(a <= b); + } + + if (end > 180 && end <= 360) + { + float x_maxII = x+radius*cos(end*M_PI/180); + float x_minII; + + if(start <= 180) + x_minII = x - radius; + else + x_minII = x+radius*cos(start*M_PI/180); + + int a = 0; + int b = radius; + int P = 1 - radius; + + do{ + if(x-a <= x_maxII && x-a >= x_minII) + gdispDrawPixel(x-a, y-b, color); + if(x+a <= x_maxII && x+a >= x_minII) + gdispDrawPixel(x+a, y-b, color); + if(x-b <= x_maxII && x-b >= x_minII) + gdispDrawPixel(x-b, y-a, color); + if(x+b <= x_maxII && x+b >= x_minII) + gdispDrawPixel(x+b, y-a, color); + + if (P < 0) + { + P = P + 3 + 2*a; + a = a + 1; + } + else + { + P = P + 5 + 2*(a - b); + a = a + 1; + b = b - 1; + } + }while (a <= b); + } +} + /* * @brief Draw an arc. * @pre The GDISP must be in powerOn or powerSleep mode. @@ -672,13 +750,12 @@ void gdispDrawBox(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { * @api */ void gdispDrawArc(coord_t x, coord_t y, coord_t radius, uint16_t start, uint16_t end, color_t color) { - uint16_t i; - float step = 0.01; - - for(i = 0; i <= (int)((abs(end-start)) / step); i++) { - gdispDrawPixel( ((float)x + (float)radius * cosf((float)start * M_PI / 180.0f) + (float)i * step * M_PI / 180.0f), - ((float)y + (float)radius * sinf((float)start * M_PI / 180.0f) + (float)i * step * M_PI / 180.0f), color); - } + if (end < start) { + _draw_arc(x, y, start, 360, radius, color); + _draw_arc(x, y, 0, end, radius, color); + } + else + _draw_arc(x, y, start, end, radius, color); } /* @@ -694,7 +771,13 @@ void gdispDrawArc(coord_t x, coord_t y, coord_t radius, uint16_t start, uint16_t * @api */ void gdispFillArc(coord_t x, coord_t y, coord_t radius, uint16_t start, uint16_t end, color_t color) { - + /* ToDo */ + (void)x; + (void)y; + (void)radius; + (void)start; + (void)end; + (void)color; } #if GDISP_NEED_TEXT || defined(__DOXYGEN__) From d71a6217907564388f36b0e99e6f6b9163a4cb83 Mon Sep 17 00:00:00 2001 From: Tectu Date: Tue, 28 Aug 2012 16:25:22 +0200 Subject: [PATCH 02/10] cleanup --- src/gdisp.c | 34 +++++++++++++--------------------- 1 file changed, 13 insertions(+), 21 deletions(-) diff --git a/src/gdisp.c b/src/gdisp.c index 2b8989e6..582d3377 100644 --- a/src/gdisp.c +++ b/src/gdisp.c @@ -660,8 +660,7 @@ void gdispDrawBox(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { } void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { - if (start >= 0 && start <= 180) - { + if (start >= 0 && start <= 180) { float x_maxI = x + radius*cos(start*M_PI/180); float x_minI; @@ -674,8 +673,7 @@ void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { int b = radius; int P = 1 - radius; - do - { + do { if(x-a <= x_maxI && x-a >= x_minI) gdispDrawPixel(x-a, y+b, color); if(x+a <= x_maxI && x+a >= x_minI) @@ -685,21 +683,18 @@ void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { if(x+b <= x_maxI && x+b >= x_minI) gdispDrawPixel(x+b, y+a, color); - if (P < 0) - { + if (P < 0) { P = P + 3 + 2*a; a = a + 1; - }else - { + } else { P = P + 5 + 2*(a - b); a = a + 1; b = b - 1; } - }while(a <= b); + } while(a <= b); } - if (end > 180 && end <= 360) - { + if (end > 180 && end <= 360) { float x_maxII = x+radius*cos(end*M_PI/180); float x_minII; @@ -712,7 +707,7 @@ void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { int b = radius; int P = 1 - radius; - do{ + do { if(x-a <= x_maxII && x-a >= x_minII) gdispDrawPixel(x-a, y-b, color); if(x+a <= x_maxII && x+a >= x_minII) @@ -722,18 +717,15 @@ void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { if(x+b <= x_maxII && x+b >= x_minII) gdispDrawPixel(x+b, y-a, color); - if (P < 0) - { + if (P < 0) { P = P + 3 + 2*a; a = a + 1; - } - else - { + } else { P = P + 5 + 2*(a - b); a = a + 1; b = b - 1; } - }while (a <= b); + } while (a <= b); } } @@ -750,12 +742,12 @@ void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { * @api */ void gdispDrawArc(coord_t x, coord_t y, coord_t radius, uint16_t start, uint16_t end, color_t color) { - if (end < start) { + if(end < start) { _draw_arc(x, y, start, 360, radius, color); _draw_arc(x, y, 0, end, radius, color); - } - else + } else { _draw_arc(x, y, start, end, radius, color); + } } /* From 661d0bb2fe91098e2ae9153f16a3f0442b558401 Mon Sep 17 00:00:00 2001 From: Tectu Date: Tue, 28 Aug 2012 16:39:05 +0200 Subject: [PATCH 03/10] cleanups & docs --- src/gdisp.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/src/gdisp.c b/src/gdisp.c index 582d3377..c3b83214 100644 --- a/src/gdisp.c +++ b/src/gdisp.c @@ -659,7 +659,20 @@ void gdispDrawBox(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { } } -void _draw_arc(int x, int y, int start, int end, int radius, color_t color) { +/* + * @brief Internal helper function for gdispDrawArc() + * + * @note DO NOT USE DIRECTLY! + * + * @param[in] x, y The middle point of the arc + * @param[in] start The start angle of the arc + * @param[in] end The end angle of the arc + * @param[in] radius The radius of the arc + * @param[in] color The color in which the arc will be drawn + * + * @notapi + */ +void _draw_arc(coord_t x, coord_t y, uint16_t start, uint16_t end, uint16_t radius, color_t color) { if (start >= 0 && start <= 180) { float x_maxI = x + radius*cos(start*M_PI/180); float x_minI; From c67453a0be1629e9b28868bf1d1055f702edec21 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Thu, 30 Aug 2012 22:40:28 +0200 Subject: [PATCH 04/10] Adding SSD1963 --- drivers/gdisp/SSD1963/gdisp_lld.c | 689 +++++++++++++++++++++++ drivers/gdisp/SSD1963/gdisp_lld.mk | 5 + drivers/gdisp/SSD1963/gdisp_lld_config.h | 66 +++ drivers/gdisp/SSD1963/gdisp_lld_panel.h | 44 ++ drivers/gdisp/SSD1963/readme.txt | 35 ++ drivers/gdisp/SSD1963/ssd1963.h | 140 +++++ 6 files changed, 979 insertions(+) create mode 100644 drivers/gdisp/SSD1963/gdisp_lld.c create mode 100644 drivers/gdisp/SSD1963/gdisp_lld.mk create mode 100644 drivers/gdisp/SSD1963/gdisp_lld_config.h create mode 100644 drivers/gdisp/SSD1963/gdisp_lld_panel.h create mode 100644 drivers/gdisp/SSD1963/readme.txt create mode 100644 drivers/gdisp/SSD1963/ssd1963.h diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c new file mode 100644 index 00000000..ceb9108b --- /dev/null +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -0,0 +1,689 @@ +/* + ChibiOS/RT - Copyright (C) 2012 + Joel Bodenmann aka Tectu + + This file is part of ChibiOS-LCD-Driver. + + ChibiOS-LCD-Driver is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + ChibiOS-LCD-Driver is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +/** + * @file templates/gdisp_lld.c + * @brief GDISP Graphics Driver subsystem low level driver source template. + * + * @addtogroup GDISP + * @{ + */ + +#include "ch.h" +#include "hal.h" +#include "gdisp.h" +#include "ssd1963.h" + +#if HAL_USE_GDISP || defined(__DOXYGEN__) + +/* Include the emulation code for things we don't support */ +#include "gdisp_emulation.c" + +/*===========================================================================*/ +/* Driver local definitions. */ +/*===========================================================================*/ + +/*===========================================================================*/ +/* Driver exported variables. */ +/*===========================================================================*/ + +/*===========================================================================*/ +/* Driver local variables. */ +/*===========================================================================*/ + +/*===========================================================================*/ +/* Driver local functions. */ +/*===========================================================================*/ + +#if GDISP_NEED_TEXT + #include "gdisp_fonts.h" +#endif + +/* All the board specific code should go in these include file so the driver + * can be ported to another board just by creating a suitable file. + */ +#if defined(BOARD_YOURBOARDNAME) + #include "gdisp_lld_board_yourboardname.h" +#else + /* Include the user supplied board definitions */ + #include "gdisp_lld_board.h" +#endif + +/*===========================================================================*/ +/* Driver interrupt handlers. */ +/*===========================================================================*/ + +/*===========================================================================*/ +/* Driver exported functions. */ +/*===========================================================================*/ + +/* ---- Required Routines ---- */ +/* + The following 2 routines are required. + All other routines are optional. +*/ +__inline void GDISP_LLD(writeindex)(uint8_t cmd) { + LCD_REG = cmd; +} + +__inline void GDISP_LLD(writereg)(uint16_t lcdReg,uint16_t lcdRegValue) { + LCD_REG = lcdReg; + LCD_RAM = lcdRegValue; +} + +__inline void GDISP_LLD(writedata)(uint8_t data) { + LCD_RAM = data; +} + +__inline void GDISP_LLD(readdata)(uint8_t data) { + return (LCD_RAM); +} + +__inline void GDISP_LLD(readreg)(uint8_t lcdReg) { + LCD_REG = lcdReg; + return (LCD_RAM); +} + +__inline void GDISP_LLD(writestreamstart)(void) { + LCD_REG = SSD1963_WRITE_MEMORY_START; +} + +__inline void GDISP_LLD(readstreamstart)(void) { + LCD_REG = SSD1963_READ_MEMORY_START; +} + +__inline void GDISP_LLD(writestream)(uint16_t *buffer, uint16_t size) { + uint16_t i; + for(i = 0; i < size; i++) + LCD_RAM = buffer[i]; +} + +__inline void GDISP_LLD(readstream)(uint16_t *buffer, size_t size) { + uint16_t i; + + for(i = 0; i < size; i++) { + buffer[i] = LCD_RAM; + } +} +/** + * @brief Low level GDISP driver initialisation. + * @return TRUE if successful, FALSE on error. + * + * @notapi + */ +bool_t GDISP_LLD(init)(void) { + /* Initialise your display */ + + /* Initialise the GDISP structure to match */ + GDISP.Width = SCREEN_WIDTH; + GDISP.Height = SCREEN_HEIGHT; + GDISP.Orientation = portrait; + GDISP.Powermode = powerOn; + GDISP.Backlight = 100; + GDISP.Contrast = 50; + +#ifdef LCD_USE_FSMC + +#if defined(STM32F1XX) + /* FSMC setup. TODO: this only works for STM32F1 */ + rccEnableAHB(RCC_AHBENR_FSMCEN, 0); + + /* TODO: pin setup */ +#elif defined(STM32F4XX) + /* STM32F4 FSMC init */ + rccEnableAHB3(RCC_AHB3ENR_FSMCEN, 0); + + /* set pins to FSMC mode */ + IOBus busD = {GPIOD, (1 << 0) | (1 << 1) | (1 << 4) | (1 << 5) | (1 << 7) | (1 << 8) | + (1 << 9) | (1 << 10) | (1 << 11) | (1 << 14) | (1 << 15), 0}; + + IOBus busE = {GPIOE, (1 << 7) | (1 << 8) | (1 << 9) | (1 << 10) | (1 << 11) | (1 << 12) | + (1 << 13) | (1 << 14) | (1 << 15), 0}; + + palSetBusMode(&busD, PAL_MODE_ALTERNATE(12)); + palSetBusMode(&busE, PAL_MODE_ALTERNATE(12)); +#else +#error "FSMC not implemented for this device" +#endif + const int FSMC_Bank = 0; + /* FSMC timing */ + FSMC_Bank1->BTCR[FSMC_Bank+1] = (FSMC_BTR1_ADDSET_1 | FSMC_BTR1_ADDSET_3) \ + | (FSMC_BTR1_DATAST_1 | FSMC_BTR1_DATAST_3) \ + | (FSMC_BTR1_BUSTURN_1 | FSMC_BTR1_BUSTURN_3) ; + + /* Bank1 NOR/SRAM control register configuration + * This is actually not needed as already set by default after reset */ + FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; +#endif + + GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); + + /* Driver PLL config */ + GDISP_LLD(writeindex)(SSD1963_SET_PLL_MN); + GDISP_LLD(writestreamstart)(35); // PLLclk = REFclk (10Mhz) * 36 (360Mhz) + GDISP_LLD(writestreamstart)(2); // SYSclk = PLLclk / 3 (120MHz) + GDISP_LLD(writestreamstart)(4); // Apply calculation bit, else it is ignored + + GDISP_LLD(writeindex)(SSD1963_SET_PLL); // Enable PLL + GDISP_LLD(writestreamstart)(0x01); + lld_lcdDelay(200); + + GDISP_LLD(writeindex)(SSD1963_SET_PLL); // Use PLL + GDISP_LLD(writestreamstart)(0x03); + lld_lcdDelay(200); + + GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); + + /* Screen size */ + GDISP_LLD(writeindex)(SSD1963_SET_LCD_MODE); +// GDISP_LLD(writestreamstart)(0x0000); + GDISP_LLD(writestreamstart)(0b00011000); + GDISP_LLD(writestreamstart)(0x0000); + GDISP_LLD(writestreamstart)(mHIGH((SCREEN_WIDTH+1))); + GDISP_LLD(writestreamstart)((SCREEN_WIDTH+1)); + GDISP_LLD(writestreamstart)(mHIGH((SCREEN_HEIGHT+1))); + GDISP_LLD(writestreamstart)((SCREEN_HEIGHT+1)); + GDISP_LLD(writestreamstart)(0x0000); + + GDISP_LLD(writeindex)(SSD1963_SET_PIXEL_DATA_INTERFACE); + GDISP_LLD(writestreamstart)(SSD1963_PDI_16BIT565); + + /* LCD Clock specs */ + GDISP_LLD(writeindex)(SSD1963_SET_LSHIFT_FREQ); + GDISP_LLD(writestreamstart)((LCD_FPR >> 16) & 0xFF); + GDISP_LLD(writestreamstart)((LCD_FPR >> 8) & 0xFF); + GDISP_LLD(writestreamstart)(LCD_FPR & 0xFF); + + GDISP_LLD(writeindex)(SSD1963_SET_HORI_PERIOD); + GDISP_LLD(writestreamstart)(mHIGH(SCREEN_HSYNC_PERIOD)); + GDISP_LLD(writestreamstart)(mLOW(SCREEN_HSYNC_PERIOD)); + GDISP_LLD(writestreamstart)(mHIGH((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); + GDISP_LLD(writestreamstart)(mLOW((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); + GDISP_LLD(writestreamstart)(SCREEN_HSYNC_PULSE); + GDISP_LLD(writestreamstart)(0x00); + GDISP_LLD(writestreamstart)(0x00); + GDISP_LLD(writestreamstart)(0x00); + + GDISP_LLD(writeindex)(SSD1963_SET_VERT_PERIOD); + GDISP_LLD(writestreamstart)(mHIGH(SCREEN_VSYNC_PERIOD)); + GDISP_LLD(writestreamstart)(mLOW(SCREEN_VSYNC_PERIOD)); + GDISP_LLD(writestreamstart)(mHIGH((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); + GDISP_LLD(writestreamstart)(mLOW((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); + GDISP_LLD(writestreamstart)(SCREEN_VSYNC_PULSE); + GDISP_LLD(writestreamstart)(0x00); + GDISP_LLD(writestreamstart)(0x00); + + /* Tear effect indicator ON. This is used to tell the host MCU when the driver is not refreshing the panel */ + GDISP_LLD(writeindex)(SSD1963_SET_TEAR_ON); + GDISP_LLD(writestreamstart)(0x0000); + + /* Turn on */ + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); +#ifdef LCD_USE_FSMC + /* FSMC delay reduced as the controller now runs at full speed */ + FSMC_Bank1->BTCR[FSMC_Bank+1] = FSMC_BTR1_ADDSET_0 | (FSMC_BTR1_DATAST_2 | FSMC_BTR1_DATAST_0) | FSMC_BTR1_BUSTURN_0 ; + FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; +#endif + + return TRUE; +} + +void GDISP_LLD(setwindow)(coord_t x0, coord_t y0, coord_t x1, coord_t y1) { + #if GDISP_NEED_VALIDATION + if (x0 >= GDISP.Width || y0 >= GDISP.Height) return; + else if (x1 >= GDISP.Width || y1 >= GDISP.Height) return; + #endif + GDISP_LLD(writeindex)(SSD1963_SET_COLUMN_ADDRESS); + GDISP_LLD(writestreamstart)((y0 >> 8) & 0xFF); + GDISP_LLD(writestreamstart)((y0 >> 0) & 0xFF); + GDISP_LLD(writestreamstart)((y1 >> 8) & 0xFF); + GDISP_LLD(writestreamstart)((y1 >> 0) & 0xFF); + GDISP_LLD(writeindex)(SSD1963_SET_PAGE_ADDRESS); + GDISP_LLD(writestreamstart)((x0 >> 8) & 0xFF); + GDISP_LLD(writestreamstart)((x0 >> 0) & 0xFF); + GDISP_LLD(writestreamstart)((x1 >> 8) & 0xFF); + GDISP_LLD(writestreamstart)((x1 >> 0) & 0xFF); +} + +/** + * @brief Draws a pixel on the display. + * + * @param[in] x X location of the pixel + * @param[in] y Y location of the pixel + * @param[in] color The color of the pixel + * + * @notapi + */ +void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { + #if GDISP_NEED_VALIDATION + if (x >= GDISP.Width || y >= GDISP.Height) return; + #endif + GDISP_LLD(setwindow)(x, y, x, y); + GDISP_LLD(writestreamstart); + GDISP_LLD(writedata)(color); +} + +/* ---- Optional Routines ---- */ +/* + All the below routines are optional. + Defining them will increase speed but everything + will work if they are not defined. + If you are not using a routine - turn it off using + the appropriate GDISP_HARDWARE_XXXX macro. + Don't bother coding for obvious similar routines if + there is no performance penalty as the emulation software + makes a good job of using similar routines. + eg. If fillarea() is defined there is little + point in defining clear() unless the + performance bonus is significant. + For good performance it is suggested to implement + fillarea() and blitarea(). +*/ + +#if GDISP_HARDWARE_CLEARS || defined(__DOXYGEN__) + /** + * @brief Clear the display. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] color The color of the pixel + * + * @notapi + */ + void GDISP_LLD(clear)(color_t color) { + /* Code here */ + } +#endif + +#if GDISP_HARDWARE_LINES || defined(__DOXYGEN__) + /** + * @brief Draw a line. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] x0, y0 The start of the line + * @param[in] x1, y1 The end of the line + * @param[in] color The color of the line + * + * @notapi + */ + void GDISP_LLD(drawline)(coord_t x0, coord_t y0, coord_t x1, coord_t y1, color_t color) { + #if GDISP_NEED_VALIDATION + /* Need to clip to screen */ + #endif + /* Code here */ + } +#endif + +#if GDISP_HARDWARE_FILLS || defined(__DOXYGEN__) + /** + * @brief Fill an area with a color. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] x, y The start filled area + * @param[in] cx, cy The width and height to be filled + * @param[in] color The color of the fill + * + * @notapi + */ + void GDISP_LLD(fillarea)(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { + #if GDISP_NEED_VALIDATION + if (cx < 1 || cy < 1 || x >= GDISP.Width || y >= GDISP.Height) return; + if (x+cx > GDISP.Width) cx = GDISP.Width - x; + if (y+cy > GDISP.Height) cy = GDISP.Height - y; + #endif + + uint32_t index = 0, area; + + area = ((x1-x0+1)*(y1-y0+1)); + + lld_lcdSetWindow(x0, y0, x1, y1); + lld_lcdwritestreamstart(); + + for(index = 0; index <= area; index++) + GDISP_LLD(writestreamstart)(color); + + } +#endif + +#if GDISP_HARDWARE_BITFILLS || defined(__DOXYGEN__) + /** + * @brief Fill an area with a bitmap. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] x, y The start filled area + * @param[in] cx, cy The width and height to be filled + * @param[in] buffer The pixels to use to fill the area. + * + * @notapi + */ + void GDISP_LLD(blitarea)(coord_t x, coord_t y, coord_t cx, coord_t cy, const pixel_t *buffer) { + #if GDISP_NEED_VALIDATION + if (cx < 1 || cy < 1 || x >= GDISP.Width || y >= GDISP.Height) return; + if (x+cx > GDISP.Width) return; + if (y+cy > GDISP.Height) cy = GDISP.Height - y; + #endif + /* Code here */ + } +#endif + +/* Circular Drawing Functions */ +#if (GDISP_NEED_CIRCLE && GDISP_HARDWARE_CIRCLES) || defined(__DOXYGEN__) + /** + * @brief Draw a circle. + * @note Optional - The high level driver can emulate using software. + * @note If GDISP_NEED_CLIPPING is defined this routine MUST behave + * correctly if the circle is over the edges of the screen. + * + * @param[in] x, y The centre of the circle + * @param[in] radius The radius of the circle + * @param[in] color The color of the circle + * + * @notapi + */ + void GDISP_LLD(drawcircle)(coord_t x, coord_t y, coord_t radius, color_t color) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_CIRCLE && GDISP_HARDWARE_CIRCLEFILLS) || defined(__DOXYGEN__) + /** + * @brief Create a filled circle. + * @note Optional - The high level driver can emulate using software. + * @note If GDISP_NEED_CLIPPING is defined this routine MUST behave + * correctly if the circle is over the edges of the screen. + * + * @param[in] x, y The centre of the circle + * @param[in] radius The radius of the circle + * @param[in] color The color of the circle + * + * @notapi + */ + void GDISP_LLD(fillcircle)(coord_t x, coord_t y, coord_t radius, color_t color) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_ELLIPSE && GDISP_HARDWARE_ELLIPSES) || defined(__DOXYGEN__) + /** + * @brief Draw an ellipse. + * @note Optional - The high level driver can emulate using software. + * @note If GDISP_NEED_CLIPPING is defined this routine MUST behave + * correctly if the ellipse is over the edges of the screen. + * + * @param[in] x, y The centre of the ellipse + * @param[in] a, b The dimensions of the ellipse + * @param[in] color The color of the ellipse + * + * @notapi + */ + void GDISP_LLD(drawellipse)(coord_t x, coord_t y, coord_t a, coord_t b, color_t color) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_ELLIPSE && GDISP_HARDWARE_ELLIPSEFILLS) || defined(__DOXYGEN__) + /** + * @brief Create a filled ellipse. + * @note Optional - The high level driver can emulate using software. + * @note If GDISP_NEED_CLIPPING is defined this routine MUST behave + * correctly if the ellipse is over the edges of the screen. + * + * @param[in] x, y The centre of the ellipse + * @param[in] a, b The dimensions of the ellipse + * @param[in] color The color of the ellipse + * + * @notapi + */ + void GDISP_LLD(fillellipse)(coord_t x, coord_t y, coord_t a, coord_t b, color_t color) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_TEXT && GDISP_HARDWARE_TEXT) || defined(__DOXYGEN__) + /** + * @brief Draw a character using a transparent background. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] x, y The top-left corner of the text + * @param[in] c The character to print + * @param[in] color The color of the character + * + * @notapi + */ + void GDISP_LLD(drawchar)(coord_t x, coord_t y, char c, font_t font, color_t color) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_TEXT && GDISP_HARDWARE_TEXTFILLS) || defined(__DOXYGEN__) + /** + * @brief Draw a character using a filled background. + * @note Optional - The high level driver can emulate using software. + * + * @param[in] x, y The top-left corner of the text + * @param[in] c The character to print + * @param[in] color The color of the character + * @param[in] bgcolor The background color + * + * @notapi + */ + void GDISP_LLD(fillchar)(coord_t x, coord_t y, char c, font_t font, color_t color, color_t bgcolor) { + #if GDISP_NEED_VALIDATION + /* Code here */ + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_PIXELREAD && GDISP_HARDWARE_PIXELREAD) || defined(__DOXYGEN__) + /** + * @brief Get the color of a particular pixel. + * @note Optional. + * @note If x,y is off the screen, the result is undefined. + * @return The color of the specified pixel. + * + * @param[in] x, y The start of the text + * + * @notapi + */ + color_t GDISP_LLD(getpixelcolor)(coord_t x, coord_t y) { + #if GDISP_NEED_VALIDATION + if (x >= GDISP.Width || y >= GDISP.Height) return 0; + #endif + /* Code here */ + } +#endif + +#if (GDISP_NEED_SCROLL && GDISP_HARDWARE_SCROLL) || defined(__DOXYGEN__) + /** + * @brief Scroll vertically a section of the screen. + * @note Optional. + * @note If x,y + cx,cy is off the screen, the result is undefined. + * @note If lines is >= cy, it is equivelent to a area fill with bgcolor. + * + * @param[in] x, y The start of the area to be scrolled + * @param[in] cx, cy The size of the area to be scrolled + * @param[in] lines The number of lines to scroll (Can be positive or negative) + * @param[in] bgcolor The color to fill the newly exposed area. + * + * @notapi + */ + void GDISP_LLD(verticalscroll)(coord_t x, coord_t y, coord_t cx, coord_t cy, int lines, color_t bgcolor) { + #if GDISP_NEED_VALIDATION + if (cx < 1 || cy < 1 || x >= GDISP.Width || y >= GDISP.Height) return; + if (x+cx > GDISP.Width) cx = GDISP.Width - x; + if (y+cy > GDISP.Height) cy = GDISP.Height - y; + #endif + /* Code here */ + + /* + uint16_t size = x1 - x0 ; + + lld_lcdWriteIndex(SSD1963_SET_SCROLL_AREA); + lld_lcdWriteData((x0 >> 8) & 0xFF); + lld_lcdWriteData((x0 >> 0) & 0xFF); + lld_lcdWriteData((size >> 8) & 0xFF); + lld_lcdWriteData((size >> 0) & 0xFF); + lld_lcdWriteData(((lcd_height-x1) >> 8) & 0xFF); + lld_lcdWriteData(((lcd_height-x1) >> 0) & 0xFF); + + lld_lcdWriteIndex(SSD1963_SET_SCROLL_START); + lld_lcdWriteData((lines >> 8) & 0xFF); + lld_lcdWriteData((lines >> 0) & 0xFF); + */ + } + +#endif + +#if (GDISP_NEED_CONTROL && GDISP_HARDWARE_CONTROL) || defined(__DOXYGEN__) + /** + * @brief Driver Control + * @detail Unsupported control codes are ignored. + * @note The value parameter should always be typecast to (void *). + * @note There are some predefined and some specific to the low level driver. + * @note GDISP_CONTROL_POWER - Takes a gdisp_powermode_t + * GDISP_CONTROL_ORIENTATION - Takes a gdisp_orientation_t + * GDISP_CONTROL_BACKLIGHT - Takes an int from 0 to 100. For a driver + * that only supports off/on anything other + * than zero is on. + * GDISP_CONTROL_CONTRAST - Takes an int from 0 to 100. + * GDISP_CONTROL_LLD - Low level driver control constants start at + * this value. + * + * @param[in] what What to do. + * @param[in] value The value to use (always cast to a void *). + * + * @notapi + */ + void GDISP_LLD(control)(unsigned what, void *value) { + switch(what) { + case GDISP_CONTROL_POWER: + if (GDISP.Powermode == (gdisp_powermode_t)value) + return; + switch((gdisp_powermode_t)value) { + case powerOff: + GDISP_LLD(writeindex)(SSD1963_EXIT_SLEEP_MODE); // leave sleep mode + chThdSleepMicroseconds(5000); + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); + GDISP_LLD(writeindex)(SSD1963_SET_DEEP_SLEEP); // enter deep sleep mode + break; + case powerOn: + GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); // 2x Dummy reads to wake up from deep sleep + GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); + if (GDISP.Powermode != powerSleep) + GDISP_LLD(init)(); + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); + + break; + case powerSleep: + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); + GDISP_LLD(writeindex)(SSD1963_ENTER_SLEEP_MODE); // enter sleep mode + chThdSleepMicroseconds(5000); + break; + default: + return; + } + GDISP.Powermode = (gdisp_powermode_t)value; + return; + case GDISP_CONTROL_ORIENTATION: + if (GDISP.Orientation == (gdisp_orientation_t)value) + return; + switch((gdisp_orientation_t)value) { + case portrait: + /* Code here */ + GDISP.Height = SCREEN_HEIGHT; + GDISP.Width = SCREEN_WIDTH; + break; + case landscape: + /* Code here */ + GDISP.Height = SCREEN_WIDTH; + GDISP.Width = SCREEN_HEIGHT; + break; + case portraitInv: + /* Code here */ + GDISP.Height = SCREEN_HEIGHT; + GDISP.Width = SCREEN_WIDTH; + break; + case landscapeInv: + /* Code here */ + GDISP.Height = SCREEN_WIDTH; + GDISP.Width = SCREEN_HEIGHT; + break; + default: + return; + } + GDISP.Orientation = (gdisp_orientation_t)value; + return; +/* + case GDISP_CONTROL_BACKLIGHT: + case GDISP_CONTROL_CONTRAST: +*/ + } + } +#endif + +#if (GDISP_NEED_QUERY && GDISP_HARDWARE_QUERY) || defined(__DOXYGEN__) +/** + * @brief Query a driver value. + * @detail Typecase the result to the type you want. + * @note GDISP_QUERY_WIDTH - (coord_t) Gets the width of the screen + * GDISP_QUERY_HEIGHT - (coord_t) Gets the height of the screen + * GDISP_QUERY_POWER - (gdisp_powermode_t) Get the current powermode + * GDISP_QUERY_ORIENTATION - (gdisp_orientation_t) Get the current screen orientation + * GDISP_QUERY_BACKLIGHT - (coord_t) Get the backlight state (0 to 100) + * GDISP_QUERY_CONTRAST - (coord_t) Get the contrast (0 to 100). + * GDISP_QUERY_LLD - Low level driver control constants start at + * this value. + * + * @param[in] what What to Query + * + * @notapi + */ +void *GDISP_LLD(query)(unsigned what) { + switch(what) { + case GDISP_QUERY_WIDTH: return (void *)(unsigned)GDISP.Width; + case GDISP_QUERY_HEIGHT: return (void *)(unsigned)GDISP.Height; + case GDISP_QUERY_POWER: return (void *)(unsigned)GDISP.Powermode; + case GDISP_QUERY_ORIENTATION: return (void *)(unsigned)GDISP.Orientation; + case GDISP_QUERY_BACKLIGHT: return (void *)(unsigned)GDISP.Backlight; + case GDISP_QUERY_CONTRAST: return (void *)(unsigned)GDISP.Contrast; + case GDISP_QUERY_LLD+0: + /* Code here */ + default: return (void *)-1; + } +} +#endif + +#endif /* HAL_USE_GDISP */ +/** @} */ diff --git a/drivers/gdisp/SSD1963/gdisp_lld.mk b/drivers/gdisp/SSD1963/gdisp_lld.mk new file mode 100644 index 00000000..26d7a57a --- /dev/null +++ b/drivers/gdisp/SSD1963/gdisp_lld.mk @@ -0,0 +1,5 @@ +# List the required driver. +LCDSRC += $(LCDLIB)/drivers/gdisp/SSD1963/gdisp_lld.c + +# Required include directories +LCDINC += $(LCDLIB)/drivers/gdisp/SSD1963 diff --git a/drivers/gdisp/SSD1963/gdisp_lld_config.h b/drivers/gdisp/SSD1963/gdisp_lld_config.h new file mode 100644 index 00000000..25fe76d2 --- /dev/null +++ b/drivers/gdisp/SSD1963/gdisp_lld_config.h @@ -0,0 +1,66 @@ +/* + ChibiOS/RT - Copyright (C) 2012 + Joel Bodenmann aka Tectu + + This file is part of ChibiOS-LCD-Driver. + + ChibiOS-LCD-Driver is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + ChibiOS-LCD-Driver is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +/** + * @file templates/gdisp_lld_config.h + * @brief GDISP Graphic Driver subsystem low level driver header template. + * + * @addtogroup GDISP + * @{ + */ + +#ifndef _GDISP_LLD_CONFIG_H +#define _GDISP_LLD_CONFIG_H + +#if HAL_USE_GDISP || defined(__DOXYGEN__) + +/*===========================================================================*/ +/* Driver hardware support. */ +/*===========================================================================*/ + +#define GDISP_DRIVER_NAME "YourDriverName" +#define GDISP_LLD(x) gdisp_lld_##x##_YourDriverName + +#define GDISP_HARDWARE_LINES FALSE +#define GDISP_HARDWARE_CLEARS FALSE +#define GDISP_HARDWARE_FILLS FALSE +#define GDISP_HARDWARE_BITFILLS FALSE +#define GDISP_HARDWARE_CIRCLES FALSE +#define GDISP_HARDWARE_CIRCLEFILLS FALSE +#define GDISP_HARDWARE_ELLIPSES FALSE +#define GDISP_HARDWARE_ELLIPSEFILLS FALSE +#define GDISP_HARDWARE_TEXT FALSE +#define GDISP_HARDWARE_TEXTFILLS FALSE +#define GDISP_HARDWARE_SCROLL FALSE +#define GDISP_HARDWARE_PIXELREAD FALSE +#define GDISP_HARDWARE_CONTROL FALSE +#define GDISP_HARDWARE_QUERY FALSE + +#define GDISP_SOFTWARE_TEXTFILLDRAW FALSE +#define GDISP_SOFTWARE_TEXTBLITCOLUMN FALSE + +#define GDISP_PIXELFORMAT GDISP_PIXELFORMAT_RGB565 +#define GDISP_PACKED_PIXELS FALSE +#define GDISP_PACKED_LINES FALSE + +#endif /* HAL_USE_GDISP */ + +#endif /* _GDISP_LLD_CONFIG_H */ +/** @} */ diff --git a/drivers/gdisp/SSD1963/gdisp_lld_panel.h b/drivers/gdisp/SSD1963/gdisp_lld_panel.h new file mode 100644 index 00000000..f4a8595b --- /dev/null +++ b/drivers/gdisp/SSD1963/gdisp_lld_panel.h @@ -0,0 +1,44 @@ +/* + ChibiOS/RT - Copyright (C) 2012 + Fabien Poussin aka Mobyfab + + This file is part of ChibiOS-LCD-Driver. + + ChibiOS-LCD-Driver is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + ChibiOS-LCD-Driver is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef _GDISP_LLD_PANEL_H +#define _GDISP_LLD_PANEL_H + +/* LCD panel specs */ +#define SCREEN_WIDTH 480 +#define SCREEN_HEIGHT 272 + +#define SCREEN_FPS 60ULL + +#define SCREEN_HSYNC_BACK_PORCH 2LL +#define SCREEN_HSYNC_FRONT_PORCH 2ULL +#define SCREEN_HSYNC_PULSE 41ULL + +#define SCREEN_VSYNC_BACK_PORCH 2ULL +#define SCREEN_VSYNC_FRONT_PORCH 2ULL +#define SCREEN_VSYNC_PULSE 10ULL + +#define SCREEN_HSYNC_PERIOD (SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH + SCREEN_WIDTH + SCREEN_HSYNC_FRONT_PORCH) +#define SCREEN_VSYNC_PERIOD (SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH + SCREEN_HEIGHT + SCREEN_VSYNC_FRONT_PORCH) + +#define SCREEN_PCLK (SCREEN_HSYNC_PERIOD * SCREEN_VSYNC_PERIOD * SCREEN_FPS) +#define LCD_FPR ((SCREEN_PCLK * 1048576)/100000000) + +#endif diff --git a/drivers/gdisp/SSD1963/readme.txt b/drivers/gdisp/SSD1963/readme.txt new file mode 100644 index 00000000..2496fc51 --- /dev/null +++ b/drivers/gdisp/SSD1963/readme.txt @@ -0,0 +1,35 @@ +To use this driver template + 1. Copy this entire directory (including the directory itself) + into halext/drivers + 2. Rename the directory to match your hardware. + 3. Customise each file in the directory including the .mk file + and this file. An example for this file is below... + 4. Keep any board specific code in a file you create called + gdisp_lld_board_yourboardname.h and adjust gdisp.c to match. + This enables someone porting to a new board to add another + suitable boad definition without worrying about the rest of + the driver. See the gdispNokia6610 driver as an example. + +------------------------------------------------------------------ +To use this driver: + +1. Add in your halconf.h: + a) #define HAL_USE_GDISP TRUE + b) Any optional high level driver defines (see gdisp.h) eg: GDISP_NEED_MULTITHREAD + c) One (only) of: + #define LCD_USE_GPIO + #define LCD_USE_SPI + #define LCD_USE_FSMC + d) All of the following (with appropriate values): + #define SCREEN_WIDTH 128 + #define SCREEN_HEIGHT 128 + e) If you are not using a known board then create a gdisp_lld_board.h file + and ensure it is on your include path. + Use the gdisp_lld_board_example.h file as a basis. + Currently known boards are: + XXXXXXXXX + + +2. To your makefile add the following lines: + include $(CHIBIOS)/os/halext/halext.mk + include $(CHIBIOS)/os/halext/drivers/gdispXXXXX/gdisp_lld.mk diff --git a/drivers/gdisp/SSD1963/ssd1963.h b/drivers/gdisp/SSD1963/ssd1963.h new file mode 100644 index 00000000..fcac4e1d --- /dev/null +++ b/drivers/gdisp/SSD1963/ssd1963.h @@ -0,0 +1,140 @@ +/* + ChibiOS/RT - Copyright (C) 2012 + Fabien Poussin aka Mobyfab + + This file is part of ChibiOS-LCD-Driver. + + ChibiOS-LCD-Driver is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + ChibiOS-LCD-Driver is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef SSD1963_H +#define SSD1963_H + +#include "gdisp_lld_panel.h" + +#ifdef LCD_USE_GPIO + #define Set_CS palSetPad(LCD_CMD_PORT, LCD_CS); + #define Clr_CS palClearPad(LCD_CMD_PORT, LCD_CS); + #define Set_RS palSetPad(LCD_CMD_PORT, LCD_RS); + #define Clr_RS palClearPad(LCD_CMD_PORT, LCD_RS); + #define Set_WR palSetPad(LCD_CMD_PORT, LCD_WR); + #define Clr_WR palClearPad(LCD_CMD_PORT, LCD_WR); + #define Set_RD palSetPad(LCD_CMD_PORT, LCD_RD); + #define Clr_RD palClearPad(LCD_CMD_PORT, LCD_RD); +#endif + +#ifdef LCD_USE_SPI + /* TODO */ +#endif + +#ifdef LCD_USE_FSMC + +/* Using FSMC A16 as RS */ +#define LCD_REG (*((volatile uint16_t *) 0x60000000)) /* RS = 0 */ +#define LCD_RAM (*((volatile uint16_t *) 0x60020000)) /* RS = 1 */ + +#endif + +#define mHIGH(x) (x >> 8) +#define mLOW(x) (x & 0xFF) + +/* SSD1963 commands */ + +#define SSD1963_NOP 0x0000 +#define SSD1963_SOFT_RESET 0x0001 +#define SSD1963_GET_POWER_MODE 0x000A +#define SSD1963_GET_ADDRESS_MODE 0x000B +#define SSD1963_GET_DISPLAY_MODE 0x000D +#define SSD1963_GET_TEAR_EFFECT_STATUS 0x000E +#define SSD1963_ENTER_SLEEP_MODE 0x0010 +#define SSD1963_EXIT_SLEEP_MODE 0x0011 +#define SSD1963_ENTER_PARTIAL_MODE 0x0012 +#define SSD1963_ENTER_NORMAL_MODE 0x0013 +#define SSD1963_EXIT_INVERT_MODE 0x0020 +#define SSD1963_ENTER_INVERT_MODE 0x0021 +#define SSD1963_SET_GAMMA_CURVE 0x0026 +#define SSD1963_SET_DISPLAY_OFF 0x0028 +#define SSD1963_SET_DISPLAY_ON 0x0029 +#define SSD1963_SET_COLUMN_ADDRESS 0x002A +#define SSD1963_SET_PAGE_ADDRESS 0x002B +#define SSD1963_WRITE_MEMORY_START 0x002C +#define SSD1963_READ_MEMORY_START 0x002E +#define SSD1963_SET_PARTIAL_AREA 0x0030 +#define SSD1963_SET_SCROLL_AREA 0x0033 +#define SSD1963_SET_TEAR_OFF 0x0034 +#define SSD1963_SET_TEAR_ON 0x0035 +#define SSD1963_SET_ADDRESS_MODE 0x0036 +#define SSD1963_SET_SCROLL_START 0x0037 +#define SSD1963_EXIT_IDLE_MODE 0x0038 +#define SSD1963_ENTER_IDLE_MODE 0x0039 +#define SSD1963_SET_PIXEL_FORMAT 0x003A +#define SSD1963_WRITE_MEMORY_CONTINUE 0x003C +#define SSD1963_READ_MEMORY_CONTINUE 0x003E +#define SSD1963_SET_TEAR_SCANLINE 0x0044 +#define SSD1963_GET_SCANLINE 0x0045 +#define SSD1963_READ_DDB 0x00A1 +#define SSD1963_SET_LCD_MODE 0x00B0 +#define SSD1963_GET_LCD_MODE 0x00B1 +#define SSD1963_SET_HORI_PERIOD 0x00B4 +#define SSD1963_GET_HORI_PERIOD 0x00B5 +#define SSD1963_SET_VERT_PERIOD 0x00B6 +#define SSD1963_GET_VERT_PERIOD 0x00B7 +#define SSD1963_SET_GPIO_CONF 0x00B8 +#define SSD1963_GET_GPIO_CONF 0x00B9 +#define SSD1963_SET_GPIO_VALUE 0x00BA +#define SSD1963_GET_GPIO_STATUS 0x00BB +#define SSD1963_SET_POST_PROC 0x00BC +#define SSD1963_GET_POST_PROC 0x00BD +#define SSD1963_SET_PWM_CONF 0x00BE +#define SSD1963_GET_PWM_CONF 0x00BF +#define SSD1963_GET_LCD_GEN0 0x00C0 +#define SSD1963_SET_LCD_GEN0 0x00C1 +#define SSD1963_GET_LCD_GEN1 0x00C2 +#define SSD1963_SET_LCD_GEN1 0x00C3 +#define SSD1963_GET_LCD_GEN2 0x00C4 +#define SSD1963_SET_LCD_GEN2 0x00C5 +#define SSD1963_GET_LCD_GEN3 0x00C6 +#define SSD1963_SET_LCD_GEN3 0x00C7 +#define SSD1963_SET_GPIO0_ROP 0x00C8 +#define SSD1963_GET_GPIO0_ROP 0x00C9 +#define SSD1963_SET_GPIO1_ROP 0x00CA +#define SSD1963_GET_GPIO1_ROP 0x00CB +#define SSD1963_SET_GPIO2_ROP 0x00CC +#define SSD1963_GET_GPIO2_ROP 0x00CD +#define SSD1963_SET_GPIO3_ROP 0x00CE +#define SSD1963_GET_GPIO3_ROP 0x00CF +#define SSD1963_SET_DBC_CONF 0x00D0 +#define SSD1963_GET_DBC_CONF 0x00D1 +#define SSD1963_SET_DBC_TH 0x00D4 +#define SSD1963_GET_DBC_TH 0x00D5 +#define SSD1963_SET_PLL 0x00E0 +#define SSD1963_SET_PLL_MN 0x00E2 +#define SSD1963_GET_PLL_MN 0x00E3 +#define SSD1963_GET_PLL_STATUS 0x00E4 +#define SSD1963_SET_DEEP_SLEEP 0x00E5 +#define SSD1963_SET_LSHIFT_FREQ 0x00E6 +#define SSD1963_GET_LSHIFT_FREQ 0x00E7 +#define SSD1963_SET_PIXEL_DATA_INTERFACE 0x00F0 + #define SSD1963_PDI_8BIT 0 + #define SSD1963_PDI_12BIT 1 + #define SSD1963_PDI_16BIT 2 + #define SSD1963_PDI_16BIT565 3 + #define SSD1963_PDI_18BIT 4 + #define SSD1963_PDI_24BIT 5 + #define SSD1963_PDI_9BIT 6 +#define SSD1963_GET_PIXEL_DATA_INTERFACE 0x00F1 + +#endif + +#endif \ No newline at end of file From aba929d18b48eb9562ebcfbc335f2837af2ec679 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Fri, 31 Aug 2012 19:59:05 +0200 Subject: [PATCH 05/10] modifications, fixes. first working version with a couple hardware features. --- drivers/gdisp/SSD1963/gdisp_lld.c | 110 +++++++++++------------ drivers/gdisp/SSD1963/gdisp_lld_board.h | 0 drivers/gdisp/SSD1963/gdisp_lld_config.h | 8 +- drivers/gdisp/SSD1963/ssd1963.h | 2 - 4 files changed, 59 insertions(+), 61 deletions(-) create mode 100644 drivers/gdisp/SSD1963/gdisp_lld_board.h diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index ceb9108b..4908ee22 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -88,15 +88,15 @@ __inline void GDISP_LLD(writereg)(uint16_t lcdReg,uint16_t lcdRegValue) { LCD_RAM = lcdRegValue; } -__inline void GDISP_LLD(writedata)(uint8_t data) { +__inline void GDISP_LLD(writedata)(uint16_t data) { LCD_RAM = data; } -__inline void GDISP_LLD(readdata)(uint8_t data) { +__inline uint16_t GDISP_LLD(readdata)(void) { return (LCD_RAM); } -__inline void GDISP_LLD(readreg)(uint8_t lcdReg) { +__inline uint8_t GDISP_LLD(readreg)(uint8_t lcdReg) { LCD_REG = lcdReg; return (LCD_RAM); } @@ -134,7 +134,7 @@ bool_t GDISP_LLD(init)(void) { /* Initialise the GDISP structure to match */ GDISP.Width = SCREEN_WIDTH; GDISP.Height = SCREEN_HEIGHT; - GDISP.Orientation = portrait; + GDISP.Orientation = landscape; GDISP.Powermode = powerOn; GDISP.Backlight = 100; GDISP.Contrast = 50; @@ -177,62 +177,62 @@ bool_t GDISP_LLD(init)(void) { /* Driver PLL config */ GDISP_LLD(writeindex)(SSD1963_SET_PLL_MN); - GDISP_LLD(writestreamstart)(35); // PLLclk = REFclk (10Mhz) * 36 (360Mhz) - GDISP_LLD(writestreamstart)(2); // SYSclk = PLLclk / 3 (120MHz) - GDISP_LLD(writestreamstart)(4); // Apply calculation bit, else it is ignored + GDISP_LLD(writedata)(35); // PLLclk = REFclk (10Mhz) * 36 (360Mhz) + GDISP_LLD(writedata)(2); // SYSclk = PLLclk / 3 (120MHz) + GDISP_LLD(writedata)(4); // Apply calculation bit, else it is ignored GDISP_LLD(writeindex)(SSD1963_SET_PLL); // Enable PLL - GDISP_LLD(writestreamstart)(0x01); - lld_lcdDelay(200); + GDISP_LLD(writedata)(0x01); + chThdSleepMicroseconds(200); GDISP_LLD(writeindex)(SSD1963_SET_PLL); // Use PLL - GDISP_LLD(writestreamstart)(0x03); - lld_lcdDelay(200); + GDISP_LLD(writedata)(0x03); + chThdSleepMicroseconds(200); GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); /* Screen size */ GDISP_LLD(writeindex)(SSD1963_SET_LCD_MODE); -// GDISP_LLD(writestreamstart)(0x0000); - GDISP_LLD(writestreamstart)(0b00011000); - GDISP_LLD(writestreamstart)(0x0000); - GDISP_LLD(writestreamstart)(mHIGH((SCREEN_WIDTH+1))); - GDISP_LLD(writestreamstart)((SCREEN_WIDTH+1)); - GDISP_LLD(writestreamstart)(mHIGH((SCREEN_HEIGHT+1))); - GDISP_LLD(writestreamstart)((SCREEN_HEIGHT+1)); - GDISP_LLD(writestreamstart)(0x0000); +// GDISP_LLD(writedata)(0x0000); + GDISP_LLD(writedata)(0b00011000); + GDISP_LLD(writedata)(0x0000); + GDISP_LLD(writedata)(mHIGH((SCREEN_WIDTH+1))); + GDISP_LLD(writedata)((SCREEN_WIDTH+1)); + GDISP_LLD(writedata)(mHIGH((SCREEN_HEIGHT+1))); + GDISP_LLD(writedata)((SCREEN_HEIGHT+1)); + GDISP_LLD(writedata)(0x0000); GDISP_LLD(writeindex)(SSD1963_SET_PIXEL_DATA_INTERFACE); - GDISP_LLD(writestreamstart)(SSD1963_PDI_16BIT565); + GDISP_LLD(writedata)(SSD1963_PDI_16BIT565); /* LCD Clock specs */ GDISP_LLD(writeindex)(SSD1963_SET_LSHIFT_FREQ); - GDISP_LLD(writestreamstart)((LCD_FPR >> 16) & 0xFF); - GDISP_LLD(writestreamstart)((LCD_FPR >> 8) & 0xFF); - GDISP_LLD(writestreamstart)(LCD_FPR & 0xFF); + GDISP_LLD(writedata)((LCD_FPR >> 16) & 0xFF); + GDISP_LLD(writedata)((LCD_FPR >> 8) & 0xFF); + GDISP_LLD(writedata)(LCD_FPR & 0xFF); GDISP_LLD(writeindex)(SSD1963_SET_HORI_PERIOD); - GDISP_LLD(writestreamstart)(mHIGH(SCREEN_HSYNC_PERIOD)); - GDISP_LLD(writestreamstart)(mLOW(SCREEN_HSYNC_PERIOD)); - GDISP_LLD(writestreamstart)(mHIGH((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); - GDISP_LLD(writestreamstart)(mLOW((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); - GDISP_LLD(writestreamstart)(SCREEN_HSYNC_PULSE); - GDISP_LLD(writestreamstart)(0x00); - GDISP_LLD(writestreamstart)(0x00); - GDISP_LLD(writestreamstart)(0x00); + GDISP_LLD(writedata)(mHIGH(SCREEN_HSYNC_PERIOD)); + GDISP_LLD(writedata)(mLOW(SCREEN_HSYNC_PERIOD)); + GDISP_LLD(writedata)(mHIGH((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); + GDISP_LLD(writedata)(mLOW((SCREEN_HSYNC_PULSE + SCREEN_HSYNC_BACK_PORCH))); + GDISP_LLD(writedata)(SCREEN_HSYNC_PULSE); + GDISP_LLD(writedata)(0x00); + GDISP_LLD(writedata)(0x00); + GDISP_LLD(writedata)(0x00); GDISP_LLD(writeindex)(SSD1963_SET_VERT_PERIOD); - GDISP_LLD(writestreamstart)(mHIGH(SCREEN_VSYNC_PERIOD)); - GDISP_LLD(writestreamstart)(mLOW(SCREEN_VSYNC_PERIOD)); - GDISP_LLD(writestreamstart)(mHIGH((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); - GDISP_LLD(writestreamstart)(mLOW((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); - GDISP_LLD(writestreamstart)(SCREEN_VSYNC_PULSE); - GDISP_LLD(writestreamstart)(0x00); - GDISP_LLD(writestreamstart)(0x00); + GDISP_LLD(writedata)(mHIGH(SCREEN_VSYNC_PERIOD)); + GDISP_LLD(writedata)(mLOW(SCREEN_VSYNC_PERIOD)); + GDISP_LLD(writedata)(mHIGH((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); + GDISP_LLD(writedata)(mLOW((SCREEN_VSYNC_PULSE + SCREEN_VSYNC_BACK_PORCH))); + GDISP_LLD(writedata)(SCREEN_VSYNC_PULSE); + GDISP_LLD(writedata)(0x00); + GDISP_LLD(writedata)(0x00); /* Tear effect indicator ON. This is used to tell the host MCU when the driver is not refreshing the panel */ GDISP_LLD(writeindex)(SSD1963_SET_TEAR_ON); - GDISP_LLD(writestreamstart)(0x0000); + GDISP_LLD(writedata)(0x0000); /* Turn on */ GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); @@ -250,16 +250,16 @@ void GDISP_LLD(setwindow)(coord_t x0, coord_t y0, coord_t x1, coord_t y1) { if (x0 >= GDISP.Width || y0 >= GDISP.Height) return; else if (x1 >= GDISP.Width || y1 >= GDISP.Height) return; #endif - GDISP_LLD(writeindex)(SSD1963_SET_COLUMN_ADDRESS); - GDISP_LLD(writestreamstart)((y0 >> 8) & 0xFF); - GDISP_LLD(writestreamstart)((y0 >> 0) & 0xFF); - GDISP_LLD(writestreamstart)((y1 >> 8) & 0xFF); - GDISP_LLD(writestreamstart)((y1 >> 0) & 0xFF); GDISP_LLD(writeindex)(SSD1963_SET_PAGE_ADDRESS); - GDISP_LLD(writestreamstart)((x0 >> 8) & 0xFF); - GDISP_LLD(writestreamstart)((x0 >> 0) & 0xFF); - GDISP_LLD(writestreamstart)((x1 >> 8) & 0xFF); - GDISP_LLD(writestreamstart)((x1 >> 0) & 0xFF); + GDISP_LLD(writedata)((y0 >> 8) & 0xFF); + GDISP_LLD(writedata)((y0 >> 0) & 0xFF); + GDISP_LLD(writedata)((y1 >> 8) & 0xFF); + GDISP_LLD(writedata)((y1 >> 0) & 0xFF); + GDISP_LLD(writeindex)(SSD1963_SET_COLUMN_ADDRESS); + GDISP_LLD(writedata)((x0 >> 8) & 0xFF); + GDISP_LLD(writedata)((x0 >> 0) & 0xFF); + GDISP_LLD(writedata)((x1 >> 8) & 0xFF); + GDISP_LLD(writedata)((x1 >> 0) & 0xFF); } /** @@ -275,8 +275,9 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { #if GDISP_NEED_VALIDATION if (x >= GDISP.Width || y >= GDISP.Height) return; #endif + GDISP_LLD(setwindow)(x, y, x, y); - GDISP_LLD(writestreamstart); + GDISP_LLD(writestreamstart)(); GDISP_LLD(writedata)(color); } @@ -307,7 +308,7 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { * @notapi */ void GDISP_LLD(clear)(color_t color) { - /* Code here */ + GDISP_LLD(fillarea)(0, 0, GDISP.Width-1, GDISP.Height-1, color); } #endif @@ -349,14 +350,13 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { #endif uint32_t index = 0, area; + area = (cx+1)*(cy+1); - area = ((x1-x0+1)*(y1-y0+1)); - - lld_lcdSetWindow(x0, y0, x1, y1); - lld_lcdwritestreamstart(); + GDISP_LLD(setwindow)(x, y, x+cx, y+cy); + GDISP_LLD(writestreamstart)(); for(index = 0; index <= area; index++) - GDISP_LLD(writestreamstart)(color); + GDISP_LLD(writedata)(color); } #endif diff --git a/drivers/gdisp/SSD1963/gdisp_lld_board.h b/drivers/gdisp/SSD1963/gdisp_lld_board.h new file mode 100644 index 00000000..e69de29b diff --git a/drivers/gdisp/SSD1963/gdisp_lld_config.h b/drivers/gdisp/SSD1963/gdisp_lld_config.h index 25fe76d2..486ab1f2 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_config.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_config.h @@ -35,12 +35,12 @@ /* Driver hardware support. */ /*===========================================================================*/ -#define GDISP_DRIVER_NAME "YourDriverName" -#define GDISP_LLD(x) gdisp_lld_##x##_YourDriverName +#define GDISP_DRIVER_NAME "SSD1963" +#define GDISP_LLD(x) gdisp_lld_##x##_SSD1963 #define GDISP_HARDWARE_LINES FALSE -#define GDISP_HARDWARE_CLEARS FALSE -#define GDISP_HARDWARE_FILLS FALSE +#define GDISP_HARDWARE_CLEARS TRUE +#define GDISP_HARDWARE_FILLS TRUE #define GDISP_HARDWARE_BITFILLS FALSE #define GDISP_HARDWARE_CIRCLES FALSE #define GDISP_HARDWARE_CIRCLEFILLS FALSE diff --git a/drivers/gdisp/SSD1963/ssd1963.h b/drivers/gdisp/SSD1963/ssd1963.h index fcac4e1d..0faa7c4e 100644 --- a/drivers/gdisp/SSD1963/ssd1963.h +++ b/drivers/gdisp/SSD1963/ssd1963.h @@ -135,6 +135,4 @@ #define SSD1963_PDI_9BIT 6 #define SSD1963_GET_PIXEL_DATA_INTERFACE 0x00F1 -#endif - #endif \ No newline at end of file From 3c7ac9c2cf17d7a275ecb6261cc1e48bcf4a5597 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Fri, 31 Aug 2012 20:09:22 +0200 Subject: [PATCH 06/10] updated comments, cleaning --- drivers/gdisp/SSD1963/gdisp_lld.c | 4 ++-- drivers/gdisp/SSD1963/gdisp_lld_board.h | 0 drivers/gdisp/SSD1963/gdisp_lld_config.h | 4 ++-- drivers/gdisp/SSD1963/gdisp_lld_panel.h | 9 ++++++++ drivers/gdisp/SSD1963/readme.txt | 29 +++--------------------- drivers/gdisp/SSD1963/ssd1963.h | 11 ++++++++- 6 files changed, 26 insertions(+), 31 deletions(-) delete mode 100644 drivers/gdisp/SSD1963/gdisp_lld_board.h diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index 4908ee22..e22f2ca1 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -19,8 +19,8 @@ */ /** - * @file templates/gdisp_lld.c - * @brief GDISP Graphics Driver subsystem low level driver source template. + * @file SSD1963/gdisp_lld.c + * @brief GDISP Graphics Driver subsystem low level driver source. * * @addtogroup GDISP * @{ diff --git a/drivers/gdisp/SSD1963/gdisp_lld_board.h b/drivers/gdisp/SSD1963/gdisp_lld_board.h deleted file mode 100644 index e69de29b..00000000 diff --git a/drivers/gdisp/SSD1963/gdisp_lld_config.h b/drivers/gdisp/SSD1963/gdisp_lld_config.h index 486ab1f2..f6c69d92 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_config.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_config.h @@ -19,8 +19,8 @@ */ /** - * @file templates/gdisp_lld_config.h - * @brief GDISP Graphic Driver subsystem low level driver header template. + * @file SSD1963/gdisp_lld_config.h + * @brief GDISP Graphic Driver subsystem low level driver header. * * @addtogroup GDISP * @{ diff --git a/drivers/gdisp/SSD1963/gdisp_lld_panel.h b/drivers/gdisp/SSD1963/gdisp_lld_panel.h index f4a8595b..b2838250 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_panel.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_panel.h @@ -18,6 +18,14 @@ along with this program. If not, see . */ +/** + * @file SSD1963/gdisp_lld_panel.h + * @brief TFT LCD panel properties. + * + * @addtogroup GDISP + * @{ + */ + #ifndef _GDISP_LLD_PANEL_H #define _GDISP_LLD_PANEL_H @@ -42,3 +50,4 @@ #define LCD_FPR ((SCREEN_PCLK * 1048576)/100000000) #endif +/** @} */ \ No newline at end of file diff --git a/drivers/gdisp/SSD1963/readme.txt b/drivers/gdisp/SSD1963/readme.txt index 2496fc51..7803cda0 100644 --- a/drivers/gdisp/SSD1963/readme.txt +++ b/drivers/gdisp/SSD1963/readme.txt @@ -1,35 +1,12 @@ -To use this driver template - 1. Copy this entire directory (including the directory itself) - into halext/drivers - 2. Rename the directory to match your hardware. - 3. Customise each file in the directory including the .mk file - and this file. An example for this file is below... - 4. Keep any board specific code in a file you create called - gdisp_lld_board_yourboardname.h and adjust gdisp.c to match. - This enables someone porting to a new board to add another - suitable boad definition without worrying about the rest of - the driver. See the gdispNokia6610 driver as an example. - ------------------------------------------------------------------- To use this driver: 1. Add in your halconf.h: a) #define HAL_USE_GDISP TRUE b) Any optional high level driver defines (see gdisp.h) eg: GDISP_NEED_MULTITHREAD c) One (only) of: - #define LCD_USE_GPIO - #define LCD_USE_SPI + #define LCD_USE_GPIO (Work in progress) #define LCD_USE_FSMC - d) All of the following (with appropriate values): - #define SCREEN_WIDTH 128 - #define SCREEN_HEIGHT 128 - e) If you are not using a known board then create a gdisp_lld_board.h file - and ensure it is on your include path. - Use the gdisp_lld_board_example.h file as a basis. - Currently known boards are: - XXXXXXXXX - + d) Edit gdisp_lld_panel.h with your panel properties 2. To your makefile add the following lines: - include $(CHIBIOS)/os/halext/halext.mk - include $(CHIBIOS)/os/halext/drivers/gdispXXXXX/gdisp_lld.mk + include $(LCDLIB)/drivers/gdisp/SSD1963/gdisp_lld.mk \ No newline at end of file diff --git a/drivers/gdisp/SSD1963/ssd1963.h b/drivers/gdisp/SSD1963/ssd1963.h index 0faa7c4e..794658e2 100644 --- a/drivers/gdisp/SSD1963/ssd1963.h +++ b/drivers/gdisp/SSD1963/ssd1963.h @@ -18,6 +18,14 @@ along with this program. If not, see . */ +/** + * @file SSD1963/ssd1963.h + * @brief SSD1963 specific data. + * + * @addtogroup GDISP + * @{ + */ + #ifndef SSD1963_H #define SSD1963_H @@ -135,4 +143,5 @@ #define SSD1963_PDI_9BIT 6 #define SSD1963_GET_PIXEL_DATA_INTERFACE 0x00F1 -#endif \ No newline at end of file +#endif +/** @} */ \ No newline at end of file From d6000f1cbb60d3461ba24aa09d5fdae72c5b3914 Mon Sep 17 00:00:00 2001 From: Tectu Date: Mon, 3 Sep 2012 00:50:55 +0200 Subject: [PATCH 07/10] docs update --- docs/contributors.txt | 2 ++ docs/releases.txt | 2 ++ 2 files changed, 4 insertions(+) diff --git a/docs/contributors.txt b/docs/contributors.txt index 2586ed61..654e1540 100644 --- a/docs/contributors.txt +++ b/docs/contributors.txt @@ -6,6 +6,8 @@ At this point we want to thank all of these people for their work. NickName RealName Contribution ======== ======== ============ +Mobyfab Fabien Poussin SSD1289 driver + inmarket Andrew Hannam GDISP (restructorizing the entire library) VMT ASYNC and MULTITHREAD implementation diff --git a/docs/releases.txt b/docs/releases.txt index f895106e..c00de18d 100644 --- a/docs/releases.txt +++ b/docs/releases.txt @@ -4,4 +4,6 @@ *** 0.1.0 *** FIX: removed gdisp and touchpad prefix of driver directories +FIX: added SSD1289 driver (by Mobyfab) + From bdd794b8361d5bfeb6b32e1b62bdf932dad405c3 Mon Sep 17 00:00:00 2001 From: Tectu Date: Mon, 3 Sep 2012 00:52:40 +0200 Subject: [PATCH 08/10] header adjustments on SSD1963 --- drivers/gdisp/SSD1963/gdisp_lld.c | 2 +- drivers/gdisp/SSD1963/gdisp_lld_config.h | 2 +- drivers/gdisp/SSD1963/gdisp_lld_panel.h | 6 +++--- drivers/gdisp/SSD1963/ssd1963.h | 6 +++--- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index e22f2ca1..0615e25c 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -1,5 +1,5 @@ /* - ChibiOS/RT - Copyright (C) 2012 + ChibiOS-LCD-Driver - Copyright (C) 2012 Joel Bodenmann aka Tectu This file is part of ChibiOS-LCD-Driver. diff --git a/drivers/gdisp/SSD1963/gdisp_lld_config.h b/drivers/gdisp/SSD1963/gdisp_lld_config.h index f6c69d92..85dd7282 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_config.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_config.h @@ -1,5 +1,5 @@ /* - ChibiOS/RT - Copyright (C) 2012 + ChibiOS-LCD-Driver Copyright (C) 2012 Joel Bodenmann aka Tectu This file is part of ChibiOS-LCD-Driver. diff --git a/drivers/gdisp/SSD1963/gdisp_lld_panel.h b/drivers/gdisp/SSD1963/gdisp_lld_panel.h index b2838250..6d13155c 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_panel.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_panel.h @@ -1,6 +1,6 @@ /* - ChibiOS/RT - Copyright (C) 2012 - Fabien Poussin aka Mobyfab + ChibiOS-LCD-Driver Copyright (C) 2012 + Joel Bodenmann aka Tectu This file is part of ChibiOS-LCD-Driver. @@ -50,4 +50,4 @@ #define LCD_FPR ((SCREEN_PCLK * 1048576)/100000000) #endif -/** @} */ \ No newline at end of file +/** @} */ diff --git a/drivers/gdisp/SSD1963/ssd1963.h b/drivers/gdisp/SSD1963/ssd1963.h index 794658e2..19e3094a 100644 --- a/drivers/gdisp/SSD1963/ssd1963.h +++ b/drivers/gdisp/SSD1963/ssd1963.h @@ -1,6 +1,6 @@ /* - ChibiOS/RT - Copyright (C) 2012 - Fabien Poussin aka Mobyfab + ChibiOS-LCD-Driver - Copyright (C) 2012 + Joel Bodenmann aka Tectu This file is part of ChibiOS-LCD-Driver. @@ -144,4 +144,4 @@ #define SSD1963_GET_PIXEL_DATA_INTERFACE 0x00F1 #endif -/** @} */ \ No newline at end of file +/** @} */ From f47bbcb9a70abcfe7a281b468398143b9a4bf184 Mon Sep 17 00:00:00 2001 From: Tectu Date: Mon, 3 Sep 2012 00:54:40 +0200 Subject: [PATCH 09/10] docs --- docs/releases.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/releases.txt b/docs/releases.txt index c00de18d..47073038 100644 --- a/docs/releases.txt +++ b/docs/releases.txt @@ -4,6 +4,6 @@ *** 0.1.0 *** FIX: removed gdisp and touchpad prefix of driver directories -FIX: added SSD1289 driver (by Mobyfab) +UPDATE: added SSD1289 driver (by Mobyfab) From 75a3a98228913840c8f63e7e80118b18b29dc109 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Tue, 4 Sep 2012 12:51:35 +0200 Subject: [PATCH 10/10] Adding GPIO to SSD1963 --- drivers/gdisp/SSD1963/gdisp_lld.c | 132 ++++++++++++++++++++++++------ drivers/gdisp/SSD1963/ssd1963.h | 16 ++-- 2 files changed, 112 insertions(+), 36 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index 0615e25c..750affc4 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -29,7 +29,6 @@ #include "ch.h" #include "hal.h" #include "gdisp.h" -#include "ssd1963.h" #if HAL_USE_GDISP || defined(__DOXYGEN__) @@ -74,11 +73,10 @@ /* Driver exported functions. */ /*===========================================================================*/ -/* ---- Required Routines ---- */ -/* - The following 2 routines are required. - All other routines are optional. -*/ +#include "ssd1963.h" + + +#if defined(LCD_USE_FSMC) __inline void GDISP_LLD(writeindex)(uint8_t cmd) { LCD_REG = cmd; } @@ -102,11 +100,11 @@ __inline uint8_t GDISP_LLD(readreg)(uint8_t lcdReg) { } __inline void GDISP_LLD(writestreamstart)(void) { - LCD_REG = SSD1963_WRITE_MEMORY_START; + GDISP_LLD(writeindex)(SSD1963_WRITE_MEMORY_START); } __inline void GDISP_LLD(readstreamstart)(void) { - LCD_REG = SSD1963_READ_MEMORY_START; + GDISP_LLD(writeindex)(SSD1963_READ_MEMORY_START); } __inline void GDISP_LLD(writestream)(uint16_t *buffer, uint16_t size) { @@ -122,6 +120,80 @@ __inline void GDISP_LLD(readstream)(uint16_t *buffer, size_t size) { buffer[i] = LCD_RAM; } } + +#elif defined(LCD_USE_GPIO) + +__inline void GDISP_LLD(writeindex)(uint8_t cmd) { + Set_CS; Set_RS; Set_WR; Clr_RD; + palWritePort(LCD_DATA_PORT, cmd); + Clr_CS; +} + +__inline void GDISP_LLD(writereg)(uint16_t lcdReg,uint16_t lcdRegValue) { + Set_CS; Set_RS; Set_WR; Clr_RD; + palWritePort(LCD_DATA_PORT, lcdReg); + Clr_RS; + palWritePort(LCD_DATA_PORT, lcdRegValue); + Clr_CS; +} +__inline void GDISP_LLD(writedata)(uint16_t data) { + Set_CS; Clr_RS; Set_WR; Clr_RD; + palWritePort(LCD_DATA_PORT, data); + Clr_CS; +} + +__inline uint16_t GDISP_LLD(readdata)(void) { + Set_CS; Clr_RS; Clr_WR; Set_RD; + uint16_t data = palReadPort(LCD_DATA_PORT); + Clr_CS; + return data; +} + +__inline uint8_t GDISP_LLD(readreg)(uint8_t lcdReg) { + Set_CS; Set_RS; Clr_WR; Set_RD; + palWritePort(LCD_DATA_PORT, lcdReg); + Clr_RS; + uint16_t data = palReadPort(LCD_DATA_PORT); + Clr_CS; + return data; +} + +__inline void GDISP_LLD(writestreamstart)(void) { + GDISP_LLD(writeindex)(SSD1963_WRITE_MEMORY_START); +} + +__inline void GDISP_LLD(readstreamstart)(void) { + GDISP_LLD(writeindex)(SSD1963_READ_MEMORY_START); +} + +__inline void GDISP_LLD(writestream)(uint16_t *buffer, uint16_t size) { + uint16_t i; + Set_CS; Clr_RS; Set_WR; Clr_RD; + for(i = 0; i < size; i++) { + Set_WR; + palWritePort(LCD_DATA_PORT, buffer[i]); + Clr_WR; + } + Clr_CS; +} + +__inline void GDISP_LLD(readstream)(uint16_t *buffer, size_t size) { + uint16_t i; + Set_CS; Clr_RS; Clr_WR; Set_RD; + for(i = 0; i < size; i++) { + Set_RD; + buffer[i] = palReadPort(LCD_DATA_PORT); + Clr_RD; + } +} +#endif + +/* ---- Required Routines ---- */ +/* + The following 2 routines are required. + All other routines are optional. +*/ + /** * @brief Low level GDISP driver initialisation. * @return TRUE if successful, FALSE on error. @@ -139,17 +211,19 @@ bool_t GDISP_LLD(init)(void) { GDISP.Backlight = 100; GDISP.Contrast = 50; -#ifdef LCD_USE_FSMC +#if defined(LCD_USE_FSMC) -#if defined(STM32F1XX) - /* FSMC setup. TODO: this only works for STM32F1 */ + #if defined(STM32F1XX) || defined(STM32F3XX) + /* FSMC setup for F1/F3 */ rccEnableAHB(RCC_AHBENR_FSMCEN, 0); - /* TODO: pin setup */ -#elif defined(STM32F4XX) - /* STM32F4 FSMC init */ + #elif defined(STM32F4XX) || defined(STM32F2XX) + /* STM32F2-F4 FSMC init */ rccEnableAHB3(RCC_AHB3ENR_FSMCEN, 0); - + #else + #error "FSMC not implemented for this device" + #endif + /* set pins to FSMC mode */ IOBus busD = {GPIOD, (1 << 0) | (1 << 1) | (1 << 4) | (1 << 5) | (1 << 7) | (1 << 8) | (1 << 9) | (1 << 10) | (1 << 11) | (1 << 14) | (1 << 15), 0}; @@ -159,10 +233,8 @@ bool_t GDISP_LLD(init)(void) { palSetBusMode(&busD, PAL_MODE_ALTERNATE(12)); palSetBusMode(&busE, PAL_MODE_ALTERNATE(12)); -#else -#error "FSMC not implemented for this device" -#endif - const int FSMC_Bank = 0; + + const unsigned char FSMC_Bank = 0; /* FSMC timing */ FSMC_Bank1->BTCR[FSMC_Bank+1] = (FSMC_BTR1_ADDSET_1 | FSMC_BTR1_ADDSET_3) \ | (FSMC_BTR1_DATAST_1 | FSMC_BTR1_DATAST_3) \ @@ -171,9 +243,18 @@ bool_t GDISP_LLD(init)(void) { /* Bank1 NOR/SRAM control register configuration * This is actually not needed as already set by default after reset */ FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; -#endif - - GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); + + #elif defined(LCD_USE_GPIO) + IOBus busCMD = {LCD_CMD_PORT, (1 << LCD_CS) | (1 << LCD_RS) | (1 << LCD_WR) | (1 << LCD_RD), 0}; + IOBus busDATA = {LCD_CMD_PORT, 0xFFFFF, 0}; + palSetBusMode(&busCMD, PAL_MODE_OUTPUT_PUSHPULL); + palSetBusMode(&busDATA, PAL_MODE_OUTPUT_PUSHPULL); + + #else + #error "Please define LCD_USE_FSMC or LCD_USE_GPIO" +#endif + GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); + chThdSleepMicroseconds(100); /* Driver PLL config */ GDISP_LLD(writeindex)(SSD1963_SET_PLL_MN); @@ -189,7 +270,8 @@ bool_t GDISP_LLD(init)(void) { GDISP_LLD(writedata)(0x03); chThdSleepMicroseconds(200); - GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); + GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); + chThdSleepMicroseconds(100); /* Screen size */ GDISP_LLD(writeindex)(SSD1963_SET_LCD_MODE); @@ -236,9 +318,9 @@ bool_t GDISP_LLD(init)(void) { /* Turn on */ GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); -#ifdef LCD_USE_FSMC +#if defined(LCD_USE_FSMC) /* FSMC delay reduced as the controller now runs at full speed */ - FSMC_Bank1->BTCR[FSMC_Bank+1] = FSMC_BTR1_ADDSET_0 | (FSMC_BTR1_DATAST_2 | FSMC_BTR1_DATAST_0) | FSMC_BTR1_BUSTURN_0 ; + FSMC_Bank1->BTCR[FSMC_Bank+1] = FSMC_BTR1_ADDSET_0 | FSMC_BTR1_DATAST_1 | FSMC_BTR1_BUSTURN_0 ; FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; #endif diff --git a/drivers/gdisp/SSD1963/ssd1963.h b/drivers/gdisp/SSD1963/ssd1963.h index 19e3094a..198a160b 100644 --- a/drivers/gdisp/SSD1963/ssd1963.h +++ b/drivers/gdisp/SSD1963/ssd1963.h @@ -31,7 +31,7 @@ #include "gdisp_lld_panel.h" -#ifdef LCD_USE_GPIO +#if defined(LCD_USE_GPIO) #define Set_CS palSetPad(LCD_CMD_PORT, LCD_CS); #define Clr_CS palClearPad(LCD_CMD_PORT, LCD_CS); #define Set_RS palSetPad(LCD_CMD_PORT, LCD_RS); @@ -42,16 +42,10 @@ #define Clr_RD palClearPad(LCD_CMD_PORT, LCD_RD); #endif -#ifdef LCD_USE_SPI - /* TODO */ -#endif - -#ifdef LCD_USE_FSMC - -/* Using FSMC A16 as RS */ -#define LCD_REG (*((volatile uint16_t *) 0x60000000)) /* RS = 0 */ -#define LCD_RAM (*((volatile uint16_t *) 0x60020000)) /* RS = 1 */ - +#if defined(LCD_USE_FSMC) + /* Using FSMC A16 as RS */ + #define LCD_REG (*((volatile uint16_t *) 0x60000000)) /* RS = 0 */ + #define LCD_RAM (*((volatile uint16_t *) 0x60020000)) /* RS = 1 */ #endif #define mHIGH(x) (x >> 8)