Coding more than Four `7segment` display panels on Arduino

Recently I coded a seven segment display for a friend of mine. Hope this might be helpful for wiring purposes. My task was to correctly display 5 digit number on 5 `seven segments`. So, most of the examples out there including this module support only up to 4 segments. So, I wrote my own code from the scratch.


This is the code, I wrote:

const int SEGMENT_RENDER_DELAY_MS=5;//segment rendering delay
const int MAX_NUM_SEGMENTS=5;//store maximum segments
//
String inputString = ""; // a string to hold incoming data
String displayStr="hellO"; //current display string (keep empty to display all zero's!)
//unsigned long digit; // display digit, if you are dealing only with numbers
//           a
//        =======
//      ||       ||
//    f ||       || b
//      ||   g   ||
//        =======
//      ||       ||
//    e ||       || c
//      ||   d   ||
//        =======
 
byte seven_seg[16][9] = { {0,0, 1,1,1,1,1,1,0 },  // = 0
                         {0,0, 0,1,1,0,0,0,0 },  // = 1
                         {0,0, 1,1,0,1,1,0,1 },  // = 2
                         {0,0, 1,1,1,1,0,0,1 },  // = 3
                         {0,0, 0,1,1,0,0,1,1 },  // = 4
                         {0,0, 1,0,1,1,0,1,1 },  // = 5
                         {0,0, 1,0,1,1,1,1,1 },  // = 6
                         {0,0, 1,1,1,0,0,0,0 },  // = 7
                         {0,0, 1,1,1,1,1,1,1 },  // = 8
                         {0,0, 1,1,1,0,0,1,1 },   // = 9
                         {0,0, 1,0,0,1,1,1,1 },   // = e
                         {0,0, 0,0,0,0,1,0,1 },   // = r
                         {0,0, 0,0,1,1,1,0,1 },   // = o
                         {0,0, 1,1,1,1,1,1,0 },   // = O
                         {0,0, 0,1,1,0,1,1,1 },   // = h
                         {0,0, 0,0,0,1,1,1,0 }   // = l
                         };
                         
byte firstSegmentPos = 0, secSegmentPos = 0,thirdSegmentPos = 0, fourthSegmentPos = 0, fifthSegmentPos = 0;
//
int pin;

void setup() {    
   // initialize serial:
  Serial.begin(9600);
  // reserve 200 bytes for the inputString:
  inputString.reserve(200);
  
  //define output pins
  pinMode(2, OUTPUT);   
  pinMode(3, OUTPUT);
  pinMode(4, OUTPUT);
  pinMode(5, OUTPUT);
  pinMode(6, OUTPUT);
  pinMode(7, OUTPUT);
  pinMode(8, OUTPUT);
  
  pinMode(9, OUTPUT);
  pinMode(10, OUTPUT);
  pinMode(11, OUTPUT);
  pinMode(12, OUTPUT);
  pinMode(13, OUTPUT);
}

void loop() {
   updateSegments();
}

/*
  SerialEvent occurs whenever a new data comes in the
 hardware serial RX.  This routine is run between each
 time loop() runs, so using delay inside loop can delay
 response.  Multiple bytes of data may be available.
 */
void serialEvent() {
 
  while (Serial.available()) {
    // get the new byte:
    char inChar = (char)Serial.read(); 

    //if linebreak found, parse it
    if (inChar == '\r'||inChar == '\n') {
      //we got a break, parse string
      parseCode(&inputString);
      inputString="";
    }else{
      //append the character received
      inputString += inChar;
    }

  }
}

/**
* Parses one line of transaction
* If validation failed-> error displayed Or value displayed
**/
void parseCode(String* receivedLine){
  String line = *receivedLine;
  line.trim();//remove spaces
  //
  int lineLength=line.length();//length of the line received

  String rv="";
  if(lineLength <= MAX_NUM_SEGMENTS){
    rv=line;//set to display value
    //nSuccessTrans++;
  }else{
    rv="error";
    //nFailTrans++;
  }
  displayStr=rv;//set to display value
  
  //digit = displayStr.toInt();// if you are dealing only with numbers
}

