Help with 3 position toggle

I am trying to program a toggle for our intake rollers, so I can just tap 5U, and they will stay on, rolling in, until I tap 5U again to stop them, or 5D to switch directions and roll out, and roll out until I tap 5D again to stop them.

I found a post by jpearman about toggles, and I tried to adapt it to have 3 different toggle states, but when I tested it, both toggle buttons toggled the intake on and off, except they both made the intake go the same direction.

Does anybody know what is wrong, or if there is a better way to code this?

Here is my code


int rollerMode = 0;					 // Start with the intake rollers OFF
int RBtn1Pressed = 0;					 // Intake roller IN button toggle
int RBtn2Pressed = 0;				         // Intake roller OUT button toggle

/* Intake Toggle and Controls */
		if(vexRT[Btn5U] == 1)                  // Forwards
		{
			if(! RBtn1Pressed)
			{
				rollerMode = 1 - rollerMode;	// change the toggle state
				RBtn1Pressed = 1;          // Note the button is pressed
			}
		}
		else
			RBtn1Pressed = 0;               // the button is not pressed
		if(vexRT[Btn5D] == 1)			// Reverse
		{
			if(! RBtn2Pressed)
			{
				rollerMode = -rollerMode - 1; // change the toggle state
				RBtn2Pressed = 1;             // Note the button is pressed
			}
		}
		else
			RBtn2Pressed = 0;               // the button is not pressed

		if(rollerMode >= 1)
			motor[roller] = 70;
		if(rollerMode <= -1)
			motor[roller] = -70;
		else
			motor[roller] = 0;

I’m sure you can make the above code work, but it is confusing with all the subtraction and negation. You are on the right track by separating the motor control from the button pushing by using “rollerMode”. Here is another way of tackling it.

#pragma config(Motor,  port1,           roller,        tmotorVex393_HBridge, openLoop)
//*!!Code automatically generated by 'ROBOTC' configuration wizard               !!*//

typedef enum _tRollerState {
  kStateRollerStopped = 0,
  kStateRollerIn,
  kStateRollerOut
} tRollerState;

task main()
{
    tRollerState RollerState = kStateRollerStopped;
    bool  bButtonPressed = false;
    
    while(1)
    {
      if( vexRT Btn5U ] && !bButtonPressed ) {
        bButtonPressed = true;
        if( RollerState != kStateRollerIn )
          RollerState = kStateRollerIn;
        else
          RollerState = kStateRollerStopped;
      }
      
      if( vexRT Btn5D ] && !bButtonPressed ) {
        bButtonPressed = true;
        if( RollerState != kStateRollerOut )
          RollerState = kStateRollerOut;
        else
          RollerState = kStateRollerStopped;
      }
      
      if( !vexRT Btn5U ] && !vexRT Btn5D ] )
        bButtonPressed = false;
      
      // Control motor
      switch(RollerState) {
        default:               motor[roller] =   0; break;
        case kStateRollerIn:   motor[roller] =  70; break;
        case kStateRollerOut:  motor[roller] = -70; break;
      }
      
    wait1Msec(25);
    }
}

An enum (enumerated type) is a way of creating a new type of variable that can only have specific labeled values (under the hood it really does become an integer in most cases).