Library for New Haven NHD_0420DZW OLED
Embed:
(wiki syntax)
Show/hide line numbers
NHD_0420DZW_OLED.cpp
Go to the documentation of this file.
00001 /** 00002 * @file NHD_0420DZW_OLED.cpp 00003 * @brief This C++ file contains the functions to interface the New Haven 00004 * NHD_0420DZW display using a 4-wire software spi bus bus. 00005 * 10-bit SPI operation, ie spi.format(10, 3), does not work with Nucleo-F746ZG, 00006 * it remains 8-bit, so unfortunately I had to do bit banging 00007 * @author Jack Berkhout 00008 * 00009 * @date 2016-10-21 00010 */ 00011 #include "NHD_0420DZW_OLED.h" 00012 #include "mbed.h" 00013 00014 NHD_0420DZW_OLED::NHD_0420DZW_OLED(PinName sdi, PinName sdo, PinName scl, PinName csb, const char *name) : 00015 Stream(name), _lcd_sdi(sdi), _lcd_sdo(sdo), _lcd_scl(scl), _lcd_csb(csb) 00016 // TextDisplay(name), _lcd_sdi(sdi), _lcd_sdo(sdo), _lcd_scl(scl), _lcd_csb(csb) 00017 { 00018 _lcd_csb = 1; 00019 _lcd_scl = 1; 00020 _lcd_sdi = 0; 00021 00022 // --- claim --- 00023 _row = 0; 00024 _column = 0; 00025 if (name == NULL) { 00026 _path = NULL; 00027 } else { 00028 _path = new char[strlen(name) + 2]; 00029 sprintf(_path, "/%s", name); 00030 } 00031 // ------------- 00032 00033 init(); 00034 } 00035 00036 void NHD_0420DZW_OLED::init(void) 00037 { 00038 writeCommand(LCD_FUNCTION_SET); 00039 writeCommand(LCD_DISPLAY_OFF); 00040 writeCommand(LCD_CLEAR_DISPLAY); 00041 writeCommand(LCD_CURSOR_INCR); 00042 writeCommand(LCD_RETURN_HOME); 00043 writeCommand(LCD_DISPLAY_ON); 00044 00045 // custom characters 00046 // In the character generator RAM, the user can rewrite character patterns 00047 // For 5x8 dots, eight character patterns can be written 00048 // Store custom chars in LCD's CGRAM 00049 writeCommand(LCD_CGRAM(1)); 00050 char CharacterBytes[] = CHARACTERBYTES; 00051 for (unsigned char Index = 0; Index < sizeof(CharacterBytes); Index++) { 00052 writeData(CharacterBytes[Index]); 00053 } 00054 } 00055 00056 void NHD_0420DZW_OLED::cls(void) 00057 { 00058 writeCommand(LCD_CLEAR_DISPLAY); // Clear display 00059 } 00060 00061 void NHD_0420DZW_OLED::cursorHome(void) 00062 { 00063 writeCommand(LCD_RETURN_HOME); // Clear display 00064 } 00065 00066 void NHD_0420DZW_OLED::writeCharacter(int column, int row, int c) 00067 { 00068 locate(column, row); 00069 writeData(c); 00070 } 00071 00072 void NHD_0420DZW_OLED::writeCharacter(char c) 00073 { 00074 writeData((int)c); 00075 } 00076 00077 void NHD_0420DZW_OLED::writeString(char *charString) 00078 { 00079 uint8_t length = strlen(charString); 00080 for (uint8_t i = 0; i < length; i++) { 00081 writeCharacter(charString[i]); 00082 } 00083 } 00084 00085 void NHD_0420DZW_OLED::writeString(int row, char *charString) 00086 { 00087 locate(0, row); 00088 writeString(charString); 00089 } 00090 00091 void NHD_0420DZW_OLED::writeString(int column, int row, char *charString) 00092 { 00093 locate(column, row); 00094 writeString(charString); 00095 } 00096 00097 void NHD_0420DZW_OLED::clearLine(int row) 00098 { 00099 int length = LCD_NUMBER_OF_CHARACTERS; 00100 locate(0, row); 00101 while(length--) { 00102 writeCharacter(' '); 00103 } 00104 locate(0, row); 00105 } 00106 00107 void NHD_0420DZW_OLED::clearRegion(int column, int row, int length) 00108 { 00109 locate(column, row); 00110 while(length--) { 00111 writeCharacter(' '); 00112 } 00113 locate(column, row); 00114 } 00115 00116 void NHD_0420DZW_OLED::locate(int column, int row) 00117 { 00118 if ((column > LCD_NUMBER_OF_CHARACTERS) || (row > LCD_NUMBER_OF_LINES)) 00119 { 00120 return; 00121 } 00122 else 00123 { 00124 switch (row) { 00125 case 0: 00126 writeCommand(LCD_LINE_1 + column); /* command - position cursor at 0x00 (0x80 + 0x00 ) */ 00127 break; 00128 case 1: 00129 writeCommand(LCD_LINE_2 + column); /* command - position cursor at 0x40 (0x80 + 0x00 ) */ 00130 break; 00131 case 2: 00132 writeCommand(LCD_LINE_3 + column); /* command - position cursor at 0x40 (0x80 + 0x00 ) */ 00133 break; 00134 case 3: 00135 writeCommand(LCD_LINE_4 + column); /* command - position cursor at 0x40 (0x80 + 0x00 ) */ 00136 break; 00137 default: 00138 writeCommand(LCD_LINE_1 + column); /* command - position cursor at 0x00 (0x80 + 0x00 ) */ 00139 break; 00140 } 00141 } 00142 } 00143 00144 void NHD_0420DZW_OLED::drawBar(int column, int row, int Value, int Max) 00145 { 00146 int Count = 0; 00147 int Characters = Max / 5; 00148 if (Value > Max) 00149 Value = Max; 00150 locate(column, row); 00151 // Print the characters 00152 while (Count < Characters) 00153 { 00154 if ((Value >= 6) && (Value <= Max)) 00155 writeData('\6'); // ***** 00156 else 00157 if ((Value == 0) || (Value > Max)) 00158 writeData('\1'); // ..... 00159 else 00160 writeData(Value+1); // ***.. 00161 Value -= 5; 00162 Count++; 00163 } 00164 } 00165 00166 void NHD_0420DZW_OLED::writeCommand(int data) 00167 { 00168 waitBusy(); 00169 writeSerial(LCD_COMMAND, LCD_WRITE, data); 00170 } 00171 00172 void NHD_0420DZW_OLED::writeData(int data) 00173 { 00174 // waitBusy(); 00175 writeSerial(LCD_DATA, LCD_WRITE, data); 00176 } 00177 00178 int NHD_0420DZW_OLED::readAddress(void) 00179 { 00180 writeSerial(LCD_COMMAND, LCD_READ, 0x00); // Dummy read 00181 return (serialData(LCD_COMMAND, LCD_READ, 0x00, 0x00) >> 3) & 0x7F; 00182 } 00183 00184 void NHD_0420DZW_OLED::waitBusy(void) 00185 { 00186 while (readBusyFlag()); 00187 } 00188 00189 int NHD_0420DZW_OLED::readBusyFlag(void) 00190 { 00191 return (serialInstruction(LCD_COMMAND, LCD_READ, 0x00, 0x00) >> 10); 00192 } 00193 00194 void NHD_0420DZW_OLED::writeSerial(int rs, int rw, int data) 00195 { 00196 // CSB ---|_________________________________________|---- 00197 // SCL -----|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|------ 00198 // SDI .....|RS0|RW0|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |.... 00199 // SDO .............|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |.... 00200 // RS=1: Data 00201 // RS=0: Command <--- 00202 // RW=1: Read 00203 // RW=0: Write <--- 00204 if (rs > 0) { 00205 data |= LCD_RS_BIT_MASK; 00206 } 00207 if (rw > 0) { 00208 data |= LCD_Rw_BIT_MASK; 00209 } 00210 00211 selectSerial(true); 00212 clockSerial(data, 10); 00213 selectSerial(false); 00214 } 00215 00216 int NHD_0420DZW_OLED::serialInstruction(int rs, int rw, int data1, int data2) 00217 { 00218 // CSB ---|_________________________________________________________________________________|---- 00219 // SCL -----|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|------ 00220 // SDI .....|RS0|RW1|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |RS |RW |D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |.... 00221 // SDO .............|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |D7 |D6 |.... 00222 // RS=1: Data 00223 // RS=0: Command <--- 00224 // RW=1: Read <--- 00225 // RW=0: Write 00226 // Read Bussy Flag & Address BF AC6 AC5 AC4 AC3 AC2 AC1 AC0 00227 if (rs > 0) { 00228 data1 |= LCD_RS_BIT_MASK; 00229 data2 |= LCD_RS_BIT_MASK; 00230 } 00231 if (rw > 0) { 00232 data1 |= LCD_Rw_BIT_MASK; 00233 data2 |= LCD_Rw_BIT_MASK; 00234 } 00235 00236 selectSerial(true); 00237 clockSerial(data1, 10); 00238 int data = clockSerial(data2, 10); 00239 selectSerial(false); 00240 return data; 00241 } 00242 00243 int NHD_0420DZW_OLED::serialData(int rs, int rw, int data1, int data2) 00244 { 00245 // CSB ---|_________________________________________________________________________________|---- 00246 // SCL -----|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|-|_|------ 00247 // SDI .....|RS1|RW1|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |RS |RW |D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |.... 00248 // SDO .............|D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |D7 |D6 |D5 |D4 |D3 |D2 |D1 |D0 |D7 |D6 |.... 00249 // RS=1: Data <--- 00250 // RS=0: Command 00251 // RW=1: Read <--- 00252 // RW=0: Write 00253 // Read data from CGRAM or DDRAM 00254 if (rs > 0) { 00255 data1 |= LCD_RS_BIT_MASK; 00256 } 00257 if (rw > 0) { 00258 data1 |= LCD_Rw_BIT_MASK; 00259 } 00260 00261 selectSerial(true); 00262 clockSerial(data1, 10); 00263 int data = clockSerial(data2, 8); 00264 selectSerial(false); 00265 return data; 00266 } 00267 00268 int NHD_0420DZW_OLED::clockSerial(int dataOut, int bits) 00269 { 00270 int dataIn = 0; 00271 for (int bit = bits; bit > 0; bit--) { 00272 _lcd_scl = 0; 00273 if ((dataOut & (1 << (bit-1))) == 0) { 00274 _lcd_sdi = 0; 00275 } else { 00276 _lcd_sdi = 1; 00277 } 00278 // wait_us(LCD_CLOCK_PULSE_LENGTH); 00279 _lcd_scl = 1; 00280 dataIn |= _lcd_sdo; 00281 dataIn <<= 1; 00282 // wait_us(LCD_CLOCK_PULSE_LENGTH); 00283 } 00284 return dataIn; 00285 } 00286 00287 void NHD_0420DZW_OLED::selectSerial(bool select) 00288 { 00289 if (select) 00290 _lcd_csb = 0; 00291 else 00292 _lcd_csb = 1; 00293 // wait_us(LCD_CLOCK_PULSE_LENGTH); 00294 } 00295 00296 bool NHD_0420DZW_OLED::claim (FILE *stream) { 00297 if ( _path == NULL) { 00298 fprintf(stderr, "claim requires a name to be given in the instantioator of the TextDisplay instance!\r\n"); 00299 return false; 00300 } 00301 if (freopen(_path, "w", stream) == NULL) { 00302 // Failed, should not happen 00303 return false; 00304 } 00305 // make sure we use line buffering 00306 setvbuf(stdout, NULL, _IOLBF, LCD_NUMBER_OF_CHARACTERS); 00307 return true; 00308 }
Generated on Sun Aug 14 2022 11:47:20 by 1.7.2