Saturday, June 18, 2022

tinkercad 74HC595 shift register + 7 segment display 1


bool shifting = false;
int shift_count = 0;
byte data1 = 0, data2 = 0;
int num = 0;

void setup() 
{
  DDRD = 0b01111100;  //pin 2, 3, 4, 5, 6 output
  // arduino pin 3 connects to 74HC595 output enable pin
  // arduino pin 4 connects to 74HC595 serial input pin
  // arduino pin 5 connects to 74HC595 output register clock pin
  // arduino pin 6 connects to 74HC595 shift register clock pin
  
  //shift register clock
  TCCR1A = 0b00000000; //TCCR1A bit 0, 1 and TCCR1B bit 3, 4 set timer mode
  TCCR1B = 0b00001010; //Set mode to be clear on compare. set scaler to be clock/8
  OCR1A = 1999; //period = (OCR1A/B + 1)*scaler*62.5ns = 1ms
  TIMSK1 = 0b00000010; //enable timer counter
  sei();
}

void loop() 
{
  //updateShiftRegister();
  shifting = true;
  //data = random(0, 255);
  data1 = segment_decoder(num/10);
  data2 = segment_decoder(num%10);
  num++;
  if(num==100){num=0;}
  delay(200);
}

//shift register clock
ISR(TIMER1_COMPA_vect){
PORTD ^= 0b01000000; //toggle pin  6(shift register clock)
  byte array1[2] = {0b00010000, 0b00000100};
  byte array2[2] = {data1, data2};
  
  shift_register(array1, array2);
}

//shift both registers at the same time
void shift_register(byte input_pin[], byte data_byte[]){
if(shifting){
    //disable register output
    PORTD = PIND | 0b00001000; //set output enable high
    
  //if shift register clock is high
  if(PIND & 0b01000000){
    PORTD = PIND & 0b11011111; //set output register clock low
      
      for(int i=0; i<sizeof(data_byte); i++){
      //if data bit is high
      if(bitRead(data_byte[i], 7-shift_count)){
      //set serial input pin high
        PORTD = PIND | input_pin[i];
     
      //if data bit is low
      else{
      //set serial input pin low
        PORTD = PIND & ~input_pin[i];
      }
      }
      
      shift_count++;
  }
    //if shift register clock is low
    else{
      //if data bit is read
      if(shift_count >0){
      PORTD = PIND | 0b00100000; //set output register clock high
        //if all 8 data bits are read
        if(shift_count == 9){
        shifting = false;
          shift_count = 0;
        }
      }
    }
  }
  //shift finished
  else{
  PORTD = PIND & 0b11110111; //set output enable low
  }
}

byte segment_decoder(int n){
  byte b;
  
  switch(n){
  case 0:
    b = 0b01111110;
    break;
    case 1:
    b = 0b00001100;
    break;
    case 2:
    b = 0b10110110;
    break;
    case 3:
    b = 0b10011110;
    break;
    case 4:
    b = 0b11001100;
    break;
    case 5:
    b = 0b11011010;
    break;
    case 6:
    b = 0b11111000;
    break;
    case 7:
    b = 0b00001110;
    break;
    case 8:
    b = 0b11111110;
    break;
    case 9:
    b = 0b11011110;
    break;
    default:
    b = 0b00000000;
    break;
  }
  
  return b;
}

reference:

No comments:

Post a Comment