🤖
LinkIt 7697 BlocklyDuino 使用指南
  • LinkIt 7697 BlocklyDuino 使用指南
    • 認識 LinkIt 7697
    • 認識 BlocklyDuino
    • BlocklyDuino v2 & v3 比較
    • 安裝開發環境 (v2)
      • 安裝 Arduino 編輯器
      • 安裝驅動並連接開發板
      • 安裝 BlocklyDuino 編輯器
      • 連結兩個編輯器並上傳程式
    • 安裝開發環境 (v3)
    • BlocklyDuino 基礎操作
    • 實作範例教學
      • A01. 內建 LED 閃爍
      • A02. 外接 LED 閃爍
      • A03. 外接 LED 呼吸燈
      • A04. RGB LED 顏色變化
      • A05. 外部按鈕控制開關
      • A06. 蜂鳴器播放聲音
      • A07 .可變電阻控制電壓輸出
      • A08. 伺服馬達控制
      • A21. DHT: 溫濕度感應器
      • A22. HTU21D: 溫溼度感應器
      • A23. PMSX003: PM2.5 感測器
      • A24. HC-SR04P: 超音波測距
      • A25. ADXL345: 加速規(動態)
      • A26. ADXL345: 加速規(手勢)
      • A27. 1602/2004: 液晶顯示模組
      • A28. WS2812: RGB 彩色燈條
      • A29. MFRC522: RFID
      • B00. Grove 相關基礎知識
      • B01. Grove 光感應器
      • B02. Grove 超音波測距感應器
      • B03. Grove 溫溼度感應器
      • B04. Grove 繼電器
      • B05. Grove LED 燈條
      • B06. Grove OLED 顯示器
      • C01. 雲端控制 LED 開關
      • C02. 上傳溫溼度到雲端
      • D01. 手機透過 BLE 讀寫裝置資料
      • E01. 遙控器: 按鈕控制 LED
    • 資源鏈結
  • LinkIt 7697 - Arduino IDE 開發指南
    • 環境設定
      • 設定 Arduino IDE
      • 將 LinkIt 7697 連接到電腦
        • 在 Windows 上安裝 CP2102N 驅動程式
        • 在 macOS 上安裝 CP2102N 驅動程式
      • 執行第一個程式
    • 開發指南
      • GPIO
      • UART
      • ADC
      • EINT (外部中斷 / External Interrupt)
      • I2C
      • SPI
      • EEPROM
      • Timer
      • Flash (索引式儲存空間)
      • RTC (Real-Time Clock)
      • Software Serial
      • 使用 Wi-Fi 函式庫
      • 使用 MCS 函式庫
        • 連接到 MCS
        • 連接到 MCSLite
          • 建立可透過 MCS Lite 控制的 Beacon
        • MCS 函式庫 API 使用手冊
          • MCSDevice
          • MCSLiteDeviceMCSLiteDevice
          • MCSDataChannel 相關類別
      • 使用 BLE 低功耗藍牙
        • 藍牙信標
        • 主控裝置
        • 周邊裝置
        • 已知限制
        • LBLE API 指南
          • LBLE
          • LBLECentral
          • LBLEPeripheral
          • LBLEAdvertisementData
          • LBLEService
          • LBLECharacteristic
          • LBLEAddress
          • LBLEUuid
          • LBLEClient
      • 使用 LinkIt Remote
        • LRemote API
        • LRemote 控制元件 API
      • LinkIt 7697 腳位的初始狀態
      • LinkIt 7697 供電說明
      • 更新 Bootloader 與韌體
      • Flash 燒錄工具
      • FOTA 更新
      • LinkIt 7697 的功能限制
      • 自行編譯 Arduino Package
      • 回報問題
    • 週邊元件連接教學
      • SMD 按鈕
      • RGB 三色 LED
      • 可變電阻
      • 九軸感應器 (MPU-9250)
      • 溫度與濕度感應器 (AM2302)
      • 超音波距離感應器
      • 光感應器 (LM358)
      • 0.96 吋 OLED 顯示模組 (SSD1308Z)
      • 長條型 LED 顯示模組 (MY9221)
      • 繼電器
      • 伺服馬達 (EMAX 9g ES08A Servo)
      • 使用 74HC595 驅動七段顯示器
      • 使用 MAX7219 驅動七段顯示器
      • 使用 MAX7219 驅動 8x8 矩陣式顯示器
      • 使用 OLED 模組 (如 SH1106 / SSD1306... 等模組)
      • 使用 PCF8574 / PCF8574A 驅動 1602 LCD
    • 開發套件與擴充板
      • Grove Starter Kit
      • Robot Shield
        • OTTO97
    • 下載
    • 資源連結
    • BSP 版本更新資訊
  • LinkIt 7697 - Development Guide for Arduino IDE
    • Environment Setup
      • Setup Arduino IDE
      • Connecting LinkIt 7697 to Computer
        • Install CP2102N Driver on Windows
        • Install CP2102N Driver on macOS
      • Run Your First Sketch
    • Developer Guide
      • GPIO
      • UART
      • ADC
      • External Interrupt
      • I2C
      • SPI
      • EEPROM
      • Timer
      • Flash (Key-Pair Storage)
      • RTC (Real-Time Clock)
      • Software Serial
      • Using the Wi-Fi Library
      • Using MCS Library
        • Connecting to MCS
        • Connecting to MCSLite
          • Build a Beacon controlled by MCS Lite
        • MCS Library API Reference
          • MCSDevice
          • MCSLiteDevice
          • MCSDataChannel Classes
      • Using Bluetooth
        • Beacons
        • Central Devices
        • Peripheral Devices
        • Limitations of LBLE library
        • LBLE Library API Guide
          • LBLE
          • LBLECentral
          • LBLEPeripheral
          • LBLEAdvertisementData
          • LBLEService
          • LBLECharacteristic
          • LBLEAddress
          • LBLEUuid
          • LBLEClient
      • Using LinkIt Remote
        • LRemote
        • LRemote Control Classes
      • Initial Pin State of LinkIt 7697
      • Powering the LinkIt 7697
      • Update Bootloader and Firmware
      • Flash Uploading Tool
      • FOTA Update
      • Limitations of LinkIt 7697
      • Source Code of Arduino Package
      • Issue Report
    • Tutorial
      • SMD Buttons
      • RGB LED
      • Potentiometer
      • IMU 9DOF v2.0 (MPU-9250)
      • Temperature and Humidity Sensor Pro (AM2302)
      • Grove Ultrasonic Ranger
      • Light Sensor (LM358)
      • Grove OLED Display 0.96" (SSD1308Z)
      • LED Bar v2.0 (MY9221)
      • Relay
      • Mini Servo (EMAX 9g ES08A Servo)
      • Driving 7-segment Displays with 74HC595
      • Driving 7-segment Displays with MAX7219
      • Driving 8x8 Dot Matrices with MAX7219
      • Using OLED module (SH1106 / SSD1306... etc.)
      • Driving 1602 LCD with PCF8574 / PCF8574A
    • Kits and Shields
      • Grove Starter Kit
      • Robot Shield
        • OTTO97
    • Download
    • Resources
    • BSP Release Notes
