Counting Spin-up discs with an optical sensor

I’ve been trying to count the number of discs that come through the intake system of our robot but no matter what command I use (gestureUp, objectDetected, objectLost) it works but it always adds 94 discs to the count instead of just one. I’ve been trying to figure out what’s going on for the last couple of days but I can’t figure it out. Any help would be greatly appreciated.

int Discs = 0;
void Counter() {
Discs = Discs + 1;
Controller1.Screen.clearLine(3);
Controller1.Screen.print(Discs);
}
void usercontrol(void) {
ColorSense1.objectDetected(Counter);
}

First time it senses the disk the controller outputs 94, then 188, then 282 and so on and so forth.

Need a lot more context to your code, as lots of things could be influencing it.

In particular, are you waiting for a disc to no longer be detected before you enable counting of another one? My guess is that you’re looping multiple times in extremely quick succession, and so you’re getting the same disc detected multiple times.

Post more of your code and that should certainly help pinpoint things.

2 Likes

It might be that. The other parts of the code are just auto which doesn’t do anything currently and some of the other subsystems in our robot. What I put there is everything that has to do with the color sensor. You are probably right that it is looping multiple times but what doesn’t make sense to me is that it comes out as 94 each time.

Here is all of my code

#include "vex.h"

using namespace vex;

// A global instance of competition
competition Competition;

// define your global instances of motors and other devices here
int autonType = -1;
int Discs = 0;
void Counter() {
  Discs = Discs + 1;
  Controller1.Screen.clearLine(3);
  Controller1.Screen.print(Discs);
}
/*---------------------------------------------------------------------------*/
/*                          Pre-Autonomous Functions                         */
/*                                                                           */
/*  You may want to perform some actions before the competition starts.      */
/*  Do them in the following function.  You must return from this function   */
/*  or the autonomous and usercontrol tasks will not be started.  This       */
/*  function is only called once after the V5 has been powered on and        */
/*  not every time that the robot is disabled.                               */
/*---------------------------------------------------------------------------*/

void pre_auton(void) {
  // Initializing Robot Configuration. DO NOT REMOVE!
  vexcodeInit();
  bool autonSelecterStatus = false;
  ColorSense1.setLight(ledState::on);
  Brain.Screen.printAt(1, 40, "Auton");
  while (true) {
    if (autonSelecter.value() > 0 && autonSelecterStatus == false) {
      autonSelecterStatus = true;
    } else if (autonSelecter.value() == 0 && autonSelecterStatus == true) {
      Brain.Screen.clearScreen();
      if (autonType == 0 || autonType == -1) {
        autonType = 1;
        Brain.Screen.printAt(1, 40, "1st Auton");
      }else if (autonType == 1) {
        autonType = 2;
        Brain.Screen.printAt(1, 40, "2nd Auton");
      }else if (autonType == 2) {
        autonType = 3;
        Brain.Screen.printAt(1, 40, "3rd Auton");
      }else if (autonType == 3) {
        autonType = 4;
        Brain.Screen.printAt(1, 40, "4th Auton");
      }else if (autonType == 4) {
        autonType = 5;
        Brain.Screen.printAt(1, 40, "5th Auton");
      }else if (autonType == 5) {
        autonType = 0;
        Brain.Screen.printAt(1, 40, "Do Nothing");
      }
      Controller1.Screen.print(autonType);
      autonSelecterStatus = false;
    }
    wait (20, msec);
  }


  // All activities that occur before the competition starts
  // Example: clearing encoders, setting servo positions, ...
}

/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              Autonomous Task                              */
/*                                                                           */
/*  This task is used to control your robot during the autonomous phase of   */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void autonomous(void) {
/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if(autonType == 0) {
    wait(10, msec);
  }
  if (autonType == 1) {
    L1.spin(fwd, 10, percent);
    R1.spin(fwd, 10, percent);
    L2.spin(fwd, 10, percent);
    R2.spin(fwd, 10, percent);
  wait(5, sec);
    L1.stop(brake);
    L2.stop(brake);
    R1.stop(brake);
    R2.stop(brake);
  }

/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 2) {
    wait(10, msec);
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 3) {
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 4) {
    
  }



