Problem!! Drive wont stop!!

I am using easyC and I have everything dl’d correctly i have refreshed the firmware multiple times on both the joystick and the cortex!!

Problem:
When i move the drive joystick forward it moves but wont stop moving even if i go backward or turn off the joystick.:eek::eek:

if you want to see my code i can post it up!

are you getting the joystick or button repeatedly or just once right away? please post your code for us to reference.

Do you have your drive control in a loop?
We cannot provide any meaningful help, however, until you post your code…

#pragma config(Motor,  port2,           leftMotor,     tmotorNormal, openLoop)
#pragma config(Motor,  port3,           rightMotor,    tmotorNormal, openLoop, reversed)
#pragma config(Motor,  port4,           rightUpMotor,  tmotorNormal, openLoop, reversed)
#pragma config(Motor,  port5,           leftUpMotor,   tmotorNormal, openLoop)
#pragma config(Motor,  port6,           right,          tmotorServoStandard, openLoop)
#pragma config(Motor,  port7,           left,         tmotorServoStandard, openLoop)


//+++++++++++++++++++++++++++++++++++++++++++++| MAIN |+++++++++++++++++++++++++++++++++++++++++++++++
task main ()
{
  //string t ="hi";
  int threshold = 10;

  while(1==1)
  {
    //clearLCDLine(0);                    // Clear line 1 (0) of the LCD
    //clearLCDLine(1);                    // Clear line 2 (1) of the LCD
    //bLCDBacklight = true;
    //displayLCDCenteredString(0,t);
    if(vexRT[Btn7D] == 1)
    {
      motor[right] = 115;
    }
    if(vexRT[Btn7L] == 1)
    {
      motor[right] = -115;
    }
    if(vexRT[Btn8D] == 1)
    {
      motor[left] = 115;
    }
    if(vexRT[Btn8L] == 1)
    {
      motor[left] = -115;
    }
    if(vexRT[Btn6U] == 1)
    {
      motor[left] = 115;
      motor[right] = -115;
    }
    if(vexRT[Btn6D] == 1)
    {
      motor[left] = -115;
      motor[right] = 115;
    }

    motor[rightUpMotor] = vexRT[Ch3];
    motor[leftUpMotor] = vexRT[Ch3];
    if( vexRT[Ch2]>threshold && vexRT[Ch1]>threshold)
    {
      motor[leftMotor]  = (vexRT[Ch2] + vexRT[Ch1]);  // (y + x)/2
      motor[rightMotor] = (vexRT[Ch2] - vexRT[Ch1]);  // (y - x)/2
    }
  }
}

It looks like RobotC, rather than EasyC…

Is the Drive Joystick using Channels 1 & 2??

The Test for the “threshold” Limit:
if( vexRT[Ch2]>threshold && vexRT[Ch1]>threshold)
prevents updates when either Channels 1 or 2 is below 10.

You have the command to start the motor, but there is no command to stop the motor when you let go of the button. You need to include motor[port??] = 0; somewhere in the code to tell the motor to turn off when you release the button.

this is correct it prevents a staticy movement

It could be a joystick calibration issue also. I had one do this a couple of weeks ago, it just got lost somehow.

Joystick calibration instruction are on page 9 of the user guide.

edit: ok I missed that you posted you code, ignore that.

threshold detection needs to use the abs value of the joystick.

if( abs(vexRT[Ch2])>threshold && abs(vexRT[Ch1])>threshold)
    {
    motor[leftMotor]  = (vexRT[Ch2] + vexRT[Ch1]);  // (y + x)/2
    motor[rightMotor] = (vexRT[Ch2] - vexRT[Ch1]);  // (y - x)/2
    }
else
    {
    motor[leftMotor]  = 0;
    motor[rightMotor] = 0;
    }

Wow, :eek: junior poster winstryg, in his 8th post, points out the correct problem:

while notable super-seniors MarkO and jpearman wander off into the weeds on inapplicable (stick vs button) tangents about thresholds and calibration.

Note to self: double check my next few posts for weed-wandering :rolleyes:

editted: Serves me right for being a smart alec, I didn’t scroll down in the code block to see the use of joysticks/thresholds