Powered by GitBook
On this page
  • Using a shift register to reduce pin usage
  • Driving four seven-segment display with one 74HC595
  • Summary
  1. LinkIt 7697 - Development Guide for Arduino IDE
  2. Tutorial

Driving 7-segment Displays with 74HC595

PreviousMini Servo (EMAX 9g ES08A Servo)NextDriving 7-segment Displays with MAX7219

Last updated 3 years ago

A is a LED module composed of 8 LEDs. 7 of the LEDs are for segments of one digit (shown as A to G below) and the other LED is for the decimal point (shown as DP below).

Depending on it's a common-anode or a common-cathode module, its schematic can be represented as:

A common-anode seven-segment display

or

A common-cathode seven-segment display

As a consequence, an intuitive way to control a seven-segment display is to use 8 GPIOs to connect to A, B, C, D, E, F, G and DP signal pins and control each pin as turning on/off an ordinary LED. Therefore the display can show any desired pattern composed of all those 8 segments.

Use P7 to P14 to control a common-anode seven-segment display

Different combinations of possible displayed segments

Using a shift register to reduce pin usage

74HC595 shift register

For saving the pin number for controlling a seven-segment display, a shift register is used as a serial-to-parallel converter to send signals to the display. That is, we serially send 8 bits of data, which represents the way we want to turn on the display, by one signal pin into the shift register and the register can output the corresponding data pattern to its 8 output pins at once (parallel).

Input pins

  • 1 input data pin (DS)

  • 1 clock pin for input data (SHCP)

  • 1 clock pin for output data (STCP)

Output pins

  • 8 data pins (Q0 ~ Q7)

Control pins

  • 1 output enable pin (OE)

  • 1 data reset pin (MR)

And next we'll show the circuit connection for using it.

Driving one seven-segment display with 74HC595

In the circuit below, LinkIt 7697 connects to the input pins of 74HC595 with orange wires and the output pins of 74HC595 are with blue wires.