/**
* Updates Display Segments
**/
void updateSegments(){
  /*
  fifthSegmentPos = digit / 10000;
  digit %= 10000;
  fourthSegmentPos = digit / 1000;
  digit %= 1000;
  thirdSegmentPos = digit / 100;
  digit %= 100;
  secSegmentPos = digit / 10;
  firstSegmentPos = digit % 10;
  */
  firstSegmentPos = GetSegmentCharPos(&displayStr,1); 
  secSegmentPos = GetSegmentCharPos(&displayStr,2); 
  thirdSegmentPos = GetSegmentCharPos(&displayStr,3); 
  fourthSegmentPos = GetSegmentCharPos(&displayStr,4); 
  fifthSegmentPos =  GetSegmentCharPos(&displayStr,5);

  //Serial.println("first segment");
  digitalWrite(9,HIGH);   
  digitalWrite(10,LOW); 
  digitalWrite(11,LOW);   
  digitalWrite(12,LOW);   
  digitalWrite(13,LOW);     
  displaySegmentChar(&firstSegmentPos);
  delay(SEGMENT_RENDER_DELAY_MS);
  
  //Serial.println("second segment");
  digitalWrite(9,LOW);   
  digitalWrite(10,HIGH);
  digitalWrite(11,LOW);   
  digitalWrite(12,LOW);   
  digitalWrite(13,LOW);   
  displaySegmentChar(&secSegmentPos);
  delay(SEGMENT_RENDER_DELAY_MS);
  
  //Serial.println("third segment");
  digitalWrite(9,LOW);   
  digitalWrite(10,LOW);
  digitalWrite(11,HIGH);   
  digitalWrite(12,LOW);   
  digitalWrite(13,LOW);   
  displaySegmentChar(&thirdSegmentPos);
  delay(SEGMENT_RENDER_DELAY_MS);
  
  //Serial.println("fourth segment");
  digitalWrite(9,LOW);   
  digitalWrite(10,LOW);
  digitalWrite(11,LOW);   
  digitalWrite(12,HIGH);   
  digitalWrite(13,LOW);   
  displaySegmentChar(&fourthSegmentPos);
  delay(SEGMENT_RENDER_DELAY_MS);
  
  //Serial.println("fifth segment");
  digitalWrite(9,LOW);   
  digitalWrite(10,LOW);
  digitalWrite(11,LOW);   
  digitalWrite(12,LOW);   
  digitalWrite(13,HIGH);   
  displaySegmentChar(&fifthSegmentPos);
  delay(SEGMENT_RENDER_DELAY_MS);
}

/**
* Returns position of the rendering `segment character`
**/
static int GetSegmentCharPos(String* strNum, int pos){
        String strNumber = *strNum;
        if(strNumber.length()==0) return 0;
        if(strNumber.length()>=pos){
           char c = strNumber.charAt(strNumber.length()-pos);
           if(c=='e') return 10;//e
           if(c=='r') return 11;//r
           if(c=='o') return 12;//o
           if(c=='O') return 13;//O
           if(c=='h') return 14;//h
           if(c=='l') return 15;//l
           if(c-'0'>0) return c-'0';//digit [0-9]
        }
        return 0;
}
/**
* Sketches single digit
**/
void displaySegmentChar(byte* pos)  {
   int digitPos = *pos;
   for(pin = 2;pin < 9; pin++) {
        digitalWrite(pin,seven_seg[digitPos][pin]);
   }
}
 This code holds to be displayed code as a String object i.e. `displayStr` because i needed to display non-numeric characters as well(e.g. `error`). If you only need digits, you may use unsigned long called `digit`. And you can use following code to get segment numbers;
  fifthSegmentPos = digit / 10000;
  digit %= 10000;
  fourthSegmentPos = digit / 1000;
  digit %= 1000;
  thirdSegmentPos = digit / 100;
  digit %= 100;
  secSegmentPos = digit / 10;
  firstSegmentPos = digit % 10;

SHARE

Rasika Perera

  • Image
  • Image
  • Image
  • Image
  • Image
    Blogger Comment
    Facebook Comment