Go Down

Topic: Sparkfun SerLCD (Read 1 time) previous topic - next topic

aaronpropst

Hi all.

I'm trying to interface my arduino with sparkfun's SerLCD chip running one of their 16character lcd panels.
http://www.sparkfun.com/commerce/product_info.php?products_id=461

the documentation is here:
http://www.sparkfun.com/datasheets/LCD/SerLCD_V2_5.PDF

I'm hooking the lcd to the NG's tx port, and just sending commands with serial.print()

If i'm reading the documentation right,    Serial.print(0x01, HEX); should clear the screen.  Instead, the screen just prints '1'.  This is a pretty noobish mistake, i'm sure, but what exactly is going on?  does the print() function translate whatever format you send into ASCII before sending it out over the line?

is there any way i can send a literal hex command to this serial device?  According to the sparkfun documentation, if I can send it a 0x01, it will clear the screen.  Somewhere along the line though (i'm suspecting the print() command, it's being translated to a '1'

Daniel

#1
Feb 06, 2007, 07:27 pm Last Edit: Feb 06, 2007, 07:28 pm by Daniel Reason: 1
hi

look in the playground.. there is a tutorial there for interfacing serial LCD's. It will work with a few modifications.
Then, when you get it working, you can post a tutorial on it for everyone else to share .
:)

D

aaronpropst

Yup, that helped.

Turns out the key is to use:   Serial.print(0xFE, BYTE);   In other words sending the hex as 'byte' so that it is transmitted literally.  Looks like all the other .print() formats translate whatever you give them into ASCII.

I've got the LCD humming along now, and will make up a Sparkfun SerLCD specific playground page soon.  Thanks!

Daniel

that is great.. this community works best when people give back, so posting to the playground just makes it easier for others down the line!

D

BobG

Hi,
I have a simple project that talks to the Sparkfun serial LCD board.  Here it is, so enjoy.  This was built off the LCD project here, with a few changes.  Not all of the fuctions are working just yet, as it appears that the LCD needs a few commands added.  


Bob


//  *
//  * ------------
//  *  Control a Serial LCD Display
//  *  
//  *  Tested on a Matrix Orbital model LCD0821 display.
//  *  Other diplays will work but may have slightly different
//  *  command codes and hardware setups.
//  *  
//  *  Copyleft 2006 by djmatic
//  *  
//  * More copyleft 2007 Bob Grabau
//  *   ------------
//  *
//  *

// Definitions for the SparkFun SerLCD version 2 code.

#define BLINK_ON 0x0d
#define BLINK_OFF 0x0c
#define DISPLAY_ON 0x0c
#define DISPLAY_OFF 0x08
#define SHIFT_RIGHT 0x1c
#define SHIFT_LEFT 0x18
#define BACKLIGHT_OFF  128
#define BACKLIGHT_40   140
#define BACKLIGHT_70   150
#define BACKLIGHT_FULL 157

// Declare your program variables here


// Arduino and LCD setup

void setup()
{
 // Communication to the Serial LCD display is defaulted to 9600 baud.
 beginSerial(9600);
}


//  MAIN CODE

void loop()
{
 clearLCD();
 Serial.print(" Hello Arduino");  // print text to the current cursor position
 newLine();               // start a new line
 Serial.print("Frm SparkFun V2");
 cursorOn();
 delay(5000);
 cursorHome();
 delay(5000);
 cursor(BLINK_ON);
 delay(5000);
 cursor(BLINK_OFF);
 cursorOff();
 delay(5000);
 cursor(DISPLAY_OFF);
 delay(5000);
 cursor(DISPLAY_ON);
 delay(5000);
 cursor(SHIFT_RIGHT);
 delay(5000);
 cursor(SHIFT_LEFT);
 delay(5000);
 Set_Backlight(BACKLIGHT_OFF);
 delay(1000);
 Set_Backlight(BACKLIGHT_40);
 delay(1000);
 Set_Backlight(BACKLIGHT_70);
 delay(1000);
 Set_Backlight(BACKLIGHT_FULL);
 delay(5000);
}


//  LCD  FUNCTIONS-- keep the ones you need.

// clear the LCD
void clearLCD()
{
 Serial.print(254, BYTE);
 Serial.print(1, BYTE);
}

// start a new line
void newLine()
{
 Serial.print(254, BYTE);
 Serial.print(0xC0, BYTE);
}

// general cursor / display command routine
void cursor(int Mode)
{
 Serial.print(254, BYTE);
 Serial.print(Mode, BYTE);
}

