]> kolegite.com Git - vmks.git/commitdiff
Upload LCD examples without using a library
authorIvan Stefanov <istefanov@elsys-bg.org>
Tue, 15 Mar 2022 20:11:32 +0000 (22:11 +0200)
committerIvan Stefanov <istefanov@elsys-bg.org>
Tue, 15 Mar 2022 20:11:32 +0000 (22:11 +0200)
Datasheets/LCD_16x2_example_datasheet_ADM1602K-NSW-FBS-3.3v.pdf [new file with mode: 0644]
Examples/LCD_without_library/LCD_without_library.ino [new file with mode: 0644]
Examples/LCD_without_library/LCD_without_library.png [new file with mode: 0644]
Examples/LCD_without_library/tinkercad_link.txt [new file with mode: 0644]
Examples/LCD_without_library_simple/LCD_without_library_simple.ino [new file with mode: 0644]
Examples/LCD_without_library_simple/LCD_without_library_simple.png [new file with mode: 0644]
Examples/LCD_without_library_simple/tinkercad_link.txt [new file with mode: 0644]
Lesson_Plans/Lesson_20.md
Other Useful Files/LCD_without_library_notes.txt [new file with mode: 0644]

diff --git a/Datasheets/LCD_16x2_example_datasheet_ADM1602K-NSW-FBS-3.3v.pdf b/Datasheets/LCD_16x2_example_datasheet_ADM1602K-NSW-FBS-3.3v.pdf
new file mode 100644 (file)
index 0000000..81ad817
Binary files /dev/null and b/Datasheets/LCD_16x2_example_datasheet_ADM1602K-NSW-FBS-3.3v.pdf differ
diff --git a/Examples/LCD_without_library/LCD_without_library.ino b/Examples/LCD_without_library/LCD_without_library.ino
new file mode 100644 (file)
index 0000000..ed8c9e8
--- /dev/null
@@ -0,0 +1,126 @@
+#define RS  12
+#define EN  11
+#define D4  5
+#define D5  4
+#define D6  3
+#define D7  2
+
+#define COLS 16
+#define ROWS 2
+
+void lcd_cmd(uint8_t _data, bool _type);
+void lcd_init(void);
+void lcd_set_cursor(uint8_t col, uint8_t row);
+void lcd_show_char(char chr);
+void lcd_show_text(char *text, uint8_t len);
+void lcd_show_text_vmks(void);
+
+void setup() {
+  // Initialize LCD screen and IF GPIO
+  lcd_init();
+
+  // Center the text on the second line => Move cursor to
+  // (second line offset + half the line size - half the text size)
+  // (0x40 + 16/2 - 4/2) = (0x40 + 8 - 2) = (0x40 + 6) = 0x46
+  // Line 1 => 0x00 to 0x27
+  // Line 2 => 0x40 to 0x67
+  //lcd_cmd(B1100, 0); lcd_cmd(B0110, 0); // manually set DDRAM to cursor position = 0x46 = B 0100 0110
+  lcd_set_cursor(6, 2); // the same but using the function
+
+  // Show text
+  //lcd_show_text_vmks(); // Show hardcoded text "VMKS"
+  //lcd_show_char('T'); lcd_show_char('U'); lcd_show_char('E'); lcd_show_char('S');
+  lcd_show_text("VMKS", 4); // This is actually String object converting to char array but works for the demo
+}
+
+void loop() {
+  delay(5000);
+  lcd_cmd(B0000, 0); lcd_cmd(B0001, 0); delayMicroseconds(1530); // clear display - set all characters to space(' ') and return home
+  lcd_set_cursor(6, 1);
+  lcd_show_text_vmks();
+  lcd_set_cursor(6, 2);
+  lcd_show_char('T'); lcd_show_char('U'); lcd_show_char('E'); lcd_show_char('S');
+  while (1) {};
+}
+
+void lcd_init(void) {
+  // Set IF GPIO mode
+  pinMode(RS, OUTPUT);
+  pinMode(EN, OUTPUT);
+  pinMode(D4, OUTPUT);
+  pinMode(D5, OUTPUT);
+  pinMode(D6, OUTPUT);
+  pinMode(D7, OUTPUT);
+
+  // LCD Power-On Reset (POR) initialization wait
+  delay(40);
+
+  // Initialize controller HD44780
+  lcd_cmd(B0010, 0); // lcd_cmd(B1000, 0); delayMicroseconds(39); // Function set => 4-bit data bus mode, 1-line, 5x8 dots
+  lcd_cmd(B0010, 0); lcd_cmd(B1000, 0); delayMicroseconds(39);   // Function set => 4-bit data bus mode, 2-line, 5x8 dots
+  lcd_cmd(B0000, 0); lcd_cmd(B0001, 0); delayMicroseconds(1530); // clear display - set all characters to space(' ') and return home
+  lcd_cmd(B0000, 0); lcd_cmd(B1100, 0); delayMicroseconds(39);   // turn display on
+  lcd_cmd(B0000, 0); lcd_cmd(B0010, 0); delayMicroseconds(1530); // return home - move cursor to begining of first line
+  lcd_cmd(B0000, 0); lcd_cmd(B0110, 0); delayMicroseconds(39);   // entry mode set = left-justified, left-to-right, no shift text
+}
+
+// There is no parameter validation
+// COL and ROW start from 1
+void lcd_set_cursor(uint8_t col, uint8_t row) {
+  uint8_t row_offset[2] = {0x00, 0x40};
+  uint8_t pos = (col) + row_offset[row - 1];
+  pos = (pos & 0x7F) | 0x80; // Add cursor position change command code
+  uint8_t upper = (pos & 0xF0) >> 4;
+  uint8_t lower = (pos & 0x0F) >> 0;
+  lcd_cmd(upper, 0); lcd_cmd(lower, 0);
+}
+
+// Send ASCII char
+void lcd_show_char(char chr) {
+  uint8_t upper = ((uint8_t)chr & 0xF0) >> 4;
+  uint8_t lower = ((uint8_t)chr & 0x0F) >> 0;
+
+  lcd_cmd(upper, 1); lcd_cmd(lower, 1);
+}
+
+// Send ASCII text
+void lcd_show_text(char *text, uint8_t len) {
+  for (uint8_t cnt = 0; cnt < len; cnt++) {
+    lcd_show_char(text[cnt]);
+  }
+}
+
+// Send hardcoded ASCII text "VMKS"
+void lcd_show_text_vmks(void) {
+  lcd_cmd(B0101, 1); lcd_cmd(B0110, 1); // V = 0x56 = B 0101 0110
+  lcd_cmd(B0100, 1); lcd_cmd(B1101, 1); // M = 0x4D = B 0100 1101
+  lcd_cmd(B0100, 1); lcd_cmd(B1011, 1); // K = 0x4B = B 0100 1011
+  lcd_cmd(B0101, 1); lcd_cmd(B0011, 1); // S = 0x53 = B 0101 0011
+}
+
+// Data = 4-bit data to send (use lower 4 bits)
+// Type 0 = Instruction || Type 1 = Data
+// example delays are only to show the idea - they really should be in [ns] but there is no such function
+void lcd_cmd(uint8_t _data, bool _type) {
+  // Set RS
+  digitalWrite(RS, _type);
+
+  // Set Data value
+  digitalWrite(D4, (_data & 0x01));
+  digitalWrite(D5, (_data & 0x02));
+  digitalWrite(D6, (_data & 0x04));
+  digitalWrite(D7, (_data & 0x08));
+
+  // Time to select the register
+  delayMicroseconds(120);
+  // Data setup time = 60~90ns after the above delay
+  // In this example data is already set before that
+
+  // Pulse Enable
+  digitalWrite(EN, HIGH);
+  delayMicroseconds(320); // Enable pulse duration
+  digitalWrite(EN, LOW);
+
+  // Wait
+  delayMicroseconds(30); // Data hold time
+}
diff --git a/Examples/LCD_without_library/LCD_without_library.png b/Examples/LCD_without_library/LCD_without_library.png
new file mode 100644 (file)
index 0000000..9d12da2
Binary files /dev/null and b/Examples/LCD_without_library/LCD_without_library.png differ
diff --git a/Examples/LCD_without_library/tinkercad_link.txt b/Examples/LCD_without_library/tinkercad_link.txt
new file mode 100644 (file)
index 0000000..aa8b791
--- /dev/null
@@ -0,0 +1 @@
+ https://www.tinkercad.com/things/9LSofZh54nf
\ No newline at end of file
diff --git a/Examples/LCD_without_library_simple/LCD_without_library_simple.ino b/Examples/LCD_without_library_simple/LCD_without_library_simple.ino
new file mode 100644 (file)
index 0000000..93dcd97
--- /dev/null
@@ -0,0 +1,73 @@
+#define RS  12
+#define EN  11
+#define D4  5
+#define D5  4
+#define D6  3
+#define D7  2
+
+#define COLS 16
+#define ROWS 2
+
+void setup() {
+  // Initialize LCD screen and IF GPIO
+  lcd_init();
+
+  // Show hardcoded text "VMKS"
+  lcd_show_text_vmks();
+}
+
+void loop() {
+  // put your main code here, to run repeatedly:
+}
+
+void lcd_init() {
+  // Set IF GPIO mode
+  pinMode(RS, OUTPUT);
+  pinMode(EN, OUTPUT);
+  pinMode(D4, OUTPUT);
+  pinMode(D5, OUTPUT);
+  pinMode(D6, OUTPUT);
+  pinMode(D7, OUTPUT);
+
+  // LCD Power-On Reset (POR) initialization wait
+  delay(40);
+
+  // Initialize controller HD44780
+  lcd_cmd(B0010, 0); // Function set => 4-bit data bus mode, 1-line, 5x8 dots
+  lcd_cmd(B0000, 0); lcd_cmd(B0001, 0); // clear display - set all characters to space(' ') and return cursor to begining of first row (return home)
+  lcd_cmd(B0000, 0); lcd_cmd(B1100, 0); // turn display on
+}
+
+// Send ASCII text "VMKS"
+void lcd_show_text_vmks() {
+  lcd_cmd(B0101, 1); lcd_cmd(B0110, 1); // V = 0x56 = B 0101 0110
+  lcd_cmd(B0100, 1); lcd_cmd(B1101, 1); // M = 0x4D = B 0100 1101
+  lcd_cmd(B0100, 1); lcd_cmd(B1011, 1); // K = 0x4B = B 0100 1011
+  lcd_cmd(B0101, 1); lcd_cmd(B0011, 1); // S = 0x53 = B 0101 0011
+}
+
+// Data = 4-bit data to send (use lower 4 bits)
+// Type 0 = Instruction || Type 1 = Data
+void lcd_cmd(uint8_t _data, bool _type) {
+  // Set RS
+  digitalWrite(RS, _type);
+
+  // Set Data value
+  digitalWrite(D4, (_data & 0x01));
+  digitalWrite(D5, (_data & 0x02));
+  digitalWrite(D6, (_data & 0x04));
+  digitalWrite(D7, (_data & 0x08));
+
+  // Time to select the register
+  delayMicroseconds(120);
+  // Data setup time = 60~90ns after the above delay
+  // In this example data is already set before that
+
+  // Pulse Enable
+  digitalWrite(EN, HIGH);
+  delayMicroseconds(320); // Enable pulse duration
+  digitalWrite(EN, LOW);
+
+  // Wait
+  delayMicroseconds(30); // Data hold time
+}
diff --git a/Examples/LCD_without_library_simple/LCD_without_library_simple.png b/Examples/LCD_without_library_simple/LCD_without_library_simple.png
new file mode 100644 (file)
index 0000000..9d12da2
Binary files /dev/null and b/Examples/LCD_without_library_simple/LCD_without_library_simple.png differ
diff --git a/Examples/LCD_without_library_simple/tinkercad_link.txt b/Examples/LCD_without_library_simple/tinkercad_link.txt
new file mode 100644 (file)
index 0000000..1afe472
--- /dev/null
@@ -0,0 +1 @@
+ https://www.tinkercad.com/things/enhJJzIeHyr
\ No newline at end of file
index ba96571bdde7fd3e84245a1294a4a322e0f1d9f4..c6d46a228ce9e60a641ee4c1c55bd3c645523d95 100644 (file)
 [Пример за използване с микропроцесор 6502 на асемблер](https://www.youtube.com/watch?v=FY3zTUaykVo)
 [Допълнително обяснение как работи този екран(https://www.engineersgarage.com/making-custom-characters-on-16x2-lcd/)
 
-
 [Картинки за различните видове дисплей с типовете им](https://gitlab.com/tues-embedded/vmks/-/tree/master/Useful%20Pictures/LCD/Types)
 
+[Проста примерна програма за управление на LCD с HD44780 без библиотека](https://gitlab.com/tues-embedded/vmks/-/tree/master/Examples/LCD_without_library_simple)  
+[По-пълна примерна програма за управление на LCD с HD44780 без библиотека](https://gitlab.com/tues-embedded/vmks/-/tree/master/Examples/LCD_without_library)  
+[Примерна документация на LCD 16x2 модул](https://gitlab.com/tues-embedded/vmks/-/tree/master/Datasheets/LCD_16x2_example_datasheet_ADM1602K-NSW-FBS-3.3v.pdf)
+
+Кодът на стандартната библиотека LiquidCrystal на Arduino може да намерите в директория `C:\Users\[username]\Documents\Arduino\libraries\LiquidCrystal\src` под Windows (за друга ОС потърсете в интернет къде са библиотеките).
+
 -----
 
 Кодиране на символ - пример с буквата `h`, като активните пиксели са `1`:
diff --git a/Other Useful Files/LCD_without_library_notes.txt b/Other Useful Files/LCD_without_library_notes.txt
new file mode 100644 (file)
index 0000000..2faf93d
--- /dev/null
@@ -0,0 +1,52 @@
+lcd.begin(COLS,ROWS,LCD_5x8DOTS)
+
+VMKS
+
+V = 0x56 = B 0101 0110
+M = 0x4D = B 0100 1101
+K = 0x4B = B 0100 1011
+S = 0x53 = B 0101 0011
+
+Steps to send command:
+0. Set RS
+1. Set Data value
+2. Wait >=100ns
+3. Set E high
+4. Wait >=300ns (can alse use this time to set Data value)
+5. Set E low
+6. Wait >=10ns
+7. Can change Data and repeat
+
+Steps to show text - from YouTube video:
+1. Set 4-bit mode and 1-line
+2. Clear display
+3. Return home
+4. Turn display on
+5. Send text in ASCII
+
+==================================================
+
+Steps to initialise the screen - from the library:
+1. Set 4-bit 2-line 5x8-dot mode
+2. Turn display-on, cursor-off, blinking-off
+3. Clear display
+4. Set autoincrement left-to-right, left-justified
+
+// When the display powers up, it is configured as follows:
+//
+// 1. Display clear
+// 2. Function set: 
+//    DL = 1; 8-bit interface data 
+//    N = 0; 1-line display 
+//    F = 0; 5x8 dot character font 
+// 3. Display on/off control: 
+//    D = 0; Display off 
+//    C = 0; Cursor off 
+//    B = 0; Blinking off 
+// 4. Entry mode set: 
+//    I/D = 1; Increment by 1 
+//    S = 0; No shift 
+//
+// Note, however, that resetting the Arduino doesn't reset the LCD, so we
+// can't assume that its in that state when a sketch starts (and the
+// LiquidCrystal constructor is called).