Skip to content

Reading Joysticks and Binding Triggers

learnfrc.com
learnfrc.comAuthor
Veer Bajaj
Veer BajajMaintainer

Drivers use gamepads or joysticks plugged into the Driver Station. WPILib reads them through controller classes. The XboxController class works with the Xbox 360, Xbox One controllers, and the Logitech F310 when its switch is set to XInput (“X”) mode — these are the most common FRC controllers.

For command-based code, use CommandXboxController , which adds convenient button “trigger” methods.

XboxController driver = new XboxController(0); // DS USB slot 0
double forward = -driver.getLeftY(); // sticks are inverted: up is negative
double turn = driver.getRightX();
boolean shoot = driver.getAButton();

Joystick axes range from -1.0 to 1.0. A common gotcha: the Y axis is negative when pushed forward, so you usually negate it.

A Trigger represents a boolean condition (a button press, a sensor state, anything). You bind commands to triggers in a method usually called configureBindings() inside RobotContainer:

CommandXboxController driver = new CommandXboxController(0);
// Run the intake WHILE the A button is held; stop when released
driver.a().whileTrue(intake.intakeCommand());
// Run a command ONCE when the right bumper is pressed
driver.rightBumper().onTrue(arm.raiseToScore());
// Combine conditions
driver.a().and(driver.b()).onTrue(robot.specialMode());

Key binding methods:

  • onTrue(cmd) — schedule the command when the trigger becomes true (rising edge).
  • whileTrue(cmd) — run while the trigger is true; interrupt when it goes false.
  • onFalse(cmd) / toggleOnTrue(cmd) — other edge behaviors.

Because CommandXboxController has named methods (a(), b(), leftBumper(), povUp(), etc.), bindings read almost like English.

A Trigger can wrap any boolean supplier:

new Trigger(arm::atTarget).onTrue(Commands.runOnce(() -> led.setGreen()));

This is the declarative power of command-based: instead of polling if (...) every loop, you declare “when this becomes true, do that.”

A typical teleop setup combines both ideas: the drivetrain’s default command reads the sticks every loop, while triggers handle mechanism actions:

drivetrain.setDefaultCommand(
drivetrain.run(() -> drivetrain.arcadeDrive(-driver.getLeftY(), driver.getRightX())));
driver.a().whileTrue(intake.intakeCommand());
driver.b().onTrue(shooter.shoot());

Real sticks rarely rest at exactly 0. Apply a deadband (MathUtil.applyDeadband(value, 0.1)) so small stick drift doesn’t creep the robot.

  • Use XboxController (raw) or CommandXboxController (command-based) to read gamepads.
  • Axes are -1.0 to 1.0; the Y axis is negative when pushed forward — usually negate it.
  • Triggers bind commands to conditions: onTrue, whileTrue, onFalse, toggleOnTrue.
  • A Trigger can wrap any boolean, not just buttons — enabling declarative reactions.
  • Apply MathUtil.applyDeadband to stick inputs to ignore resting drift.

This lesson was adapted from learnfrc.com.