3x7 segment display issues

Hello all,

I am new to this whole Arduino tech and coding, so please be gentle.

I purchased a Kingbright 3 x 7 segment LED display:
http://uk.farnell.com/kingbright/bc56-11surkwa/display-led-0-56-red-com-cathode/dp/2335764

now, to test this out, i wrote a bit of code :

//int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<21;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<20;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
   digitalWrite(pinArray[count], LOW);
   delay(timer);
   digitalWrite(pinArray[count + 1], LOW);

 
  }
}

Basic, but it does the job of cycling through each LED checking that it works etc.

Now, i have moved on to another project where i want the segment display to show a number when a code is received:
this code is here:

#include <IRremote.h>

int recvLED = 22;
int recvPin = 13;

IRrecv irReciver(recvPin);
decode_results results;

// Defining the pins for the 3X7 segment display
int threesegment[21] = { 26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52 };

// Initializing the digits array
const unsigned long digits[][21] = {
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0}, // Digit 1 
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1}, // Digit 2
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1}, // Digit 3
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1}, // Digit 4
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1}, // Digit 5
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1}, // Digit 6
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0}, // Digit 7
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1}, // Digit 8
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1}, // Digit 9
{ 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0}, // Power button (ON)
{ 1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1}  // Program

};

const unsigned long decodeSIG[] = {
  0xB47, // digit 1
  0x80B47, // digit 2 
  0x40B47, // digit 3
  0xC0B47, // digit 4
  0x20B47, // digit 5
  0xA0B47, // digit 6
  0x60B47, // digit 7
  0xE0B47, // digit 8
  0x10B47, // digit 9
  0xA8B47, // Power button
  0x7AB47, // Program 
};
  
unsigned long lastTime = 0;
  
void setup()
{
  pinMode(recvLED, OUTPUT); //Configue the recvLED pin as an OUTPUT pin
  digitalWrite(recvLED, LOW); //Leave the LED off as we start

  Serial.begin(9600); // Initialize the serial port with a baud rate of 9600 bps

  irReciver.enableIRIn(); // Start the receiver
  
  for (int i=0; i<11; i++) 
  {
    pinMode(threesegment[i], OUTPUT); //Configure all pins in the 3X7 segments display as OUTPUT  
  }  
}

void loop()
{
  unsigned long recv_value;
  
  if (irReciver.decode(&results)) {
    recv_value = results.value; 
    
    if (  recv_value != 0xFFFFFFFF ) //Ignore the 0x00 values recived as a result of pressing and holding a button on the remote for long
    {
      // Blink the LED each time a button is pressed
      digitalWrite(recvLED, HIGH);
      delay(10);
      digitalWrite(recvLED, LOW);  
      
      // Output the decoded hash value to th serial monitor. This is for debugging purposes only.
      Serial.println(recv_value, HEX);
      Serial.println(results.value);
      
      //Iterate through the decoded hash array values to find a match
      for (int i=0; i<11; i++)
      {
        if ( recv_value == decodeSIG[i] ) // If the received value matches one of the values in the hash array
        { 
          lastTime = millis(); // Start power saving delay timer
          for (int j=0; j<=21; j++)
            //Set the relevant segments HIGH or LOW as defined in the digits[][] double array
            digitalWrite(threesegment[j], digits[i][j]);
            
          break; // Exit from the inner loop as we have now toggled all required segments to display the appropriate value
        }
      }
    }
    irReciver.resume(); // Read the next value
  }
  
  // To save power switch off all segments if 5 seconds has elapsed since 
  if ( millis() - lastTime >= 5000 )
  {
    for (int k=0; k<=21; k++)
      digitalWrite(threesegment[k], LOW);
      
    lastTime = 0; // Reset the power saving delay timer to zero '0'   
  }
}

Now, the code works fine from what i can see but the Arduino Mega 2560 is behaving in an odd fashion.

All of the LEDs in segment 1 of three (the one on the left) is showing up the correct brightness.

