PDA

View Full Version : RFID medicine teller!! problem with programming



sknee8787
- 13th November 2008, 01:09
I am doing with RFID medicine teller..

the step is as show below but i do not to start the program code, anyone know ??

1st step:
i am using 16x2 LCD display and 3 different tag. on top will display real clock and bottom is display the time i setting whereby is 12:10:00 am/pm

2nd step:
when real clock reach till 12:10:00 am/pm then the LCD will display out 'Please take medicine A' at the same time the buzzer will loud. non-stop.

3rd step:
then i take medicine B to let RFID reader scan the tag that have provided. but it is wrong medicine, so the LCD will display ' incorrect please take medicine A' while buzzer loud. then continue to take another tag.

4th step:
at the end, take medicine A to let RFID scan again. finally LCD display "correct medicine taken" buzzer loud (different sound).


at here, i really hope someboddy can help me. i am a begineer. please T.T

mackrackit
- 13th November 2008, 02:12
Sounds like a good project, might be (IS) a little ambitious for a first project.

What have you done so far?
What compiler are you using?
What chip do you plan to use?

sknee8787
- 13th November 2008, 04:34
I am using 16F876A
using microcode studio compiler
I had done everything hardware, just left program code.

mackrackit
- 13th November 2008, 04:48
OK.
MCS is not a compiler. But I will take it you are using Pic Basic or Pic Basic Pro?

What I meant was how much programing have you done so far?

Are you needing help with the timer part? Try looking at these:
http://www.picbasic.co.uk/forum/showthread.php?t=632&highlight=olympic+timer
http://www.picbasic.co.uk/forum/showthread.php?t=2129&highlight=olympic+timer

Or are you completely new and need help with something else?

sknee8787
- 13th November 2008, 05:10
2994

2995

here have sample that i took from my senior.. the project quite similiar with my project. while, the time posted from me is what i took from website. hope that can help you.

mackrackit
- 13th November 2008, 05:28
hope that can help you.
Now I am confused. I thought you were the one asking for help. :)

Start off by getting the timer code working on your chip. Then work on having an event happen at a certain time. That event for testing would be a LED blink in a certain sequence. That is what you want , correct?

But if this is your first time, write some code to make a LED blink to make sure everything is running, then work on using the display.

sknee8787
- 13th November 2008, 05:42
sorry i make you confused.
the purpose i do is RFID medicine teller. since i posted the step in previous. that is what i want.

the sample of RFID that i posted is only a guidance. i want to let you more easily to understood what i want. because that sample is also a RFID. i try to modify it on medicine teller.

the problem is i dunno how to write the program code as well. please help me

mackrackit
- 13th November 2008, 06:13
Lets start off getting familiar with the chip and and make the LED blink first.

In the PBP directory you will find *.inc files. Comment out the config lines like it is shown here.
http://www.picbasic.co.uk/forum/showpost.php?p=6775&postcount=5

We will be setting the configuration in code space. The above thread is talking about how this is done.

I will also assume and /or suggest you have MPLAB installed and tell MCS to use MPASM.
And I will assume and suggest you use a resonator for the OSC.
All the above said, the begining of your code will look like this:


DEFINE OSC 20 ' If the resonator is 4MHz then replace 20 with 4
'##The line below is the config line
'##The OSC is HS for resonators,WatchDogTimer is OFF,LowVoltagePrograming is OFF
'##CodeProtection is OFF and BrownOut is OFF
@ __config _HS_OSC & _WDT_OFF & _LVP_OFF & _CP_OFF &_BODEN_OFF

Then we will turn off the ADC and Comparators
http://www.picbasic.co.uk/forum/showthread.php?t=561


ADCON1=7
CMCON=7

Then connect an LED to PORTC.7 with a 470 resistor.
And make it turn on for .25 seconds and off for .25 seconds.


LOOP:
HIGH PORTC.7
PAUSE 250
LOW PORTC.7
PAUSE 250
GOTO LOOP

See if you can get that working and the we will go after the LCD display.

sknee8787
- 13th November 2008, 07:18
erm... easy way..
i want setting the time 12:10:00 am/pm on my LCD display
how to program it?? as i know is:

if hour = 12 and minute = 10 second = 00 then run

run:
reqout#(code) and so on...


can you help me correct it? whereby that i have wrong with the program.