We use this sketch file to show hexadecimal digits (0 ~ 9 and a ~ f) repeatedly on a common-anode seven-segment display:

//
// Use one 74HC595 to control a common-anode seven-segment display
//

// pin 11 of 74HC595 (SHCP)
const int bit_clock_pin = 16;
// pin 12 of 74HC595 (STCP)
const int digit_clock_pin = 15;
// pin 14 of 74HC595 (DS)
const int data_pin = 14;

// digit pattern for a 7-segment display
const byte digit_pattern[16] =
{
  B00111111,  // 0
  B00000110,  // 1
  B01011011,  // 2
  B01001111,  // 3
  B01100110,  // 4
  B01101101,  // 5
  B01111101,  // 6
  B00000111,  // 7
  B01111111,  // 8
  B01101111,  // 9
  B01110111,  // A
  B01111100,  // b
  B00111001,  // C
  B01011110,  // d
  B01111001,  // E
  B01110001   // F
};

unsigned int counter = 0;

void setup()
{
  pinMode(data_pin, OUTPUT);
  pinMode(bit_clock_pin, OUTPUT);
  pinMode(digit_clock_pin, OUTPUT);  
}
 
void update_one_digit(int data)
{
  int i;
  byte pattern;
  
  // get the digit pattern to be updated
  pattern = digit_pattern[data];

  // turn off the output of 74HC595
  digitalWrite(digit_clock_pin, LOW);
  
  // update data pattern to be outputed from 74HC595
  // because it's a common anode LED, the pattern needs to be inverted
  shiftOut(data_pin, bit_clock_pin, MSBFIRST, ~pattern);
  
  // turn on the output of 74HC595
  digitalWrite(digit_clock_pin, HIGH);
}

void loop()
{ 
  int i;
  unsigned int digit_base;
  
  counter++;
  
  digit_base = 16;

  // get the value to be displayed and update one digit
  update_one_digit(counter % digit_base);
  
  delay(500);
}

Explanation

  • Digit patterns are pre-defined in the digit_pattern array, which indicates what segment needs to be turned on for composing one digit.

  • digit_clock_pin is the signal we use to control the STCP pin of the 74HC595. It enables / disables the output of the shift register.

This example shows how to use 3 (instead of 8) pins on LinkIt 7697 to drive one seven-segment display with a shift register. In general, if there are N digits needed to be driven, 3N signal pins and N shift registers are necessary. In the next section, we'll show another technique to simply use one shift register to drive a four-digit seven-segment display module.

Driving four seven-segment display with one 74HC595

The schematic of the display module is shown as below:

It's a common-anode four-digit seven-segment display. And we connect it with a 74HC595 and LinkIt 7697 as:

Similar to the previous example, LinkIt 7697 connects to the input pins of 74HC595 with orange wires and the output pins of 74HC595 are with blue wires. Moreover, four control pins (yellow wires) are needed from LinkIt 7697 to turn on / off each digit in the module. We use the sketch below to drive the display and it will show numbers counting increasingly as in the video:

Sketch file

//
// Use one 74HC595 to control a 12-pin common-anode 4-digit seven-segment display with fast scanning
// the display: http://www.icshop.com.tw/product_info.php/products_id/19357
//

#define DELAY_FACTOR  (100)
#define NUM_OF_DIGITS (4)

// 4 display on/off pin (for the common anode/cathode)
const int control_pins[NUM_OF_DIGITS] = {17, 5, 4, 3};
// pin 11 of 74HC595 (SHCP)
const int bit_clock_pin = 16;
// pin 12 of 74HC595 (STCP)
const int digit_clock_pin = 15;
// pin 14 of 74HC595 (DS)
const int data_pin = 14;

// digit pattern for a 7-segment display
const byte digit_pattern[16] =
{
  B00111111,  // 0
  B00000110,  // 1
  B01011011,  // 2
  B01001111,  // 3
  B01100110,  // 4
  B01101101,  // 5
  B01111101,  // 6
  B00000111,  // 7
  B01111111,  // 8
  B01101111,  // 9
  B01110111,  // A
  B01111100,  // b
  B00111001,  // C
  B01011110,  // d
  B01111001,  // E
  B01110001   // F
};

int digit_data[NUM_OF_DIGITS] = {0};
int scan_position = 0;

unsigned int counter = 0;

void setup()
{
  int i;

  // set related pins as output pins
  for (i = 0; i < NUM_OF_DIGITS; i++)
  {
    pinMode(control_pins[i], OUTPUT);
  }

  pinMode(data_pin, OUTPUT);
  pinMode(bit_clock_pin, OUTPUT);
  pinMode(digit_clock_pin, OUTPUT);  
}
 