SOME of the segment 2 LED's (I.e The middle segment) are bright, and some are very dim

ALL of the segment 3 LED's (one on the right) are all very dim...

Now, if i pull out the jump wire from pin 26 on the board (one that shows up full brightness) and relocate it to a pin on the Display that is DIM, then the DIM segment, becomes full brightness.

so this must be something to do with the Arduino Itself... BUT if i run the code to test each pin, i have no problem at all and they all show full brightness.......

Can anyone shed some light on this (pun not intended !)

thanks

Mutley

EDIT
I have pulled out my trusty DMM and it looks like im getting 1.67v on all the DIM LED's and 4.3v on all the bright LED's....

Any reason why ? I am using the Digital Output pins on the Mega board

Please describe how the common anodes are connected and what you have for current limit resistors.

Please review the notes in Section 31.1 of the datasheet and see if some alternate pin assignments might be needed:

  1. Although each I/O port can sink more than the test conditions (20mA at VCC = 5V, 10mA at VCC = 3V) under steady state conditions (non-transient), the following must be observed:
    ATmega640/1280/2560:
    1.)The sum of all IOL, for ports J0-J7, A0-A7, G2 should not exceed 200mA.
    2.)The sum of all IOL, for ports C0-C7, G0-G1, D0-D7, L0-L7 should not exceed 200mA.
    3.)The sum of all IOL, for ports G3-G4, B0-B7, H0-B7 should not exceed 200mA.
    4.)The sum of all IOL, for ports E0-E7, G5 should not exceed 100mA.
    5.)The sum of all IOL, for ports F0-F7, K0-K7 should not exceed 100mA.
    If IOL exceeds the test condition, VOL may exceed the related specification. Pins are not guaranteed to sink current greater than the listed test condition.

Hello CR

Sorry i should have mentioned in my initial post!!!

the pins being used for this are the digital pin numbers:
{26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52}

This segment display that can be found here: (did link in inital post) :
http://uk.farnell.com/kingbright/bc56-11surkwa/display-led-0-56-red-com-cathode/dp/2335764.

All the required Ground pins: 3,26,19 & 18 are all connected to the ground plane on the solderless breadboard and then this in turn is connected to the Digital ground on the Arduino.

each pin from the Arduino has a flying lead down to a solderless breadboard. A 220ohm resistor then connects this output from the Arduino to the Input of each required pin on the segment display which is also positioned on the solderless breadboard.

Whilst i understand the current limit on these boards, i have been careful to limit what is displayed.

Whilst i know it is not recommended, i adapted my first 'test' code and removed the DigitalPin LOW as shown here:

int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
//int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<10;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<9;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
  // digitalWrite(pinArray[count], LOW);
   delay(timer);
   //digitalWrite(pinArray[count + 1], LOW);

 
  }
}

the segments powered up and stayed on with no problem at all.
I then edited the code above to this:

//int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<21;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<20;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
  // digitalWrite(pinArray[count], LOW);
   delay(timer);
   //digitalWrite(pinArray[count + 1], LOW);

 
  }
}

I do not recommend this to anyone else as i know i was stepping on / over the current limit with this code.
still, i fired it up and all segments where illuminated with no problem at a good brightness as well.

ok lets make this more confusing.....

Using this code here:

