What is best way to deal with button timing issue?
I have a GPS data logger program that has a long loop with a waitcnt of 4 seconds between writes to a kml file. I use a button to start and stop recording of the kml file.
I have been using a separate cog to check the state of the button pin so that it doesn't have to be pressed at the exact time it goes back through the repeat loop.
I am sure there is a better way people are doing this, but couldn't find anything like this in the labs.
I want to add an accelerometer and need to free up a cog. I was thinking counters might could be used, but the counter examples are over my head.
I have been using a separate cog to check the state of the button pin so that it doesn't have to be pressed at the exact time it goes back through the repeat loop.
PUB InitButton
cognew(button(@buttonpressed), @stack)
Pub button(bp)
dira[8]~
long[bp] := 0
repeat
if ina[8] == 1 'stores a button press until an action is done in main program to remove timing issues.
long[bp] := 1
I am sure there is a better way people are doing this, but couldn't find anything like this in the labs.
I want to add an accelerometer and need to free up a cog. I was thinking counters might could be used, but the counter examples are over my head.

Comments
repeat t := cnt bp := 0 repeat if INA[8] bp := 1 quit until (cnt - t) > (CLKFREQ * 4) if bp quit '' WRITE TO FILECON _clkmode = xtal1 + pll16x _xinfreq = 5_000_000 VAR long timer1 long eTime1 OBJ debug : "FullDuplexSerial" PUB Main 'the FIRST PUB-Method inside a spinfile is ALWAYS the startpoint where the program starts to run debug.start(31, 30, 0, 115200) timer1 := cnt 'make inital snapshot of systemcounter repeat 'do whatever you like inside this loop ' 'the method elapsed_time_msec calculates the time that has gone since 'variable timer1 has set to the (former) value of systemcounter eTime1 := elapsed_time_msec(timer1) if eTime1 => 1340 debug.str(string("snapshot of systemcounter: timer1=")) debug.dec(timer1) debug.str(string(" elapsed time=")) debug.dec(eTime1) debug.tx(13) debug.tx(13) 'make new snapshot of systemcouner to set new startvalue timer1 := cnt PUB elapsed_time_msec(p_TimeVar) | RightNow, ClockTicks RightNow := cnt if RightNow < p_TimeVar ClockTicks := ||($FFFFFFFF - RightNow + p_TimeVar) else ClockTicks := ||(RightNow - p_TimeVar) result := ClockTicks / (clkfreq / 1_000) 'calculate milliseconds ' SPIN treats longs as SIGNED longs meaning bit 32 represents the sign "+-" ' the systemcounter thinks of the 32bits as UNsigned meaning bit 32 is ' just another bit of the number and NOT a sign "+-" ' if one or both values are negative it could happen ' that the result is negative too ' the command "||" calculates the absolute value of the SIGNED longs 'if the systemcounter has wrapped around since snapshot of 'systemcounter (value of parameter p_TimeVar), 'this method calculates the timedifference in the right way 'wrap-around example with easy numbers: counter maxvalue 1000 'p_TimeVar containing value 980 'time goes on counter wraps around from 1000 to 0 'time goes on 'RightNow containing 300. This means 20 ticks until maximum 1000 and 300 ticks 'since wrapping from 1000 to 0 in summary 320 ticks of time has gone 'this is calculated by MaxCounter - p_TimeVar + RightNow 'in numbers 1000 - 980 + 300 = 320 'the real systemcounter has 32bits max value 2^32 -1 = 4294967295 'hexadecimal $FFFFFFFF 'end of PUB elapsed_time_msec(p_TimeVar) | RightNow, ClockTicksThe repeat-loop will run pretty fast and check very often if the elapsed time is more than
a value you can adjust. If elapsed time is more than log the data else don't store data
This way you can slow down the execution of a lot of things while your main loop is still running fast
best regards
Stefan