mackrackit
- 13th November 2008, 07:26
can you help me correct it? whereby that i have wrong with the program.

Post the code you wrote and we will see what is wrong.

sknee8787
- 13th November 2008, 08:17
2996

the error is start from mainloop.

mackrackit
- 13th November 2008, 08:47
Some of the things I see are Variable that have not been declared.
This is not like some basics, in PBP all variables have to be defined
For example:
MYVAR VAR BYTE

A label name can only be used once.
You have bad_tag used at least twice.

Read through the code you have and see if it flows the way you want it.
You may find it easier to write your own from scratch and not do a copy paste. That is what it looks like to me.

Below is the code as you have it posted in code brackets
Make it easier for people to see and maybe help you.


' LCD clock program using On Interrupt
' Uses TMR0 and prescaler. Watchdog Timer should be
' set to off at program time and Nap and Sleep should not be used.
' Buttons may be used to set time

define LOADER_USED 1
define OSC 4
define LCD_DREG PORTB
DEFINE LCD_DBIT 0
DEFINE LCD_RSREG PORTB
DEFINE LCD_RSBIT 5
DEFINE LCD_EREG PORTB
DEFINE LCD_EBIT 4
DEFINE LCD_BITS 4

adcon1 = 7
trisa = %11111111


hour var byte ' Define hour variable
dhour var byte ' Define display hour variable
minute var byte ' Define minute variable
second var byte ' Define second variable
ticks var byte ' Define pieces of seconds variable
update var byte ' Define variable to indicate update of LCD

i var byte ' Debounce loop variable

@ device WDT_OFF

CMCON = 7 ' PORTA digital

Pause 100 ' Wait for LCD to startup

hour = 0 ' Set initial time to 00:00:00
minute = 0
second = 0
ticks = 0
update = 1 ' Force first display

' Set TMR0 to interrupt every 16.384 milliseconds

OPTION_REG = $55 ' Set TMR0 configuration and enable PORTB pullups
INTCON = $a0 ' Enable TMR0 interrupts
On Interrupt Goto tickint
PORTB = 0 ' PORTB lines low to read buttons
TRISB = %11001111 ' Enable buttons

' Main program loop - in this case, it only updates the LCD with the time
mainloop:
' Check any button pressed to set time
If PORTa.2 = 1 Then decmin
If PORTA.3 = 1 Then incmin

' Check for time to update screen
chkup: If update = 1 Then
Lcdout $fe, 1 ' Clear screen
lcdout $FE,$c0,"12:10:00"