Unfortunately due to large delay between reading question, starting to answer, OP posting his code, and (then returning from meeting) hitting submit. Props to @winstryg but the threshold code was in error as well. Now back off to the weeds …

This is correct for use of the buttons, but the main issue with the joystick (what was asked) is indeed due to not taking the absolute value of the joystick value.

jpearman pointed out where this is applicable in the joystick code and supplied the solution.

The drive power never updates when the joystick is <= 10, so it will never go backwards.

WOW!! 6 Posts after mine… And it looks like I “stuck my foot in my mouth”… https://vexforum.com/images/smilies/eek.gif I am going to Break this down, so I understand it…

My Excuse is… I had 5 Bugs to Squash in a Product that needed to ship out Today, Overnight delivery… So I spent, 30-45 Seconds looking at the Code and posting, in haste an answer…

I will be forward and up front here… I now have Licenses for Three Versions of RobotC, Four Versions of EasyC, and MPLAB with C18… But know the least about implementing RobotC…

So… I was assuming that the OP, knows what their doing, and that they are truly concerned about the Motors, leftMotor and rightMotor, controlled with the Joystick, by focusing on just this code:


    if( vexRT[Ch2]>threshold && vexRT[Ch1]>threshold)
    {
      motor[leftMotor]  = (vexRT[Ch2] + vexRT[Ch1]);  // (y + x)/2
      motor[rightMotor] = (vexRT[Ch2] - vexRT[Ch1]);  // (y - x)/2
    }


Since these seem to be the Only Relevant lines related to Joysticks and Moving Forward ( and Backwards )… These didn’t make much sense to me, but I figured that this was something Special in RobotC or achieving some sort of particular Control Mode I had not seen before…

First Off… Ditto on the Kudos to winstryg, yes you need motor[port??] = 0; to stop the motors… OR… some, very close approximation
This is a Summation of what went wrong… :slight_smile:

Second, jgraber, what was your understanding ( before you Scrolled Down ) on why this was “inapplicable (stick vs button) tangents about thresholds and calibration”?? I am curious what you thought was happening… Since, I really don’t understand much about RobotC…

Now, jpearman, After you added the abs() to the Channel Return Values, then that made sense to me… You are Creating a Dead Band, of ±10 Counts, which is setting neither Forward or Backward direction… And the else, sets the Motors to OFF, as winstryg pointed out was needed to Stop the Motors…
Also, I understand that Read Post, GoTo Meeting, Post Response, Retract Mistakes, Apologize for Haste, Fall on Sword in Shame, while Working…

And last in the postings ( at this time ), dontworryaboutit, * summarizes* what I was focusing on in connor776’s Code, “The drive power never updates when the joystick is <= 10, so it will never go backwards.”
Because if there was no Threshold Check, the Two Joystick Axises, could achieve a result close to ( or exactly ) Zero, and stop the Motors…

So, Now… I have one Final Question…

The Comments show, " // (y + x)/2 and // (y - x)/2 ". I see the “(y + x)” and “(y - x)”, but where does the “/2” happen??? Just for my own education… :wink:

The ROBOTC example code, and also many other examples, demonstrate arcade drive by using (as Pseudocode)

leftMotor = (vertical_joystick_value + horizontal_joystick_value) / 2;
rightMotor = (vertical_joystick_value - horizontal_joystick_value) / 2;

Here, for example, is the actual code from their natural language arcade drive function
(and I really don’t like their threshold test)

//-----------------------------------------| ArcadeControl |------------------------------------------
#ifndef _ARCADECONTROL_H_GUARD
#define _ARCADECONTROL_H_GUARD

void arcadeControl(TVexJoysticks verticalJoystick = Ch2, TVexJoysticks horizontalJoystick = Ch1, short threshold = 10)
{
	if( (verticalJoystick <= abs(threshold)  &&  verticalJoystick >= (abs(threshold) * -1))  &&
	    (horizontalJoystick <= abs(threshold)  &&  horizontalJoystick >= (abs(threshold) * -1)))
	{
		motor[port2] = 0;
		motor[port3] = 0;
	}
	else
	{	
		motor[port3] = (vexRT[verticalJoystick] + vexRT[horizontalJoystick])/2;  // (y + x)/2
		motor[port2] = (vexRT[verticalJoystick] - vexRT[horizontalJoystick])/2;  // (y - x)/2
	}
}