/*
{ 0, 1, 1, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 1 
{ 1, 1, 0, 1, 1, 0, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 2
{ 1, 1, 1, 1, 0, 0, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 3
{ 0, 1, 1, 0, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 4
{ 1, 0, 1, 1, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 5
{ 1, 0, 1, 1, 1, 1, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 6
{ 1, 1, 1, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 7
{ 1, 1, 1, 1, 1, 1, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 8
{ 1, 1, 1, 1, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 9
*/
{ 0, 0, 0, 0, 0, 0, 0,  0, 1, 1, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 1 
{ 0, 0, 0, 0, 0, 0, 0,  1, 1, 0, 1, 1, 0, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 2
{ 0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 0, 0, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 3
{ 0, 0, 0, 0, 0, 0, 0,  0, 1, 1, 0, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 4
{ 0, 0, 0, 0, 0, 0, 0,  1, 0, 1, 1, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 5
{ 0, 0, 0, 0, 0, 0, 0,  1, 0, 1, 1, 1, 1, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 6
{ 0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 7
{ 0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 1, 1, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 8
{ 0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 0, 1, 1,  0, 0, 0, 0, 0, 0, 0,  }, // Digit 9
/*
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  0, 1, 1, 0, 0, 0, 0, }, // Digit 1 
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 1, 0, 1, 1, 0, 1, }, // Digit 2
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 0, 0, 1, }, // Digit 3
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  0, 1, 1, 0, 0, 1, 1, }, // Digit 4
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 0, 1, 1, 0, 1, 1, }, // Digit 5
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 0, 1, 1, 1, 1, 1, }, // Digit 6
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 0, 0, 0, 0, }, // Digit 7
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 1, 1, 1, }, // Digit 8
{ 0, 0, 0, 0, 0, 0, 0,  0, 0, 0, 0, 0, 0, 0,  1, 1, 1, 1, 0, 1, 1, }, // Digit 9
*/ 
};

These are my findings:

Using the 1st of the three examples of code above. all numbers illuminated correctly.

Using the 2nd of the three examples above, E,F & G on the middle segment where only dimly lit, whilst A,B,C,D where all at correct brightness.

Using the last of the three examples above, ALL Segments A,B,C,D,E,F & G Where ALL Dimly lit.

Now, the Pins being used for those effected are being driven by pins:
{40, 41, 42, 46, 47, 48, 49, 50, 51, 52}; respectively.

Is there something i am missing when i am using these pins ?

Farnell page says common cathode, Datasheet link on the page is to a common anode page. Thus my question on the anodes.

Look at the Ports behind the pins being used to see if there were any other restrictions with respect to the notes in the table referenced earlier. If you are not exceeding those, then wiriing issue would be the next thing to look at.

arduino-mega2560_R3-sch.pdf (47.1 KB)

Ah yes, sorry over looked that one.. its a common Cathode. All 4 ground pins are grounded back to the arduino.

As i say, the layout is not a problem and i can easily get all segments to illuminate properly with my test code:

//int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<21;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<20;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
  // digitalWrite(pinArray[count], LOW);
   delay(timer);
   //digitalWrite(pinArray[count + 1], LOW);

 
  }
}

And I have had all segments on this device illuminated at one time to the correct brightness.

I wonder if im doing something stupid in my original code, but i cannot see anything.....

Where can i get this data sheet from, I swear i downloaded it from the arduino main page not that long ago, but now it seems to have gone... all i can find is the schematic files and pin references.. not the full on datasheet for the device

From Atmel:

Table 31-1, Note 4 since you are sourcing current:
4. Although each I/O port can source more than the test conditions (20mA at VCC = 5V, 10mA at VCC = 3V) under steady state conditions (non-transient), the following must be observed:
ATmega640/1280/2560:

  1. The sum of all IOH, for ports J0-J7, G2, A0-A7 should not exceed 200mA.
  2. The sum of all IOH, for ports C0-C7, G0-G1, D0-D7, L0-L7 should not exceed 200mA.
    3 )The sum of all IOH, for ports G3-G4, B0-B7, H0-H7 should not exceed 200mA.
    4 )The sum of all IOH, for ports E0-E7, G5 should not exceed 100mA.
  3. The sum of all IOH, for ports F0-F7, K0-K7 should not exceed 100mA.
    If IOH exceeds the test condition, VOH may exceed the related specification. Pins are not guaranteed to source current greater than the listed test condition.

CrossRoads:
Table 31-1, Note 4 since you are sourcing current:
4. Although each I/O port can source more than the test conditions (20mA at VCC = 5V, 10mA at VCC = 3V) under steady state conditions (non-transient), the following must be observed:
ATmega640/1280/2560:

  1. The sum of all IOH, for ports J0-J7, G2, A0-A7 should not exceed 200mA.
  2. The sum of all IOH, for ports C0-C7, G0-G1, D0-D7, L0-L7 should not exceed 200mA.
    3 )The sum of all IOH, for ports G3-G4, B0-B7, H0-H7 should not exceed 200mA.
    4 )The sum of all IOH, for ports E0-E7, G5 should not exceed 100mA.
  3. The sum of all IOH, for ports F0-F7, K0-K7 should not exceed 100mA.
    If IOH exceeds the test condition, VOH may exceed the related specification. Pins are not guaranteed to source current greater than the listed test condition.

Thanks Again, but im having difficulty getting my head around this...

If i run this code here:

//int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<21;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<20;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
  // digitalWrite(pinArray[count], LOW);
   delay(timer);
   //digitalWrite(pinArray[count + 1], LOW);

 
  }
}

