our team has been experiencing an issue with implementing the spark max code, the code will compile but sends error 4 & 5 to the Roborio. The code however will enable but will also send the error message error 4. Here’s our code
// Copyright (c) FIRST and other WPILib contributors.
// Open Source Software; you can modify and/or share it under the terms of
// the WPILib BSD license file in the root directory of this project.
package frc.robot;
import edu.wpi.first.wpilibj.TimedRobot;
import edu.wpi.first.wpilibj2.command.Command;
import edu.wpi.first.wpilibj2.command.CommandScheduler;
//import edu.wpi.first.wpilibj.TimedRobot;
import edu.wpi.first.wpilibj.smartdashboard.SmartDashboard;
import com.revrobotics.RelativeEncoder;
import com.revrobotics.SparkMaxAlternateEncoder;
import com.revrobotics.SparkMaxPIDController;
import com.revrobotics.CANSparkMax;
import com.revrobotics.CANSparkMaxLowLevel.MotorType;
/**
- The VM is configured to automatically run this class, and to call the functions corresponding to
- each mode, as described in the TimedRobot documentation. If you change the name of this class or
- the package after creating this project, you must also update the build.gradle file in the
- project.
*/
public class Robot extends TimedRobot {
private Command m_autonomousCommand;
private RobotContainer m_robotContainer;
/**
- Change these parameters to match your setup
*/
static final int kCanID = 2;
private static final MotorType kMotorType = MotorType.kBrushless;
private static final SparkMaxAlternateEncoder.Type kAltEncType = SparkMaxAlternateEncoder.Type.kQuadrature;
private static final int kCPR = 8192;
private CANSparkMax m_motor;
private SparkMaxPIDController m_pidController;
public double kP, kI, kD, kIz, kFF, kMaxOutput, kMinOutput;
/**
- An alternate encoder object is constructed using the GetAlternateEncoder()
- method on an existing CANSparkMax object. If using a REV Through Bore
- Encoder, the type should be set to quadrature and the counts per
- revolution set to 8192
*/
private RelativeEncoder m_alternateEncoder;
/**
- This function is run when the robot is first started up and should be used for any
- initialization code.
*/
@Override
public void robotInit() {
// Instantiate our RobotContainer. This will perform all our button bindings, and put our
// autonomous chooser on the dashboard.
// initialize SPARK MAX with CAN ID
m_motor = new CANSparkMax(kCanID, kMotorType);
m_motor.restoreFactoryDefaults();
m_alternateEncoder = m_motor.getAlternateEncoder(kAltEncType, kCPR);
/**
* In order to use PID functionality for a controller, a SparkMaxPIDController object
* is constructed by calling the getPIDController() method on an existing
* CANSparkMax object
*/
m_pidController = m_motor.getPIDController();
/**
* By default, the PID controller will use the Hall sensor from a NEO for its
* feedback device. Instead, we can set the feedback device to the alternate
* encoder object
*/
m_pidController.setFeedbackDevice(m_alternateEncoder);
/**
* From here on out, code looks exactly like running PID control with the
* built-in NEO encoder, but feedback will come from the alternate encoder
*/
// PID coefficients
kP = 0.1;
kI = 1e-4;
kD = 1;
kIz = 0;
kFF = 0;
kMaxOutput = 1;
kMinOutput = -1;
// set PID coefficients
m_pidController.setP(kP);
m_pidController.setI(kI);
m_pidController.setD(kD);
m_pidController.setIZone(kIz);
m_pidController.setFF(kFF);
m_pidController.setOutputRange(kMinOutput, kMaxOutput);
// display PID coefficients on SmartDashboard
SmartDashboard.putNumber("P Gain", kP);
SmartDashboard.putNumber("I Gain", kI);
SmartDashboard.putNumber("D Gain", kD);
SmartDashboard.putNumber("I Zone", kIz);
SmartDashboard.putNumber("Feed Forward", kFF);
SmartDashboard.putNumber("Max Output", kMaxOutput);
SmartDashboard.putNumber("Min Output", kMinOutput);
SmartDashboard.putNumber("Set Rotations", 0);
m_robotContainer = new RobotContainer();
}
/**
- This function is called every 20 ms, no matter the mode. Use this for items like diagnostics
- that you want ran during disabled, autonomous, teleoperated and test.
-
This runs after the mode specific periodic functions, but before LiveWindow and
- SmartDashboard integrated updating.
*/
@Override
public void robotPeriodic() {
// Runs the Scheduler. This is responsible for polling buttons, adding newly-scheduled
// commands, running already-scheduled commands, removing finished or interrupted commands,
// and running subsystem periodic() methods. This must be called from the robot’s periodic
// block in order for anything in the Command-based framework to work.
CommandScheduler.getInstance().run();
}
/** This function is called once each time the robot enters Disabled mode. */
@Override
public void disabledInit() {}
@Override
public void disabledPeriodic() {}
/** This autonomous runs the autonomous command selected by your {@link RobotContainer} class. */
@Override
public void autonomousInit() {
m_autonomousCommand = m_robotContainer.getAutonomousCommand();
// schedule the autonomous command (example)
if (m_autonomousCommand != null) {
m_autonomousCommand.schedule();
}
}
/** This function is called periodically during autonomous. */
@Override
public void autonomousPeriodic() {}
@Override
public void teleopInit() {
// This makes sure that the autonomous stops running when
// teleop starts running. If you want the autonomous to
// continue until interrupted by another command, remove
// this line or comment it out.
if (m_autonomousCommand != null) {
m_autonomousCommand.cancel();
}
}
/** This function is called periodically during operator control. */
@Override
public void teleopPeriodic() {
// read PID coefficients from SmartDashboard
double p = SmartDashboard.getNumber(“P Gain”, 0);
double i = SmartDashboard.getNumber(“I Gain”, 0);
double d = SmartDashboard.getNumber(“D Gain”, 0);
double iz = SmartDashboard.getNumber(“I Zone”, 0);
double ff = SmartDashboard.getNumber(“Feed Forward”, 0);
double max = SmartDashboard.getNumber(“Max Output”, 0);
double min = SmartDashboard.getNumber(“Min Output”, 0);
double rotations = SmartDashboard.getNumber(“Set Rotations”, 0);
// if PID coefficients on SmartDashboard have changed, write new values to controller
if((p != kP)) { m_pidController.setP(p); kP = p; }
if((i != kI)) { m_pidController.setI(i); kI = i; }
if((d != kD)) { m_pidController.setD(d); kD = d; }
if((iz != kIz)) { m_pidController.setIZone(iz); kIz = iz; }
if((ff != kFF)) { m_pidController.setFF(ff); kFF = ff; }
if((max != kMaxOutput) || (min != kMinOutput)) {
m_pidController.setOutputRange(min, max);
kMinOutput = min; kMaxOutput = max;
}
/**
* PIDController objects are commanded to a set point using the
* SetReference() method.
*
* The first parameter is the value of the set point, whose units vary
* depending on the control type set in the second parameter.
*
* The second parameter is the control type can be set to one of four
* parameters:
* com.revrobotics.CANSparkMax.ControlType.kDutyCycle
* com.revrobotics.CANSparkMax.ControlType.kPosition
* com.revrobotics.CANSparkMax.ControlType.kVelocity
* com.revrobotics.CANSparkMax.ControlType.kVoltage
*/
m_pidController.setReference(rotations, CANSparkMax.ControlType.kPosition);
SmartDashboard.putNumber("SetPoint", rotations);
SmartDashboard.putNumber("ProcessVariable", m_alternateEncoder.getPosition());
}
@Override
public void testInit() {
// Cancels all running commands at the start of test mode.
CommandScheduler.getInstance().cancelAll();
}
/** This function is called periodically during test mode. */
@Override
public void testPeriodic() {}
/** This function is called once when the robot is first started up. */
@Override
public void simulationInit() {}
/** This function is called periodically whilst in simulation. */
@Override
public void simulationPeriodic() {}
}
Any help would be appreciated