for

Dependents:   LV_FGSE_Controller_Interface

Committer:
wim
Date:
Sat Feb 09 15:10:36 2013 +0000
Revision:
13:24506ba22480
Parent:
12:6bf9d9957d31
Child:
14:0c32b66b14b8
First version with I2C interface, refactored code

Who changed what in which revision?

UserRevisionLine numberNew contents of line
simon 1:ac48b187213c 1 /* mbed TextLCD Library, for a 4-bit LCD based on HD44780
simon 6:e4cb7ddee0d3 2 * Copyright (c) 2007-2010, sford, http://mbed.org
wim 12:6bf9d9957d31 3 * 2013, WH, Added LCD types, fixed LCD address issues, added Cursor and UDCs
simon 1:ac48b187213c 4 *
simon 1:ac48b187213c 5 * Permission is hereby granted, free of charge, to any person obtaining a copy
simon 1:ac48b187213c 6 * of this software and associated documentation files (the "Software"), to deal
simon 1:ac48b187213c 7 * in the Software without restriction, including without limitation the rights
simon 1:ac48b187213c 8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
simon 1:ac48b187213c 9 * copies of the Software, and to permit persons to whom the Software is
simon 1:ac48b187213c 10 * furnished to do so, subject to the following conditions:
simon 1:ac48b187213c 11 *
simon 1:ac48b187213c 12 * The above copyright notice and this permission notice shall be included in
simon 1:ac48b187213c 13 * all copies or substantial portions of the Software.
simon 1:ac48b187213c 14 *
simon 1:ac48b187213c 15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
simon 1:ac48b187213c 16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
simon 1:ac48b187213c 17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
simon 1:ac48b187213c 18 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
simon 1:ac48b187213c 19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
simon 1:ac48b187213c 20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
simon 1:ac48b187213c 21 * THE SOFTWARE.
simon 1:ac48b187213c 22 */
simon 1:ac48b187213c 23
simon 1:ac48b187213c 24 #include "TextLCD.h"
simon 1:ac48b187213c 25 #include "mbed.h"
simon 1:ac48b187213c 26
wim 13:24506ba22480 27 TextLCD::TextLCD(PinName rs, PinName e,
wim 13:24506ba22480 28 PinName d4, PinName d5, PinName d6, PinName d7,
wim 13:24506ba22480 29 LCDType type): _rs(rs), _e(e),
wim 13:24506ba22480 30 _d(d4, d5, d6, d7),
wim 13:24506ba22480 31 _type(type) {
wim 13:24506ba22480 32
wim 13:24506ba22480 33
wim 13:24506ba22480 34 _busType = _PinBus;
wim 13:24506ba22480 35
wim 13:24506ba22480 36 _init();
wim 13:24506ba22480 37
wim 13:24506ba22480 38 }
wim 13:24506ba22480 39
wim 13:24506ba22480 40
wim 13:24506ba22480 41 TextLCD::TextLCD(I2C *i2c, char deviceAddress, LCDType type) :
wim 13:24506ba22480 42 _rs(NC), _e(NC), _d(NC),
wim 13:24506ba22480 43 _i2c(i2c),
simon 1:ac48b187213c 44 _type(type) {
wim 13:24506ba22480 45
wim 13:24506ba22480 46 _slaveAddress = deviceAddress;
wim 13:24506ba22480 47 _busType = _I2CBus;
simon 1:ac48b187213c 48
wim 13:24506ba22480 49
wim 13:24506ba22480 50 // Init the portexpander bus
wim 13:24506ba22480 51 _lcd_bus = 0x80;
wim 13:24506ba22480 52
wim 13:24506ba22480 53 // write the new data to the portexpander
wim 13:24506ba22480 54 _i2c->write(_slaveAddress, &_lcd_bus, 1);
wim 13:24506ba22480 55
wim 13:24506ba22480 56 _init();
wim 13:24506ba22480 57
wim 13:24506ba22480 58 }
simon 1:ac48b187213c 59
wim 13:24506ba22480 60 /** Init the LCD controller
wim 13:24506ba22480 61 * 4-bit mode, number of lines, no cursor etc
wim 13:24506ba22480 62 * Clear display
wim 13:24506ba22480 63 */
wim 13:24506ba22480 64 void TextLCD::_init() {
wim 13:24506ba22480 65 // _e = 1;
wim 13:24506ba22480 66 // _rs = 0; // command mode
wim 13:24506ba22480 67
wim 13:24506ba22480 68 _setEnable(true);
wim 13:24506ba22480 69 _setRS(false); // command mode
wim 13:24506ba22480 70
simon 1:ac48b187213c 71 wait(0.015); // Wait 15ms to ensure powered up
simon 1:ac48b187213c 72
simon 1:ac48b187213c 73 // send "Display Settings" 3 times (Only top nibble of 0x30 as we've got 4-bit bus)
simon 1:ac48b187213c 74 for (int i=0; i<3; i++) {
wim 13:24506ba22480 75 _writeByte(0x3);
simon 1:ac48b187213c 76 wait(0.00164); // this command takes 1.64ms, so wait for it
simon 1:ac48b187213c 77 }
wim 13:24506ba22480 78 _writeByte(0x2); // 4-bit mode
wim 13:24506ba22480 79 wait(0.000040f); // most instructions take 40us
simon 1:ac48b187213c 80
wim 10:dd9b3a696acd 81 // Display is now in 4-bit mode
wim 10:dd9b3a696acd 82 switch (_type) {
wim 10:dd9b3a696acd 83 case LCD8x1:
wim 13:24506ba22480 84 _writeCommand(0x20); // Function set 001 BW N F - -
wim 13:24506ba22480 85 // N=0 (1 line)
wim 13:24506ba22480 86 // F=0 (5x7 dots font)
wim 10:dd9b3a696acd 87 break;
wim 10:dd9b3a696acd 88
wim 10:dd9b3a696acd 89 case LCD24x4:
wim 10:dd9b3a696acd 90 // Special mode for KS0078
wim 13:24506ba22480 91 _writeCommand(0x2A); // Function set 001 BW N RE DH REV
wim 13:24506ba22480 92 // N=1 (Dont care for KS0078)
wim 13:24506ba22480 93 // RE=0 (Extended Regs, special mode for KS0078)
wim 13:24506ba22480 94 // DH=1 (Disp shift, special mode for KS0078)
wim 13:24506ba22480 95 // REV=0 (Reverse, special mode for KS0078)
wim 10:dd9b3a696acd 96
wim 13:24506ba22480 97 _writeCommand(0x2E); // Function set 001 BW N RE DH REV
wim 13:24506ba22480 98 // N=1 (Dont care for KS0078)
wim 13:24506ba22480 99 // RE=1 (Ena Extended Regs, special mode for KS0078)
wim 13:24506ba22480 100 // DH=1 (Disp shift, special mode for KS0078)
wim 13:24506ba22480 101 // REV=0 (Reverse, special mode for KS0078)
wim 10:dd9b3a696acd 102
wim 13:24506ba22480 103 _writeCommand(0x09); // Ext Function set 0000 1 FW BW NW
wim 13:24506ba22480 104 // FW=0 (5-dot font, special mode for KS0078)
wim 13:24506ba22480 105 // BW=0 (Cur BW invert disable, special mode for KS0078)
wim 13:24506ba22480 106 // NW=1 (4 Line, special mode for KS0078)
wim 10:dd9b3a696acd 107
wim 13:24506ba22480 108 _writeCommand(0x2A); // Function set 001 BW N RE DH REV
wim 13:24506ba22480 109 // N=1 (Dont care for KS0078)
wim 13:24506ba22480 110 // RE=0 (Dis. Extended Regs, special mode for KS0078)
wim 13:24506ba22480 111 // DH=1 (Disp shift, special mode for KS0078)
wim 13:24506ba22480 112 // REV=0 (Reverse, special mode for KS0078)
wim 10:dd9b3a696acd 113 break;
wim 10:dd9b3a696acd 114
wim 10:dd9b3a696acd 115 default:
wim 13:24506ba22480 116 _writeCommand(0x28); // Function set 001 BW N F - -
wim 13:24506ba22480 117 // N=1 (2 lines)
wim 13:24506ba22480 118 // F=0 (5x7 dots font)
wim 13:24506ba22480 119 // - (Don't care)
wim 10:dd9b3a696acd 120
wim 10:dd9b3a696acd 121 break;
wim 10:dd9b3a696acd 122 }
wim 10:dd9b3a696acd 123
wim 13:24506ba22480 124 _writeCommand(0x06); // Entry Mode 0000 01 CD S
wim 13:24506ba22480 125 // Cursor Direction and Display Shift
wim 13:24506ba22480 126 // CD=1 (Cur incr)
wim 13:24506ba22480 127 // S=0 (No display shift)
wim 10:dd9b3a696acd 128
wim 13:24506ba22480 129 // _writeCommand(0x0C); // Display Ctrl 0000 1 D C B
wim 13:24506ba22480 130 // // Display On, Cursor Off, Blink Off
wim 13:24506ba22480 131 setCursor(TextLCD::CurOff_BlkOff);
wim 11:9ec02df863a1 132
wim 10:dd9b3a696acd 133 cls();
simon 1:ac48b187213c 134 }
simon 1:ac48b187213c 135
wim 8:03116f75b66e 136
wim 13:24506ba22480 137 void TextLCD::_character(int column, int row, int c) {
wim 8:03116f75b66e 138 int addr = getAddress(column, row);
wim 8:03116f75b66e 139
wim 13:24506ba22480 140 _writeCommand(0x80 | addr);
wim 13:24506ba22480 141 _writeData(c);
simon 1:ac48b187213c 142 }
simon 1:ac48b187213c 143
wim 8:03116f75b66e 144
simon 1:ac48b187213c 145 void TextLCD::cls() {
wim 13:24506ba22480 146 _writeCommand(0x01); // cls, and set cursor to 0
wim 13:24506ba22480 147 wait(0.00164f); // This command takes 1.64 ms
simon 1:ac48b187213c 148 locate(0, 0);
simon 1:ac48b187213c 149 }
simon 1:ac48b187213c 150
simon 1:ac48b187213c 151 void TextLCD::locate(int column, int row) {
simon 1:ac48b187213c 152 _column = column;
simon 1:ac48b187213c 153 _row = row;
simon 1:ac48b187213c 154 }
simon 1:ac48b187213c 155
simon 1:ac48b187213c 156 int TextLCD::_putc(int value) {
simon 1:ac48b187213c 157 if (value == '\n') {
simon 1:ac48b187213c 158 _column = 0;
simon 1:ac48b187213c 159 _row++;
simon 1:ac48b187213c 160 if (_row >= rows()) {
simon 1:ac48b187213c 161 _row = 0;
simon 1:ac48b187213c 162 }
simon 1:ac48b187213c 163 } else {
wim 13:24506ba22480 164 _character(_column, _row, value);
simon 1:ac48b187213c 165 _column++;
simon 1:ac48b187213c 166 if (_column >= columns()) {
simon 1:ac48b187213c 167 _column = 0;
simon 1:ac48b187213c 168 _row++;
simon 1:ac48b187213c 169 if (_row >= rows()) {
simon 1:ac48b187213c 170 _row = 0;
simon 1:ac48b187213c 171 }
simon 1:ac48b187213c 172 }
simon 1:ac48b187213c 173 }
simon 1:ac48b187213c 174 return value;
simon 1:ac48b187213c 175 }
simon 1:ac48b187213c 176
simon 1:ac48b187213c 177 int TextLCD::_getc() {
simon 1:ac48b187213c 178 return -1;
simon 1:ac48b187213c 179 }
simon 1:ac48b187213c 180
wim 13:24506ba22480 181
wim 13:24506ba22480 182 void TextLCD::_setEnable(bool value) {
wim 13:24506ba22480 183
wim 13:24506ba22480 184 switch(_busType) {
wim 13:24506ba22480 185 case _PinBus :
wim 13:24506ba22480 186 if (value)
wim 13:24506ba22480 187 _e = 1; // Set E bit
wim 13:24506ba22480 188 else
wim 13:24506ba22480 189 _e = 0; // Reset E bit
wim 13:24506ba22480 190
wim 13:24506ba22480 191 break;
wim 13:24506ba22480 192
wim 13:24506ba22480 193 case _I2CBus :
wim 13:24506ba22480 194 if (value)
wim 13:24506ba22480 195 _lcd_bus |= D_LCD_E; // Set E bit
wim 13:24506ba22480 196 else
wim 13:24506ba22480 197 _lcd_bus &= ~D_LCD_E; // Reset E bit
wim 13:24506ba22480 198
wim 13:24506ba22480 199 // write the new data to the portexpander
wim 13:24506ba22480 200 _i2c->write(_slaveAddress, &_lcd_bus, 1);
wim 13:24506ba22480 201
wim 13:24506ba22480 202 break;
wim 13:24506ba22480 203
wim 13:24506ba22480 204 case _SPIBus :
wim 13:24506ba22480 205 break;
wim 13:24506ba22480 206 }
wim 13:24506ba22480 207 }
wim 13:24506ba22480 208
wim 13:24506ba22480 209 void TextLCD::_setRS(bool value) {
wim 13:24506ba22480 210
wim 13:24506ba22480 211 switch(_busType) {
wim 13:24506ba22480 212 case _PinBus :
wim 13:24506ba22480 213 if (value)
wim 13:24506ba22480 214 _rs = 1; // Set RS bit
wim 13:24506ba22480 215 else
wim 13:24506ba22480 216 _rs = 0; // Reset RS bit
wim 13:24506ba22480 217
wim 13:24506ba22480 218 break;
wim 13:24506ba22480 219
wim 13:24506ba22480 220 case _I2CBus :
wim 13:24506ba22480 221 if (value)
wim 13:24506ba22480 222 _lcd_bus |= D_LCD_RS; // Set RS bit
wim 13:24506ba22480 223 else
wim 13:24506ba22480 224 _lcd_bus &= ~D_LCD_RS; // Reset RS bit
wim 13:24506ba22480 225
wim 13:24506ba22480 226 // write the new data to the portexpander
wim 13:24506ba22480 227 _i2c->write(_slaveAddress, &_lcd_bus, 1);
wim 13:24506ba22480 228
wim 13:24506ba22480 229 break;
wim 13:24506ba22480 230
wim 13:24506ba22480 231 case _SPIBus :
wim 13:24506ba22480 232 break;
wim 13:24506ba22480 233 }
wim 13:24506ba22480 234
wim 13:24506ba22480 235 }
wim 13:24506ba22480 236
wim 13:24506ba22480 237 void TextLCD::_setData(int value) {
wim 13:24506ba22480 238 int data;
wim 13:24506ba22480 239
wim 13:24506ba22480 240 switch(_busType) {
wim 13:24506ba22480 241 case _PinBus :
wim 13:24506ba22480 242 _d = value & 0x0F; // Write Databits
wim 13:24506ba22480 243
wim 13:24506ba22480 244 break;
wim 13:24506ba22480 245
wim 13:24506ba22480 246 case _I2CBus :
wim 13:24506ba22480 247 data = value & 0x0F;
wim 13:24506ba22480 248 if (data & 0x01)
wim 13:24506ba22480 249 _lcd_bus |= D_LCD_D4; // Set Databit
wim 13:24506ba22480 250 else
wim 13:24506ba22480 251 _lcd_bus &= ~D_LCD_D4; // Reset Databit
wim 13:24506ba22480 252
wim 13:24506ba22480 253 if (data & 0x02)
wim 13:24506ba22480 254 _lcd_bus |= D_LCD_D5; // Set Databit
wim 13:24506ba22480 255 else
wim 13:24506ba22480 256 _lcd_bus &= ~D_LCD_D5; // Reset Databit
wim 13:24506ba22480 257
wim 13:24506ba22480 258 if (data & 0x04)
wim 13:24506ba22480 259 _lcd_bus |= D_LCD_D6; // Set Databit
wim 13:24506ba22480 260 else
wim 13:24506ba22480 261 _lcd_bus &= ~D_LCD_D6; // Reset Databit
wim 13:24506ba22480 262
wim 13:24506ba22480 263 if (data & 0x08)
wim 13:24506ba22480 264 _lcd_bus |= D_LCD_D7; // Set Databit
wim 13:24506ba22480 265 else
wim 13:24506ba22480 266 _lcd_bus &= ~D_LCD_D7; // Reset Databit
wim 13:24506ba22480 267
wim 13:24506ba22480 268 // write the new data to the portexpander
wim 13:24506ba22480 269 _i2c->write(_slaveAddress, &_lcd_bus, 1);
wim 13:24506ba22480 270
wim 13:24506ba22480 271 break;
wim 13:24506ba22480 272
wim 13:24506ba22480 273 case _SPIBus :
wim 13:24506ba22480 274 break;
wim 13:24506ba22480 275 }
wim 13:24506ba22480 276
wim 13:24506ba22480 277 }
wim 13:24506ba22480 278
wim 13:24506ba22480 279
wim 13:24506ba22480 280
wim 13:24506ba22480 281 void TextLCD::_writeByte(int value) {
wim 13:24506ba22480 282 // _d = value >> 4;
wim 13:24506ba22480 283 _setData(value >> 4);
simon 1:ac48b187213c 284 wait(0.000040f); // most instructions take 40us
wim 13:24506ba22480 285 // _e = 0;
wim 13:24506ba22480 286 _setEnable(false);
simon 1:ac48b187213c 287 wait(0.000040f);
wim 13:24506ba22480 288 // _e = 1;
wim 13:24506ba22480 289 _setEnable(true);
wim 13:24506ba22480 290 // _d = value >> 0;
wim 13:24506ba22480 291 _setData(value >> 0);
simon 1:ac48b187213c 292 wait(0.000040f);
wim 13:24506ba22480 293 // _e = 0;
wim 13:24506ba22480 294 _setEnable(false);
simon 1:ac48b187213c 295 wait(0.000040f); // most instructions take 40us
wim 13:24506ba22480 296 // _e = 1;
wim 13:24506ba22480 297 _setEnable(true);
simon 1:ac48b187213c 298 }
simon 1:ac48b187213c 299
wim 13:24506ba22480 300 void TextLCD::_writeCommand(int command) {
wim 13:24506ba22480 301 // _rs = 0;
wim 13:24506ba22480 302 _setRS(false);
wim 13:24506ba22480 303 _writeByte(command);
simon 1:ac48b187213c 304 }
simon 1:ac48b187213c 305
wim 13:24506ba22480 306 void TextLCD::_writeData(int data) {
wim 13:24506ba22480 307 // _rs = 1;
wim 13:24506ba22480 308 _setRS(true);
wim 13:24506ba22480 309 _writeByte(data);
simon 1:ac48b187213c 310 }
simon 1:ac48b187213c 311
wim 8:03116f75b66e 312
wim 8:03116f75b66e 313 #if (0)
wim 8:03116f75b66e 314 // This is the original method.
wim 8:03116f75b66e 315 // It is confusing since it returns the memoryaddress or-ed with the set memorycommand 0x80.
wim 8:03116f75b66e 316 // Left it in here for compatibility with older code. New applications should use getAddress() instead.
wim 8:03116f75b66e 317 //
wim 13:24506ba22480 318 int TextLCD::_address(int column, int row) {
simon 1:ac48b187213c 319 switch (_type) {
simon 1:ac48b187213c 320 case LCD20x4:
simon 1:ac48b187213c 321 switch (row) {
simon 1:ac48b187213c 322 case 0:
simon 1:ac48b187213c 323 return 0x80 + column;
simon 1:ac48b187213c 324 case 1:
simon 1:ac48b187213c 325 return 0xc0 + column;
simon 1:ac48b187213c 326 case 2:
simon 1:ac48b187213c 327 return 0x94 + column;
simon 1:ac48b187213c 328 case 3:
simon 1:ac48b187213c 329 return 0xd4 + column;
simon 1:ac48b187213c 330 }
simon 1:ac48b187213c 331 case LCD16x2B:
simon 4:bf5b706f8d32 332 return 0x80 + (row * 40) + column;
simon 1:ac48b187213c 333 case LCD16x2:
simon 1:ac48b187213c 334 case LCD20x2:
simon 1:ac48b187213c 335 default:
simon 4:bf5b706f8d32 336 return 0x80 + (row * 0x40) + column;
simon 1:ac48b187213c 337 }
simon 1:ac48b187213c 338 }
wim 8:03116f75b66e 339 #endif
wim 8:03116f75b66e 340
wim 8:03116f75b66e 341
wim 8:03116f75b66e 342 // This replaces the original method.
wim 8:03116f75b66e 343 // Left it in here for compatibility with older code. New applications should use getAddress() instead.
wim 13:24506ba22480 344 int TextLCD::_address(int column, int row) {
wim 8:03116f75b66e 345 return 0x80 | getAddress(column, row);
wim 8:03116f75b66e 346 }
wim 8:03116f75b66e 347
wim 8:03116f75b66e 348 // This is new method to return the memory address based on row, column and displaytype.
wim 8:03116f75b66e 349 //
wim 8:03116f75b66e 350 int TextLCD::getAddress(int column, int row) {
wim 8:03116f75b66e 351
wim 8:03116f75b66e 352 switch (_type) {
wim 8:03116f75b66e 353 case LCD8x1:
wim 8:03116f75b66e 354 return 0x00 + column;
wim 8:03116f75b66e 355
wim 13:24506ba22480 356 case LCD16x1:
wim 13:24506ba22480 357 // LCD16x1 is a special layout of LCD8x2
wim 13:24506ba22480 358 if (column<8)
wim 13:24506ba22480 359 return 0x00 + column;
wim 13:24506ba22480 360 else
wim 13:24506ba22480 361 return 0x40 + (column - 8);
wim 13:24506ba22480 362
wim 8:03116f75b66e 363 case LCD16x4:
wim 8:03116f75b66e 364 switch (row) {
wim 8:03116f75b66e 365 case 0:
wim 8:03116f75b66e 366 return 0x00 + column;
wim 8:03116f75b66e 367 case 1:
wim 8:03116f75b66e 368 return 0x40 + column;
wim 8:03116f75b66e 369 case 2:
wim 8:03116f75b66e 370 return 0x10 + column;
wim 8:03116f75b66e 371 case 3:
wim 8:03116f75b66e 372 return 0x50 + column;
wim 8:03116f75b66e 373 }
wim 8:03116f75b66e 374
wim 8:03116f75b66e 375 case LCD20x4:
wim 8:03116f75b66e 376 switch (row) {
wim 8:03116f75b66e 377 case 0:
wim 8:03116f75b66e 378 return 0x00 + column;
wim 8:03116f75b66e 379 case 1:
wim 8:03116f75b66e 380 return 0x40 + column;
wim 8:03116f75b66e 381 case 2:
wim 8:03116f75b66e 382 return 0x14 + column;
wim 8:03116f75b66e 383 case 3:
wim 8:03116f75b66e 384 return 0x54 + column;
wim 8:03116f75b66e 385 }
wim 8:03116f75b66e 386
wim 10:dd9b3a696acd 387 // Special mode for KS0078
wim 10:dd9b3a696acd 388 case LCD24x4:
wim 10:dd9b3a696acd 389 switch (row) {
wim 10:dd9b3a696acd 390 case 0:
wim 10:dd9b3a696acd 391 return 0x00 + column;
wim 10:dd9b3a696acd 392 case 1:
wim 10:dd9b3a696acd 393 return 0x20 + column;
wim 10:dd9b3a696acd 394 case 2:
wim 10:dd9b3a696acd 395 return 0x40 + column;
wim 10:dd9b3a696acd 396 case 3:
wim 10:dd9b3a696acd 397 return 0x60 + column;
wim 10:dd9b3a696acd 398 }
wim 10:dd9b3a696acd 399
wim 8:03116f75b66e 400 // Not sure about this one, seems wrong.
wim 8:03116f75b66e 401 case LCD16x2B:
wim 8:03116f75b66e 402 return 0x00 + (row * 40) + column;
wim 8:03116f75b66e 403
wim 8:03116f75b66e 404 case LCD8x2:
wim 8:03116f75b66e 405 case LCD16x2:
wim 8:03116f75b66e 406 case LCD20x2:
wim 8:03116f75b66e 407 case LCD24x2:
wim 9:0893d986e717 408 case LCD40x2:
wim 8:03116f75b66e 409 return 0x00 + (row * 0x40) + column;
wim 8:03116f75b66e 410
wim 8:03116f75b66e 411 // Should never get here.
wim 8:03116f75b66e 412 default:
wim 8:03116f75b66e 413 return 0x00;
wim 8:03116f75b66e 414 }
wim 8:03116f75b66e 415 }
wim 8:03116f75b66e 416
wim 8:03116f75b66e 417
wim 13:24506ba22480 418 // Added for consistency. Set row, column and update memoryaddress.
wim 8:03116f75b66e 419 //
wim 8:03116f75b66e 420 void TextLCD::setAddress(int column, int row) {
wim 8:03116f75b66e 421
wim 8:03116f75b66e 422 locate(column, row);
wim 8:03116f75b66e 423
wim 8:03116f75b66e 424 int addr = getAddress(column, row);
wim 8:03116f75b66e 425
wim 13:24506ba22480 426 _writeCommand(0x80 | addr);
wim 8:03116f75b66e 427 }
simon 1:ac48b187213c 428
simon 1:ac48b187213c 429 int TextLCD::columns() {
simon 1:ac48b187213c 430 switch (_type) {
wim 8:03116f75b66e 431 case LCD8x1:
wim 8:03116f75b66e 432 case LCD8x2:
wim 8:03116f75b66e 433 return 8;
wim 8:03116f75b66e 434
wim 13:24506ba22480 435 case LCD16x1:
simon 1:ac48b187213c 436 case LCD16x2:
simon 1:ac48b187213c 437 case LCD16x2B:
wim 8:03116f75b66e 438 case LCD16x4:
wim 8:03116f75b66e 439 return 16;
wim 8:03116f75b66e 440
wim 8:03116f75b66e 441 case LCD20x2:
wim 8:03116f75b66e 442 case LCD20x4:
wim 8:03116f75b66e 443 return 20;
wim 8:03116f75b66e 444
wim 8:03116f75b66e 445 case LCD24x2:
wim 10:dd9b3a696acd 446 case LCD24x4:
wim 8:03116f75b66e 447 return 24;
wim 9:0893d986e717 448
wim 9:0893d986e717 449 case LCD40x2:
wim 9:0893d986e717 450 return 40;
wim 8:03116f75b66e 451
wim 8:03116f75b66e 452 // Should never get here.
simon 1:ac48b187213c 453 default:
wim 8:03116f75b66e 454 return 0;
simon 1:ac48b187213c 455 }
simon 1:ac48b187213c 456 }
simon 1:ac48b187213c 457
simon 1:ac48b187213c 458 int TextLCD::rows() {
simon 1:ac48b187213c 459 switch (_type) {
wim 8:03116f75b66e 460 case LCD8x1:
wim 13:24506ba22480 461 case LCD16x1:
wim 8:03116f75b66e 462 return 1;
wim 8:03116f75b66e 463
wim 8:03116f75b66e 464 case LCD8x2:
simon 1:ac48b187213c 465 case LCD16x2:
simon 1:ac48b187213c 466 case LCD16x2B:
simon 1:ac48b187213c 467 case LCD20x2:
wim 8:03116f75b66e 468 case LCD24x2:
wim 9:0893d986e717 469 case LCD40x2:
wim 8:03116f75b66e 470 return 2;
wim 8:03116f75b66e 471
wim 8:03116f75b66e 472 case LCD16x4:
wim 8:03116f75b66e 473 case LCD20x4:
wim 10:dd9b3a696acd 474 case LCD24x4:
wim 8:03116f75b66e 475 return 4;
wim 12:6bf9d9957d31 476
wim 12:6bf9d9957d31 477 // Should never get here.
simon 1:ac48b187213c 478 default:
wim 8:03116f75b66e 479 return 0;
simon 1:ac48b187213c 480 }
simon 1:ac48b187213c 481 }
wim 10:dd9b3a696acd 482
wim 10:dd9b3a696acd 483
wim 13:24506ba22480 484 void TextLCD::setCursor(TextLCD::LCDCursor show) {
wim 10:dd9b3a696acd 485
wim 10:dd9b3a696acd 486 switch (show) {
wim 13:24506ba22480 487 case CurOff_BlkOff : _writeCommand(0x0C); // Cursor off and Blink Off
wim 11:9ec02df863a1 488 wait_us(40);
wim 11:9ec02df863a1 489 _cursor = show;
wim 11:9ec02df863a1 490 break;
wim 11:9ec02df863a1 491
wim 13:24506ba22480 492 case CurOn_BlkOff : _writeCommand(0x0E); // Cursor on and Blink Off
wim 11:9ec02df863a1 493 wait_us(40);
wim 11:9ec02df863a1 494 _cursor = show;
wim 11:9ec02df863a1 495 break;
wim 11:9ec02df863a1 496
wim 13:24506ba22480 497 case CurOff_BlkOn : _writeCommand(0x0D); // Cursor off and Blink On
wim 11:9ec02df863a1 498 wait_us(40);
wim 11:9ec02df863a1 499 _cursor = show;
wim 11:9ec02df863a1 500 break;
wim 11:9ec02df863a1 501
wim 13:24506ba22480 502 case CurOn_BlkOn : _writeCommand(0x0F); // Cursor on and Blink char
wim 11:9ec02df863a1 503 wait_us(40);
wim 11:9ec02df863a1 504 _cursor = show;
wim 11:9ec02df863a1 505 break;
wim 11:9ec02df863a1 506
wim 12:6bf9d9957d31 507 // Should never get here.
wim 10:dd9b3a696acd 508 default :
wim 11:9ec02df863a1 509 break;
wim 10:dd9b3a696acd 510
wim 10:dd9b3a696acd 511 }
wim 11:9ec02df863a1 512
wim 10:dd9b3a696acd 513 }
wim 10:dd9b3a696acd 514
wim 10:dd9b3a696acd 515
wim 11:9ec02df863a1 516 void TextLCD::setUDC(unsigned char c, char *udc_data) {
wim 13:24506ba22480 517 _writeCommand(0x40 + ((c & 0x07) << 3)); //Set CG-RAM address
wim 11:9ec02df863a1 518
wim 11:9ec02df863a1 519 for (int i=0; i<8; i++) {
wim 13:24506ba22480 520 _writeData(*udc_data++);
wim 11:9ec02df863a1 521 }
wim 11:9ec02df863a1 522 }
wim 10:dd9b3a696acd 523
wim 10:dd9b3a696acd 524