/*---------------------------------------------------------------------------*/
/*                          Fake Auto if we need it                          */
/*---------------------------------------------------------------------------*/

  if (autonType == 5) {
    
  }
}

/*---------------------------------------------------------------------------*/
/*                              End of Auton's                               */
/*---------------------------------------------------------------------------*/



/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              User Control Task                            */
/*                                                                           */
/*  This task is used to control your robot during the user control phase of */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void usercontrol(void) {
  bool brakeSystem = false;
  bool shootSystem = false;
  bool intakeSystem = false;
  double intakeRotate = (200 * 0.01666666666 * 3);
  int timerSet = 0;
  ColorSense1.setLight(ledState::on);
  ColorSense1.gestureEnable();
  FWSM1.setRotation(0, rev);
  FWSM2.setRotation(0, rev);
  Intake.setRotation(0, rev);
  Brake.setRotation(0, rev);
  while (1) {
      //Driver Controls for Mechanum Wheels.
      if(Controller1.Axis3.position() > -15 && Controller1.Axis3.position() < 15 && Controller1.Axis1.position() > -15 && Controller1.Axis1.position() < 15 && Controller1.Axis4.position() > -15 && Controller1.Axis4.position() < 15) {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.stop(brake);
      L2.stop(brake);
      R1.stop(brake);
      R2.stop(brake);
      Brain.Screen.printAt(1, 200, "Not Moving");
      }else {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      R1.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      L2.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      R2.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      Brain.Screen.printAt(1, 200, "Moving");
      }
  

      //Shooting system
      if(Controller1.ButtonR1.pressing() && shootSystem == false) {
      shootSystem = true;
      } else if (!Controller1.ButtonR1.pressing() && shootSystem == true) {
        if(FWSM1.rotation(rev) < .5 && FWSM2.rotation(rev) < .5) {
        FWSM1.spin(fwd, 100, pct);
        FWSM2.spin(reverse, 100, pct);
        Brain.Screen.printAt(1, 70, "Shooting");
        }else {
        FWSM1.stop(brake);
        FWSM2.stop(brake);
        FWSM1.setRotation(0, rev);
        FWSM2.setRotation(0, rev);
        Brain.Screen.clearLine(3);
        Brain.Screen.clearLine(4);
        }
        shootSystem = false;
      }

      //Intake System  
      ColorSense1.setLight(ledState::on); 

      if (ColorSense1.isNearObject() && ColorSense1.color() == yellow ) {
        timerSet = 3;
      }
      
      if (timerSet != 0) {
        while(timerSet != 0) {
          this_thread::sleep_for(1000);
          Brain.Screen.clearLine(5);
          Brain.Screen.clearLine(6);
          Brain.Screen.printAt(1, 100, "Out-taking");
          Intake.setTimeout(300, msec);
          Intake.startRotateFor(reverse, intakeRotate, rev, 200, rpm);
          this_thread::sleep_for(3000);
          timerSet = timerSet - 3;
        } 
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Intake.setRotation(0, rev);
      }
      
      if (Controller1.ButtonR2.pressing() && intakeSystem == false) {
      intakeSystem = true;
      } else if (!Controller1.ButtonR2.pressing() && intakeSystem == true) {
        if (Intake.rotation(rev) < .5) {
        Intake.spin(fwd, 100, pct);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Brain.Screen.printAt(1, 100, "Intaking");  
        } else {
        Intake.stop(brake);
        Intake.setRotation(0, rev);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        }
        intakeSystem = false;
      }

ColorSense1.objectDetected(Counter);


      //Brake System
      if(Controller1.ButtonL2.pressing() == true && brakeSystem == false) {
        brakeSystem = true;
      }
      else if (!Controller1.ButtonL2.pressing() && brakeSystem == true) {
        if(Brake.rotation(rev) < .3 && Brake.rotation(rev) > -100) {
          Brain.Screen.clearLine(7);  
          Brain.Screen.printAt(1, 140, "Brake Down");
          Brake.startRotateFor(fwd, 1.2, rev, 200, rpm);
        }else {
          Brain.Screen.clearLine(7);
          Brain.Screen.printAt(1, 140, "Brake Up");
          Brake.startRotateFor(reverse, 1.2, rev, 200, rpm);
          Brake.setRotation(0, rev);
        }
        brakeSystem = false;
      }


    wait(20, msec); // Sleep the task for a short amount of time to
                    // prevent wasted resources.
  }
}

