Tạo màn hình với led 7 đoạn và thanh ghi dịch 74HC595 | Dự án Arduino

Tạo màn hình với led 7 đoạn và thanh ghi dịch 74HC595 | Dự án Arduino

Thêm một thanh ghi dịch song song / nối tiếp như 74HC595 phổ biến vào màn hình led 7 đoạn sẽ giúp giảm số lượng chân cần thiết để điều khiển nó (màn hình).

Về cơ bản, màn hình led 7 đoạn cần 9 chân: 8 chân phân đoạn (A, B, C, D, E, F, G và DP) + chân chung. Bằng cách nối tất cả các chân phân đoạn với một thanh ghi thay đổi, số lượng chân cần thiết sẽ giảm còn 3: chân clock và chân dữ liệu (đối với thanh ghi dịch) + chân chung.

Vì vậy, đối với màn hình led 7 đoạn gồm 4 led 7 đoạn, chúng ta chỉ cần 6 chân: clock, dữ liệu và 4 chân chung (mỗi led có chân chung riêng).

Dự án này cho thấy cách xây dựng bộ đếm digital đơn giản bằng Arduino, hiển thị 7 đoạn anode chung với 4 led 7 đoạn và thanh ghi 74HC595.

Yêu cầu phần cứng:

  • Board UNO
  • Led 7 đoạn loại có 4 led chung
  • 74HC595
  • 4 x Transistor PNP ( 2SA1015 , 2S9015 , 2N3906 ])
  • 8 x Điện trở 100 ohm
  • 4 x Điện trở 4,7k ohm
  • Nút ấn
  • Breadboard
  • Dây dẫn

Sơ đồ mạch của dự án:

Hình ảnh dưới đây cho thấy sơ đồ mạch ví dụ của chúng tôi.

Như được hiển thị trong sơ đồ mạch ở trên, tất cả các chân phân đoạn được nối với các chân đầu ra 74HC595, mỗi chân qua điện trở 100 ohm, trong đó:

Đoạn A … G được nối với chân 74HC595 Q7 … Q1 và DP phân đoạn được nối với chân Q0.

