The clock (1)

I told you that it’s possible to control multiple 7-segment displays with transistors only.
First, I started with four 7-segment displays to test the Multiplexing. It runs perfectly!
One day later I decide me to build the clock.

There was only one problem: the extremely amount of wires! I must connect each pin from each display together. These are 7 wires per pin. And we have 7 pins. To solve this, I decide to use a circuit board and to solder the 6 displays.

After two and a half hour I finished the soldering! Done!
Ok, I forgot to test the displays before soldering, and so I have one which is a little bit darker.

The circuit:

For this tutorial, wee need the following components:

• 6x SA56-11GMA (common anode, green) or similar
• 7x resistors, 220 ohm
• 6x resistor, 1K ohm
• 6x transistor, BC546B or similar … some comments later

Here is the wiring diagram: The Arduino sketch:

```/*
The clock!
6x 7-segment-display with multiplexing
playground2014.wordpress.com
*/

byte ziffer = { { 0,0,0,0,0,0,1 }, // 0
{ 1,0,0,1,1,1,1 }, // 1
{ 0,0,1,0,0,1,0 }, // 2
{ 0,0,0,0,1,1,0 }, // 3
{ 1,0,0,1,1,0,0 }, // 4
{ 0,1,0,0,1,0,0 }, // 5
{ 0,1,0,0,0,0,0 }, // 6
{ 0,0,0,1,1,1,1 }, // 7
{ 0,0,0,0,0,0,0 }, // 8
{ 0,0,0,0,1,0,0 }, // 9
{ 1,1,1,1,1,1,1 } // off
};

volatile byte ii=0;
byte a1=1;
byte a2=1;
byte a3=0;
byte a4=3;
byte a5=0;
byte a6=0;

void setup() {

for (byte i=0;i<=13;++i) {
pinMode(i, OUTPUT);
}

for (byte i=0; i<7;++i) {
digitalWrite(i, HIGH);
}

cli();

//set timer0 interrupt at 1kHz
TCCR0A = 0;
TCCR0B = 0;
TCNT0 = 0;            //initialize counter value to 0
OCR0A = 10;           // set compare match register for 1.5625khz
TCCR0A |= (1 << WGM01);
TCCR0B |= (1 << CS02) | (1 << CS00);
TIMSK0 |= (1 << OCIE0A);

//set timer1 interrupt at 1Hz
TCCR1A = 0;
TCCR1B = 0;
TCNT1 = 0;
OCR1A = 15624;      // set compare match register for 1Hz
TCCR1B |= (1 << WGM12);
TCCR1B |= (1 << CS12) | (1 << CS10);
TIMSK1 |= (1 << OCIE1A);

sei();
}

ISR(TIMER0_COMPA_vect){

digitalWrite(8,0);
digitalWrite(9,0);
digitalWrite(10,0);
digitalWrite(11,0);
digitalWrite(12,0);
digitalWrite(13,0);

ii++;
if (ii==7) ii=1;

// 1. digit
if (ii==1) {
setDigit(a1);
digitalWrite(8,1);
}
// 2.digit
if (ii==2) {
setDigit(a2);
digitalWrite(9,1);
}
// 3. digit
if (ii==3) {
setDigit(a3);
digitalWrite(10,1);
}
// 4. digit
if (ii==4) {
setDigit(a4);
digitalWrite(11,1);
}
// 5. digit
if (ii==5) {
setDigit(a5);
digitalWrite(12,1);
}
// 6. digit
if (ii==6) {
setDigit(a6);
digitalWrite(13,1);
}
}

ISR(TIMER1_COMPA_vect){

a6++;
if (a6 == 10) {
a5++;
a6=0;
}

if (a5 == 6) {
a4++;
a5=0;
}

if (a4 == 10) {
a3++;
a4=0;
}

if (a3 == 6) {
a2++;
a3=0;
}

if ((a2 == 4) && (a1 == 2)) {
a2=0;
a1=0;
}

if ((a2 == 10) && ((a1 == 0) || (a1 == 1))) {
a1++;
a2=0;
}

}

void setDigit(byte inZi) {
digitalWrite(0,ziffer[inZi]);
digitalWrite(1,ziffer[inZi]);
digitalWrite(2,ziffer[inZi]);
digitalWrite(3,ziffer[inZi]);
digitalWrite(4,ziffer[inZi]);
digitalWrite(5,ziffer[inZi]);
digitalWrite(6,ziffer[inZi]);
}

void loop() {

}```

The function: Multiplexing

Multiplexing means, you switch on the first display, wait a little bit, than switch it off. Now, switch on the next display, wait a little bit again and switch it off. And so on. If you switched off the last display, you start with the first display again. It’ s a loop.

We switch on / switch off the display with our transistor. If we switch the transistor basic to LOW, the transistor is locked, no current at the common anode.

To realise the loop, we need a timer interrupt. Why a timer interrupt? Maybe, we can use the delay-function. No, this is not possible! During the waiting time we can do nothing else! Bu we must change values, etc.

Our Arduino Uno has three timer interrupts. One of them is an 16 bit timer (timer1), the other two are only 8 bit (timer0 and timer2).

With an 8 bit timer we can design loops with more than 2000 repetitions per second.
Let’s calculate a little bit: We have 6 displays and each display must switch on more than 24 times per second (If not, we register a flicker). Ok, let us use 30 times per second an we are sure! With 30 times per second and 6 displays need we 180 loops per second. This are 160 Hz.

Now, you can say, no problem, let’s use 2 kHz. Possible, but we have another thing to consider.
What is one cycle?
At the begin we set all the pins to LOW. Than we send the value we want to see to the display, but we see nothing at this moment. We must open the transistor base with a HIGH. If the transistor base open, we see the value, the display is switched on.

And now we answer the question about higher frequency. If the frequency is to high, you hasn’t enough time to open the transistor base. The display will be dark. In one moment you open the base, in the other moment you locked it. There is not enough current if the open time too short.

ISR(TIMER0_COMPA_vect){}
This is the timer0 interrupt loop. Per setup we define the frequency at 1562 Hz. We use a variable (ii) to control, which display should switch on.

ISR(TIMER1_COMPA_vect){}
This is the timer1 interrupt loop. Per setup we define the frequency at 1Hz. This is the clock pulse we use to change the counters for seconds, minutes and hours.

void loop() { … }
There is nothing to do!