First call ignored in repeat loop - beginner sub-section question candidate
W9GFO
Posts: 4,010
Today I figured out some code to control the wheel motors on my Protoboard BoeBot or ProtoBot for short.
The way I have it now I start a new cog that endlessly loops through a drive routine. It is initialized with
the pulse values set to center the servos. Then, as the variables change the servos respond accordingly.
It appears to work just fine with one exception.
I expect it to start with the motors turning FWD for three seconds, slow for two seconds and then go backward for three seconds and repeat endlessly.
Instead, the motors start out slow for two seconds - not fast for three. The loop works fine when it gets started, I just don't understand why
it's missing the first one. The 3 second pause seems to be occurring because it takes three seconds after loading before the motors start turning.
The way I have it now I start a new cog that endlessly loops through a drive routine. It is initialized with
the pulse values set to center the servos. Then, as the variables change the servos respond accordingly.
It appears to work just fine with one exception.
PUB Main motors.start repeat motors.FWD(5) ' Speed = 0 to 5 waitcnt(clkfreq * 3 + cnt) motors.FWD(1) waitcnt(clkfreq * 2 + cnt) motors.BACK(5) waitcnt(clkfreq * 3+ cnt)
I expect it to start with the motors turning FWD for three seconds, slow for two seconds and then go backward for three seconds and repeat endlessly.
Instead, the motors start out slow for two seconds - not fast for three. The loop works fine when it gets started, I just don't understand why
it's missing the first one. The 3 second pause seems to be occurring because it takes three seconds after loading before the motors start turning.
Comments
The first call to motors.FWD doesn't work the way you expect because your motors cog hasn't settled down before you modify its variables.
You call motors.start which does a cognew, then returns immediately. The cognew may not even have finished loading and starting the Spin interpreter, certainly hasn't finished initializing your routine.
I suggest adding a small delay to your motors.start routine, perhaps 100-250ms
The other way to handle this sort of thing is to pass a "boolean" style variable in your method call... set your test variable to one value in your calling routine...any value will do... then change that value to some other value... which will indicate the state of your called method... again any value that makes sense to you is fine... then you just set that value at the end of your called method. This will let you wait in your main method for a value that indicates completion. You could have a series of set values to indicate various states of your called method... one for cog started... one for end of repeat loop reached, etc.
Mike's suggestion is the easiest way to fix this, but using a general approach, which minimizes and tailors the wait state is a good programming habit to acquire.
Rich