Chân dữ liệu của thanh ghi 74HC595 được đặt tên là DS (# 14) và nó được nối với chân Arduino 6.

ST_CP (hoặc RCLK) và SH_CP (hoặc SRCLK) được nối với nhau, sau đó được nối với chân Arduino 7. Đây là chân clock.

Vì màn hình có 4 led 7 đoạn nên có 4 chân chung: 1 (hầu hết bên trái), 2, 3 và 4. Mỗi chân chung được nối với đầu cực collector của một transistor. Điểm mút cực phát của 4 transistor được nối với + 5V từ board Arduino. Điểm mút cơ sở của bốn transistor được nối với Arduino thông qua điện trở 4,7k.

4 transistor cùng loại (PNP).

Nút ấn được nối với chân analog Arduino 0 (A0) được sử dụng để tăng số lượng hiển thị.

Code dự án:

Code Arduino bên dưới không sử dụng bất kỳ thư viện nào cho màn hình 7 đoạn.

Khai báo nút ấn được xác định trong code là:

// counter button definition

#define button    A0

Khai báo chân clock và chân dữ liệu được xác định là:

// shift register chân definitions

#define clockChân  7   // chân clock

#define dataChân   6   // chân data

Màn hình cần được làm mới định kỳ, vì tôi đã sử dụng mô-đun Timer1 ngắt với cấu hình sau:

// Timer1 module overflow interrupt configuration

TCCR1A = 0;

TCCR1B = 1;  // enable Timer1 with prescaler = 1 ( 16 ticks each 1 µs)

TCNT1  = 0;  // set Timer1 preload value to 0 (reset)

TIMSK1 = 1;  // enable Timer1 overflow interrupt

Với bộ đếm trước Timer1 = 1, chúng tôi sẽ ngắt mỗi 4096 micro giây. Điều đó có nghĩa là mỗi led 7 đoạn được hiển thị 4096 us. {4096 us = 65536 / (16 * prescaler)}

Lưu ý rằng mô-đun Timer1 là bộ định thời 16 bit và tần số xung Arduino là 16 MHz.

Các hàm được sử dụng trong code:

ISR(TIMER1_OVF_vect): là chức năng ngắt Timer1, khi vi điều khiển bị gián đoạn bởi Timer1, nó sẽ trực tiếp thực hiện ‘chức năng’ này.

void disp(byte number, bool dec_point = 0): chức năng này là dành cho dữ liệu hiển thị trên màn hình 7-segment, nó in biến số có thể thay đổi giữa 0 và 9. Biến dec_point quyết định liệu các DP sẽ được in hay không , giá trị mặc định là 0 (không in), nếu dec_point = 1, phân đoạn DP sẽ BẬT.

void dist_off () : chức năng này sẽ tắt toàn bộ màn hình.

Tôi đã sử dụng chức năng Arduino shiftOut (built-in) để gửi dữ liệu một cách an toàn đến thanh ghi thay đổi 74HC595.

Code Arduino đầy đủ:

// counter button definition
#define button    A0
// shift register pin definitions
#define clockPin  7   // clock pin
#define dataPin   6   // data pin
// common pins of the four digits definitions
#define Dig1    5
#define Dig2    4
#define Dig3    3
#define Dig4    2
// variable declarations
byte current_digit;
int  count = 0;
void disp(byte number, bool dec_point = 0);
void setup()
{
  pinMode(button, INPUT_PULLUP);
  pinMode(Dig1, OUTPUT);
  pinMode(Dig2, OUTPUT);
  pinMode(Dig3, OUTPUT);
  pinMode(Dig4, OUTPUT);
  pinMode(clockPin, OUTPUT);
  pinMode(dataPin, OUTPUT);
  disp_off();  // turn off the display
  // Timer1 module overflow interrupt configuration
  TCCR1A = 0;
  TCCR1B = 1;  // enable Timer1 with prescaler = 1 ( 16 ticks each 1 µs)
  TCNT1  = 0;  // set Timer1 preload value to 0 (reset)
  TIMSK1 = 1;  // enable Timer1 overflow interrupt
}
ISR(TIMER1_OVF_vect)   // Timer1 interrupt service routine (ISR)
{
  disp_off();  // turn off the display
  switch (current_digit)
  {
    case 1:
      disp(count / 1000);   // prepare to display digit 1 (most left)
      digitalWrite(Dig1, LOW);  // turn on digit 1
      break;
    case 2:
      disp( (count / 100) % 10 );   // prepare to display digit 2
      digitalWrite(Dig2, LOW);     // turn on digit 2
      break;
    case 3:
      disp( (count / 10) % 10 );   // prepare to display digit 3
      digitalWrite(Dig3, LOW);    // turn on digit 3
      break;
    case 4:
      disp(count % 10);   // prepare to display digit 4 (most right)
      digitalWrite(Dig4, LOW);  // turn on digit 4
  }
  current_digit = (current_digit % 4) + 1;
}
// main loop
void loop()
{
  if(digitalRead(button) == 0)
  {
    count++;  // increment ‘count’ by 1
    if(count > 9999)
      count = 0;
    delay(200);  // wait 200 milliseconds
  }
}
void disp(byte number, bool dec_point)
{
  switch (number)
  {
    case 0:  // print 0
      shiftOut(dataPin, clockPin, MSBFIRST, 0x02 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 1:  // print 1
      shiftOut(dataPin, clockPin, MSBFIRST, 0x9E | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 2:  // print 2
      shiftOut(dataPin, clockPin, MSBFIRST, 0x24 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 3:  // print 3
      shiftOut(dataPin, clockPin, MSBFIRST, 0x0C | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 4:  // print 4
      shiftOut(dataPin, clockPin, MSBFIRST, 0x98 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 5:  // print 5
      shiftOut(dataPin, clockPin, MSBFIRST, 0x48 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 6:  // print 6
      shiftOut(dataPin, clockPin, MSBFIRST, 0x40 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    
    case 7:  // print 7
      shiftOut(dataPin, clockPin, MSBFIRST, 0x1E | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 8:  // print 8
      shiftOut(dataPin, clockPin, MSBFIRST, !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
      break;
    case 9:  // print 9
      shiftOut(dataPin, clockPin, MSBFIRST, 0x08 | !dec_point);
      digitalWrite(clockPin, HIGH);
      digitalWrite(clockPin, LOW);
  }
}
void disp_off()
{
   digitalWrite(Dig1, HIGH);
   digitalWrite(Dig2, HIGH);
   digitalWrite(Dig3, HIGH);
   digitalWrite(Dig4, HIGH);
}
// end of code.

Video demo dự án:

 

Trả lời

Email của bạn sẽ không được hiển thị công khai. Các trường bắt buộc được đánh dấu *