(this code counts up each segment on the device and leaves each segment ON)
If i run this, then ALL segments illuminate to the correct brightness. I know the data sheet states that it cannot be guaranteed to sink this current demand, mine will. and i only allow it to do it for a matter of seconds.

Now, if i display the number '2' on the display...
on the first of the 3 segments the Number 2 is displayed perfectly,
On the middle of the three segments, the Number 2 Isnt displayed correctly. as a few segments are dimmer than the others...

then of the third display, when displaying the number 2, all Segments are dim..

I will see if i can get a few pictures up to show what i am trying to explain :slight_smile:

Right, lets hope this will help a bit....

This image is of the first segment, the camera is very close to the display and i have my hand blocking out as much light as possible to show what is going on..

This next image is of the middle segment, again trying to display the number 2.

Then last but not least...this is the third segment trying to display the number 2....

the difference between the 1st segment and 3rd segment in terms of light output is vastly different..
in a well lit room i have no issues seeing the 1st segment display, but i have to hold my hand over the display to see the third one.

But as i have said before, if i use my test code, i can get all the segments to illuminate like the ones in the first segment

This needs to be <21
for (count=0;count<20;count++) {
to get to the final segment.
0 to 20 = 21 segments

If you change that to
0 to <7,
7 to <14,
and 14 <21,
with timer set at 2 instead of 100, do the three digits display the same brightness?

Yes, they all are the same brightness.

I can get all the 21 segments to display at the same time and brightness brightness as you can see on the first segment showing the number 2.

I have not modified the setup at all, all i have done is uploaded this code:

//int pinArray[] = {26, 31, 30, 29, 39, 49, 48, 47, 46, 36};
int pinArray[] = {26, 27, 28, 29, 30, 31, 32, 36, 37, 38, 39, 40, 41, 42, 46, 47, 48, 49, 50, 51, 52};
int count = 0;
int timer = 100;

void setup(){
  for (count=0;count<21;count++) {
    pinMode(pinArray[count], OUTPUT);
  }
}

void loop() {
  for (count=0;count<20;count++) {
    
   digitalWrite(pinArray[count], HIGH);
   delay(timer);
   digitalWrite(pinArray[count + 1], HIGH);
   delay(timer);
 // digitalWrite(pinArray[count], LOW);
   delay(timer);
 // digitalWrite(pinArray[count + 1], LOW);
  }
}

As soon as i load my other code back on the Arduino... i get the same dimming as before :cold_sweat: :~

I don't know then.

Thank you for your help :).

Im stumped too, i just do not understand how with one code, i can get all segments to illuminate brightly, then load another code and half of the digits are dim....

I would point fingers at my code, but i cannot see anything glaringly obvious..

Chap at work pointed this out in seconds... i honestly dont know how i missed it!!!

on line:

for (int i=0; i<11; i++)

it should not be 11, it should be 21!!!

so after changing it to:

for (int i=0; i<21; i++)

she works perfectly :grin:

Huh - I did point out in reply #10 that you needed 21 - you never posted a change showing other then 20 tho.
Glad you got it worked out.