Serial LCD - NHD-0220D3Z-FL-GBW-ND is unresponsive

EDIT - I need some freaking coffee... I had the pins wired incorrectly... Whoops...

Hate to start a new thread since there already so many LCD threads but after a lot of searching I was unable to find a solution.

Datasheet for Serial LCD - http://www.newhavendisplay.com/specs/NHD-0220D3Z-FL-GBW.pdf
It does use the HD44780 chip but the commands are slightly different than the pre-made libraries I found...

Here's how I have it connected

LCD <---> Arduino
Pin1          5v
Pin2          GND
Pin3          Pin 1 (TX)

When I run my test program the backlight comes on. So the LCD 'seems' to be working. But I can't output any data. It doesn't seem to be responding to any commands either.

I did make the mistake of uploading my program to the LCD with the TX Pin connected and the IDE gave me an error. I promptly removed the Pin and re-uploaded my program. Could this have caused any issues? Or am I just sending commands to the LCD incorrectly.

Here's the program that the Arduino is currently running.

void setup()
{
  Serial.begin(9600);
}

void loop() 
{ 
   Serial.print(254, BYTE); // begin command
  Serial.print(97, BYTE); // start set baud rate - 0x61 HEx
  Serial.print( 4, BYTE); // set 9600
  delay(100);

  Serial.print(254, BYTE);
  Serial.print(70, BYTE); // set home cursor - 0x46 HEX
  delay(100);
  
  Serial.print(254, BYTE);
  Serial.print(112, BYTE); // display firmware - 0x70 HEX
  delay(100);
  
  Serial.print(254, BYTE);
  Serial.print(127, BYTE); // display character - 0x7F HEX
  delay(100); 
}

mrf582:

commands are slightly different than the pre-made libraries I found...

This appears to be a Serial / I2C device so the regular LCD libraries such as LiquidCrystal are not appropriate. Make sure that any pre-made Serial library that you try is written for this device. I suspect that most of them are written for the PHAnderson serial chip that has been around for decades. The commands may or may not be the same.

What really concerns me is that your program has most of the commands in loop() rather than where they belong which is in setup(). You only have to send the information to the LCD module once and it will remain displayed until overwritten by new information.

Don

Understood!

They are in loop only because my mouse just happened to land there... This was just a test to see if i could even output anything to the screen. My actual program will definitely use the setup () function and will be writing my own functions to do 'housekeeping' tasks.

I guess I might as well make my own library that I can call from my main program. Then just '#include' that in my actual program. So how do I organize the functions in my own 'library'? I guess I should just take a look at a sample 'library' or '*.h' file to make it easier on myself.

I haven't messed with Java since 2001 when I took one or two classes before I switched majors to Engineering. The OOP nature of Java will apply quite well to this language.

Just wanted to update this thread with my code. There's a LOT of things to do still but it's getting very very close. I'm about to go to sleep, so I figured I'd update this thread (maybe just to have another copy of the code available somewhere...).

Current known issues:

  • speaker is way too quiet. seemed to work fine when it was the only thing connected via hardware.
  • need to figure out how to deal with peak displays.
  • i guess warnings should be enough?
  • other things i'm forgetting since my liver has been more functional than my brain for the past few hours :wink:
  • clean up/ document code/ orgainze etc.
/*
  Abhishek Shinde
  Multigauge LCD (c) 2009

*/


// define analog inputs as constants : 0v = 0, 5v = 1023 
const int oiltPin = 1;     // oil temperature signal wire                <- voltage divider from Prosport oilt sensor 32F = 4550ohm, 104F = 925ohm, 176F = 224ohm, 212 = 120ohm
const int oilpPin = 2;     // oil pressure signal wire                   <- voltage divider from Prosport oilp sensor 0-145psi, 3-160ohm
const int  mrpPin = 3;     // manifold absolute pressure signal wire     <- 0-5v input from ECU pin
const int  afrPin = 4;     // wideband oxygen sensor                     <- 0-5v input from LC-1
const int  h2oPin = 5;     // factory coolant temperature sensor         <- 0-5v input from ECU pin

const int oiltMax = 230;   // maximum oil temp       (Fahrenheit)
const int  mrpMax = 20;    // maximum boost pressure (psi)
const int  h2oMax = 220;   // maximum water temp     (Fahrenheit)