//
// Main will set up the competition functions and callbacks.
//
int main() {
  // Set up callbacks for autonomous and driver control periods.
  Competition.autonomous(autonomous);
  Competition.drivercontrol(usercontrol);

  // Run the pre-autonomous function.
  pre_auton();

  // Prevent main from exiting with an infinite loop.
  while (true) {
    wait(100, msec);
  }
}

Did you register the event handler inside a while loop ?
Edit: looks like you did, so you exhausted number of available event slots and all 94 of them fire each time.

6 Likes

Sorry but I am fairly new at this. What is the event handler inside the while loop

This line of code is registering the event handler.

ColorSense1.objectDetected(Counter);

What that code says is “register the function “Counter” to be called every time the ColorSense1 detects an object”, it should be called once and once only, preferably near the beginning of main. By repeatedly calling it inside the while loop you register the function “Counter” many times and the function will be called each time the object is detected.
The V5 has a limit of 100 events, but some events will be automatically added by the system code when your program starts. When the 100 event limit is reached any further event registration calls will be ignored, that’s why you get 94 increments on the Disc variable.

7 Likes

Ok i understand. Thank you for the explanation. However, I moved the command to outside of the loop and it still doesn’t work. Do I need to add some sort of wait or sleep command in the “Counter” function so it only loops once?
I also looked in some other forums and I’m pretty sure I should have a sleep statement in my loop but I tried that too at the end of the function after the Controller1.Screen.print(Discs) line and it still doesn’t work.

This is my code so far

#include "vex.h"

using namespace vex;

// A global instance of competition
competition Competition;

// define your global instances of motors and other devices here
int autonType = -1;
int Discs = 0;
void Counter() {
  Discs = Discs + 1;
  Controller1.Screen.clearLine(3);
  Controller1.Screen.print(Discs);
  vex::task::sleep(1000);
}
/*---------------------------------------------------------------------------*/
/*                          Pre-Autonomous Functions                         */
/*                                                                           */
/*  You may want to perform some actions before the competition starts.      */
/*  Do them in the following function.  You must return from this function   */
/*  or the autonomous and usercontrol tasks will not be started.  This       */
/*  function is only called once after the V5 has been powered on and        */
/*  not every time that the robot is disabled.                               */
/*---------------------------------------------------------------------------*/

void pre_auton(void) {
  // Initializing Robot Configuration. DO NOT REMOVE!
  vexcodeInit();
  bool autonSelecterStatus = false;
  ColorSense1.setLight(ledState::on);
  Brain.Screen.printAt(1, 40, "Auton");
  while (true) {
    if (autonSelecter.value() > 0 && autonSelecterStatus == false) {
      autonSelecterStatus = true;
    } else if (autonSelecter.value() == 0 && autonSelecterStatus == true) {
      Brain.Screen.clearScreen();
      if (autonType == 0 || autonType == -1) {
        autonType = 1;
        Brain.Screen.printAt(1, 40, "1st Auton");
      }else if (autonType == 1) {
        autonType = 2;
        Brain.Screen.printAt(1, 40, "2nd Auton");
      }else if (autonType == 2) {
        autonType = 3;
        Brain.Screen.printAt(1, 40, "3rd Auton");
      }else if (autonType == 3) {
        autonType = 4;
        Brain.Screen.printAt(1, 40, "4th Auton");
      }else if (autonType == 4) {
        autonType = 5;
        Brain.Screen.printAt(1, 40, "5th Auton");
      }else if (autonType == 5) {
        autonType = 0;
        Brain.Screen.printAt(1, 40, "Do Nothing");
      }
      Controller1.Screen.print(autonType);
      autonSelecterStatus = false;
    }
    wait (20, msec);
  }


  // All activities that occur before the competition starts
  // Example: clearing encoders, setting servo positions, ...
}

