1. Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.
    Dismiss Notice

Simplistic reaction timer

Discussion in 'Microcontrollers' started by MrDEB, Apr 2, 2018.

  1. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    My neighbor is constructing a "man cave" with a hot rod, fast car theme (old gas pump front panel, drag slick, stop light etc.
    I got crazy idea to build a Chrondike Christmas Tree (a "tree" used in drag racing indicating when to leave the starting line. The starting line utilizes clocks to measure drivers reaction time)
    Reaction time is measured how fast a driver gets their car moving after the green light on the tree comes on.
    So I wrote a short code to begin a reaction time that is displayed on an LCD. This is a crude start and for a better clock to use TMR1 and interrupts.
    So a work in progress. End project to utilize 12v Leds using mosfets.
     
  2. tumbleweed

    tumbleweed Active Member

    Joined:
    Jan 25, 2007
    Messages:
    110
    Likes:
    32
    If you want to count msecs your loop should look more like this:
    Code (text):

    time = 0
    REPEAT
        DELAYMS(1)
        INC (time)
    UNTIL button = 0
     
    Otherwise you'll increment the 'time' variable as fast as the loop runs
     
  3. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    no wonder it was displaying large numbers
     
  4. dave miyares

    Dave New Member

    Joined:
    Jan 12, 1997
    Messages:
    2
    Likes:
    -10


     
  5. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    After using tumbleweeds suggestion it looks like it works but being really bad at math, how to display time in one thousands of a second?
    .0075 as an example
    1ms is 1000 of a second and um is 10000 of a second so how to display correctly.
    I tried dividing by 1000 but that isn't right either
    Pretty sure the indents are correct??
     
  6. Ian Rogers

    Ian Rogers User Extraordinaire Forum Supporter Most Helpful Member

    Joined:
    Mar 28, 2011
    Messages:
    9,678
    Likes:
    947
    Location:
    Rochdale UK
    You are desperately trying to show code... Here is your code in code tags..
    Code (basic):

    DEVICE = 18F4321
    CLOCK = 8
    CONFIG MCLRE = off
    // some LCD options...
    #option LCD_DATA = PORTD.4
    #option LCD_RS = PORTd.0
    #option LCD_EN = PORTd.1
    // import LCD library...
    INCLUDE "SetDigitalIO.bas"
    INCLUDE "IntOSC8.bas"
    INCLUDE "LCD.bas"
    INCLUDE "utils.bas"
    INCLUDE "Convert.bas"
    DIM blue AS portB.7
    DIM green AS portb.5
    DIM button AS portb.4
    DIM time AS WORD
    DIM start AS portb.0
    time = 0
    setalldigital
    OUTPUT (blue)
    OUTPUT (green)
    INPUT(start)
    cls
    DELAYMS(50)
    blue =1
    green = 1
    start = 1
    WHILE true
       blue = 0
       DELAYMS(3000)
       blue = 1
       green = 0      //go
       REPEAT
          DELAYuS(time)
          INC (time)
       UNTIL button = 0
       green = 1
       'time = time /1000
       WriteAt(1,1,"reaction=",DecToStr(time),"ms",4)
       DELAYMS(3000)
       time = 0 //reset to zero
       WriteAt(1,1,"try again=",DecToStr(time),"ms",4)
    WEND
     
    Type "["code=basic"]"
    at the end "["/code"]" All except the inverted commas These are so you can see
     
  7. tumbleweed

    tumbleweed Active Member

    Joined:
    Jan 25, 2007
    Messages:
    110
    Likes:
    32
    Do you really have a need to show more than 1/1000 of a second?
    One msec resolution seems like it would be more than acceptable unless you've got a bunch of Olympic neighbors.

    In any event, there are now at least two things wrong.
    Code (text):

    dim time as word

       REPEAT
          DELAYuS(time)
          INC (time)
       UNTIL button = 0
     
    First, 'time' is a word. That's 16 bits. The max value it can hold is (2^16)-1 = 65535.
    If 'time' is counting usecs then that's 65,535 usecs = 65.535 msecs, which is far too short.
    If 'time' counts msecs then it's 65535 msecs = 65.535 secs which sounds just fine for what you're doing.

    Secondly, 'DELAYUS(time)' delays more and more time each iteration through the loop as 'time' gets incremented.

    Put 'DELAYUS(time)' back to 'DELAYMS(1)'.

    I'll leave the printing part to others. Wouldn't want this to end prematurely.
     
  8. dave miyares

    Dave New Member

    Joined:
    Jan 12, 1997
    Messages:
    2
    Likes:
    -10


     
  9. Pommie

    Pommie Well-Known Member Most Helpful Member

    Joined:
    Mar 18, 2005
    Messages:
    10,568
    Likes:
    395
    Location:
    Brisbane Australia
    ONLINE
    Tumbleweed, whatever code you post will be randomly changed until it doesn't work.

    Mike.
     
  10. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    Whats a 12V led? serious question...

    I got some 10W ones that i rarely use(way too bright) and some 1 W ones I normally use. I run then off a 5V rail, why use 12V out of interest.
    For what your doing i would get a busted bulls eye bulb (old style non led), take apart and stick a led in it. it should give ample reflection for a traffic light with one led per colour. And why use a LCD?? for that kind of thing a read out in leds above the traffic lights seems more authentic and a better option

     
    • Like Like x 1
  11. tumbleweed

    tumbleweed Active Member

    Joined:
    Jan 25, 2007
    Messages:
    110
    Likes:
    32
    Mike, that's a given.

    I now take bets with myself as to what portion of the code will get screwed up first.
    I know there's no real point in answering, it's just for my own amusement.
     
  12. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    DIM will be first

    All old hands know that Dim is always the major issue in these posts ;)
     
  13. Pommie

    Pommie Well-Known Member Most Helpful Member

    Joined:
    Mar 18, 2005
    Messages:
    10,568
    Likes:
    395
    Location:
    Brisbane Australia
    ONLINE
    Dim LG as Funny = 100%.

    Mike.
     
  14. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    this looks more accurate and runs better. Still need to figure out how to display (example 1ms = .001)


    [code = basic]
    DEVICE = 18F4321
    CLOCK = 8
    CONFIG MCLRE = off
    // some LCD options...
    '#option KEYPAD_PORT = PORTc
    #option LCD_DATA = PORTD.4
    #option LCD_RS = PORTd.0
    #option LCD_EN = PORTd.1
    // import LCD library...
    INCLUDE "SetDigitalIO.bas"
    INCLUDE "IntOSC8.bas"
    INCLUDE "LCD.bas"
    INCLUDE "utils.bas"
    'INCLUDE "Keypad16pullup.bas"
    INCLUDE "Convert.bas"
    // include ISR timer module
    INCLUDE "ISRTimer.bas"
    DIM mS AS WORD
    DIM blue AS portb.7
    DIM button AS portb.4
    DIM green AS portb.5
    dim red as portb.6
    // OnTimer event, flash LED...
    SUB OnTimer()
    INC(mS)
    END SUB
    // initialise the timer module...
    Timer.Initialize(1)
    // initialise timer.items(0)
    Timer.Items(0).Interval = 1 // 1mS
    Timer.Items(0).OnTimer = @OnTimer // timer event handler
    // enable the timers...
    Timer.Items(0).Enabled = true
    INPUT (button)
    OUTPUT (blue)
    output (green)
    output (red)
    setalldigital
    green = 1
    blue = 1
    button = 1
    red = 1
    WHILE True
    mS = 0
    green = 0 //turn on green until button is pressed

    Timer.Start //start timing reaction time

    REPEAT
    UNTIL
    button = 0 // button pressed then turn off green, turn on blue
    green = 1 //off
    blue = 0 //on
    Timer.Stop //stop timer
    WriteAt(1,1,"reaction=",DecToStr(mS),"ms",2)
    DELAYMS(3000)
    blue = 1 //led is off
    DELAYMS(1000)

    WEND
    [/code]
     
  15. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    try displaying 001
    lets face it anything over 999 and you might as well use a candle and bands marked on it.
    Also stop the timer as soon as something is pressed, dont leave it until last ;)
     
  16. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    Code (basic):


    [code = basic]
    DEVICE = 18F4321
    CLOCK = 8
    CONFIG MCLRE = off
    // some LCD options...
    '#option KEYPAD_PORT = PORTc
    #option LCD_DATA = PORTD.4
    #option LCD_RS = PORTd.0
    #option LCD_EN = PORTd.1
    // import LCD library...
    INCLUDE "SetDigitalIO.bas"
    INCLUDE "IntOSC8.bas"
    INCLUDE "LCD.bas"
    INCLUDE "utils.bas"
    'INCLUDE "Keypad16pullup.bas"
    INCLUDE "Convert.bas"
    // include ISR timer module
    INCLUDE "ISRTimer.bas"
    DIM mS AS WORD
    DIM blue AS portb.7
    DIM button AS portb.4
    DIM green AS portb.5
    dim red as portb.6
    // OnTimer event, flash LED...
    SUB OnTimer()
    INC(mS)
    END SUB
    // initialise the timer module...
    Timer.Initialize(1)
    // initialise timer.items(0)
    Timer.Items(0).Interval = 1 // 1mS
    Timer.Items(0).OnTimer = @OnTimer // timer event handler
    // enable the timers...
    Timer.Items(0).Enabled = true
    INPUT (button)
    OUTPUT (blue)
    output (green)
    output (red)
    setalldigital
    green = 1
    blue = 1
    button = 1
    red = 1
    WHILE True
    mS = 0
    green = 0 //turn on green until button is pressed

    Timer.Start //start timing reaction time

    REPEAT
    UNTIL
    button = 0 // button pressed then turn off green, turn on blue
    green = 1 //off
    blue = 0 //on
    Timer.Stop //stop timer
    WriteAt(1,1,"reaction=",DecToStr(mS),"ms",2)
    DELAYMS(3000)
    blue = 1 //led is off
    DELAYMS(1000)

    WEND
     
    The above is your code, i was trying to work out how you messed up code tags! I think in the top code tag you got a space, no spaces

    How the feck can you mess that up??finally worked it out.............

    you put a space both sides of = there is no space its code=basic but with square brackets around it and no spaces
     
    Last edited: Apr 7, 2018
    • Like Like x 1
  17. tumbleweed

    tumbleweed Active Member

    Joined:
    Jan 25, 2007
    Messages:
    110
    Likes:
    32
    Here's how you would convert ms to a secs string, broken up into its steps
    Code (text):

    include "convert.bas"
    dim ms as word
    dim s as string

    // convert word ms to secs string (ie "D.DDD")
    s = DecToStr(ms/1000)               ' print whole portion (number before decpt)
    s = s + "."                         ' add decpt
    s = s + DecToStr((ms MOD 1000), 3)  ' add three digits fractional part
    s = s + "secs"

    // or all in one shot
    s = DecToStr(ms/1000) + "." + DecToStr((ms MOD 1000), 3) + "secs"
     
    To write it to the LCD you could just use
    Code (text):

    // write string to LCD
    s = DecToStr(ms/1000) + "." + DecToStr((ms MOD 1000), 3) + "secs"
    WriteAt(1,1,"reaction=",s,2)
     
    or put it all into the WriteAt statement
     
    • Like Like x 1
  18. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    Seriously it takes you guys a second to notice a color change and press a button?? I am not looking forward to getting over 30! :D
     
  19. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    Thanks tumbleweed. I will try your suggestion out.
    I tried ms/1000 but it didn't work as I wanted it to.
    Your suggestion is very imaganitive. I was even thinking a CONST ARRAY but then what do I know. Would screw up the indenting--lol
     
  20. Little Ghostman

    Little Ghostman Well-Known Member Most Helpful Member

    Joined:
    Jan 7, 2011
    Messages:
    4,220
    Likes:
    484
    Location:
    SCOTLAND
    You need a random seed value, muscle memory will quickly sync with a set speed of light change. Try it with a stop watch and try and hit exactly one second. I bet 15 mins your within a few ms
     
    • Agree Agree x 1
  21. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    the addition of tumbleweeds suggestion worked like a charm. My best reaction was .042 but mostly .160 or so. I kinda jumped the gun in anticipation.
    What I want to add now is a Red led to indicate if the player jumped the gun before the green led sand display how bad the reaction was before the green.
    LG is correct that I need a random # before the green led. Will add AFTER I get the basic code working then add the random #
     
  22. MrDEB

    MrDEB Well-Known Member

    Joined:
    Apr 16, 2007
    Messages:
    4,576
    Likes:
    25
    For the fun of the game, as a suggestion only, is to build the circuit and have fun with playing with friends, add a second player option, random # and the red led.
    I did have a reaction of .001 but am sure that was a fluke
     

Share This Page