hi,
i made a simple counter on breadboard with 2 switches and 3 digita 7 segments CA display.
sw1 counts up and sw2 counts down. counter resets if both are pressed
somehow i completed program but there is a problem:
the counter can count between 0 and 255. i wanted 0-999 counter but the counter returns 0 when i increased >255.
i tried a few things like canceling systempx… not working…
'===> Timer interrupt example - Timer Setup
'Replace with your interrupt requirements
InitTimer1 (Osc, PS1_1/8) '==> Init timer prescaler
StartTimer 1
CounterValue = 0
'================================================================
'===== SET DIRECTION OF THE PORTS
'================================================================
'Pin14 ===> Vdd
dir portb out
dir porta.4 out
set PORTa.3 off'Disp1 MSD
set PORTa.6 off'Disp2
set PORTa.7 off'Disp3 LSD
set PORTb.3 off'A
set PORTa.1 off'B
set PORTb.7 off'C
set PORTb.5 off'D
set PORTb.4 off'E
set PORTa.2 off'F
set PORTa.0 off'G
set PORTb.6 on'DP
dir sw1 in
dir sw2 in
'Pin5 ===> Vss
dim delay as byte
dim swdelay as word
dim num as integer
swdelay=250
delay=5
Startup:
Wait StartUpDelay
'===> Timer interrupt example - Enable interrupt
'Replace with your interrupt requirements
On Interrupt Timer1Overflow Call IncCounter
'================================================================
'===== MAIN PROGRAM LOOP
'================================================================
Main:
'Main App code here
epread 20, num
set PORTa.3 off'Disp1 MSD
set PORTa.6 off'Disp2
set PORTa.7 off'Disp3 LSD
set PORTb.3 off'A
set PORTa.1 off'B
set PORTb.7 off'C
set PORTb.5 off'D
set PORTb.4 off'E
set PORTa.2 off'F
set PORTa.0 off'G
set PORTb.6 on'DP
if sw1=1 and sw2=1 then
wait swdelay ms
num=0
EPWrite 20,num
end if
if sw1=1 then
wait swdelay ms
num=num+1
EPWrite 20,num
end if
if sw2=1 then
wait swdelay ms
num=num-1
EPWrite 20,num
end if
gosub showdisp
Goto Main
'================================================================
'===== SUBROUTINES AND FUNCTIONS
'================================================================
sub showdisp
do
select case num
case >=100
DispNum1=num/100
DisplayValue 1,dispnum1
wait delay ms
Num2=num-(dispnum1*100)
if Num2>=10 then
DispNum2=num2/10
DispNum3=num2-(dispnum2*10)
DisplayValue 2,dispnum2
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
else
DispNum3=num2
displayvalue 2,0
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
end if
case =>10 and num<100
DispNum2=num/10
DispNum3=num-(dispnum2*10)
DisplayValue 2,dispnum2
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
case <10
DispNum3=num
DisplayValue 3,dispnum3
wait delay ms
end select
goto main
loop
end sub
Sub IncCounter '===> Sub called by Timer interrupt example
CounterValue ++
End Sub
PS:
* i am not good at english, please forgive my mistakes
* the code probably is not optimum. i don't care if it is working…
* this is a learning practice for me. no serious goal at this moment.
* i don't understand how to use an interrupt with these switches. can you help me about that too?
* the 7segment.h file edited by me because Common Anode displays with no transistor used
* i am tired of pull out / put in the IC. i know i need a simulator. can you recommend working one on winxp?
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
I haven't seen a reply so I have a couple comments.
1) num is defined as an integer which only has a range of 0 - 255. When the variable overflows to 1000 then you have to reset it to 0 with a statement. Are you making a timer or a counter?
2) CounterValue is not being used. To use an interrupt you would need an "On Interrupt" statement calling the interrput subroutine.
3) You should not write to EEPROM so often. It is only guaranteed X number writes. X could be 1000000 but if you write every 250 ms that could pass quick.
Sorry that is all the time I have,
GL
Mike
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
thank you mike,
1) as far as i know "byte" has 0 / 255 range and "integer" must be -32768 / 32767 range according to gcbasic help file
2) i dont know how to connect oninterrupt and switches. i need to make an interrupt when a particular switch pressed… this "oninterrupt" word is not written by me. it is "gcbide"s example code which i didn't delete.
3) yes, i know eeproms have short lifespan. i will do it better way.
PS:
* i don't know what is changed but 0-999 is working now :P
* i really need a working simulator. it is annoying to put in/out pic to breadboard for every trial… you guys, how do you do that trials?
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
in your downloaded "update file" : http://gcbasic.sourceforge.net/update.html
Look at the help file gcbasic.chm which opens into Great Cow Basic Help > command reference> interrupts> on interrupt
on the 16f628a the "B port" has a on change of bits 4-7 RBIF
You could hang your switches on these bits but that would require a decision when entering the interrupt to see if it is Port B interrput or a timer interrupt and then service that interrupt. Switches and people that push them are relatively slow so just having them in the main loop and polling them should be fast enough( like you have now).
73
mike
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@fisyon
You are using a ziff socket for programming? Best way is to use icsp or in circuit serial programming. To do that break out the MCLR , Vdd, Vss, icspDAT, iscpCLK lines respectively. You can use jumpers or make up a cable to go between the programmer and the bread board. Using a straight or 90 deg. 6 pin 0.100" header also works for the highly recommended pickit programmers.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
mike,
thank you for the fast reply,
so you are saying i can only use portb 4-7 pins for interrupts on 16f628a?
if so i will need to change all circut and code :P
whatever, thanks for your patience
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@kent_twt4
yes, i am using usb programmer with ziff socket (k182?)
icsp may be good idea but i am not feeling that i can handle it properly at this moment.
thank you anyway
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Here is the developers page on icsp programming for the kitsrus programmers http://www.kitsrus.com/icsp.html
I would implore you to effect the icsp diagram with the three commonly available parts. There is no shame in hitting the compile button repeatably, I do it all the time. Taking a chip in and out of the ziff socket all the time would just take the fun out of doing projects :-)
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Your problem is here . EPWrite 20,num
The EEPROM in a 16F628 is only 8 bits wide not 16 , so you can only write and read 8 bit values
to any EEPROM memory location.
To write and read 16 bit values , you have to break the variable into 2, 8 bit variables and then write them to multiple memory locations.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
'Goto main' there is not allowed, because your stack will get messed-up.
you may never jump out of a sub without using the stack pointer.
Goto doesn't use the stack-pointer, 'end Sub' does. So, 'end sub' should be the call to make to return where it cam from
Op 12 aug. 2012, om 22:58 heeft SourceForge.net het volgende geschreven:
end select
goto main <- not allowed
loop
end sub
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
hi,
i made a simple counter on breadboard with 2 switches and 3 digita 7 segments CA display.
sw1 counts up and sw2 counts down. counter resets if both are pressed
somehow i completed program but there is a problem:
the counter can count between 0 and 255. i wanted 0-999 counter but the counter returns 0 when i increased >255.
i tried a few things like canceling systempx… not working…
here is my whole code:
'================================================================
'===== CHIP SETUP
'================================================================
#chip 16F628a, 4
#config OSC=int, BODEN=OFF, WDT=OFF
#define StartUpDelay 100 ms
'#define Delay 500 ms
'================================================================
'===== DEFINE THE PORTS
'================================================================
'Pin14 ===> Vdd
#define DISP_SEL_1 PORTa.3 'Disp1 MSD 2->12
#define DISP_SEL_2 PORTa.6 'Disp2 15->9
#define DISP_SEL_3 PORTa.7 'Disp3 LSD 16->8
#Define DISP_SEG_A PORTb.3 'A 9->11
#Define DISP_SEG_B PORTb.1 'B 7->7
#Define DISP_SEG_C PORTb.7 'C 13->4
#Define DISP_SEG_D PORTb.5 'D 11->2
#Define DISP_SEG_E PORTb.4 'E 10->1
#Define DISP_SEG_F PORTb.2 'F 8->10
#Define DISP_SEG_G PORTa.0 'G 17->5
#define DP PORTb.6 'DP 12->3
#define sw1 porta.1 'Buton1
#define sw2 porta.2 'Buton2
'Pin5 ===> Vss
'===> Timer interrupt example - Timer Setup
'Replace with your interrupt requirements
InitTimer1 (Osc, PS1_1/8) '==> Init timer prescaler
StartTimer 1
CounterValue = 0
'================================================================
'===== SET DIRECTION OF THE PORTS
'================================================================
'Pin14 ===> Vdd
dir portb out
dir porta.4 out
set PORTa.3 off'Disp1 MSD
set PORTa.6 off'Disp2
set PORTa.7 off'Disp3 LSD
set PORTb.3 off'A
set PORTa.1 off'B
set PORTb.7 off'C
set PORTb.5 off'D
set PORTb.4 off'E
set PORTa.2 off'F
set PORTa.0 off'G
set PORTb.6 on'DP
dir sw1 in
dir sw2 in
'Pin5 ===> Vss
dim delay as byte
dim swdelay as word
dim num as integer
swdelay=250
delay=5
Startup:
Wait StartUpDelay
'===> Timer interrupt example - Enable interrupt
'Replace with your interrupt requirements
On Interrupt Timer1Overflow Call IncCounter
'================================================================
'===== MAIN PROGRAM LOOP
'================================================================
Main:
'Main App code here
epread 20, num
set PORTa.3 off'Disp1 MSD
set PORTa.6 off'Disp2
set PORTa.7 off'Disp3 LSD
set PORTb.3 off'A
set PORTa.1 off'B
set PORTb.7 off'C
set PORTb.5 off'D
set PORTb.4 off'E
set PORTa.2 off'F
set PORTa.0 off'G
set PORTb.6 on'DP
if sw1=1 and sw2=1 then
wait swdelay ms
num=0
EPWrite 20,num
end if
if sw1=1 then
wait swdelay ms
num=num+1
EPWrite 20,num
end if
if sw2=1 then
wait swdelay ms
num=num-1
EPWrite 20,num
end if
gosub showdisp
Goto Main
'================================================================
'===== SUBROUTINES AND FUNCTIONS
'================================================================
sub showdisp
do
select case num
case >=100
DispNum1=num/100
DisplayValue 1,dispnum1
wait delay ms
Num2=num-(dispnum1*100)
if Num2>=10 then
DispNum2=num2/10
DispNum3=num2-(dispnum2*10)
DisplayValue 2,dispnum2
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
else
DispNum3=num2
displayvalue 2,0
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
end if
case =>10 and num<100
DispNum2=num/10
DispNum3=num-(dispnum2*10)
DisplayValue 2,dispnum2
wait delay ms
DisplayValue 3,dispnum3
wait delay ms
case <10
DispNum3=num
DisplayValue 3,dispnum3
wait delay ms
end select
goto main
loop
end sub
Sub IncCounter '===> Sub called by Timer interrupt example
CounterValue ++
End Sub
PS:
* i am not good at english, please forgive my mistakes
* the code probably is not optimum. i don't care if it is working…
* this is a learning practice for me. no serious goal at this moment.
* i don't understand how to use an interrupt with these switches. can you help me about that too?
* the 7segment.h file edited by me because Common Anode displays with no transistor used
* i am tired of pull out / put in the IC. i know i need a simulator. can you recommend working one on winxp?
I haven't seen a reply so I have a couple comments.
1) num is defined as an integer which only has a range of 0 - 255. When the variable overflows to 1000 then you have to reset it to 0 with a statement. Are you making a timer or a counter?
2) CounterValue is not being used. To use an interrupt you would need an "On Interrupt" statement calling the interrput subroutine.
3) You should not write to EEPROM so often. It is only guaranteed X number writes. X could be 1000000 but if you write every 250 ms that could pass quick.
Sorry that is all the time I have,
GL
Mike
Now I see the "On Interrupt" ! skip that comment.
sorry
mike
thank you mike,
1) as far as i know "byte" has 0 / 255 range and "integer" must be -32768 / 32767 range according to gcbasic help file
2) i dont know how to connect oninterrupt and switches. i need to make an interrupt when a particular switch pressed… this "oninterrupt" word is not written by me. it is "gcbide"s example code which i didn't delete.
3) yes, i know eeproms have short lifespan. i will do it better way.
PS:
* i don't know what is changed but 0-999 is working now :P
* i really need a working simulator. it is annoying to put in/out pic to breadboard for every trial… you guys, how do you do that trials?
in your downloaded "update file" : http://gcbasic.sourceforge.net/update.html
Look at the help file gcbasic.chm which opens into Great Cow Basic Help > command reference> interrupts> on interrupt
on the 16f628a the "B port" has a on change of bits 4-7 RBIF
You could hang your switches on these bits but that would require a decision when entering the interrupt to see if it is Port B interrput or a timer interrupt and then service that interrupt. Switches and people that push them are relatively slow so just having them in the main loop and polling them should be fast enough( like you have now).
73
mike
@fisyon
You are using a ziff socket for programming? Best way is to use icsp or in circuit serial programming. To do that break out the MCLR , Vdd, Vss, icspDAT, iscpCLK lines respectively. You can use jumpers or make up a cable to go between the programmer and the bread board. Using a straight or 90 deg. 6 pin 0.100" header also works for the highly recommended pickit programmers.
mike,
thank you for the fast reply,
so you are saying i can only use portb 4-7 pins for interrupts on 16f628a?
if so i will need to change all circut and code :P
whatever, thanks for your patience
@kent_twt4
yes, i am using usb programmer with ziff socket (k182?)
icsp may be good idea but i am not feeling that i can handle it properly at this moment.
thank you anyway
Here is the developers page on icsp programming for the kitsrus programmers http://www.kitsrus.com/icsp.html
I would implore you to effect the icsp diagram with the three commonly available parts. There is no shame in hitting the compile button repeatably, I do it all the time. Taking a chip in and out of the ziff socket all the time would just take the fun out of doing projects :-)
Your problem is here . EPWrite 20,num
The EEPROM in a 16F628 is only 8 bits wide not 16 , so you can only write and read 8 bit values
to any EEPROM memory location.
To write and read 16 bit values , you have to break the variable into 2, 8 bit variables and then write them to multiple memory locations.
Back to the code.
'Goto main' there is not allowed, because your stack will get messed-up.
you may never jump out of a sub without using the stack pointer.
Goto doesn't use the stack-pointer, 'end Sub' does. So, 'end sub' should be the call to make to return where it cam from
Op 12 aug. 2012, om 22:58 heeft SourceForge.net het volgende geschreven: