Home→Forums→MonoBrick EV3 Firmware→Motor Control not behaving
- This topic has 8 replies, 4 voices, and was last updated 10 years, 8 months ago by Anders Søborg.
-
AuthorPosts
-
January 27, 2014 at 02:30 #3879
Rich ChampeauxParticipantI’m confused and a bit frustrated because the motor control is not working right.
Motor.On(speed, degrees, brake, waitforcompletion) doesn’t wait for completion regardless of what I pass for the 4th parameter. Neither does Motor.MoveTo(). They both return immediately.
Motor.On(20) returns immediately as I would expect. But MotorSync.On(20, 200) never returns, leaving the motors running forever.
I need to run my medium motor until it reaches a specific position then I need to run my larger drive motors in a full turn while reading sensors. The Motor.MoveTo() doesn’t wait until it completes and then MotorSync.On() starts immediately and never returns.
I solved the MotorSync issue by just starting each drive motor separately using leftMOtor.On(20) and rightMotor.On(-20), but that defeats the purpose of MotorSync.
I guess I’ll have to solve the medium motor not waiting for completion by going into a loop and looking for the target position.
Are these known bugs? Is it just me?
January 27, 2014 at 12:04 #3880
Rich ChampeauxParticipantSo I used Resharper to decompile MonoBrickFirmware.dll and I’ve figured out why MotorSync.On(speed, turnRatio) never returns. It’s calling the On(speed, turnRatio, degrees, brake, waitForCompletion) overload and is passing “true” for waitForCompletion. Therefore it will never return.
public void On(sbyte speed, short turnRatio)
{
this.On(speed, turnRatio, 0U, false, true);
}public void On(sbyte speed, short turnRatio, uint degrees, bool brake, bool waitForCompletion = true)
{
this.StepSync(speed, turnRatio, degrees, brake, waitForCompletion);
if (!waitForCompletion)
return;
this.WaitForMotorToStop();
}So, I can just use the 5 parameter overload instead of the two parameter one.
- This reply was modified 10 years, 11 months ago by Rich Champeaux.
January 27, 2014 at 12:26 #3882
Jacek SParticipantYou don’t need to decompile. You can grab sources from github. There is a visual studio solution with several examples.
January 27, 2014 at 12:33 #3883
Rich ChampeauxParticipantI think I’ve also figured out why the MoveTo() calls to move my medium motor return immediately. I do a MoveTo() with a speed of 100 and a position of 2160 (6 rotations). As I trace through the code, I discovered that MoveTo() calls On(speed, degrees, brake, waitForCompletion), which calculates a ramp up and ramp down step count. However, since my number of steps is so high (2160), it creates a large rampUpSteps of 324 steps.
I think the large ramp up time, coupled with a delay I noticed when starting the motors, is responsible for WaitForMotorToStop() not working correctly. WaitForMotorToStop() is implemented as follows:
protected virtual void WaitForMotorToStop()
{
Thread.Sleep(300);
do
{
Thread.Sleep(50);
}
while ((int) this.output.GetSpeed(this.PortList[0]) != 0);
}I think that the large ramp up time and the start-up delay I’ve noticed results in the speed still being 0 after the 350 ms that WaitForMotorToStop() waits before it checks the speed. Therefore it thinks the motor has already stopped when it hasn’t actually started moving.
Before looking at the source code I had tried directly using the SpeedProfileStep() method and specifying the ramp up of only 50 steps. This worked better but was still unreliable. The first time I called it, it always failed to wait. Subsequent calls would usually wait, but occasionally wouldn’t. I’m guessing that the first time, the start-up delay is longer for some reason, and for subsequent calls, it’s right on the edge of the 350 ms.
Anyhow, now that I can see what’s going on inside MonoBrickFirmware.dll, I can work around the issues I’m having. I think I’ll make my own MoveTo method that checks the tacho first to make sure the motor has started moving before it checks the speed to see if it’s stopped.
January 27, 2014 at 18:15 #3884
Rich ChampeauxParticipantJacek S,
I found the source on github. Thanks.With Resharper, all I have to do is ctrl-click on a symbol and it takes me to the definition. If the definition is from a DLL, instead of my own source, then it automatically decompiles the assembly into C# code.
It’s rather handy for debugging stuff, but the downside is that it makes up names for local variables, and you end up with a local variable named “flag1” instead of “moveBackwards”. So it’s nice to have the real source code. Also, having the solution means I can tweak the code myself when I hit a roadblock.
- This reply was modified 10 years, 11 months ago by Rich Champeaux.
January 27, 2014 at 21:22 #3888
Anders SøborgKeymasterHi all
Thanks for taking part in this discussion. The motor functions/Interface will be changed in a couple of days. Our own PID controller will be used for position movement instead of the kernel profiles that is currently used. I will post a message in this thread to let you know when it is available. Then you can grab it from github…
Anders
January 28, 2014 at 15:32 #3894
Anders SøborgKeymasterHi Rick
I completely forgot to thank you for your input and bug findings… but as I said I will have a look at motor class in the next couple of days and your findings will be usefull…
Anders
April 3, 2014 at 11:13 #4116
Stefan NilssonParticipantHi Anders, has this been solved as of current version?
April 3, 2014 at 14:38 #4117
Anders SøborgKeymasterHi Stefan
Get the latest version of GIT and use the speed and step profile… then there should be no problems. Under normal operations MoveTo and Move should work however. The PID controller there can be found in the source has not been apllied to MoveTo and Move yet, but in the meantime you can use the PID class/controller if you like…
Anders
-
AuthorPosts
You must be logged in to reply to this topic.
Follow