Parallax single instance text scroll

Hi all and thanks for taking the time to read my question.

This is a combination of questions that I have. I've only had my Arduino Uno about a week so I apologize in advance if I ask something that seems dumb.

Facts:

I am currently running an arduino uno r3 with a parallax 16char x 2 char display model # 27922-RT.
I have the display up and running simple texts that I feed it in my "setup" class.

I wanted to try something a little more difficult and have the text loop one time on the display from right to left on line 1.
Additionally, I want line 2 to display a static text.

here is the code I have written to do so with some pseudo code at the top (commented out) to help me jot my thoughts down as I approached the problem.

Code:

/* Pseudo code
if the length of the string is greater than 16
then display the first character at the far right
then display the first and second character
then display the first, second, and third character....
till you hit the 17 char then display char 2-16 and so on
until you hit the end. then display the blank char at length-15 + one blank

if the length of the string is greater than 16,
add 16 blank spaces to it " "
add this new string with 16 blanks to a temporary variable
then, itterate through the string to display it.
*/

const int TxPin = 6;

#include <SoftwareSerial.h>
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);

int delayTime = 2000;

String x = "Hello, teo from Meow, AKA Slim, AKA The Prince of Darkness";

void setup() {

pinMode(TxPin, OUTPUT);
digitalWrite(TxPin, HIGH);

mySerial.begin(9600);
delay(100);

mySerial.write(22); // disable cursor disable blink
mySerial.write(12); // Clear

mySerial.write(17); // Turn backlight on
delay(5); // Required delay

if(x.length() > 16){
String tempX = x + " ";
int tempXLen = tempX.length();
for(int i = 0; i < tempXLen; i++){
String tempDisp = tempDisp.substring(i, i+15);
mySerial.print(tempDisp);
delay(2000);
}
}
else {

mySerial.write(x);
}

mySerial.write(13); // Form feed
mySerial.print("from the cat!"); // Second line
mySerial.write(212); // Quarter note
mySerial.write(220); // A tone
delay(3000); // Wait 3 seconds
mySerial.write(18); // Turn backlight off

}

void loop() {

}

//

I'm getting an error that points to the following line

mySerial.write(x);

the error states "no matching function for call to 'SoftwareSerial::write(String&)'

Questions:

  1. Can I get the parallax display to scroll text using a loop the way that I have?
  2. Is there a better way to get the display to scroll text than how I have approached it?
  3. Why does my code not function the way it is written?

I thank anyone and everyone for looking.

Best,
Warmonger0

Hi warmonger, and welcome.

  1. In terms of general form, most of your code should actually be in loop(), rather than setup(). Setup() is really just for setting up initial hardware requirements. If you don't want to actually loop() your code, you can put a "while (1) ;" at the end of the loop. I don't use LCDs, but in general terms your code looks like it is in the ballpark. You may have to put a "\n" on the end of lines to be sure you're always starting a new line, or maybe the lcd has a method to print specifically to line 1 or line 2.

  2. There's always many ways to skin a cat, but your substring is a decent way to go.

  3. The error is because you are calling mySerial.write(x); x is a String object. mySerial.write() only takes a string (character array) - Notice the small 's' string instead of big 'S' String. You would have to call mySerial.write(x.toCharArray());

I'm not entirely sure but i believe the code
mySerial.write(13); //form feed

actually makes it print to the second line.

with regards to your explanation of the error, 2 things

  1. thank you for pointing out that that it is for a char array and not a string. little s v S. I understand that now.

  2. as for your proposed edit of my code
    mySerial.write(x.toCharArray());

this returns an error as well
" no matching function to call to 'String;;toCharArray()'"

i'm assuming that means that toCharArray() is not defined in the arduino language? or am I wrong?

Yep, mySerial.write(13); is the way to go (I just checked the LCD datasheet here: Microcontroller KickStarts | LEARN.PARALLAX.COM )

