ChuckR
- 8th October 2021, 17:00
This sample code demonstrates writing to an 8-digit 7-segment LED display (the HW-179 module) that uses the MAX7219 driver device. The MAX7219 is fully SPI compliant, and as such does not require the bit-banging exercises that were present in my earlier posts on LED displays equipped with the TM1637 and TM1638 drivers. Furthermore, the MAX7219 provides for BCD decoding that eliminates the necessity of code that converts numerical digits into their corresponding 7-segment 8-bit codes (although this mode of operation is possible with the MAX7219). The objective of this code sample is only to illustrate initialization of the MAX7219 display, and to show how the 16-bit address+data sequences can be sent as either 16-bit constants, 8-bit variable + 8-bit constant, or by two 8-bit variables, using PBP's SHIFTOUT command.
The MAX7219 driver provides for cascading configurations, thus allowing the HW-179 modules to be chained together to provide 16, 24, 32, etc. digit displays. An example of this will be provided in a subsequent code sample post.
'************************************************* ***************
'* Name : MAX7219_8-Digit_7-Segment_Demo.BAS *
'* Author : Roberts *
'* Notice : Copyright (c) 2021 Copyright (c) 2019 *
'* : All Rights Reserved *
'* Date : 10/6/2021 *
'* Version : 1.0 *
'* Notes : Developed on Microchip Curiosity Board with *
'* : PIC16F183456 uC and the HW-179 8-digit/7-segment *
'* : display driven by the MAX7219 driver via 3-wire *
'* : SPI interface, set to operate at 5 VDC. *
'************************************************* ***************
'
' This brief demo program writes the digits 0 thru 9 and "-" to the HW-179 8-digit 7-segment LED display based on the
' MAX7219 interface driver. The code includes the initialization sequence that (a) sets the decode mode to BCD,
' (b) sets the LED intensity to half-scale (8/16), (c) sets all 8 digits active, and (d) activates the display.
' After initialization, the code sets the test mode active for 1 second (e.g., all digits and all segments lit). Then
' all digits are cleared, and counting begins with the right-hand most digit. Each digit counts from 0 to 9 and then
' "-", and the counting progresses to the left one digit at a time. Once all 8 digits are showing "-", the program
' cycles back to clearing the display and repeating.
' Data is sent to the display using PBP's SHIFTOUT command. The code demonstrates how these 16-bit address + data
' commands can be constructed as either a single 16-bit constant, by an 8-bit variable + 8-bit constant, and by two 8-bit
' variables. While the MAX7219 data registers are blanked upon power on, a microcontroller reset requires a procedure
' that writes 0x0F to all 8 digits in order to blank the digits.
'
'****************************************** PIC16F18346 Initialization *************************************************
'************************************** Configuration File for the PIC 16F18346 ****************************************
#CONFIG
__config _CONFIG1, _FEXTOSC_OFF & _RSTOSC_HFINT32 & _CLKOUTEN_OFF & _CSWEN_ON & _FCMEN_ON
__config _CONFIG2, _MCLRE_ON & _PWRTE_OFF & _WDTE_ON & _LPBOREN_OFF & _BOREN_ON & _BORV_LOW & _PPS1WAY_OFF & _STVREN_ON & _DEBUG_OFF
__config _CONFIG3, _WRT_OFF & _LVP_OFF
__config _CONFIG4, _CP_OFF & _CPD_OFF
#ENDCONFIG
@ ERRORLEVEL -306 ; turn off crossing page boundary message
OSCFRQ = 000100 ' Set internal osc to 16MHz
DEFINE OSC 16 ' Tell PBP that the device will clock at 16MHz (necessary for uSec pauses used in bit-banging)
ANSELA = 000000 ' PortA all digital / available pins are A0 through A5 (6 I/O's)
TRISA = 000000 ' PortA all outputs
'
'************************** Initialization and Variable Declarations *****************************************
'
' SPI signals use LATx.x assignments to prevent read/modify/write conflicts on a single I/O port
CS Var LATA.2 ' uC chip select output pin
SCK Var LATA.4 ' uC clock out pin
SI Var LATA.5 ' uC data out / LCD Data in pin
'
'
i VAR WORD ' loop counter variable
j VAR byte ' loop counter variable
CS = 1 ' Disable SPI device select CS for OLED
'
'************************* Initialize the display parameters by sending 16-bit constants **********************
' (See MAX7219 spec sheet for tables listing full range of initialization values)
CS = 0
SHIFTOUT SI, SCK, 1, [$0F01\16] 'Test display - illuminate all segments & all digits
CS = 1
PAUSE 1000 'hold for 1 second
CS = 0
SHIFTOUT SI, SCK, 1, [$0F00\16] 'Return to normal display mode
CS = 1
PAUSE 1000 'Pause 1 second
CS = 0
SHIFTOUT SI, SCK, 1, [$09FF\16] 'Set decode mode for BCD
CS = 1 '($0900 for no decoding - see MAX7219 spec sheet)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0A07\16] 'Set display intensity to half scale
CS = 1 '($0A00 for minimum brightness / $0A0F for maximum brightness)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0B07\16] 'All 8 digits active
CS = 1 '($0B01 for only digit 1 active - see MAX7219 spec sheet)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0C01\16] 'Activate display
CS = 1 '($0C00 for powering down the display - see MAX7219 spec sheet)
PAUSE 10
'********************************************* Main Program ************************************************** ********
main:
For i = 1 to 8 'Clear all 8 digit registers to blank
CS = 0
Shiftout SI, SCK, 1, [i,$0F] 'Clear each digit "i" by sending the blank character constant 0x0F
CS = 1
Pause 10
Next i 'hold the display blank for 1 second
Pause 1000
For j = 1 to 8 'the variable j is the 8-bit digit address register
For i = 0 to 10 'the variable i is the 8-bit data register
CS = 0
SHIFTOUT SI, SCK, 1, [j,i] 'Display 0 through 9 in digit 1 position (r/h most digit)
CS = 1
PAUSE 500 'pause 1/2 second for counting
Next i
Next j
Pause 2000 'hold the display for 2 seconds
Goto main
The MAX7219 driver provides for cascading configurations, thus allowing the HW-179 modules to be chained together to provide 16, 24, 32, etc. digit displays. An example of this will be provided in a subsequent code sample post.
'************************************************* ***************
'* Name : MAX7219_8-Digit_7-Segment_Demo.BAS *
'* Author : Roberts *
'* Notice : Copyright (c) 2021 Copyright (c) 2019 *
'* : All Rights Reserved *
'* Date : 10/6/2021 *
'* Version : 1.0 *
'* Notes : Developed on Microchip Curiosity Board with *
'* : PIC16F183456 uC and the HW-179 8-digit/7-segment *
'* : display driven by the MAX7219 driver via 3-wire *
'* : SPI interface, set to operate at 5 VDC. *
'************************************************* ***************
'
' This brief demo program writes the digits 0 thru 9 and "-" to the HW-179 8-digit 7-segment LED display based on the
' MAX7219 interface driver. The code includes the initialization sequence that (a) sets the decode mode to BCD,
' (b) sets the LED intensity to half-scale (8/16), (c) sets all 8 digits active, and (d) activates the display.
' After initialization, the code sets the test mode active for 1 second (e.g., all digits and all segments lit). Then
' all digits are cleared, and counting begins with the right-hand most digit. Each digit counts from 0 to 9 and then
' "-", and the counting progresses to the left one digit at a time. Once all 8 digits are showing "-", the program
' cycles back to clearing the display and repeating.
' Data is sent to the display using PBP's SHIFTOUT command. The code demonstrates how these 16-bit address + data
' commands can be constructed as either a single 16-bit constant, by an 8-bit variable + 8-bit constant, and by two 8-bit
' variables. While the MAX7219 data registers are blanked upon power on, a microcontroller reset requires a procedure
' that writes 0x0F to all 8 digits in order to blank the digits.
'
'****************************************** PIC16F18346 Initialization *************************************************
'************************************** Configuration File for the PIC 16F18346 ****************************************
#CONFIG
__config _CONFIG1, _FEXTOSC_OFF & _RSTOSC_HFINT32 & _CLKOUTEN_OFF & _CSWEN_ON & _FCMEN_ON
__config _CONFIG2, _MCLRE_ON & _PWRTE_OFF & _WDTE_ON & _LPBOREN_OFF & _BOREN_ON & _BORV_LOW & _PPS1WAY_OFF & _STVREN_ON & _DEBUG_OFF
__config _CONFIG3, _WRT_OFF & _LVP_OFF
__config _CONFIG4, _CP_OFF & _CPD_OFF
#ENDCONFIG
@ ERRORLEVEL -306 ; turn off crossing page boundary message
OSCFRQ = 000100 ' Set internal osc to 16MHz
DEFINE OSC 16 ' Tell PBP that the device will clock at 16MHz (necessary for uSec pauses used in bit-banging)
ANSELA = 000000 ' PortA all digital / available pins are A0 through A5 (6 I/O's)
TRISA = 000000 ' PortA all outputs
'
'************************** Initialization and Variable Declarations *****************************************
'
' SPI signals use LATx.x assignments to prevent read/modify/write conflicts on a single I/O port
CS Var LATA.2 ' uC chip select output pin
SCK Var LATA.4 ' uC clock out pin
SI Var LATA.5 ' uC data out / LCD Data in pin
'
'
i VAR WORD ' loop counter variable
j VAR byte ' loop counter variable
CS = 1 ' Disable SPI device select CS for OLED
'
'************************* Initialize the display parameters by sending 16-bit constants **********************
' (See MAX7219 spec sheet for tables listing full range of initialization values)
CS = 0
SHIFTOUT SI, SCK, 1, [$0F01\16] 'Test display - illuminate all segments & all digits
CS = 1
PAUSE 1000 'hold for 1 second
CS = 0
SHIFTOUT SI, SCK, 1, [$0F00\16] 'Return to normal display mode
CS = 1
PAUSE 1000 'Pause 1 second
CS = 0
SHIFTOUT SI, SCK, 1, [$09FF\16] 'Set decode mode for BCD
CS = 1 '($0900 for no decoding - see MAX7219 spec sheet)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0A07\16] 'Set display intensity to half scale
CS = 1 '($0A00 for minimum brightness / $0A0F for maximum brightness)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0B07\16] 'All 8 digits active
CS = 1 '($0B01 for only digit 1 active - see MAX7219 spec sheet)
PAUSE 10
CS = 0
SHIFTOUT SI, SCK, 1, [$0C01\16] 'Activate display
CS = 1 '($0C00 for powering down the display - see MAX7219 spec sheet)
PAUSE 10
'********************************************* Main Program ************************************************** ********
main:
For i = 1 to 8 'Clear all 8 digit registers to blank
CS = 0
Shiftout SI, SCK, 1, [i,$0F] 'Clear each digit "i" by sending the blank character constant 0x0F
CS = 1
Pause 10
Next i 'hold the display blank for 1 second
Pause 1000
For j = 1 to 8 'the variable j is the 8-bit digit address register
For i = 0 to 10 'the variable i is the 8-bit data register
CS = 0
SHIFTOUT SI, SCK, 1, [j,i] 'Display 0 through 9 in digit 1 position (r/h most digit)
CS = 1
PAUSE 500 'pause 1/2 second for counting
Next i
Next j
Pause 2000 'hold the display for 2 seconds
Goto main