Need help programming IME's with an X-drive.

I am trying to use the Integrated Motor Encoders to program my autonomous since it requires exact movements. I have looked at all the threads about programming these, and the sample programs, and I have got an idea of how to program them, but the encoders still aren’t working. I don’t understand exactly how to program them. I have somewhat of a program but the encoders are obviously not working in the program since when I test it, it tends to move to the right. I don’t know exactly what in the program is throwing it off. I also have the “code chooser” programmed within this for the LCD display, and I don’t know if that has anything to do with the encoders not working. Also my chassis is an x-drive. (I don’t know if that will change anything or not.) Can anyone help?

(In the code, the part of the program that ** hasn’t** been commented out is the portion that I have tested and hasn’t worked.)

Thanks in advance!
robotc encoder.c (19.7 KB)

Have you looked in the debugger to be sure the encoders are all reading the same? If your weight is off, one wheel could be spinning.

You are waiting until all the motors have gone a specific distance per step.

You also don’t tell your motors to stop while clamping. It will keep moving unless you tell the motors to go to 0. You reset the encoder but not stopped the motor.

		wait1Msec(100);
		while (nMotorEncoder[BL] <146.3458 && nMotorEncoder[FR] <146.3458 && nMotorEncoder[BR] <146.3458 && nMotorEncoder[FL] <146.3458)
		{
			motor(BL) = 127;//motor will move
			motor(FR) = 127;//motor will move
			motor(BR) = 0;//motor will move
			motor(FL) = 0;//motor will move
			//move forwards
		}

		wait1Msec(100);
		nMotorEncoder[BL] = 0;//clear
		nMotorEncoder[FR] = 0;//clear
		nMotorEncoder[BR] = 0;//clear
		nMotorEncoder[FL] = 0;//clear


**  // you should stop the motors here.....
**

		//encoder set zero
		wait1Msec(100);
		motor(CLMP) = 127;//clamp will close
		wait1Msec(1200);//
		motor(CLMP) = 20;//motor will not move
		wait1Msec(50);
		//close the clamp and keep constant pressure on skyirse

Oh boy! I’d suggest using PID loops on your drive, the way you have your drive set up currently, is highly dependent on battery charge. In addition, it’s a great thing to learn if you’re interested in hardware programming when older.

Yes, I have looked in the debugger window to make sure that everything is counting properly. The values are relatively close when I give it a push on the ground. Also, I forgot to mention that the only motors that I am using encoders on are the “BL”, “FR” “BR”, “FL”.

Also what is PID loops?

How would I then program this so that it doesn’t depend on battery charge?

(Also BTW that “Clamp” doesn’t stop for a reason. After that piece of coding it keeps a small amount of pressure on it, until I need it to let go.)

You said, “You are waiting until all the motors have gone a specific distance per step.” Is this not right, and how would I fix that?

Thanks.

If You search PID Loop on the forums, you will find tons of answers to your very question :slight_smile: But, what it does is more based on sensor feedback, so you will ALWAYS reach a target. My top 2 recommendations for PID Loops to begin with, are either the one in BNSLib, or writing one yourself, which may seem daunting, but George wrote a very handy guide as to how to write PID! WIth pseudocode and all!

What is BNSlib?

Linky: https://vexforum.com/t/introducing-bnslib-an-advanced-programming-library-from-team-bns/28315/1&highlight=BNSLib

Many people will average together the like distances of the encoders. It helps somewhat but still is off with a faulty encoder. But you say yours is OK.


while (((nMotorEncoder[BL] + nMotorEncoder[FR])/2 <146) && /* you do the rest */) 

Averaging between the like wheels is another way. Also, these encoders are integers so no need for the decimals as they will be truncated anyway.

My question to harrio now is how do you use only just two encoders on an x-drive if you need to move in all sorts of directions where in some instances, the other two wheels without encoders are the only two wheels moving, or one has an encoder, and the other not? Also this code below that I found on this forum is what I need to make my robot go straight, but how do I incorporate this code into my code which has specific tasks moving around the field?

Here is a portion of my code:

task autonomous()// task autonomous
{
//------------- Beginning of Robot Movement Code ---------------
//Clear LCD
clearLCDLine(0);
clearLCDLine(1);
//Switch Case that actually runs the user choice
switch(count){
case 0:
//If count = 0, run the code correspoinding with choice 1
displayLCDCenteredString(0, “AutoSkyRed”);
displayLCDCenteredString(1, “is running!”);
wait1Msec(1000); // Robot waits for 2000 milliseconds

	nMotorEncoder[BL] = 0;//clear
	nMotorEncoder[FR] = 0;//clear
	nMotorEncoder[BR] = 0;//clear
	nMotorEncoder[FL] = 0;//clear
	//encoder set zero
	wait1Msec(100);
	while (nMotorEncoder[BL] >-83.6266 && nMotorEncoder[FR] >-83.6266 && nMotorEncoder[BR] >-83.6266 && nMotorEncoder[FL] >-83.6266)
	{
		motor(BL) = -127;//motor will move
		motor(FR) = -127;//motor will move
		motor(BR) = -127;//motor will move
		motor(FL) = -127;//motor will move
		//move backwards
	}

	nMotorEncoder[BL] = 0;//clear
	nMotorEncoder[FR] = 0;//clear
	nMotorEncoder[BR] = 0;//clear
	nMotorEncoder[FL] = 0;//clear
	//encoder set zero
	wait1Msec(100);
	while (nMotorEncoder[BL] <83.6266 && nMotorEncoder[FR] <83.6266 && nMotorEncoder[BR] <83.6266 && nMotorEncoder[FL] <83.6266)
	{
		motor(BL) = 127;//motor will move
		motor(FR) = 127;//motor will move
		motor(BR) = 127;//motor will move
		motor(FL) = 127;//motor will move
		//move forwards
	}
	nMotorEncoder[BL] = 0;//clear
	nMotorEncoder[FR] = 0;//clear
	nMotorEncoder[BR] = 0;//clear
	nMotorEncoder[FL] = 0;//clear
	//encoder set zero
	wait1Msec(100);

Would this be the correct way to program it?

nMotorEncoder[BL] = 0;//clear
	nMotorEncoder[FR] = 0;//clear
	nMotorEncoder[BR] = 0;//clear
	nMotorEncoder[FL] = 0;//clear
	//encoder set zero
	wait1Msec(100);
	while (nMotorEncoder[BL] >-84 && nMotorEncoder[FR] >-84 && nMotorEncoder[BR] >-84 && nMotorEncoder[FL] >-84)//while the encoders are all less than -84 counts
	{
		{
			if(nMotorEncoder[BL] < nMotorEncoder[FR] && nMotorEncoder[BR] && nMotorEncoder[FL])//if the back left  motor counts are greater than the rest
			{
				motor(BL) = -127/2;//motor will move slower
				motor(FR) = -127;//motor will move
				motor(BR) = -127;//motor will move
				motor(FL) = -127;//motor will move
			}
			else if (nMotorEncoder[FR] < nMotorEncoder[BL] && nMotorEncoder[BR] && nMotorEncoder[FL])//if the front right  motor counts are greater than the rest
			{
				motor(BL) = -127;//motor will move
				motor(FR) = -127/2;//motor will move slower
				motor(BR) = -127;//motor will move
				motor(FL) = -127;//motor will move
			}
			else if (nMotorEncoder[BR] < nMotorEncoder[BL] && nMotorEncoder[FR] && nMotorEncoder[FL])//if the back right  motor counts are greater than the rest
			{
				motor(BL) = -127;//motor will move
				motor(FR) = -127;//motor will move
				motor(BR) = -127/2;//motor will move slower
				motor(FL) = -127;//motor will move
			}		
			else if (nMotorEncoder[FL] < nMotorEncoder[BL] && nMotorEncoder[FR] && nMotorEncoder[BR])//if the front left  motor counts are greater than the rest
			{
				motor(BL) = -127;//motor will move
				motor(FR) = -127;//motor will move
				motor(BR) = -127;//motor will move
				motor(FL) = -127/2;//motor will move slower
			}	
			else if (nMotorEncoder[FL] == nMotorEncoder[BL] == nMotorEncoder[FR] == nMotorEncoder[BR])//if all counts are equal
			{
				motor(BL) = -127;//motor will move
				motor(FR) = -127;//motor will move
				motor(BR) = -127;//motor will move
				motor(FL) = -127;//motor will move
			}	
		}//move backwards	
	}

Here is the file of the code posted above
robotc encoder program.c (3.18 KB)

Alright, I seem to have got the encoder program working now with the format of programming shown in my above posts. But I do have another problem now. There is one part of my code which continues going on while everything else continues on. Here is that code below. Can anyone help? Thanks again for everyone’s help!! I appreciate it.

wait1Msec(100);
nMotorEncoder[BL] = 0;//clear
nMotorEncoder[FR] = 0;//clear
nMotorEncoder[BR] = 0;//clear
nMotorEncoder[FL] = 0;//clear
//encoder set zero

	while (nMotorEncoder[BL] <146 && nMotorEncoder[FR] <146 && nMotorEncoder[BR] >-150 && nMotorEncoder[FL] >-150)//while the encoders are all less than 146 counts
	{
		if(nMotorEncoder[BL] > nMotorEncoder[FR])//if the back left  motor counts are greater than the rest
		{
			motor(BL) = 127/2;//motor will move slower
			motor(FR) = 127;//motor will move
			motor(BR) = 0;
			motor(FL) = 0;				
		}
		else if (nMotorEncoder[FR] > nMotorEncoder[BL] && nMotorEncoder[BR] >-150 && nMotorEncoder[FL] >-150)//if the front right  motor counts are greater than the rest
		{
			motor(BL) = 127;//motor will move
			motor(FR) = 127/2;//motor will move slower
			motor(BR) = 0;
			motor(FL) = 0;				
		}
		else if (nMotorEncoder[FR] == nMotorEncoder[BL] && nMotorEncoder[BR] >-150 && nMotorEncoder[FL] >-150)//if all counts are equal
		{
			motor(BL) = 127;//motor will move
			motor(FR) = 127;//motor will move slower
			motor(BR) = 0;
			motor(FL) = 0;
		}//move north west	
	}