If you haven't seen it, the full datasheet with all the available commands is here:

  1. Hmmm, that surprises me a little. It's definitely defined for the String class in ardunio.

See:

Also, the valid parameters for Serial.write() (supposedly the same as mySerial.write()) are here:

I just looked it up (and I misused toCharArray() anyway :P). It seems like you might have to do something like this:

byte buf[100];
x.getBytes(buf, 100) ;
mySerial.write(buf);

okay, I knew the toChar from java so i thought it would be valid too. thanks for taking the time to look at this.

Can you explain why i would have to use these first 2 lines?
byte buf[100];
x.getBytes(buf, 100) ;

my understanding is that i'm making an array of bytes called buf
then ...getting the bytes from x and storing them in buf?
then writing the output of buf?

sorry i'm just not seeing it at this point and further explanation would really be helpful. I like to learn it as i go rather than just putting in the code and getting it to work.

thanks again,
War

Your understanding is correct.

We need to transform the String object contents into something acceptable to Serial.write(). One of the options for Serial.write is a string, which seems to be a null terminated array of bytes in this world. So we need to extra the characters from x into an array of bytes, in order for us to be able to pass them to Serial.write(string);

So yeah, we create a place to store them, then copy them in. Then we pass that into Serial.write();

okay, here's what I have now and still...not quite working

the new error is
"cakk if iverkiaded 'write(byte [100])' is ambiguous"

Code:

/* Pseudo code
if the length of the string is greater than 16
then display the first character at the far right
then display the first and second character
then display the first, second, and third character....
till you hit the 17 char then display char 2-16 and so on
until you hit the end. then display the blank char at length-15 + one blank

if the length of the string is greater than 16,
add 16 blank spaces to it " "
add this new string with 16 blanks to a temporary variable
then, itterate through the string to display it.
*/

const int TxPin = 6;

#include <SoftwareSerial.h>
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);

//variables
int dTime = 2000;
char tChar[16];
String x = "Hello, teo from Meow, AKA Slim, AKA The Prince of Darkness";

void setup() {

pinMode(TxPin, OUTPUT);
digitalWrite(TxPin, HIGH);

mySerial.begin(9600);
delay(100);

mySerial.write(22); // disable cursor disable blink
mySerial.write(12); // Clear

mySerial.write(17); // Turn backlight on
delay(5); // Required delay

if(x.length() > 16){
String tempX = x + " ";
int tempXLen = tempX.length();
for(int i = 0; i < tempXLen; i++){
String tempDisp = tempDisp.substring(i, i+15);
mySerial.print(tempDisp);
delay(dTime);
}
}
else {

byte buf[100];
x.getBytes(buf, 100) ;
mySerial.write(buf);

}

mySerial.write(13); // Form feed
mySerial.print("from the cat!"); // Second line
mySerial.write(212); // Quarter note
mySerial.write(220); // A tone
delay(dTime); // Wait 3 seconds
mySerial.write(18); // Turn backlight off

}

void loop() {

}

It turns out the arduino documentation is a little off. It needs a character array, not a byte array.

You need:

char buf[100];
x.toCharArray(buf, 100) ;
Serial.write(buf);

haha,

well, that solved the error but, it looks like my scrolling text portion needs a little work. It still doesn't display at all.

I'll keep working at it.

Probably this line:

String tempDisp = tempDisp.substring(i, i+15);

should be

String tempDisp = tempX.substring(i, i+15);

yup, I was just commenting my code and caught it.

it still has some weird display issues though.

const int TxPin = 6;

#include <SoftwareSerial.h>
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);

//variables
int dTime = 2000;

String x = "Hello, teo from Meow, AKA Slim, AKA The Prince of Darkness";