/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              Autonomous Task                              */
/*                                                                           */
/*  This task is used to control your robot during the autonomous phase of   */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void autonomous(void) {
/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if(autonType == 0) {
    wait(10, msec);
  }
  if (autonType == 1) {
    L1.spin(fwd, 10, percent);
    R1.spin(fwd, 10, percent);
    L2.spin(fwd, 10, percent);
    R2.spin(fwd, 10, percent);
  wait(5, sec);
    L1.stop(brake);
    L2.stop(brake);
    R1.stop(brake);
    R2.stop(brake);
  }

/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 2) {
    wait(10, msec);
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 3) {
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 4) {
    
  }



/*---------------------------------------------------------------------------*/
/*                          Fake Auto if we need it                          */
/*---------------------------------------------------------------------------*/

  if (autonType == 5) {
    
  }
}

/*---------------------------------------------------------------------------*/
/*                              End of Auton's                               */
/*---------------------------------------------------------------------------*/



/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              User Control Task                            */
/*                                                                           */
/*  This task is used to control your robot during the user control phase of */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void usercontrol(void) {
  bool brakeSystem = false;
  bool shootSystem = false;
  bool intakeSystem = false;
  double intakeRotate = (200 * 0.01666666666 * 3);
  int timerSet = 0;
  ColorSense1.setLight(ledState::on);

  ColorSense1.objectDetected(Counter);

  FWSM1.setRotation(0, rev);
  FWSM2.setRotation(0, rev);
  Intake.setRotation(0, rev);
  Brake.setRotation(0, rev);
  while (1) {
      //Driver Controls for Mechanum Wheels.
      if(Controller1.Axis3.position() > -15 && Controller1.Axis3.position() < 15 && Controller1.Axis1.position() > -15 && Controller1.Axis1.position() < 15 && Controller1.Axis4.position() > -15 && Controller1.Axis4.position() < 15) {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.stop(brake);
      L2.stop(brake);
      R1.stop(brake);
      R2.stop(brake);
      Brain.Screen.printAt(1, 200, "Not Moving");
      }else {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      R1.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      L2.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      R2.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      Brain.Screen.printAt(1, 200, "Moving");
      }
  

      //Shooting system
      if(Controller1.ButtonR1.pressing() && shootSystem == false) {
      shootSystem = true;
      } else if (!Controller1.ButtonR1.pressing() && shootSystem == true) {
        if(FWSM1.rotation(rev) < .5 && FWSM2.rotation(rev) < .5) {
        FWSM1.spin(fwd, 100, pct);
        FWSM2.spin(reverse, 100, pct);
        Brain.Screen.printAt(1, 70, "Shooting");
        }else {
        FWSM1.stop(brake);
        FWSM2.stop(brake);
        FWSM1.setRotation(0, rev);
        FWSM2.setRotation(0, rev);
        Brain.Screen.clearLine(3);
        Brain.Screen.clearLine(4);
        }
        shootSystem = false;
      }

      //Intake System  
      ColorSense1.setLight(ledState::on); 
/*
      if (ColorSense1.isNearObject() && ColorSense1.color() == yellow ) {
        timerSet = 3;
      }
      
      if (timerSet != 0) {
        while(timerSet != 0) {
          this_thread::sleep_for(1000);
          Brain.Screen.clearLine(5);
          Brain.Screen.clearLine(6);
          Brain.Screen.printAt(1, 100, "Out-taking");
          Intake.setTimeout(300, msec);
          Intake.startRotateFor(reverse, intakeRotate, rev, 200, rpm);
          this_thread::sleep_for(3000);
          timerSet = timerSet - 3;
        } 
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Intake.setRotation(0, rev);
      }
      
      if (Controller1.ButtonR2.pressing() && intakeSystem == false) {
      intakeSystem = true;
      } else if (!Controller1.ButtonR2.pressing() && intakeSystem == true) {
        if (Intake.rotation(rev) < .5) {
        Intake.spin(fwd, 100, pct);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Brain.Screen.printAt(1, 100, "Intaking");  
        } else {
        Intake.stop(brake);
        Intake.setRotation(0, rev);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        }
        intakeSystem = false;
      } */

      


      //Brake System
      if(Controller1.ButtonL2.pressing() == true && brakeSystem == false) {
        brakeSystem = true;
      }
      else if (!Controller1.ButtonL2.pressing() && brakeSystem == true) {
        if(Brake.rotation(rev) < .3 && Brake.rotation(rev) > -100) {
          Brain.Screen.clearLine(7);  
          Brain.Screen.printAt(1, 140, "Brake Down");
          Brake.startRotateFor(fwd, 1.2, rev, 200, rpm);
        }else {
          Brain.Screen.clearLine(7);
          Brain.Screen.printAt(1, 140, "Brake Up");
          Brake.startRotateFor(reverse, 1.2, rev, 200, rpm);
          Brake.setRotation(0, rev);
        }
        brakeSystem = false;
      }


    wait(20, msec); // Sleep the task for a short amount of time to
                    // prevent wasted resources.
  }
}