// move the cursor to the home position
void cursorHome()
{
 Serial.print(254, BYTE);
 Serial.print(2, BYTE);
}

// turn the cursor on
void cursorOn()
{
 Serial.print(254, BYTE);
 Serial.print(0x0E, BYTE);
}

// turn the coursor off
void cursorOff()
{
 Serial.print(254, BYTE);
 Serial.print(0x0C, BYTE);
}

// move the cursor to a specific place
// e.g.: cursorSet(3,2) sets the cursor to x = 3 and y = 2
void cursorSet(int xpos, int ypos)
{  
#define HSIZE 16
#define VSIZE 2
 int pos;
 pos = (ypos * HSIZE) + xpos;
 pos += 0x80;

 // cur pos still broken
 Serial.print(pos, HEX);

 Serial.print(254, BYTE);
 Serial.print(pos, BYTE);
}

// backspace and erase previous character
void backSpace()
{
 //  Serial.print(8, BYTE);
}

// move cursor left
void cursorLeft()
{    
 //  Serial.print(254, BYTE);
 //  Serial.print(76, BYTE);  
}


// move cursor right
void cursorRight()
{
 //  Serial.print(254, BYTE);
 //  Serial.print(77, BYTE);  
}

// set LCD contrast
void setContrast(int contrast)
{
 //  Serial.print(254, BYTE);
 //  Serial.print(80, BYTE);  
 //  Serial.print(contrast);  
}

// turn on backlight
void backlightOn(int minutes)
{
 //  Serial.print(254, BYTE);
 //  Serial.print(66, BYTE);  
 //  Serial.print(minutes); // use 0 minutes to turn the backlight on indefinitely  
}

// Set the backlight by value
void Set_Backlight(int val)
{
 Serial.print(124, BYTE);
 Serial.print(val, BYTE);  
}

Daniel

#5
Feb 15, 2007, 10:23 am Last Edit: Feb 15, 2007, 10:23 am by Daniel Reason: 1
hey @BobG why don't you add this to the Playground LCD tutorials? It's useful down the line to all kinds of poeple. In the forum it tends to get lost after a while. Here's the page, just waiting to be edited  :)

D  

richard

I spent a few hours this morning trying to make a device that would make my real life job easier- a serial port message reporting device.  However, in order to use the SparkFun led display I needed a second serial port.  I had a bunch of really complicated ideas, but then saw the tutorial on software serial communications.  Since all I need to talk to the LED (with a serial backpack) is one 9600 baud tx, I hooked it up, adjusted the defined delay slightly, and it worked like a champ.

Added a switch to cycle through baud rates on the receiving end, and cut out everything above 28800 because it didn't seem to work at all.  I didn't troubleshoot this, as most of the communications I want to listen to are at 9600 baud...  I also block any characters that either don't have an associated graphic on my led or are one of the reserved command bytes and replace them with character 174, which looks like a little E on my led.

here's the code:
Code: [Select]
//Created August 15 2006
//Heather Dewey-Hagborg
//Modified February 25 2007
//Richard Shields
//Modifications:  Adjusted to only include software serial out,
//  takes serial in from pin 1 at adjustable baud rate and
//  retransmits those values to a 9600 baud serial display

//http://www.arduino.cc

#include <ctype.h>

#define bit9600Delay 92  
#define halfBit9600Delay 42
#define bit4800Delay 188
#define halfBit4800Delay 94

byte tx = 7;
byte switchBaud = 10;
byte switchSet = 0;
byte SWval;
int charCount = 0;  // variable to clear display when it gets full
int serialRate = 4800;  // change serial rate with this variable

void setup() {
 Serial.begin(serialRate);  // open the hardware serial port
 pinMode(tx,OUTPUT);
 pinMode(switchBaud,INPUT);
 digitalWrite(tx,HIGH);
 digitalWrite(13,HIGH); //turn on debugging LED
 SWprint(254);  // LED control message begin
 SWprint(1);  // Clear the display
 SWprint('S');
 SWprint('e');
 SWprint('r');
 SWprint('i');
 SWprint('a');
 SWprint('l');
 SWprint(' ');
 SWprint('M');
 SWprint('o');
 SWprint('n');
 SWprint('i');
 SWprint('t');
 SWprint('o');
 SWprint('r');
 SWprint(' ');
 SWprint(' ');
 SWprint('R');
 SWprint(' ');
 SWprint('S');
 SWprint('h');
 SWprint('i');
 SWprint('e');
 SWprint('l');
 SWprint('d');
 SWprint('s');
 SWprint(' ');
 SWprint(' ');
 SWprint('B');
 SWprint('B');
 SWprint('I');
 delay(3000);
 changeBaud();
}