#endif
//----------------------------------------------------------------------------------------------------

Now this works just fine, except for the fact that forward motion is limited to half speed as (127 + 0) / 2 = 63.5 (where the full speed of the motor is defined as being 127), so many roboteers modify the code to remove the “/2” but forget to update the comment. The downside to this is values may exceed the maximum that the motors can handle. Luckily ROBOTC limits motor control values for the user although I still prefer to add explicit clipping.

Mark, I’m sure you already knew this but it’s worth explaining for others that may be wondering.

Right… I’m a Tank Drive Man, myself, but I should recognize an Arcade Drive Algorithm…

I would think a High Order Truncation would occur, ( An IBM’ism referring to the Most Significant Bits being Lost Learned as the result of a misspent youth, learning Business Programming Languages… ] ), so Over-driving the Motors would be of Minimal concern…

What I see as an Issue, is making turns Slow, because of the Minimal Difference in Motor Speeds… Or am I thinking this Through Incorrectly??

Comparing the Above Code to your Threshold Code, Below:



<< SNIP >>

if( abs(vexRT[Ch2])>threshold && abs(vexRT[Ch1])>threshold)

<< SNIP >>


Your Code will Execute in a lot less time, with Two Less calls to abs(), Two Multiples by -1 and Two additional Logical Tests by AND ( && ). I see that as a Win, All the Way Around… :wink:

I was not quite Thinking it Through… Maybe I can claim, I was in a hurry, Officer… I didn’t see the Ramification… :wink:

Without scrolling, the initial RobotC code I saw showed that all
the VexRT references are to digital Buttons UP/DN, (not sticks),
and all the motor speeds were +115 or -115.

With scrolling, there is an arcade drive code that sets the same motors,
I may not have even noticed the threshold problem if I had seen the code.

I put my own foot-in-mouth with my snarky comment, by not reading the full post.

Speaking of calibration/threshold/deadband,
I’ve previously posted this workaround to use a button to auto-center the joysticks values:

Its not as good as full calibration, but its handy to easily stop annoying motor hum or wheel creep.

Actually not the same motors. This clearly demonstrates the importance of picking good variable names :wink:

Cheers,

  • Dean

Jeez, Right vs RightMotor;
yet another pointer about ‘Drive’ with arcade code missed by me.
I better slow down.

I did Scroll, and Ignored the Buttons, because the OP mentioned Joysticks…

I noticed the Threshold for Channels 1 and 2, but did not know what the Threshold was limiting, so I did not notice a problem with it either… ( Score: -1 ) :wink:

Well, it can happen to anyone… :wink: I seriously only gave the whole code a 30-45 Second look over… I had an extremely large chance of putting my own foot-in-mouth… In retrospect, I look competent, but Not Expert level.

Nice Work… With an explanation and the Note to Use a Spread Sheet and Plot it for our Visual Learners… I might add a little to it… Maybe make it a Library… Include a Picture of the Graph Plot…

Thanks for the After Action Review ( AAR ). I am still getting use to some of RobotC’s way of doing things…

I think this “sums it up”…


#pragma config(Motor,  port2,           leftMotor,     tmotorNormal, openLoop)
#pragma config(Motor,  port3,           rightMotor,    tmotorNormal, openLoop, reversed)
#pragma config(Motor,  port4,           rightUpMotor,  tmotorNormal, openLoop, reversed)
#pragma config(Motor,  port5,           leftUpMotor,   tmotorNormal, openLoop)
#pragma config(Motor,  port6,           right,          tmotorServoStandard, openLoop)
#pragma config(Motor,  port7,           left,         tmotorServoStandard, openLoop)


I skipped on the the Joystick Part… And “assumed” the Motor Names were correct…

Lot’s of fun on this thread while I was tied up in meetings all morning.

One further point I don’t think anyone has noticed (or perhaps they have) is that “right” and “left” are not motors but servos, thats presumably why 0 is never sent to them, they are directed to one end or the other.