Controlling a MAX7219 8-digit 7-segment display from ATtiny85

/* One MAX7219 connected to an 8-digit 7-sgement display Adapted from https://halfbyteblog.wordpress.com/2015/11/29/using-a-max7219-8x8-led-matrix-with-an-attiny85-like-trinket-or-digispark/ */ #include #include #define CLK_HIGH() PORTB |= (1<#define CLK_LOW() PORTB &= ~(1<#define CS_HIGH() PORTB |= (1<#define CS_LOW() PORTB &= ~(1<#define DATA_HIGH() PORTB |= (1<#define DATA_LOW() PORTB &= ~(1<#define INIT_PORT() DDRB |= (1< uint8_t ZERO = 0b01111110; uint8_t ONE = 0b00110000; uint8_t TWO = 0b01101101; uint8_t THREE = 0b01111001; uint8_t FOUR = 0b00110011; uint8_t FIVE = 0b01011011; uint8_t SIX = 0b00011111; uint8_t SEVEN = 0b01110000; uint8_t EIGHT = 0b01111111; uint8_t NINE = 0b01110011; uint8_t DOT = 0b10000000; uint8_t smile[8] = { ZERO, ONE, TWO, THREE, FOUR, FIVE, SIX, SEVEN}; uint8_t sad[8] = { EIGHT, NINE, ZERO + DOT, ONE + DOT, TWO + DOT, THREE + DOT, FOUR + DOT, FIVE + DOT, }; void spi_send(uint8_t data) { uint8_t i; for (i = 0; i < 8; i++, data <<= 1) { CLK_LOW(); if (data & 0x80) DATA_HIGH(); else DATA_LOW(); CLK_HIGH(); } } void max7219_writec(uint8_t high_byte, uint8_t low_byte) { CS_LOW(); spi_send(high_byte); spi_send(low_byte); CS_HIGH(); } void max7219_clear(void) { uint8_t i; for (i = 0; i < 8; i++) { max7219_writec(i+1, 0); } } void max7219_init(void) { INIT_PORT(); // Decode mode: none max7219_writec(0x09, 0); // Intensity: 3 (0-15) max7219_writec(0x0A, 1); // Scan limit: All "digits" (rows) on max7219_writec(0x0B, 7); // Shutdown register: Display on max7219_writec(0x0C, 1); // Display test: off max7219_writec(0x0F, 0); max7219_clear(); } uint8_t display[8]; void update_display(void) { uint8_t i; for (i = 0; i < 8; i++) { max7219_writec(i+1, display[i]); } } void image(uint8_t im[8]) { uint8_t i; for (i = 0; i < 8; i++) display[i] = im[i]; } void set_pixel(uint8_t r, uint8_t c, uint8_t value) { switch (value) { case 0: // Clear bit display[r] &= (uint8_t) ~(0x80 >> c); break; case 1: // Set bit display[r] |= (0x80 >> c); break; default: // XOR bit display[r] ^= (0x80 >> c); break; } } int main(void) { uint8_t i; max7219_init(); while(1) { image(sad); update_display(); _delay_ms(500); image(smile); update_display(); _delay_ms(500); // Invert display // for (i = 0 ; i < 8*8; i++) // { // set_pixel(i / 8, i % 8, 2); // update_display(); // _delay_ms(10); // } _delay_ms(500); } }