const byte datapin = 2;
const byte clockpin = 3;
const byte latchpin = 4;
const byte digits = 8;
volatile uint8_t isr_buffer[digits];
volatile uint8_t isr_digit;
SIGNAL(TIMER0_COMPA_vect) {
shiftOut(datapin, clockpin, LSBFIRST, ~(1 << isr_digit));
shiftOut(datapin, clockpin, LSBFIRST, isr_buffer[isr_digit]);
digitalWrite(latchpin, HIGH);
digitalWrite(latchpin, LOW);
if (++isr_digit == sizeof(isr_buffer))
isr_digit = 0;
}
void setup() {
pinMode(datapin, OUTPUT);
pinMode(clockpin, OUTPUT);
pinMode(latchpin, OUTPUT);
// piggy back on the existing 1kHz Timer0 used by millis()
OCR0A = 0xAF;
TIMSK0 |= _BV(OCIE0A);
}
void loop() {
uint32_t num = 0;
while (1) {
write_7seg(num, 10);
delay(50);
num += random(1000);
if (num > 99999999)
num = 0;
}
}
const uint8_t segment_map[] = {
// 0 to 9
0b11111100, 0b01100000, 0b11011010, 0b11110010, 0b01100110,
0b10110110, 0b10111110, 0b11100000, 0b11111110, 0b11110110,
// A to F
0b11101110, 0b00111110, 0b00011010, 0b01111010, 0b10011110,
0b10001110
};
// base can be 2 to 16.
void write_7seg(uint32_t num, uint8_t base) {
for (uint8_t i = 0; i < digits; i++) {
byte digit = num % base;
num /= base;
isr_buffer[i] = segment_map[digit];
}
// overflow? set all the decimal points
if (num != 0) {
for (uint8_t i = 0; i < digits; i++)
isr_buffer[i] |= 1;
}
}