// define peak and warn variables
boolean oiltWarn = false;
boolean  mrpWarn = false;
boolean  h2oWarn = false;
int     oiltPeak = 0;
int      mrpPeak = 0;
int      h2oPeak = 0;

// TESTING CRAP
int ledPin = 13;              // test
int ledState = LOW;           // test
long previousMillis = 0;      // test
int pinSpeaker = 13;          // speaker output



// Setup 
void setup() {
  delay(500);              // delay before program start. may not be needed
  Serial.begin(9600);
  pinMode(ledPin,OUTPUT);     // test
  pinMode(pinSpeaker, OUTPUT);

  // LCD stuff
  initLCD ();              // one time intialization of LCD
}





// check warning code
int read_oilt () {                                      // returns actual oil temperature in Fahrenheit
  
  float raw = (analogRead(oiltPin) + 1) * .00488;       // read digital value and convert to actual analog volt value, analogRead() : 0v = 0, 5v = 1023 (1024 steps) : .00488v = 1 step

  //Serial.print("volt = ");                              //debug to serial monitor
  //Serial.print(raw);                                    //debug to serial monitor
  //Serial.print(" temp     = ");                         //debug to serial monitor
  
  // oil temp = 6.298x^3 - 45.72x^2 + 139.8x - 60.4 - derived equation using temp sensor and '1000' ohm voltage divider
  int oiltValue = ((6.298 * raw * raw * raw) - (45.72 * raw * raw) + (139.8 * raw) - 60.4); // convert to actual temperature reading in fahrenheit
  
  if (oiltValue >= oiltMax) {                           // check if oil level is above Max
    oiltWarn = true;                                    // set warning level
    if (oiltValue > oiltPeak) oiltPeak = oiltValue;     // update peak oil temp if above current peak
  } else {                                              // do this if oil level is below Max
    oiltWarn = false;
  }
  
  return oiltValue;
}

// done
int read_oilp () { // return actual oil pressure in psi
  
  float raw = (analogRead(oilpPin) + 1) * .00488; // read digital value and convert to actual analog volt value

  
  //Serial.print("   volt = ");                          //debug to serial monitor
  //Serial.print(raw);                                   //debug to serial monitor
  //Serial.print(" pressure = ");                        //debug to serial monitor
  
  // oil pressure = -.322x^3 + 4.278x^2 -20.59x + 35.98 - derived equation using 3-160ohm pressure sensor and '100' ohm voltage divider
  int oilpValue = ((-4.698 * raw * raw * raw) + (61.9 * raw * raw) - (295.5* raw) + 513.1); // convert to actual pressure reading in psi
 
  return oilpValue;
}


int read_mrp () {                                     // return actual boost pressure in psi at 'sea level'
   
   float raw = (analogRead(mrpPin) + 1) * .00488;     // read digital value and convert to actual analog volt value

   int mrpValue = raw * 9.943 - 8.005 - 14.7;         // equation from factory map scaling and subtracted 'sea level' pressure
   
   if (mrpValue >= mrpMax) {
     mrpWarn = true;
     if (mrpValue >= mrpMax) mrpPeak = mrpValue;     // update peak oil temp if above current peak
   } else {                                              // do if oil level is below Max
    mrpWarn = false;
   }
   
   return mrpValue;
}

int read_h2o () {
    
  
    float raw = (analogRead(h2oPin) + 1) * .00488;
    int h2oValue = (-6.445 * raw * raw * raw) + (50.11 * raw * raw) + (-167.0 * raw) + (313.4);
    
    if (h2oValue >= h2oMax) {
      h2oWarn = true; // set warning level
      h2oPeak = h2oValue; // error check
    }
    
    return h2oValue;
}



boolean flip = true;

//simulation variables
int simoilt = 44;
int simoilp = 125;
int simmrp = -.8;
int simwt = 50;
float simafr = 14.7;

