I start to play with one of this cheap 4 digit 7 segment display. The display is driven by two 74HC595 which one is for segments and the other is for common cathodes (digits).
Here is the schematic:
I writed a simple code using Darrel's interrupts. Code multiplexing the digits using TMR1 interrupt.
It works OK, but I think that code is not as elegant. It looks rough, because I'm not a skilled programmer.
Can someone explain to me a better way to do this task?
Here is my code:
Code:
'****************************************************************
'* Name : 4 bit 7 segment display *
'* Author : LouisLouis *
'* Notice : Copyright (c) 2018 *
'* : All Rights Reserved *
'* Date : 18. 2. 2018 *
'* Version : 1.0 *
'* Notes : *
'* MCU : PIC 12F1840 *
'****************************************************************
#CONFIG
__config _CONFIG1, _FOSC_INTOSC & _WDTE_OFF & _PWRTE_ON & _MCLRE_OFF & _CP_OFF & _CPD_OFF & _BOREN_ON & _CLKOUTEN_OFF & _IESO_ON & _FCMEN_ON
__config _CONFIG2, _WRT_OFF & _PLLEN_ON & _STVREN_ON & _BORV_19 & _LVP_OFF
#ENDCONFIG
DEFINE OSC 32 ; Use internal clock
OSCCON = 110000
CLKRCON = 0
Include "modedefs.bas"
INCLUDE "DT_INTS-14.bas" ; Base Interrupt System
INCLUDE "ReEnterPBP.bas" ; Include if using PBP interrupts
TRISA = %0000
ANSELA = 00
OPTION_REG.7=0 ; Enable internal pull-ups
LPIN var porta.2 ; Latch
DPIN var porta.4 ; Data
CPIN var porta.5 ; Clock
segment var byte
value var word
place var byte[4]
ones var word
tens var word
hundreds var word
thousands var word
ASM
INT_LIST macro ; IntSource, Label, Type, ResetFlag?
INT_Handler TMR1_INT, _DISP, PBP, yes
endm
INT_CREATE ; Creates the interrupt processor
ENDASM
@ INT_ENABLE TMR1_INT ; enable Timer 1 interrupts
T1CON = $1
;---[simple counter 0 - to 9999]------------------------------------------------
Main:
for value = 0 to 9999
pause 100
next value
value = 0
GOTO Main
;---[TMR1 - interrupt handler]--------------------------------------------------
DISP:
T1CON.0 = 0 ; stop timer
TMR1H = 111100
TMR1L = 011111
T1CON.0 = 1 ; restart timer
;---[extract ones and show]-----------------------------------------------------
ones = value//10
lookup ones, [000000,111001,100100,110000,011001,010010,000010,111000,000000,010000],segment
LOW LPIN
Shiftout DPIN, CPIN, MSBFIRST,[segment,01]
high lpin
pause 4
;---[extract tens and show]-----------------------------------------------------
tens = value/10
tens = tens//10
lookup tens, [000000,111001,100100,110000,011001,010010,000010,111000,000000,010000],segment
LOW LPIN
Shiftout DPIN, CPIN, MSBFIRST,[segment,10]
high lpin
pause 4
;---[extract hundreds and show]-------------------------------------------------
hundreds = value/100
hundreds = hundreds//10
lookup hundreds, [000000,111001,100100,110000,011001,010010,000010,111000,000000,010000],segment
LOW LPIN
Shiftout DPIN, CPIN, MSBFIRST,[segment,00]
high lpin
pause 4
;---[extract thousands and show]------------------------------------------------
thousands = value/1000
place = 00
lookup thousands, [000000,111001,100100,110000,011001,010010,000010,111000,000000,010000,001000],segment
LOW LPIN
Shiftout DPIN, CPIN, MSBFIRST,[segment,00]
high lpin
@ INT_RETURN
it adds unnecessary bloat for this app
Code:
'****************************************************************
'* Name : 4 bit 7 segment display *
'* Author : RICHARD *
'* Notice : *
'* : *
'* Date : 18. 2. 2018 *
'* Version : 1.0 *
'* Notes : *
'* MCU : PIC 12F1822 @32MHZ *
'****************************************************************
#CONFIG
__config _CONFIG1, _FOSC_INTOSC & _WDTE_OFF & _PWRTE_ON & _MCLRE_OFF & _CP_OFF & _CPD_OFF & _BOREN_ON & _CLKOUTEN_OFF & _IESO_ON & _FCMEN_ON
__config _CONFIG2, _WRT_OFF & _PLLEN_ON & _STVREN_ON & _BORV_19 & _LVP_OFF
#ENDCONFIG
goto overasm
ASM
seg_val
CHK?RP _TM_TMP
MOVWF _TM_TMP
SUBLW 0x21
btfsc STATUS, C
retlw 0 ;" "
MOVF _TM_TMP,W
SUBLW 0x2f
btfsc STATUS, C
retlw 64 ;"-"
MOVF _TM_TMP,W
MOVLW 0X40
SUBWF _TM_TMP,W
btfsC STATUS, C
GOTO TM_ALPHA
MOVF _TM_TMP,W
ANDLW 0X0F
GOTO TM_LU
TM_ALPHA
ANDLW 0xdf ;ucase
SUBLW 6
btfsS STATUS, C
retlw 0 ;ERROR
MOVLW 0X37
SUBWF _TM_TMP,W
ANDLW 0xdf ;ucase
TM_LU
BRW
retlw 0X3F ;0
retlw 6
retlw 0X5B
retlw 0X4F
retlw 0X66
retlw 0X6D
retlw 0X7D
retlw 7
retlw 0X7F
retlw 0X67 ;9
retlw 0X77 ;A
retlw 0X7C ;b
retlw 0X39 ;C
retlw 0X5E ;d
retlw 0X79 ;E
retlw 0X71 ;F
endasm
overasm:
DEFINE OSC 32 ; Use internal clock
ANSELA=0
SSP1CON1=$22
SSP1STAT=$40
OSCCON=$70
DEFINE INTHAND _DISP
TRISA = %111000
@LPORT=LATA
LPIN CON 2 ;var LATa.2 ; Latch
DPIN var porta.0 ; Data SDO
CPIN var porta.1 ; Clock SCK
segment var byte
value var word
d_index var byte
buff var byte[5]
seg_buff var byte[4]
seg_cnt var byte
seg_dat var byte
tmp var byte
TM_TMP var byte
d_pointer var byte
timer1_reload con 33543 ;4mS
PIR1.0=0
INTCON=$C0
PIE1.0=1
T1CON = $1
d_index=0
;---[simple counter 0 - to ffff]------------------------------------------------
Main:
for value = 0 to 65535
arraywrite buff ,[HEX4 value,0]
gosub load_seg
pause 100
next value
value = 0
GOTO Main
load_seg :
for seg_cnt=0 to 3
seg_dat= buff[seg_cnt]
asm
MOVE?BA _seg_dat
L?CALL seg_val
MOVE?AB _seg_dat
endasm
seg_buff[seg_cnt]= seg_dat
next
return
;---[TMR1 - interrupt handler]--------------------------------------------------
DISP:
asm
MOVE?CT 0, T1CON, TMR1ON ; 1 stop timer
MOVLW LOW(_timer1_reload) ; 1 Add TimerReload to the
ADDWF TMR1L,F ; 1 value in Timer1
BTFSC STATUS,C ; 1/2
INCF TMR1H,F ; 1
MOVLW HIGH(_timer1_reload) ; 1
ADDWF TMR1H,F ; 1
MOVE?CT 1, T1CON, TMR1ON ; 1 start timer
MOVE?CB high _seg_buff, FSR0H ;load highbyte
MOVE?CB low _seg_buff, FSR0L ;load low byte
MOVE?BA _d_index
ADDWF FSR0L,F
MOVF INDF0,W
;L?CALL seg_val
MOVE?AB _segment
MOVE?BB _d_index ,_tmp
BANKSEL _tmp
INCF _tmp,F
MOVLW 16
BANKSEL _d_pointer
movwf _d_pointer
BcF STATUS ,C
N_BIT
BANKSEL _d_pointer
RRF _d_pointer,F
BANKSEL _tmp
DECFSZ _tmp,F
GOTO N_BIT
BANKSEL _d_index
INCF _d_index,F
MOVLW 3
ANDWF _d_index,F
BANKSEL LPORT
BCF LPORT ,_LPIN
BANKSEL PIR1
BCF PIR1,3
BANKSEL _segment
MOVF _segment,W ;COMMENT USED TO INVERT DATA FOR COMMON cathode DISPLAY
;COMF _segment,W ;COMMENT USED TO INVERT DATA FOR COMMON ANODE DISPLAY
BANKSEL SSP1BUF
movwf SSP1BUF
BANKSEL PIR1
BTFSs PIR1,3
GOTO $-1
BANKSEL _d_pointer
COMF _d_pointer,W ;COMMENT USED FOR COMMON cathode DISPLAY
;MOVF _d_pointer,W ;COMMENT USED FOR COMMON ANODE DISPLAY
BANKSEL PIR1
BCF PIR1,3
BANKSEL SSP1BUF
movwf SSP1BUF
BANKSEL PIR1
BTFSs PIR1,3
GOTO $-1
BANKSEL LPORT
BSF LPORT ,_LPIN
BANKSEL PIR1
BCF PIR1 ,0
RETFIE
endasm
Code:
Main:
for value = 0 to 65535
arraywrite buff ,[HEX4 value]
gosub load_seg
seg_buff[2]=seg_buff[2]|128 ; place a dp in digit 2
pause 100
next value
value = 0
GOTO Main


Menu
Re: LCDOUT command followed by variable data
no , you can create your alias names for the array address' in the buffer in any way that you prefer or just use array notation and have no alias' at all
richard Yesterday, 23:08