void update_one_digit()
{
  int i;
  byte pattern;
  
  // turn off all digit
  for (i = 0; i < NUM_OF_DIGITS; i++)
  {
    digitalWrite(control_pins[i], LOW);
  }

  // get the digit pattern of the position to be updated
  pattern = digit_pattern[digit_data[scan_position]];

  // turn off the output of 74HC595
  digitalWrite(digit_clock_pin, LOW);
  
  // update data pattern to be outputed from 74HC595
  // because it's a common anode LED, the pattern needs to be inverted
  shiftOut(data_pin, bit_clock_pin, MSBFIRST, ~pattern);
  
  // turn on the output of 74HC595
  digitalWrite(digit_clock_pin, HIGH);

  // turn on the digit to be updated in this round
  digitalWrite(control_pins[scan_position], HIGH);

  // go to next update position
  scan_position++;
  
  if (scan_position >= NUM_OF_DIGITS)
  {
    scan_position = 0; 
  }
}

void loop()
{ 
  int i;
  unsigned int number;
  unsigned int digit_base;
  
  counter++;
  
  // get the value to be displayed
  number = counter / DELAY_FACTOR;

  digit_base = 10;

  // get every values in each position of those 4 digits based on "digit_base"
  //
  // digit_base should be <= 16
  //
  // for example, if digit_base := 2, binary values will be shown. If digit_base := 16, hexidecimal values will be shown
  //
  for (i = 0; i < NUM_OF_DIGITS; i++)
  {
    digit_data[i] = number % digit_base;
    number /= digit_base;
  }

  // update one digit
  update_one_digit();
  
  delay(4);
}

Explanation

  • The on / off switch of each digit is controlled through the control_pins array.

  • When the pattern is correctly set through the shift register, the sketch then turn on that digit by setting control_pins[scan_position] to HIGH.

  • Each loop() routine only updates one digit. In order to make the persistence of vision take effects, the loop() routine needs to be executed frequently.

As a result, you can simply use one shift register to drive 4 digits. Comparing to the original 8-GPIO-for-one-digit method, now only 7 control pins (instead of 32) from LinkIt 7697 are needed for driving 4 digits. This saves lots of control pins needed and reduces the circuit layout complexity.

Summary

Seven-segment displays are commonly used in different areas to display numerical information for user interaction. So it's worth understanding how to drive them correctly and efficiently. In this tutorial, we introduced three ways to drive the seven-segment display:

  1. Intuitive LED on / off mechanism.

  2. Using one shift register to drive one digit.

  3. Utilizing the effect of persistence of vision to drive a 4-digit display with one shift register.

This gives the fundamental concept about how to drive a seven-segment display and the idea about using a shift register as a serial-to-parallel converter. Also, the technique to utilize persistence of vision is introduced. In another tutorial, we will show how to control a 8-digit seven-segment display module with LinkIt 7697, by using a dedicated seven-segment display driving IC MAX7219.

In the above example, 8 GPIO pins are needed to drive a single seven-segment display. Though it's intuitive, this circuit setup is very pin-consuming. Assuming the case where a four-digit display is needed, this setup means a total 32 (8 pins x 4 digits) pins are required to control the display. It's usually not feasible for a development board to provide so many GPIOs and it also introduces huge complexity in the circuit setup. To solve this issue, a shift register chip can be used to reduce the necessary pin numbers for controlling a seven-segment display. In the following sections, the shift register chip would be used as an example. In the first part, we'll show how to simply use 3 GPIOs to control one seven-segment display by using a shift register. And based on this configuration, an example for how to extend it to control 4 seven-segment displays, by still using one shift register, is also introduced.

Signal pins we need to take care about when using a 74HC595 are (please refer to its for pin names):

API is called to serially send the data pattern to the shift register. Note: because a common-anode seven-segment display is used here, the data pattern needs to be inverted (~pattern) for correctly showing the digit. If you're using a common-cathode display, the pattern doesn't need to be inverted (and of course, the circuit needs to be adjusted accordingly).

When it comes to display more than one digit, more seven-segment displays are needed. According to the example above, N-digit display needs N shift registers and 3N control pins from a development board. Here we use a commonly seen to demonstrate how to drive four digits by still using one shift register.

How to drive 4 displays with still one shift register? is utilized and this sketch rapidly updates one digit in every loop() routine.

74HC595
datasheet
shiftOut()
four-digit seven-segment display module
Persistence of vision
seven-segment display