// Main program
void loop() {
  //dispDebug ();   // debug to serial monitor
  //dispData();
  doSim();
  dispData();
  checkWarn();
}  
  
 
void doSim() {  
       if (millis() - previousMillis > 2000) {
       // save the last time you blinked the LED 
       previousMillis = millis();
       simoilt++;
       simoilp--;
       simmrp += 1;
       simwt += 1;
       simafr = 14.7;
       }

}
  //if (millis() < 1000) delay(1000);                              // wait atleast one second to start the program

  
   
   /*
   if (oiltWarn || mrpWarn || h2oWarn) {                                              // blink LED if any Warn = true
     if (millis() - previousMillis > 250) {
       // save the last time you blinked the LED 
       previousMillis = millis();   
       oiltMax++; 
       // if the LED is off turn it on and vice-versa:
       if (ledState == LOW) ledState = HIGH;
       else ledState = LOW;
     }
   } else {
       ledState = LOW;
   }
    digitalWrite(ledPin, ledState);              // set the LED with the ledState of the variable:
                                 
    //playTone(150, 1000);
    //playTone(150, 2500);
    //playTone(50, 1800);
    //playTone(750, 3000);
    */
    
void checkWarn () {                              // sound siren if any warning flags are set true
   if (oiltWarn || mrpWarn || h2oWarn) { 
     if (flip) {
       playTone(100,2500);
       flip = false;
     } else {
         playTone(100,2000); // LOUD!!!
         flip=true;
       } 
   }
}
    //delay(5000);
  








// ********** DEBUG  OUTPUT  *************************8
void dispDebug() {

   Serial.println();
   
   Serial.println("TEST");
   Serial.print("temperature ");
   Serial.print(read_oilt());
   Serial.println(" F");
   Serial.print("pressure ");
   Serial.print(read_oilp());
   Serial.println(" psi");
   Serial.print("elapsed time = ");
   Serial.println(millis());
   Serial.println();
   delay(5000);
}



// *************  SPEAKER  STUFF  ****************************
// duration in mSecs, frequency in hertz
void playTone(long duration, int freq) {
    duration *= 1000;
    int period = (1.0 / freq) * 1000000;
    long elapsed_time = 0;
    while (elapsed_time < duration) {
        digitalWrite(pinSpeaker,HIGH);
        delayMicroseconds(period / 2);
        digitalWrite(pinSpeaker, LOW);
        delayMicroseconds(period / 2);
        elapsed_time += (period);
    }
}




// **************  LCD  STUFF  ******************************
void clearLCD () {
  Serial.print(254, BYTE);
  Serial.print(81, BYTE);
  //delay(50);
}

// done
void dispLogo () {
  clearLCD();
  goTo(1, 4);                       // Row 1, Column 2
  Serial.print("MultiGauge LCD");
  goTo(2,1);
  Serial.print("(c) Abhishek Shinde");
}


void dispLabels () {
  clearLCD();
  goTo(1,1);
  Serial.print ("*FoilPSI mrp h2o wbo2");
}


void dispData () {
  
       goTo(2,1);
       Serial.print(simoilt);
       if (simoilt < 100) {
         goTo(2,3);
         Serial.print(" ");
       }
       
       goTo(2,5);
       Serial.print(simoilp);
       if (simoilp < 100) {
         goTo(2,7);
         Serial.print(" ");
       }
       
       goTo(2,9);
       //Serial.print(simmrp);
       Serial.print(
       //goTo(2, 12);  
       //Serial.print(" ");
       goTo(2, 13);
       Serial.print(simwt);
       goTo(2,17);
       Serial.print(simafr);
  
  
}

// done
void goTo (int row, int col) {      // moves cursor to indicated position - row/column
  int rowcol = 0;
  switch (row) {
    case 1:
        rowcol = col-1;
        break;
    case 2:
        rowcol = col - 1 + 64;
        break;
  }
  Serial.print(254, BYTE);          // use command
  Serial.print(69, BYTE);           // "Set Cursor Position"
  Serial.print(rowcol, BYTE);            // row/col value
  //delay(40);
}  

// done
void LCDBright(int bright) { // set LCD brightness : 8 = Brightest, 1 = Lightest
  Serial.print(254, BYTE);
  Serial.print(83, BYTE);
  Serial.print(bright, BYTE);
}

void initLCD () {          // initalize LCD for the first time
  //delay(100);              // delay to let the LCD initialize
  clearLCD();
  dispLogo();  
  delay(3000);
  dispLabels();
}