//
// Main will set up the competition functions and callbacks.
//
int main() {
  // Set up callbacks for autonomous and driver control periods.
  Competition.autonomous(autonomous);
  Competition.drivercontrol(usercontrol);

  // Run the pre-autonomous function.
  pre_auton();

  // Prevent main from exiting with an infinite loop.
  while (true) {
    wait(100, msec);
  }
}

Event handlers must be registered at the beginning of int main(). If you register them anywhere else, they might be registered multiple times, for example, 94. There are 94 copies of ColorSense1.objectDetected(Counter);, and every time an object is detected, all of them call Counter(), which makes Discs += 1… 94 times in a row.

Move ColorSense1.objectDetected(Counter); to here:

5 Likes

Thank you so much. Its working perfect and I really appreciate the support

Another problem I’m having is that the this_thread::sleep_for(1000); stops all code currently running when it should only stop the code in the while(timerSet != 0) loop.

Current Code

#include "vex.h"

using namespace vex;

// A global instance of competition
competition Competition;

// define your global instances of motors and other devices here
int autonType = -1;
int Discs = 0;
void CounterUP() {
  Discs = Discs + 1;
  Controller1.Screen.clearLine(3);
  Controller1.Screen.print(Discs);
  vex::task::sleep(1000);
}
void CounterDOWN() {
  Discs = Discs - 1;
  Controller1.Screen.clearLine(3);
  Controller1.Screen.print(Discs);
  vex::task::sleep(1000);
}
/*---------------------------------------------------------------------------*/
/*                          Pre-Autonomous Functions                         */
/*                                                                           */
/*  You may want to perform some actions before the competition starts.      */
/*  Do them in the following function.  You must return from this function   */
/*  or the autonomous and usercontrol tasks will not be started.  This       */
/*  function is only called once after the V5 has been powered on and        */
/*  not every time that the robot is disabled.                               */
/*---------------------------------------------------------------------------*/

void pre_auton(void) {
  // Initializing Robot Configuration. DO NOT REMOVE!
  vexcodeInit();
  bool autonSelecterStatus = false;
  ColorSense1.setLight(ledState::on);
  ColorSense1.gestureEnable();
  Brain.Screen.printAt(1, 40, "Auton");
  while (true) {
    if (autonSelecter.value() > 0 && autonSelecterStatus == false) {
      autonSelecterStatus = true;
    } else if (autonSelecter.value() == 0 && autonSelecterStatus == true) {
      Brain.Screen.clearScreen();
      if (autonType == 0 || autonType == -1) {
        autonType = 1;
        Brain.Screen.printAt(1, 40, "1st Auton");
      }else if (autonType == 1) {
        autonType = 2;
        Brain.Screen.printAt(1, 40, "2nd Auton");
      }else if (autonType == 2) {
        autonType = 3;
        Brain.Screen.printAt(1, 40, "3rd Auton");
      }else if (autonType == 3) {
        autonType = 4;
        Brain.Screen.printAt(1, 40, "4th Auton");
      }else if (autonType == 4) {
        autonType = 5;
        Brain.Screen.printAt(1, 40, "5th Auton");
      }else if (autonType == 5) {
        autonType = 0;
        Brain.Screen.printAt(1, 40, "Do Nothing");
      }
      Controller1.Screen.print(autonType);
      autonSelecterStatus = false;
    }
    wait (20, msec);
  }


  // All activities that occur before the competition starts
  // Example: clearing encoders, setting servo positions, ...
}

