PIC Projects

Driving a seven-segment LED display

In this project the PIC is used to control the 7-segment LED display directly. The demonstration program is just a counter from 0 to 9 in about 1sec intervals. I use a 2-digit LED display, whose both digits are connected in parallel, so are driven simultaneously. Therefore, the displayed sequence of numbers is 00, 11, 22, ..., 99 repeated periodically.

The LED display I use is HDSP-521E, all whose segments have a common anode. For simplicity I use just one current-limiting resistor of 220 Ohm connected to the common anode of each digit. This is not a very good solution, since the number of highlighted segments for digits varies from 2 to 7 which results in variation of the digit brightness. The digit 8 becomes this way brighter that digit 1, because practically the same current goes through 7 or 2 segments, respectively. However, the dependency of the LED brightness on current is not linear so the difference is not very noticeable. This is particularly true for a dark room. A better solution would be to put a separate resistor between the PIC and LED block, this way raising their count up to 7.

Schematic Layout Segm. codes
matrix

Taking into account the segments topology, in order to display, say, number 5 we have to connect the segments a,f,g,c,d to the ground. As it follows from the schematic, the following byte has to written to PORTB: 01110110. The program starts with initializing the digit codes for each of 10 digits in the function initSegments(). The ones in each code correspond to segments needed to be on for displaying the corresponding digit. In our application the binary complements of the codes has to be written to portB. This is achieved by applying the instruction xorlw 0xFF. If a LED with common cathodes is used then this instruction should be taken off.

After displaying each of 10 numbers 00, ..., 99 we wait for about 1sec before updating it. The currently displayed number is stored in variable n. If after incrementing n becomes 10 it is reset back to 0 and the sequence starts again over and over.

 TITLE  "7seg1.asm"                    ; displaying 0,1,...,9 on a 7-seg LED
 List P=16F84a, R=DEC
 INCLUDE "p16F84a.inc"

; data segment
 CBLOCK 0x00C 
 n                                     ; the number to display
 i,j,k                                 ; variables used in delay()
 segments:10                           ; storage for segment codes
 ENDC

; code segment
 PAGE
 __CONFIG _CP_OFF & _PWRTE_ON  & _WDT_OFF & _XT_OSC

  org    0
  	bsf    	STATUS, RP0            ; change to BANK 1
    	movlw 	0xFF
	movwf	PORTB                  ; turn off all LED segments
  	clrf    TRISB ^ 0x80           ; Enable RB1-RB7 for Output
  	movlw  	0x7F                   ; Enable Internal Pull-Ups
  	movwf  	OPTION_REG ^ 0x80
  	bcf    	STATUS, RP0            ; back to BANK 0

; setup codes for the LED segments
	call 	initSegments
    	clrf	n           		; start counting with n=0 

loop
	movf	n, w
	addlw	segments
	movwf	FSR         		; FSR = pointer to digit code
	movf	INDF, w			; w = code[digit]
	xorlw	0xFF			; highlight only segs for bit=0
	movwf	PORTB       		; light on the digit
	call 	delay			; delay

	incf	n, f			; n++
 	movf	n, w
	sublw	10	   
	btfss	STATUS, Z		; n == 10?	
	goto	loop			; NO - continue
	clrf 	n 			; YES - start from digit 0 again
	goto 	loop

initSegments                            ; fill the array of segment codes
  	movlw	b'11011110' 		; gidit 0
	movwf	segments+0
	movlw	b'00011000' 		; digit 1
	movwf	segments+1
	movlw	b'11101100'		; digit 2
	movwf	segments+2
	movlw	b'01111100'		; digit 3
	movwf	segments+3
	movlw	b'00111010'		; digit 4	
	movwf	segments+4
	movlw	b'01110110'		; digit 5
	movwf	segments+5
	movlw	b'11110110'		; digit 6
	movwf	segments+6
	movlw	b'00011100'		; digit 7
	movwf	segments+7
	movlw	b'11111110' 		; digit 8
	movwf	segments+8
	movlw	b'01111110'		; digit 9
	movwf	segments+9
	return

delay                                   ; a simple delay procedure
	movlw	3
	movwf	k
	
L1	movlw	200
	movwf	i

L2 	movlw	200
	movwf 	j

L3 	decfsz	j, f
	goto 	L3

	decfsz	i, f
	goto 	L2

    	decfsz 	k, f
	goto 	L1

	return

 end

Download 7seg1.asm


Last modified:Mon, Jan 23, 2023.

09313