Project 4 — Build a Fuel Launcher for REBUILT
The 2026 game, REBUILT presented by Haas, is built around scoring foam balls called Fuel into a Hub goal, with a Tower to climb in endgame. The simplest scoring mechanism is a flywheel launcher — exactly the kind of mechanism the official KitBot and the AndyMark Everybot iterate toward. We will add one as a clean subsystem.
Hardware: one launcher wheel driven by a NEO on a SPARK MAX (CAN ID 5). A flywheel works by spinning fast, then transferring momentum to the ball on contact.
LauncherSubsystem.java:
package frc.robot.subsystems;
import com.revrobotics.spark.SparkMax;import com.revrobotics.spark.SparkLowLevel.MotorType;import com.revrobotics.spark.SparkBase.ResetMode;import com.revrobotics.spark.SparkBase.PersistMode;import com.revrobotics.spark.config.SparkMaxConfig;import com.revrobotics.spark.config.SparkBaseConfig.IdleMode;import edu.wpi.first.wpilibj2.command.Command;import edu.wpi.first.wpilibj2.command.SubsystemBase;
public class LauncherSubsystem extends SubsystemBase { private final SparkMax m_launch = new SparkMax(5, MotorType.kBrushless);
public LauncherSubsystem() { SparkMaxConfig cfg = new SparkMaxConfig(); cfg.idleMode(IdleMode.kCoast) // let the wheel spin down freely .smartCurrentLimit(40); // protect the motor and battery m_launch.configure(cfg, ResetMode.kResetSafeParameters, PersistMode.kPersistParameters); }
public Command shoot() { return startEnd(() -> m_launch.set(0.85), // spin up to 85% () -> m_launch.set(0.0)); // stop on release }}The configure(...) call with ResetMode.kResetSafeParameters and PersistMode.kPersistParameters is the REVLib 2025+ pattern for applying and saving a config. The startEnd factory returns a command that runs the first lambda when scheduled and the second when it ends — perfect for ‘hold to shoot’. The smartCurrentLimit(40) call matters: a flywheel pulls a large inrush current when spinning up, and capping it helps keep you from tripping a breaker or browning out the roboRIO.
Bind it in RobotContainer:
private final LauncherSubsystem m_launcher = new LauncherSubsystem();// inside configureBindings():m_ctrl.rightTrigger().whileTrue(m_launcher.shoot());Tuning the shot: start at 85% and adjust. Too slow and the Fuel arcs short of the Hub; too fast and it bounces out. Real teams later replace the open-loop set() with a velocity PID + feedforward so the wheel recovers to target RPM between shots — that consistency is what helps you reach the Energized (100 Fuel) and Supercharged (360 Fuel) ranking-point thresholds. For now, open-loop is a perfect first launcher. Give the wheel a moment to spin up before feeding a ball, and use coast idle so it does not jerk to a stop.
Key takeaways
Section titled “Key takeaways”- A flywheel launcher transfers momentum to the Fuel ball; startEnd() gives you a clean hold-to-shoot command
- smartCurrentLimit(40) on the launcher reduces the spin-up inrush that can brown out the robot
- Open-loop set(0.85) is fine to start; velocity PID+feedforward later gives the consistent shots needed for the Energized/Supercharged ranking points
This lesson was adapted from learnfrc.com.