void SWprint(int data)
{
 charCount++;
 byte mask;
 //startbit
 digitalWrite(tx,LOW);
 delayMicroseconds(bit9600Delay);
 for (mask = 0x01; mask>0; mask <<= 1) {
   if (data & mask){ // choose bit
    digitalWrite(tx,HIGH); // send 1
   }
   else{
    digitalWrite(tx,LOW); // send 0
   }
   delayMicroseconds(bit9600Delay);
 }
 //stop bit
 digitalWrite(tx, HIGH);
 delayMicroseconds(bit9600Delay);
}

void changeBaud() {
 SWprint(254);  // LED control message begin
 SWprint(1);
 SWprint('B');
 SWprint('a');
 SWprint('u');
 SWprint('d');
 SWprint(':');
 SWprint(' ');
 switch (serialRate) {
  case 300:
    serialRate = 1200;
    SWprint('1');
    SWprint('2');
    SWprint('0');
    SWprint('0');
    break;
  case 1200:
    serialRate = 2400;
    SWprint('2');
    SWprint('4');
    SWprint('0');
    SWprint('0');
    break;
  case 2400:
    serialRate = 4800;
    SWprint('4');
    SWprint('8');
    SWprint('0');
    SWprint('0');
    break;
  case 4800:
    serialRate = 9600;
    SWprint('9');
    SWprint('6');
    SWprint('0');
    SWprint('0');
    break;
  case 9600:
    serialRate = 14400;
    SWprint('1');
    SWprint('4');
    SWprint('4');
    SWprint('0');
    SWprint('0');
    break;
  case 14400:
    serialRate = 19200;
    SWprint('1');
    SWprint('9');
    SWprint('2');
    SWprint('0');
    SWprint('0');
    break;
  case 19200:
    serialRate = 28800;
    SWprint('2');
    SWprint('8');
    SWprint('8');
    SWprint('0');
    SWprint('0');
    break;
  case 28800:
    serialRate = 300;
    SWprint('3');
    SWprint('0');
    SWprint('0');
    break;
   default:
    serialRate = 9600;
    SWprint('9');
    SWprint('6');
    SWprint('0');
    SWprint('0');
    break;
 }
 Serial.flush();
 Serial.begin(serialRate);  // open the hardware serial port
 delay(750);
 SWprint(254);  // LED control message begin
 SWprint(1);  // Clear the display
 charCount = 1;  // reset character count
}

void loop()
{
 if (digitalRead(switchBaud) == HIGH) {
   if(!switchSet) {
    changeBaud();
   }
 } else {
    switchSet = 0;
 }
 if (Serial.available() > 0) {
   if (charCount > 32) {
     SWprint(254);  // LED control message begin
     SWprint(1);  // Clear the display
     charCount = 1;  // reset character count
   }
   SWval = Serial.read();
   if ((SWval > 31) && (SWval != 124) && (SWval != 254) && ((SWval < 129) || (SWval > 160))) {
     SWprint(SWval);
   } else {
     SWprint(174);
   }
 }
}


Here is the hardware, but don't hook this up directly to a serial port; I'll be revising the drawing after I play with the hardware tomorrow.  The serial connector and circuit are probably going to look a lot like the rs232 connection on the original Arduino schematic...



-richard

mellis

BTW, there's also a SoftwareSerial library built into the latest version of Arduino: http://www.arduino.cc/en/Reference/SoftwareSerial.  I'll add a pointer to it from that tutorial.

richard

I was checking that out and thinking about using it, but had already started with Heather's code and it was working fine...

I got to work this morning and found a SparkFun rs232 Shifter in my desk, which made assembly all that much easier!  I also used a basic 7805 circuit to power the device from a 9 volt battery (dropped down to 5 volts and a power switch on the battery).  An hour of soldering and I have my serial monitoring tool.  Works great, all it needs now is some kind of box with mounting so I can throw it in my toolbag.

One funny thing that happened; when I passed the serial wire from the mini to the serial led too close to my 7805 and it's capacitors, the output on the serial led went to all pixels lit; moved that wire away from them and everything went back to normal.  Just something to be wary of if anyone else is making one of these; keep your communication cables away from your power regulator!

-richard

Go Up