Difference between revisions of "ECE 110/Equipment/Serial LCD"
(Created page with "== Introduction == There are several multi-character LCD displays available. For ECE 110, we will specifically be using a 16x2 display that has a Parallax Serial LCD module a...") |
|||
(9 intermediate revisions by 2 users not shown) | |||
Line 8: | Line 8: | ||
* 3 (right): Ground | * 3 (right): Ground | ||
− | The CX-Bot has a header for the three-pin serial version; the | + | The CX-Bot has a header for the three-pin serial version; the RX pin is connected to Serial3 Tx (pin 14). |
== Operation == | == Operation == | ||
− | The serial version of the LCD receives characters through a serial bus; for the CX-Bot, these are linked to Serial3 which has pin 14 as its | + | The serial version of the LCD receives characters through a serial bus; for the CX-Bot, these are linked to Serial3 which has pin 14 as its Tx3 line and pin 15 as its Rx3 line. The header will allow you to connect Serial3's transmit line (Tx3) to the LCD's receive line (RX). You will create a connection to the display using the <code>SoftwareSerial</code> library, which provides an object type of the same name: |
<syntaxhighlight lang=C++> | <syntaxhighlight lang=C++> | ||
#include <SoftwareSerial.h> | #include <SoftwareSerial.h> | ||
Line 34: | Line 34: | ||
The Parallax Serial LCD also has a piezoelectric speaker you can use. If you want to play a note, you basically need to send three codes: duration, octave, and note within octave. | The Parallax Serial LCD also has a piezoelectric speaker you can use. If you want to play a note, you basically need to send three codes: duration, octave, and note within octave. | ||
* 208-214: duration from 1/64th to a whole note. Whole notes are 2 seconds long | * 208-214: duration from 1/64th to a whole note. Whole notes are 2 seconds long | ||
− | * 215-219: octave; 215 starts at middle A (440 Hz), each octave doubles the frequency after that | + | * 215-219: octave; 215 starts at middle A (440 Hz), each octave doubles the frequency after that. '''''Note''''' - in music, typically an octave starts with C; C4 or "middle C" (262 Hz) is just above B3 and just below Dflat4. For this device, however, the scales start at A, meaning "middle A" (440 Hz) is scale 4 note A and middle C, which is a few steps below middle A, is scale '''''3''''' note C. The bottom of p. 7 of the PDF guide shows the table of frequencies. |
− | * 220-231: note; | + | * 220-231: note; 220 is A, 221 is A#, etc. |
* 232: no note; play silence for the duration specified. | * 232: no note; play silence for the duration specified. | ||
Line 70: | Line 70: | ||
} | } | ||
} | } | ||
+ | </syntaxhighlight> | ||
+ | === Turn Off === | ||
+ | When you are done using the display for the day, you should turn it off before disconnecting it. Here is some code that will do that: | ||
+ | |||
+ | <syntaxhighlight lang=C++> | ||
+ | #include <SoftwareSerial.h> | ||
+ | |||
+ | #define TxPin 14 | ||
+ | |||
+ | SoftwareSerial mySerial = SoftwareSerial(255, TxPin); | ||
+ | |||
+ | void setup() { | ||
+ | mySerial.begin(9600); | ||
+ | delay(100); | ||
+ | mySerial.write(12); // clear | ||
+ | delay(10); | ||
+ | mySerial.write(21); // display off | ||
+ | delay(10); | ||
+ | mySerial.write(18); // backlight off | ||
+ | delay(10); | ||
+ | } | ||
+ | |||
+ | void loop() { | ||
+ | } | ||
+ | </syntaxhighlight> | ||
+ | |||
+ | === Music and Text === | ||
+ | Here is code that uses both lines of the display and plays a short song; the delay is to make sure a note has finished playing before sending the next note over serial - without this, the memory buffer for the LCD may fill up and miss signals that come later. The only hardware you need is the Parallax LCD connected to the LCD Serial 3 header on the CX-Bot. | ||
+ | <syntaxhighlight lang=c++> | ||
+ | #include <SoftwareSerial.h> | ||
+ | |||
+ | #define TxPin 14 | ||
+ | |||
+ | SoftwareSerial mySerial = SoftwareSerial(255, TxPin); | ||
+ | |||
+ | #define num 9 | ||
+ | |||
+ | int durs[num] = {211, 212, 212, 211, 212, | ||
+ | 212, 212, 212, 212 | ||
+ | }; | ||
+ | int octs[num] = {216, 216, 216, 216, 216, | ||
+ | 216, 216, 215, 216 | ||
+ | }; | ||
+ | int notes[num] = {227, 227, 227, 223, 227, | ||
+ | 230, 232, 230, 232 | ||
+ | }; | ||
+ | |||
+ | void setup() { | ||
+ | mySerial.begin(9600); | ||
+ | delay(100); | ||
+ | mySerial.write(12); // clear | ||
+ | delay(10); | ||
+ | mySerial.write(22); // no cursor no blink | ||
+ | delay(10); | ||
+ | mySerial.write(17); // backlight | ||
+ | delay(10); | ||
+ | mySerial.print("Super Mario"); | ||
+ | mySerial.write(13); | ||
+ | mySerial.print("Brothers!"); | ||
+ | for(long k=0; k<num; k++){ | ||
+ | |||
+ | mySerial.write(durs[k]); mySerial.write(octs[k]); mySerial.write(notes[k]); | ||
+ | int len = 214 - durs[k]; | ||
+ | float del = 2000 / pow(2, len); | ||
+ | delay(int(del*1.1)); | ||
+ | } | ||
+ | |||
+ | } | ||
+ | |||
+ | void loop() { | ||
+ | |||
+ | } | ||
+ | |||
+ | </syntaxhighlight> | ||
+ | |||
+ | |||
+ | === Music and Text with Functions === | ||
+ | This is effectively the same code as above, only the musical part is in a function. | ||
+ | <syntaxhighlight lang=c++> | ||
+ | #include <SoftwareSerial.h> | ||
+ | |||
+ | #define TxPin 14 | ||
+ | |||
+ | SoftwareSerial mySerial = SoftwareSerial(255, TxPin); | ||
+ | |||
+ | #define num 9 | ||
+ | |||
+ | int durs[num] = {211, 212, 212, 211, 212, | ||
+ | 212, 212, 212, 212 | ||
+ | }; | ||
+ | int octs[num] = {216, 216, 216, 216, 216, | ||
+ | 216, 216, 215, 216 | ||
+ | }; | ||
+ | int notes[num] = {227, 227, 227, 223, 227, | ||
+ | 230, 232, 230, 232 | ||
+ | }; | ||
+ | |||
+ | void setup() { | ||
+ | mySerial.begin(9600); | ||
+ | delay(100); | ||
+ | mySerial.write(12); // clear | ||
+ | delay(10); | ||
+ | mySerial.write(22); // no cursor no blink | ||
+ | delay(10); | ||
+ | mySerial.write(17); // backlight | ||
+ | delay(10); | ||
+ | mySerial.print("Super Mario"); | ||
+ | mySerial.write(13); | ||
+ | mySerial.print("Brothers!"); | ||
+ | play_song(); | ||
+ | |||
+ | } | ||
+ | |||
+ | void loop() { | ||
+ | |||
+ | } | ||
+ | |||
+ | void play_song() { | ||
+ | for(long k=0; k<num; k++){ | ||
+ | |||
+ | mySerial.write(durs[k]); mySerial.write(octs[k]); mySerial.write(notes[k]); | ||
+ | int len = 214 - durs[k]; | ||
+ | float del = 2000 / pow(2, len); | ||
+ | delay(int(del*1.1)); | ||
+ | } | ||
+ | } | ||
+ | |||
</syntaxhighlight> | </syntaxhighlight> | ||
Latest revision as of 17:59, 26 July 2024
Contents
Introduction
There are several multi-character LCD displays available. For ECE 110, we will specifically be using a 16x2 display that has a Parallax Serial LCD module attached to it. Among other things, this makes the display a three-pin device versus a 16-pin device! It also allows for brightness control and sound on board.
Leads
- 1 (left): RX (receive)
- 2 (middle): 5 V
- 3 (right): Ground
The CX-Bot has a header for the three-pin serial version; the RX pin is connected to Serial3 Tx (pin 14).
Operation
The serial version of the LCD receives characters through a serial bus; for the CX-Bot, these are linked to Serial3 which has pin 14 as its Tx3 line and pin 15 as its Rx3 line. The header will allow you to connect Serial3's transmit line (Tx3) to the LCD's receive line (RX). You will create a connection to the display using the SoftwareSerial
library, which provides an object type of the same name:
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
You can then use mySerial.write(VAL)
to send a single raw byte to the display or mySerial.print(STRING)
to send a collection of characters. The codes are given on pp. 8-13 of Product Guide; here are some of the more used ones (codes given in decimal):
- 12: clear the display and move cursor to top left (line 0 position 0). There needs to be at least a 5 ms delay after this.
- 22-25: turn the display on set the cursor (line or not under current location) and blink (blink or not at current location):
- 22 cursor off, blink off
- 23 cursor off, blink on
- 24 cursor on, blink off (default)
- 25 cursor on, blink on
- 17, 18: turn the backlight on, off
- 128-143: move cursor directly to line 0 positions 0-15
- 148-163: move cursor directly to line 1 positions 0-15
Music
The Parallax Serial LCD also has a piezoelectric speaker you can use. If you want to play a note, you basically need to send three codes: duration, octave, and note within octave.
- 208-214: duration from 1/64th to a whole note. Whole notes are 2 seconds long
- 215-219: octave; 215 starts at middle A (440 Hz), each octave doubles the frequency after that. Note - in music, typically an octave starts with C; C4 or "middle C" (262 Hz) is just above B3 and just below Dflat4. For this device, however, the scales start at A, meaning "middle A" (440 Hz) is scale 4 note A and middle C, which is a few steps below middle A, is scale 3 note C. The bottom of p. 7 of the PDF guide shows the table of frequencies.
- 220-231: note; 220 is A, 221 is A#, etc.
- 232: no note; play silence for the duration specified.
Sample Code
Simple
The following example will use the Serial Monitor to receive input from the user; the input will be displayed on the LCD starting with the first character on the top left row (line 0, position 0). If the input has more than 16 characters, the input will wrap to the second line. If the input has more than 32 characters, the 33rd will overwrite the 1st and any more will overwrite other ones that were there before. The LCD starts at the first character every time due to the
mySerial.write(12);
line.
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
void setup() {
Serial.begin(9600);
mySerial.begin(9600);
delay(100);
mySerial.write(12); // clear
delay(10);
mySerial.write(22); // no cursor no blink
delay(10);
mySerial.write(17); // backlight
delay(10);
}
void loop() {
if (Serial.available() > 0){
mySerial.write(12); delay(5);
String myInput = Serial.readString();
myInput.trim();
mySerial.print(myInput);
}
}
Turn Off
When you are done using the display for the day, you should turn it off before disconnecting it. Here is some code that will do that:
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
void setup() {
mySerial.begin(9600);
delay(100);
mySerial.write(12); // clear
delay(10);
mySerial.write(21); // display off
delay(10);
mySerial.write(18); // backlight off
delay(10);
}
void loop() {
}
Music and Text
Here is code that uses both lines of the display and plays a short song; the delay is to make sure a note has finished playing before sending the next note over serial - without this, the memory buffer for the LCD may fill up and miss signals that come later. The only hardware you need is the Parallax LCD connected to the LCD Serial 3 header on the CX-Bot.
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
#define num 9
int durs[num] = {211, 212, 212, 211, 212,
212, 212, 212, 212
};
int octs[num] = {216, 216, 216, 216, 216,
216, 216, 215, 216
};
int notes[num] = {227, 227, 227, 223, 227,
230, 232, 230, 232
};
void setup() {
mySerial.begin(9600);
delay(100);
mySerial.write(12); // clear
delay(10);
mySerial.write(22); // no cursor no blink
delay(10);
mySerial.write(17); // backlight
delay(10);
mySerial.print("Super Mario");
mySerial.write(13);
mySerial.print("Brothers!");
for(long k=0; k<num; k++){
mySerial.write(durs[k]); mySerial.write(octs[k]); mySerial.write(notes[k]);
int len = 214 - durs[k];
float del = 2000 / pow(2, len);
delay(int(del*1.1));
}
}
void loop() {
}
Music and Text with Functions
This is effectively the same code as above, only the musical part is in a function.
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
#define num 9
int durs[num] = {211, 212, 212, 211, 212,
212, 212, 212, 212
};
int octs[num] = {216, 216, 216, 216, 216,
216, 216, 215, 216
};
int notes[num] = {227, 227, 227, 223, 227,
230, 232, 230, 232
};
void setup() {
mySerial.begin(9600);
delay(100);
mySerial.write(12); // clear
delay(10);
mySerial.write(22); // no cursor no blink
delay(10);
mySerial.write(17); // backlight
delay(10);
mySerial.print("Super Mario");
mySerial.write(13);
mySerial.print("Brothers!");
play_song();
}
void loop() {
}
void play_song() {
for(long k=0; k<num; k++){
mySerial.write(durs[k]); mySerial.write(octs[k]); mySerial.write(notes[k]);
int len = 214 - durs[k];
float del = 2000 / pow(2, len);
delay(int(del*1.1));
}
}
Formatted Text and Music
Here is a code that shows how to use buffers and sprintf to create formatted text and how to play music. Note - this gets very annoying very fast, so be sure to have the BareMinimum script prepared for loading...
#include <SoftwareSerial.h>
#define TxPin 14
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);
void setup() {
Serial.begin(9600);
mySerial.begin(9600);
delay(100);
mySerial.write(12); // clear
delay(10);
mySerial.write(22); // no cursor no blink
delay(10);
mySerial.write(17); // backlight
delay(10);
}
void loop() {
int x = random(0, 10);
int y = random(0, 10);
char buffer[16];
sprintf(buffer, "%d + %d = %2d", x, y, x+y);
mySerial.write(12); // clear
delay(10);
mySerial.write(buffer);
mySerial.write(13); // cr
int note = (x+y)%12; // get a number between 0 and 11
note = note + 220; // map [0-11] to [220-231] for note
sprintf(buffer, "%d * %d %% 12 = %2d", x, y, (x+y) % 12);
mySerial.write(buffer);
mySerial.write(211); mySerial.write(216); mySerial.write(note);
delay(500);
}
Notes
References
- Parallax 2 x 16 Serial LCD with Piezo Speaker (Backlit)
- Includes link to Product Guide