A ST7565R display driver written with backbuffering capabilities. Model used and tested: NHD-C12832A1Z-FSW-FBW-3V3
ST7565R.cpp@0:59cb20947fd6, 2011-08-11 (annotated)
- Committer:
- celeritous
- Date:
- Thu Aug 11 16:00:05 2011 +0000
- Revision:
- 0:59cb20947fd6
Added doxygen tags.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
celeritous | 0:59cb20947fd6 | 1 | |
celeritous | 0:59cb20947fd6 | 2 | #include "ST7565R.h" |
celeritous | 0:59cb20947fd6 | 3 | #include "mbed.h" |
celeritous | 0:59cb20947fd6 | 4 | |
celeritous | 0:59cb20947fd6 | 5 | ST7565R::ST7565R(PinName cs, PinName a0, PinName scl, PinName si, PinName rst, bool BackBuffer) : _cs(cs), _a0(a0), _spi(si, NC, scl), _rst(rst) |
celeritous | 0:59cb20947fd6 | 6 | { |
celeritous | 0:59cb20947fd6 | 7 | _spi.format(8,3); |
celeritous | 0:59cb20947fd6 | 8 | _spi.frequency(20000000); //datasheet 50 ns sclk |
celeritous | 0:59cb20947fd6 | 9 | _rst=1; |
celeritous | 0:59cb20947fd6 | 10 | _a0=0; |
celeritous | 0:59cb20947fd6 | 11 | _cs=1; |
celeritous | 0:59cb20947fd6 | 12 | scr=1; |
celeritous | 0:59cb20947fd6 | 13 | reset(); |
celeritous | 0:59cb20947fd6 | 14 | UsingBackBuffer = BackBuffer; |
celeritous | 0:59cb20947fd6 | 15 | } |
celeritous | 0:59cb20947fd6 | 16 | |
celeritous | 0:59cb20947fd6 | 17 | void ST7565R::reset() |
celeritous | 0:59cb20947fd6 | 18 | { |
celeritous | 0:59cb20947fd6 | 19 | _rst = 0; |
celeritous | 0:59cb20947fd6 | 20 | wait_ms(1); |
celeritous | 0:59cb20947fd6 | 21 | _rst = 1; |
celeritous | 0:59cb20947fd6 | 22 | wait_ms(1); |
celeritous | 0:59cb20947fd6 | 23 | command(0xA0); |
celeritous | 0:59cb20947fd6 | 24 | command(0xAF); |
celeritous | 0:59cb20947fd6 | 25 | command(0xC0); |
celeritous | 0:59cb20947fd6 | 26 | command(0xA2); |
celeritous | 0:59cb20947fd6 | 27 | command(0x2F); |
celeritous | 0:59cb20947fd6 | 28 | command(0x24); |
celeritous | 0:59cb20947fd6 | 29 | command(0x81); |
celeritous | 0:59cb20947fd6 | 30 | command(0x00); |
celeritous | 0:59cb20947fd6 | 31 | command(0xA7); |
celeritous | 0:59cb20947fd6 | 32 | |
celeritous | 0:59cb20947fd6 | 33 | |
celeritous | 0:59cb20947fd6 | 34 | clearBuffer(); |
celeritous | 0:59cb20947fd6 | 35 | |
celeritous | 0:59cb20947fd6 | 36 | } |
celeritous | 0:59cb20947fd6 | 37 | #define FONT_SIZE_X 6 |
celeritous | 0:59cb20947fd6 | 38 | #define FONT_SIZE_Y 8 |
celeritous | 0:59cb20947fd6 | 39 | void ST7565R::moveto(int col, int row) |
celeritous | 0:59cb20947fd6 | 40 | { |
celeritous | 0:59cb20947fd6 | 41 | _column = col; |
celeritous | 0:59cb20947fd6 | 42 | _row = row; |
celeritous | 0:59cb20947fd6 | 43 | } |
celeritous | 0:59cb20947fd6 | 44 | void ST7565R::character(int column, int row, char c) |
celeritous | 0:59cb20947fd6 | 45 | { |
celeritous | 0:59cb20947fd6 | 46 | char v = c - 0x20; |
celeritous | 0:59cb20947fd6 | 47 | if (c >= 0x20 && c < 0x80) |
celeritous | 0:59cb20947fd6 | 48 | { |
celeritous | 0:59cb20947fd6 | 49 | c-=0x20; |
celeritous | 0:59cb20947fd6 | 50 | bitblt(column*FONT_SIZE_X,row*FONT_SIZE_Y, |
celeritous | 0:59cb20947fd6 | 51 | FONT_SIZE_X, FONT_SIZE_Y, (char*)TEXT, |
celeritous | 0:59cb20947fd6 | 52 | TEXT_WIDTH, TEXT_HEIGHT, |
celeritous | 0:59cb20947fd6 | 53 | (v%0x10) * FONT_SIZE_X, (v/0x10)*FONT_SIZE_Y,BITBLT_SRCCOPY); |
celeritous | 0:59cb20947fd6 | 54 | } |
celeritous | 0:59cb20947fd6 | 55 | } |
celeritous | 0:59cb20947fd6 | 56 | int ST7565R::_putc(int value) { |
celeritous | 0:59cb20947fd6 | 57 | if (value == '\n') { |
celeritous | 0:59cb20947fd6 | 58 | _column = 0; |
celeritous | 0:59cb20947fd6 | 59 | _row++; |
celeritous | 0:59cb20947fd6 | 60 | if (_row >= rows()) { |
celeritous | 0:59cb20947fd6 | 61 | _row = 0; |
celeritous | 0:59cb20947fd6 | 62 | } |
celeritous | 0:59cb20947fd6 | 63 | } else { |
celeritous | 0:59cb20947fd6 | 64 | character(_column, _row, value); |
celeritous | 0:59cb20947fd6 | 65 | _column++; |
celeritous | 0:59cb20947fd6 | 66 | if (_column >= columns()) { |
celeritous | 0:59cb20947fd6 | 67 | _column = 0; |
celeritous | 0:59cb20947fd6 | 68 | _row++; |
celeritous | 0:59cb20947fd6 | 69 | if (_row >= rows()) { |
celeritous | 0:59cb20947fd6 | 70 | _row = 0; |
celeritous | 0:59cb20947fd6 | 71 | } |
celeritous | 0:59cb20947fd6 | 72 | } |
celeritous | 0:59cb20947fd6 | 73 | } |
celeritous | 0:59cb20947fd6 | 74 | return value; |
celeritous | 0:59cb20947fd6 | 75 | } |
celeritous | 0:59cb20947fd6 | 76 | |
celeritous | 0:59cb20947fd6 | 77 | int ST7565R::rows() { return 4; } |
celeritous | 0:59cb20947fd6 | 78 | int ST7565R::columns() { return 21; } |
celeritous | 0:59cb20947fd6 | 79 | int ST7565R::_getc() { |
celeritous | 0:59cb20947fd6 | 80 | return -1; |
celeritous | 0:59cb20947fd6 | 81 | } |
celeritous | 0:59cb20947fd6 | 82 | |
celeritous | 0:59cb20947fd6 | 83 | |
celeritous | 0:59cb20947fd6 | 84 | void ST7565R::clearBuffer() |
celeritous | 0:59cb20947fd6 | 85 | { |
celeritous | 0:59cb20947fd6 | 86 | |
celeritous | 0:59cb20947fd6 | 87 | char * screen =getDrawingScreen(); |
celeritous | 0:59cb20947fd6 | 88 | int i=512; |
celeritous | 0:59cb20947fd6 | 89 | while(i--) |
celeritous | 0:59cb20947fd6 | 90 | screen[i]=0xff; |
celeritous | 0:59cb20947fd6 | 91 | |
celeritous | 0:59cb20947fd6 | 92 | |
celeritous | 0:59cb20947fd6 | 93 | if (!UsingBackBuffer) |
celeritous | 0:59cb20947fd6 | 94 | swapBuffers(); //should just commit the white to memory |
celeritous | 0:59cb20947fd6 | 95 | } |
celeritous | 0:59cb20947fd6 | 96 | void ST7565R::setpixel(int x, int y) |
celeritous | 0:59cb20947fd6 | 97 | { |
celeritous | 0:59cb20947fd6 | 98 | if (x < 0 || x > 127) return; |
celeritous | 0:59cb20947fd6 | 99 | if (y < 0 || y > 31) return; |
celeritous | 0:59cb20947fd6 | 100 | char * screen = getDrawingScreen(); |
celeritous | 0:59cb20947fd6 | 101 | loc_t byte = { x , (y / 8) * 128}; |
celeritous | 0:59cb20947fd6 | 102 | screen[byte.y + byte.x] |= 0x80 >> (y%8); |
celeritous | 0:59cb20947fd6 | 103 | |
celeritous | 0:59cb20947fd6 | 104 | //if theres no backbuffer,then we'll do our writes immediately |
celeritous | 0:59cb20947fd6 | 105 | if (!UsingBackBuffer) |
celeritous | 0:59cb20947fd6 | 106 | { |
celeritous | 0:59cb20947fd6 | 107 | command(0xb0 | ( (3-(y/8))+scr*4)); |
celeritous | 0:59cb20947fd6 | 108 | command(0x10 | (x >> 4)); //column upper |
celeritous | 0:59cb20947fd6 | 109 | command(0x00 | (x & 0x0f)); //column lower |
celeritous | 0:59cb20947fd6 | 110 | data(screen[byte.y +byte.x]); |
celeritous | 0:59cb20947fd6 | 111 | } |
celeritous | 0:59cb20947fd6 | 112 | } |
celeritous | 0:59cb20947fd6 | 113 | |
celeritous | 0:59cb20947fd6 | 114 | void ST7565R::clearpixel(int x, int y) |
celeritous | 0:59cb20947fd6 | 115 | { |
celeritous | 0:59cb20947fd6 | 116 | if (x < 0 || x > 127) return; |
celeritous | 0:59cb20947fd6 | 117 | if (y < 0 || y > 31) return; |
celeritous | 0:59cb20947fd6 | 118 | char * screen = getDrawingScreen(); |
celeritous | 0:59cb20947fd6 | 119 | loc_t byte = { x , (y / 8) * 128}; |
celeritous | 0:59cb20947fd6 | 120 | screen[byte.y + byte.x] &= ~(0x80 >> (y%8)); |
celeritous | 0:59cb20947fd6 | 121 | |
celeritous | 0:59cb20947fd6 | 122 | //if theres no backbuffer,then we'll do our writes immediately |
celeritous | 0:59cb20947fd6 | 123 | if (!UsingBackBuffer) |
celeritous | 0:59cb20947fd6 | 124 | { |
celeritous | 0:59cb20947fd6 | 125 | command(0xb0 | ( (3-(y/8))+scr*4)); |
celeritous | 0:59cb20947fd6 | 126 | command(0x10 | (x >> 4)); //column upper |
celeritous | 0:59cb20947fd6 | 127 | command(0x00 | (x & 0x0f)); //column lower |
celeritous | 0:59cb20947fd6 | 128 | data(screen[byte.y +byte.x]); |
celeritous | 0:59cb20947fd6 | 129 | } |
celeritous | 0:59cb20947fd6 | 130 | } |
celeritous | 0:59cb20947fd6 | 131 | |
celeritous | 0:59cb20947fd6 | 132 | void ST7565R::data(int value) |
celeritous | 0:59cb20947fd6 | 133 | { |
celeritous | 0:59cb20947fd6 | 134 | _cs = 0; |
celeritous | 0:59cb20947fd6 | 135 | _a0 = 1; |
celeritous | 0:59cb20947fd6 | 136 | _spi.write(value); |
celeritous | 0:59cb20947fd6 | 137 | _cs = 1; |
celeritous | 0:59cb20947fd6 | 138 | |
celeritous | 0:59cb20947fd6 | 139 | } |
celeritous | 0:59cb20947fd6 | 140 | void ST7565R::command(int value) |
celeritous | 0:59cb20947fd6 | 141 | { |
celeritous | 0:59cb20947fd6 | 142 | _cs = 0; |
celeritous | 0:59cb20947fd6 | 143 | _a0 = 0; |
celeritous | 0:59cb20947fd6 | 144 | _spi.write(value); |
celeritous | 0:59cb20947fd6 | 145 | _cs = 1; |
celeritous | 0:59cb20947fd6 | 146 | } |
celeritous | 0:59cb20947fd6 | 147 | |
celeritous | 0:59cb20947fd6 | 148 | void ST7565R::swapBuffers() |
celeritous | 0:59cb20947fd6 | 149 | { |
celeritous | 0:59cb20947fd6 | 150 | char * screen = getDrawingScreen(); |
celeritous | 0:59cb20947fd6 | 151 | for (int i=0; i<4; i++) |
celeritous | 0:59cb20947fd6 | 152 | { |
celeritous | 0:59cb20947fd6 | 153 | |
celeritous | 0:59cb20947fd6 | 154 | command(0xb0 | ( (3-i)+scr*4)); |
celeritous | 0:59cb20947fd6 | 155 | command(0x10); |
celeritous | 0:59cb20947fd6 | 156 | command(0x00); |
celeritous | 0:59cb20947fd6 | 157 | for (int j=0; j<128; j++) |
celeritous | 0:59cb20947fd6 | 158 | { |
celeritous | 0:59cb20947fd6 | 159 | data(screen[i*128+j]); |
celeritous | 0:59cb20947fd6 | 160 | } |
celeritous | 0:59cb20947fd6 | 161 | } |
celeritous | 0:59cb20947fd6 | 162 | command(0x40 | scr * 32); |
celeritous | 0:59cb20947fd6 | 163 | if (UsingBackBuffer) scr^=1; |
celeritous | 0:59cb20947fd6 | 164 | } |
celeritous | 0:59cb20947fd6 | 165 | #define SCREEN_1 0 |
celeritous | 0:59cb20947fd6 | 166 | #define SCREEN_2 1 |
celeritous | 0:59cb20947fd6 | 167 | |
celeritous | 0:59cb20947fd6 | 168 | |
celeritous | 0:59cb20947fd6 | 169 | char * ST7565R::getDrawingScreen() |
celeritous | 0:59cb20947fd6 | 170 | { |
celeritous | 0:59cb20947fd6 | 171 | if (scr) |
celeritous | 0:59cb20947fd6 | 172 | return screen.screen1; |
celeritous | 0:59cb20947fd6 | 173 | else |
celeritous | 0:59cb20947fd6 | 174 | return screen.screen2; |
celeritous | 0:59cb20947fd6 | 175 | } |
celeritous | 0:59cb20947fd6 | 176 | void ST7565R::bitblt(int dstx, int dsty, |
celeritous | 0:59cb20947fd6 | 177 | int blit_width, int blit_height, |
celeritous | 0:59cb20947fd6 | 178 | char* img, |
celeritous | 0:59cb20947fd6 | 179 | int img_width, int img_height, |
celeritous | 0:59cb20947fd6 | 180 | int srcx, int srcy, |
celeritous | 0:59cb20947fd6 | 181 | int format) |
celeritous | 0:59cb20947fd6 | 182 | { |
celeritous | 0:59cb20947fd6 | 183 | char * current_draw_buffer = getDrawingScreen(); |
celeritous | 0:59cb20947fd6 | 184 | bool pixel = 0; |
celeritous | 0:59cb20947fd6 | 185 | int byte_size_wide = img_width / 8; |
celeritous | 0:59cb20947fd6 | 186 | for (int i=0; i < blit_height; i++) |
celeritous | 0:59cb20947fd6 | 187 | { |
celeritous | 0:59cb20947fd6 | 188 | for (int j=0; j < blit_width; j++) |
celeritous | 0:59cb20947fd6 | 189 | { |
celeritous | 0:59cb20947fd6 | 190 | pixel = img[ byte_size_wide*(srcy+i) + (srcx+j)/8] & (0x80 >> ((srcx+j)%8)); |
celeritous | 0:59cb20947fd6 | 191 | |
celeritous | 0:59cb20947fd6 | 192 | switch(format) |
celeritous | 0:59cb20947fd6 | 193 | { |
celeritous | 0:59cb20947fd6 | 194 | case BITBLT_SRCCOPY: if (pixel) setpixel(dstx+j,dsty+i); else |
celeritous | 0:59cb20947fd6 | 195 | clearpixel(dstx+j,dsty+i); break; |
celeritous | 0:59cb20947fd6 | 196 | case BITBLT_SRCOR: if (pixel) setpixel(dstx+j,dsty+i); break; |
celeritous | 0:59cb20947fd6 | 197 | case BITBLT_SRCAND: if (!pixel) clearpixel(dstx+j,dsty+i); break; |
celeritous | 0:59cb20947fd6 | 198 | } |
celeritous | 0:59cb20947fd6 | 199 | } |
celeritous | 0:59cb20947fd6 | 200 | } |
celeritous | 0:59cb20947fd6 | 201 | |
celeritous | 0:59cb20947fd6 | 202 | } |