' Display time as hh:mm:ss
dhour = hour ' Change hour 0 to 12
If (hour // 12) = 0 Then
dhour = dhour + 12
Endif

' Check for AM or PM
If hour < 12 Then
Lcdout dec2 dhour, ":", dec2 minute, ":", dec2 second, " AM"
Else
Lcdout dec2 (dhour - 12), ":", dec2 minute, ":", dec2 second, " PM"
Endif
update = 0 ' Screen updated
Endif
if hour = 12 and minute = 10 and second = 00 then run
run:

next
bad_tag:
low porta.3 'green LED
pause 500
high portc.0 'red LED
tagnum = 0
lcdout $FE,1,"Sorry Wrong medicine"
freqout portC.5,1000*/$100,115*/$100
pause 3000
serin2 portc.0,84,[str buf\10]
for tagnum = 1 to 2
for idx = 0 to 9
read(((tagnum-1)*10)+idx),char
if(char<>buf(idx)) then goto bad_char
next

goto tag_found_unlock
bad_char:
next

bad_tag:
low porta.3
pause 500
high portc.0
tagnum = 0
lcdout $FE,1,"Incorrect~!!"
freqout portC.5,1000*/$100,115*/$100
pause 3000
goto main

tag_found_unlock
low portc.0
high porta.3
freqout portC.5,2000*/$100,880*/$100
lcdout $FE,1,"Correct"
lcdout $FE,$c0,"right medicine!!"
high porta.3

Goto mainloop ' Do it all foreve
' Increment minutes
incmin: minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Goto debounce

' Decrement minutes
decmin: minute = minute - 1
If minute >= 60 Then
minute = 59
hour = hour - 1
If hour >= 24 Then
hour = 23
Endif
Endif

' Debounce and delay for 250ms
debounce: For i = 1 to 25
Pause 10 ' 10ms at a time so no interrupts are lost
Next i
update = 1 ' Set to update screen
Goto chkup

' Interrupt routine to handle each timer tick
disable ' Disable interrupts during interrupt handler
tickint: ticks = ticks + 1 ' Count pieces of seconds
If ticks < 61 Then tiexit ' 61 ticks per second (16.384ms per tick)

' One second elasped - update time
ticks = 0
second = second + 1
If second >= 60 Then
second = 0
minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Endif
update = 1 ' Set to update LCD
tiexit: INTCON.2 = 0 ' Reset timer interrupt flag
Resume

End

sknee8787
- 13th November 2008, 10:08
ok.. thanks for your help..
i will try it

if i found that have any problem then i will post again. :D

aratti
- 13th November 2008, 10:53
This piece of code is wrong!



' Decrement minutes
decmin: minute = minute - 1
If minute >= 60 Then
minute = 59
hour = hour - 1
If hour >= 24 Then
hour = 23
Endif
Endif


Al.

mister_e
- 13th November 2008, 20:19
Not really...
if minutes was 0, if you decrement it and it's a BYTE, this will gives you...255... same apply to hour.

aratti
- 13th November 2008, 22:08
Hops... True! But using the overflow you don't need the "=" sign.

Al.

sknee8787
- 14th November 2008, 04:40
i have found out the problem. freqout and sound commant will delay my overall circuit function when display the result on the LCD screen.

then anyone have a solution can replace for freqout and sound??



define LOADER_USED 1
define OSC 4
define LCD_DREG PORTB
DEFINE LCD_DBIT 0
DEFINE LCD_RSREG PORTB
DEFINE LCD_RSBIT 5
DEFINE LCD_EREG PORTB
DEFINE LCD_EBIT 4
DEFINE LCD_BITS 4

adcon1 = 7
trisa = %11111111


hour var byte ' Define hour variable
dhour var byte ' Define display hour variable
minute var byte ' Define minute variable
second var byte ' Define second variable
ticks var byte ' Define pieces of seconds variable
update var byte ' Define variable to indicate update of LCD

i var byte ' Debounce loop variable

cl var byte
buf var byte(10)
tagNum var byte
idx var byte
char var byte

tag1 data "0010828978"

@ device WDT_OFF

CMCON = 7 ' PORTA digital

Pause 100 ' Wait for LCD to startup

hour = 00 ' Set initial time to 00:00:00
minute = 00
second = 00
ticks = 00
update = 1 ' Force first display

' Set TMR0 to interrupt every 16.384 milliseconds

OPTION_REG = $55 ' Set TMR0 configuration and enable PORTB pullups
INTCON = $a0 ' Enable TMR0 interrupts
On Interrupt Goto tickint

PORTB = 0 ' PORTB lines low to read buttons
TRISB = %11001111 ' Enable buttons

' Main program loop - in this case, it only updates the LCD with the time
mainloop:
' Check any button pressed to set time
If PORTa.0 = 1 Then decmin
If PORTA.1 = 1 Then incmin

bbb:
if porta.2 = 1 then nice

' Check for time to update screen
chkup: If update = 1 Then
Lcdout $fe,1 ' Clear screen
'lcdout $FE,$c0,"Next 12:10:00"

' Display time as hh:mm:ss
dhour = hour ' Change hour 0 to 12
If (hour // 12) = 0 Then
dhour = dhour + 12
Endif

' Check for AM or PM
If hour < 12 Then
Lcdout dec2 dhour, ":", dec2 minute, ":", dec2 second, " AM"
Else
Lcdout dec2 (dhour - 12), ":", dec2 minute, ":", dec2 second, " PM"
Endif
update = 0 ' Screen updated
Endif

lcdout $FE,$c0,"Next 12:10:10 AM"

if (dhour = 12) and (minute = 10) and (second = 10) then aaa

goto mainloop


aaa:
'freqout porta.5,1000*/$100,115*/$100
sound porta.5, [200,100]
lcdout $FE,1,"please"
lcdout $FE,$c0,"Medicine!!"
high portc.0
update = 1
'pause 2000

goto mainloop





nice:
high porta.3
low portc.0
'freqout porta.5,1000*/$100,115*/$100
high porta.3
'pause 3000

serin2 portc.7,84,[str buf\10]
'nextline:
for tagnum = 1 to 2
for idx = 0 to 9
read(((tagnum-1)*10)+idx),char
if(char<>buf(idx)) then goto bad_char

next
goto tag_correct
bad_char:
next
bad_tag:
low porta.3
'pause 500
high portc.0
tagnum = 0
lcdout $FE,1,"Sorry,Wrong"
lcdout $FE,$c0,"Medicine!!"
sound porta.5, [200,100]
'freqout porta.5,1000*/$100,115*/$100
'pause 3000

lcdout $FE,1,"Please Take"
lcdout $FE,$c0,"Medicine A"

goto nice

tag_correct
low porta.4
high porta.5

freqout porta.5,2000*/$100,880*/$100
lcdout $FE,1,"Correct take"
lcdout $FE,$c0,"Medicine!!"
high portc.3
pause 3000



goto mainloop


'Goto mainloop ' Do it all foreve
' Increment minutes
incmin: minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Goto debounce

' Decrement minutes
decmin: minute = minute - 1
If minute >= 60 Then
minute = 59
hour = hour - 1
If hour >= 24 Then
hour = 23
Endif
Endif

' Debounce and delay for 250ms
debounce: For i = 1 to 25
Pause 10 ' 10ms at a time so no interrupts are lost
Next i
update = 1 ' Set to update screen
Goto chkup

' Interrupt routine to handle each timer tick
disable ' Disable interrupts during interrupt handler
tickint: ticks = ticks + 1 ' Count pieces of seconds
If ticks < 61 Then tiexit ' 61 ticks per second (16.384ms per tick)

' One second elasped - update time
ticks = 0
second = second + 1
If second >= 60 Then
second = 0
minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Endif
update = 1 ' Set to update LCD
tiexit: INTCON.2 = 0 ' Reset timer interrupt flag
Resume

End

mackrackit
- 14th November 2008, 05:44
Check out FREQOUT in the manual. It does not look correct the way you have it.

sknee8787
- 14th November 2008, 06:15
except FREQOUT and SOUND. have any different command is also for speaker?? While, after display out the result then pause 2000. it will delay the time to go for next stage. for example,


nice:
lcdout $FE,1,"Sorry,Wrong"
lcdout $FE,$c0,"Medicine!!"
freqout porta.5,1000*/$100,115*/$100
high porta.3
pause 3000

serin2 portc.7,84,[str buf\10]
'nextline:
for tagnum = 1 to 2
for idx = 0 to 9
read(((tagnum-1)*10)+idx),char
if(char<>buf(idx)) then goto bad_char

mackrackit
- 14th November 2008, 06:31
freqout porta.5,1000*/$100,115*/$100
If I am doing my math correctly the above code is trying to produce a -256Hz tone for 1 second. I do not think this is possible:)

Try:

FREQOUT PORTA.5,1000,440,350
and see what happens.

sknee8787
- 18th November 2008, 03:09
define LOADER_USED 1
define OSC 4
define LCD_DREG PORTB
DEFINE LCD_DBIT 0
DEFINE LCD_RSREG PORTB
DEFINE LCD_RSBIT 5
DEFINE LCD_EREG PORTB
DEFINE LCD_EBIT 4
DEFINE LCD_BITS 4

adcon1 = 7
trisa = %11111111


hour var byte ' Define hour variable
dhour var byte ' Define display hour variable
minute var byte ' Define minute variable
second var byte ' Define second variable
ticks var byte ' Define pieces of seconds variable
update var byte ' Define variable to indicate update of LCD

i var byte ' Debounce loop variable

cl var byte
buf var byte(10)
tagNum var byte
idx var byte
char var byte

tag1 data "0010828978"

@ device WDT_OFF

CMCON = 7 ' PORTA digital

Pause 100 ' Wait for LCD to startup

hour = 00 ' Set initial time to 00:00:00
minute = 00
second = 00
ticks = 00
update = 1 ' Force first display

' Set TMR0 to interrupt every 16.384 milliseconds

OPTION_REG = $55 ' Set TMR0 configuration and enable PORTB pullups
INTCON = $a0 ' Enable TMR0 interrupts
On Interrupt Goto tickint

PORTB = 0 ' PORTB lines low to read buttons
TRISB = %11001111 ' Enable buttons

' Main program loop - in this case, it only updates the LCD with the time
mainloop:
' Check any button pressed to set time
If PORTa.0 = 1 Then decmin
If PORTA.1 = 1 Then incmin

bbb:
if porta.2 = 1 then nice

' Check for time to update screen
chkup: If update = 1 Then
Lcdout $fe,1 ' Clear screen
'lcdout $FE,$c0,"Next 12:10:00"

' Display time as hh:mm:ss
dhour = hour ' Change hour 0 to 12
If (hour // 12) = 0 Then
dhour = dhour + 12
Endif

' Check for AM or PM
If hour < 12 Then
Lcdout dec2 dhour, ":", dec2 minute, ":", dec2 second, " AM"
Else
Lcdout dec2 (dhour - 12), ":", dec2 minute, ":", dec2 second, " PM"
Endif
update = 0 ' Screen updated
Endif

lcdout $FE,$c0,"Next 12:10:10 AM"

if (dhour = 12) and (minute = 10) and (second = 10) then aaa

goto mainloop


aaa:
'freqout porta.5,1000*/$100,115*/$100
sound porta.5, [200,100]
lcdout $FE,1,"please"
lcdout $FE,$c0,"Medicine!!"
high portc.0
update = 1
'pause 2000

goto mainloop





nice:
high porta.3
low portc.0
'freqout porta.5,1000*/$100,115*/$100
high porta.3
'pause 3000

serin2 portc.7,84,[str buf\10]
'nextline:
for tagnum = 1 to 2
for idx = 0 to 9
read(((tagnum-1)*10)+idx),char
if(char<>buf(idx)) then goto bad_char

next
goto tag_correct
bad_char:
next
bad_tag:
low porta.3
'pause 500
high portc.0
tagnum = 0
lcdout $FE,1,"Sorry,Wrong"
lcdout $FE,$c0,"Medicine!!"
sound porta.5, [200,100]
'freqout porta.5,1000*/$100,115*/$100
'pause 3000

lcdout $FE,1,"Please Take"
lcdout $FE,$c0,"Medicine A"

goto nice

tag_correct
low porta.4
high porta.5

freqout porta.5,2000*/$100,880*/$100
lcdout $FE,1,"Correct take"
lcdout $FE,$c0,"Medicine!!"
high portc.3
second = second + 1
pause 3000



goto mainloop


'Goto mainloop ' Do it all foreve
' Increment minutes
incmin: minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Goto debounce

' Decrement minutes
decmin: minute = minute - 1
If minute >= 60 Then
minute = 59
hour = hour - 1
If hour >= 24 Then
hour = 23
Endif
Endif

' Debounce and delay for 250ms
debounce: For i = 1 to 25
Pause 10 ' 10ms at a time so no interrupts are lost
Next i
update = 1 ' Set to update screen
Goto chkup

' Interrupt routine to handle each timer tick
disable ' Disable interrupts during interrupt handler
tickint: ticks = ticks + 1 ' Count pieces of seconds
If ticks < 61 Then tiexit ' 61 ticks per second (16.384ms per tick)

' One second elasped - update time
ticks = 0
second = second + 1
If second >= 60 Then
second = 0
minute = minute + 1
If minute >= 60 Then
minute = 0
hour = hour + 1
If hour >= 24 Then
hour = 0
Endif
Endif
Endif
update = 1 ' Set to update LCD
tiexit: INTCON.2 = 0 ' Reset timer interrupt flag
Resume

End


code shown on top is my program code. i want to know how to let real time work continuing when the time is match which what the time i was setted. because i has foind out the problem when time is matched. the real time will stopped it there. :(

mackrackit
- 18th November 2008, 13:59
Not sure...but I think the code might be hanging here
I do not see anything else at the moment.


goto nice

tag_correct
low porta.4
high porta.5

freqout porta.5,2000*/$100,880*/$100
lcdout $FE,1,"Correct take"
lcdout $FE,$c0,"Medicine!!"
high portc.3
second = second + 1
pause 3000

goto mainloop

sknee8787
- 18th November 2008, 17:31
erm.. i has following your instruction, but still remain same thing happening. athrough i ignore the frequency the time still might stopped when the time is matched with the time i setted.:(