/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              Autonomous Task                              */
/*                                                                           */
/*  This task is used to control your robot during the autonomous phase of   */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void autonomous(void) {
/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if(autonType == 0) {
    wait(10, msec);
  }
  if (autonType == 1) {
    L1.spin(fwd, 10, percent);
    R1.spin(fwd, 10, percent);
    L2.spin(fwd, 10, percent);
    R2.spin(fwd, 10, percent);
  wait(5, sec);
    L1.stop(brake);
    L2.stop(brake);
    R1.stop(brake);
    R2.stop(brake);
  }

/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 2) {
    wait(10, msec);
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 3) {
    
  }


/*---------------------------------------------------------------------------*/
/*                              Description                                  */
/*---------------------------------------------------------------------------*/

  if (autonType == 4) {
    
  }



/*---------------------------------------------------------------------------*/
/*                          Fake Auto if we need it                          */
/*---------------------------------------------------------------------------*/

  if (autonType == 5) {
    
  }
}

/*---------------------------------------------------------------------------*/
/*                              End of Auton's                               */
/*---------------------------------------------------------------------------*/



/*---------------------------------------------------------------------------*/
/*                                                                           */
/*                              User Control Task                            */
/*                                                                           */
/*  This task is used to control your robot during the user control phase of */
/*  a VEX Competition.                                                       */
/*                                                                           */
/*  You must modify the code to add your own robot specific commands here.   */
/*---------------------------------------------------------------------------*/

void usercontrol(void) {
  bool brakeSystem = false;
  bool shootSystem = false;
  bool intakeSystem = false;
  double intakeRotate = (200 * 0.01666666666 * 3);
  int timerSet = 0;
  ColorSense1.setLight(ledState::on);
  ColorSense1.setLightPower(100);
  ColorSense1.gestureEnable();
  FWSM1.setRotation(0, rev);
  FWSM2.setRotation(0, rev);
  Intake.setRotation(0, rev);
  Brake.setRotation(0, rev);
  while (1) {
      //Driver Controls for Mechanum Wheels.
      if(Controller1.Axis3.position() > -15 && Controller1.Axis3.position() < 15 && Controller1.Axis1.position() > -15 && Controller1.Axis1.position() < 15 && Controller1.Axis4.position() > -15 && Controller1.Axis4.position() < 15) {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.stop(brake);
      L2.stop(brake);
      R1.stop(brake);
      R2.stop(brake);
      Brain.Screen.printAt(1, 200, "Not Moving");
      }else {
      Brain.Screen.clearLine(10);
      Brain.Screen.clearLine(11);
      L1.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      R1.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      L2.spin(fwd, Controller1.Axis3.position() + Controller1.Axis1.position() - Controller1.Axis4.position(), percent);
      R2.spin(fwd, Controller1.Axis3.position() - Controller1.Axis1.position() + Controller1.Axis4.position(), percent);
      Brain.Screen.printAt(1, 200, "Moving");
      }
  

      //Shooting system
      if(Controller1.ButtonR1.pressing() && shootSystem == false) {
      shootSystem = true;
      } else if (!Controller1.ButtonR1.pressing() && shootSystem == true) {
        if(FWSM1.rotation(rev) < .5 && FWSM2.rotation(rev) < .5) {
        FWSM1.spin(fwd, 100, pct);
        FWSM2.spin(reverse, 100, pct);
        Brain.Screen.printAt(1, 70, "Shooting");
        }else {
        FWSM1.stop(brake);
        FWSM2.stop(brake);
        FWSM1.setRotation(0, rev);
        FWSM2.setRotation(0, rev);
        Brain.Screen.clearLine(3);
        Brain.Screen.clearLine(4);
        }
        shootSystem = false;
      }

      //Intake System  

      //Color Sensor stopping the Intake after 3 Discs
      if (Discs == 3) {
        timerSet = 3;
        Discs = 0;
      }

      if(Discs < 0) {
        Discs = 0;
      }

      if (timerSet != 0) {
        while(timerSet != 0) {
          this_thread::sleep_for(1000);
          Brain.Screen.clearLine(5);
          Brain.Screen.clearLine(6);
          Brain.Screen.printAt(1, 100, "Out-taking");
          Controller1.Screen.clearLine(3);
          Controller1.Screen.print(Discs);
          Intake.startRotateFor(reverse, intakeRotate, rev, 600, rpm);
          this_thread::sleep_for(3000);
          timerSet = timerSet - 3;
        } 
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Intake.setRotation(0, rev);
      }
      
      //Manual Start-Stop of the Intake System
      if (Controller1.ButtonR2.pressing() && intakeSystem == false) {
      intakeSystem = true;
      } else if (!Controller1.ButtonR2.pressing() && intakeSystem == true) {
        if (Intake.rotation(rev) < .5) {
        Intake.spin(fwd, 100, pct);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Brain.Screen.printAt(1, 100, "Intaking");  
        } else {
        Intake.stop(brake);
        Intake.setRotation(0, rev);
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        }
        intakeSystem = false;
      } 

      


      //Brake System
      if(Controller1.ButtonL2.pressing() == true && brakeSystem == false) {
        brakeSystem = true;
      }
      else if (!Controller1.ButtonL2.pressing() && brakeSystem == true) {
        if(Brake.rotation(rev) < .3 && Brake.rotation(rev) > -100) {
          Brain.Screen.clearLine(7);  
          Brain.Screen.printAt(1, 140, "Brake Down");
          Brake.startRotateFor(fwd, 1.2, rev, 200, rpm);
        }else {
          Brain.Screen.clearLine(7);
          Brain.Screen.printAt(1, 140, "Brake Up");
          Brake.startRotateFor(reverse, 1.2, rev, 200, rpm);
          Brake.setRotation(0, rev);
        }
        brakeSystem = false;
      }


    wait(20, msec); // Sleep the task for a short amount of time to
                    // prevent wasted resources.
  }
}