void setup() {

pinMode(TxPin, OUTPUT);
digitalWrite(TxPin, HIGH);

mySerial.begin(9600);
delay(100);

mySerial.write(22); // disable cursor disable blink
mySerial.write(12); // Clear

mySerial.write(17); // Turn backlight on
delay(5); // Required delay

if(x.length() > 16){ //if the length of the input string, in this case x, is longer than 16
//this loop should run
String tempX = x + " "; // adds 16 " " spaces to the end of the string so the text can be length + 16 for a full scroll.
int tempXLen = tempX.length(); //creates a temporary variable to hold the length of the new temporary string tempX.
for(int i = 0; i < tempXLen; i++){ // for loop to itterate through the string tempX.
String tempDisp = tempX.substring(i, i+15); //creates a String tempDisp which is a substring of tempX that is 16 characters long.
mySerial.print(tempDisp); //prints out tempDisp variable on the display
delay(500); // delays .5 seconds (delay before the loop runs again).
}
}
else { //if the string x is length 16 or less then, just display the string

char buf[100];
x.toCharArray(buf, 100) ;
Serial.write(buf);

}

mySerial.write(13); // Form feed
mySerial.print("from the cat!"); // Second line
mySerial.write(212); // Quarter note
mySerial.write(220); // A tone
delay(dTime); // Wait 2 seconds
mySerial.write(18); // Turn backlight off

}

void loop() {

}

when it's scrolling it does not display very well. the very first instance of the loop displays perfectly

it says "hello, teo from"
then it begins to jumble a bit. as well as begins to display characters on the second line of the display with out having advanced to that portion of the code.

obviously the comments in my editor are on single lines and do not scroll down to the next line in the code.

Actually I think this will better explain what is happening.

I've recorded the code in action and put it on my youtube.

thanks again for taking the time to help me through this arduinodlb.

Getting better.

In your loop, you need to reset the cursor to position 0, otherwise it just appends the text to what was already on the screen.

There's some control code for home in the parallax LCD I believe.

for(int i = 0; i < tempXLen; i++){
// You need a line here to set the cursor to 0,0 on your LCD screen.
String tempDisp = tempX.substring(i, i+15);
mySerial.print(tempDisp);
delay(500);
}

I think you might have a #27977

Here's the datasheet:

Try:

mySerial.write(128);

dude,
you rock. i got it working.

final code

const int TxPin = 6;

#include <SoftwareSerial.h>
SoftwareSerial mySerial = SoftwareSerial(255, TxPin);

//variables
int dTime = 2000;

String x = "Hello, teo from Meow, AKA Slim, AKA The Prince of Darkness";

void setup() {

pinMode(TxPin, OUTPUT);
digitalWrite(TxPin, HIGH);

mySerial.begin(9600);
delay(100);

mySerial.write(22); // disable cursor disable blink
mySerial.write(12); // Clear

mySerial.write(17); // Turn backlight on
delay(5); // Required delay

if(x.length() > 16){ //if the length of the input string, in this case x, is longer than 16

String tempX = " " + x + " "; // adds 16 " " spaces to the end of the string so the text can be length + 16 for a full scroll.
int tempXLen = tempX.length(); //creates a temporary variable to hold the length of the new temporary string tempX.
for(int i = 0; i < tempXLen; i++){ // for loop to itterate through the string tempX.

mySerial.write(128);
String tempDisp = tempX.substring(i, i+15); //creates a String tempDisp which is a substring of tempX that is 16 characters long.
mySerial.print(tempDisp); //prints out tempDisp variable on the display
delay(150); // delays .5 seconds (delay before the loop runs again).
}
}
else { //if the string x is length 16 or less then, just display the string

char buf[100];
x.toCharArray(buf, 100) ;
Serial.write(buf);

}

mySerial.write(13); // Form feed
mySerial.print("from the cat!"); // Second line
mySerial.write(212); // Quarter note
mySerial.write(220); // A tone
delay(dTime); // Wait 2 seconds
mySerial.write(18); // Turn backlight off

}

void loop() {

}

Congrats!

Hi folks,

I am new to programing and trying to learn a few things using this example. The "else" part of this script doesn't seem to work. If I change String x to "String x = "Test"", the sketch doesn't work.

Thanks,
Mike