//
// Main will set up the competition functions and callbacks.
//
int main() {
  // Set up callbacks for autonomous and driver control periods and for when the color sensor counts the incoming discs.
  Competition.autonomous(autonomous);
  Competition.drivercontrol(usercontrol);
  ColorSense1.gestureUp(CounterUP);
  ColorSense1.gestureDown(CounterDOWN);

  // Run the pre-autonomous function.
  pre_auton();

  // Prevent main from exiting with an infinite loop.
  while (true) {
    wait(100, msec);
  }
}

Assuming you mean this block of code:

      if (timerSet != 0) {
        while(timerSet != 0) {
          this_thread::sleep_for(1000);
          Brain.Screen.clearLine(5);
          Brain.Screen.clearLine(6);
          Brain.Screen.printAt(1, 100, "Out-taking");
          Controller1.Screen.clearLine(3);
          Controller1.Screen.print(Discs);
          Intake.startRotateFor(reverse, intakeRotate, rev, 600, rpm);
          this_thread::sleep_for(3000);
          timerSet = timerSet - 3;
        } 
        Brain.Screen.clearLine(5);
        Brain.Screen.clearLine(6);
        Intake.setRotation(0, rev);
      }

Which is included inside your main while(1) { loop in usercontrol, the code is behaving exactly as you wrote it and describe. Generally speaking, each line of code is “blocking” - the next line will not run until the current line finishes. If you want this code to execute at the same time as other code in usercontrol, creating a thread for it is the most common approach. Threading provides the illusion of the single-core V5 user CPU performing multiple code paths at once.

5 Likes

So I should create another while(1) outside of the existing one that’s still under usercontrol and have only this part of the code inside the new while(1)

?

Slightly off topic, and it does not answer the question above, but use of all the startRotateFor and rotateFor functions will be removed from the SDK in the next few weeks. We sort of deprecated these when coding studio was scrapped and have had both motor APIs around since then (ie. spin… and rotate…) so this code

Intake.startRotateFor(reverse, intakeRotate, rev, 600, rpm);

should be replaced with

Intake.spinFor(reverse, intakeRotate, rev, 600, rpm, false);

for future compatibility with VEXcode.

6 Likes

WIll do right away. Thank you

Please just go look up multi-threading. This topic has been solved. After you look up multi-threading, if you run into issues, make a new topic.

I’ll even give you a free starting point:

7 Likes