New for 2024
A number of improvements have been made to FRC® Control System software for 2024. This article will describe and provide a brief overview of the new changes and features as well as a more complete changelog for Java/C++ WPILib changes. This document only includes the most relevant changes for end users, the full list of changes can be viewed on the various WPILib GitHub repositories.
It’s recommended to also review the list of known issues.
Importing Projects from Previous Years
Due to internal GradleRIO changes, it is necessary to update projects from previous years. After Installing WPILib for 2024, any 2023 projects must be imported to be compatible.
Major Changes (Java/C++)
These changes contain some of the major changes to the library that it’s important for the user to recognize. This does not include all of the breaking changes, see the other sections of this document for more changes.
Added support for XRP robots
Projects now default to supporting Java 17 features
Multiple NetworkTables networking improvements for improved reliability and robustness and structured data support using protobuf
Java now uses the Serial GC by default on the roboRIO; this should improve performance and reduce memory usage for most robot programs
Performance improvements and reduced worst-case memory usage throughout libraries
Added a typesafe unit system for Java (not used by the main part of WPILib yet)
Disabled LiveWindow in Test Mode by default. See See Enabling LiveWindow in Test Mode to enable it.
SysId has been rewritten to remove project generation; Replaced with data logging within team robot program
- Supported Operating Systems and Architectures:
Windows 10 & 11, 64 bit. 32 bit and Arm are not supported
Ubuntu 22.04, 64 bit. Other Linux distributions with glibc >= 2.32 may work, but are unsupported
macOS 12 or later, Intel and Arm.
Warning
The following OSes are no longer supported: macOS 11, Ubuntu 18.04 & 20.04, Windows 7, Windows 8.1, and any 32-bit Windows.
WPILib
General Library
Commands:
Added proxy factory to
Commands
Added
IdleCommand
Fixed
RepeatCommand
callingend()
twiceAdded
onlyWhile()
andonlyIf()
decoratorsImplemented
ConditionalCommand.getInterruptBehavior()
Added interruptor parameter to
onCommandInterrupt
callbacksAdded
DeferredCommand
,Commands.defer()
, andSubsystem.defer()
Add requirements parameter to
Commands.idle()
Fix Java
CommandXboxController.leftTrigger()
parameter orderMake Java
SelectCommand
genericAdd finallyDo with zero-arg lambda
NetworkTables:
Networking improvements for improved reliability and robustness
Added subprotocol to improve web-based dashboard connection aliveness checking
Bugfixes and stability improvements (reduced worst case memory usage)
Improved update behavior for values continuously updated from robot code (improves command button behavior)
Data Logging:
Improved handling of low free space conditions (now stops logging if less than 5 MB free)
Added warning about logging to built-in storage on RoboRIO 1
Reduced worst case memory usage
Improved file rename functionality to only use system time after it is updated by DS
NT publishers created before the log is started are now captured
Add delete without download functionality to DataLogTool
Changed default log location to logs subdirectory for better organization
Hardware interfaces:
Getting timestamps is now ~10x faster
Exposed power rail disable and CPU temperature functionality
Exposed CAN timestamp base clock
Fixed and documented addressable LED timings
Fixed
DutyCycleEncoder
reset behaviorAdded function to read the RSL state
Raw PWM now uses microseconds units
Fixed REVPH faults bitfield
C++: Fix
Counter
default distance per pulse to match Java
Math:
Refactored kinematics, odometry, and pose estimator internals to have less code duplication; you can implement custom drivetrains via the
Kinematics
andOdometry
interfaces and thePoseEstimator
class.LTV controllers use a faster DARE solver for faster construction (from 2.33 ms per solve on a roboRIO to 0.432 ms in Java and 0.188 ms in C++ on a roboRIO)
(Java)
Rotation3d.rotateBy()
got a 100x speed improvement by using doubles in Quaternion instead of EJML vectors(Java)
Pose3d.exp()
andPose3d.log()
got a speed improvement by calling the C++ version through JNI instead of using EJML matricesImproved accuracy of Rotation3d Euler angle calculations (
getX()
,getY()
,getZ()
, aka roll-pitch-yaw) near gimbal lockFixed
CoordinateSystem.convert()
Transform3d overloadModified
TrapezoidProfile
API to not require creating new instances forProfiledPIDController
-like use casesAdded Exponential motion profile support
Add constructor overloads for easier Transform2d and Transform3d creation from X, Y, Z coordinates
Add
ChassisSpeeds
fromRobotRelativeSpeeds
to convert from robot relative to field relativeAdd method to create a LinearSystem from kA and kV, for example from a characterized mechanism
Add
SimulatedAnnealing
classFixed MecanumDriveWheelSpeeds desaturate()
Added
RobotController
function to get the assigned team numberUpdated
GetMatchTime
docs and unitsAdded function to wait for DS connection
Added reflection based cleanup helper
Added Java class preloader (no preloading is actually performed yet)
Deprecated
Accelerometer
andGyro
interfaces (no replacement is planned)Updated to OpenCV 4.8.0 and EJML 0.43.1 and C++ JSON to 3.11.2
Add
PS5Controller
classAdd accessors for
AprilTagFieldLayout
origin and field dimensionsArcadeDrive: Fix max output handling
Add
PWMSparkFlex
Motor ControllerADIS16470: allow accessing all three axes
Deprecated
MotorControllerGroup
. UsePWMMotorController
addFollower()
method or if using CAN motor controllers use their method of following.Added functional inteface to
DifferentialDrive
andMecanumDrive
. TheMotorController
interface may be removed in the future to reduce coupling with vendor libraries. Instead of passingMotorController
objects, the following method references or lambda expressions can be used:Java:
DifferentialDrive drive = new DifferentialDrive(m_leftMotor::set, m_rightMotor::set);
C++:
frc::DifferentialDrive m_drive{[&](double output) { m_leftMotor.Set(output); }, & <double output>__ { m_rightMotor.Set(output); }};
Breaking Changes
Changed
DriverStation.getAllianceStation()
to return optional value. See example usageMerged CommandBase into Command (Command is now a base class instead of an interface)
Potentially breaking: made command scheduling order consistent
Removed various deprecated command classes and functions:
PerpetualCommand
andCommand.perpetually()
(useRepeatCommand
/repeatedly()
instead)CommandGroupBase
,Command.IsGrouped()
(C++ only), andCommand.SetGrouped()
(C++ only); the static factories have been moved toCommands
Command.withInterrupt()
ProxyScheduleCommand
Button
(useTrigger
instead)- Old-style Trigger functions:
whenActive()
,whileActiveOnce()
,whileActiveContinuous()
,whenInactive()
,toggleWhenActive()
,cancelWhenActive()
. Each binding type has bothTrue
andFalse
variants; for brevity, only theTrue
variants are listed here: onTrue()
(replaceswhenActive()
andwhenPressed()
): schedule on rising edge.whileTrue()
(replaceswhileActiveOnce()
): schedule on rising edge, cancel on falling edge.toggleOnTrue()
(replacestoggleWhenActive()
): on rising edge, schedule if unscheduled and cancel if scheduled.cancelWhenActive()
: this is a fairly niche use case which is better described as having the trigger’s rising edge (Trigger.rising()
) as an end condition for the command (usingCommand.until()
).whileActiveContinuously()
: however common, this relied on the no-op behavior of scheduling an already-scheduled command. The more correct way to repeat the command if it ends before the falling edge is usingCommand.repeatedly()
/RepeatCommand
or aRunCommand
– the only difference is if the command is interrupted, but that is more likely to result in two commands perpetually canceling each other than achieve the desired behavior. Manually implementing a blindly-scheduling binding likewhileActiveContinuously()
is still possible, though might not be intuitive.
- Old-style Trigger functions:
CommandScheduler.clearButtons()
CommandScheduler.addButtons()
(Java only)Command supplier constructor of
SelectCommand
(useProxyCommand
instead)
Removed
Compressor.enabled()
function (useisEnabled()
instead)Removed
CameraServer.setSize()
function (usesetResolution()
on the camera object instead)Removed deprecated and broken SPI methods
Removed 2-argument constructor to
SlewRateLimiter
Removed
frc2::PIDController
alias (frc::PIDController
already existed)For ease of use,
loadAprilTagFieldLayout()
now throws an unchecked exception instead of a checked exceptionAdd new parameter for
ElevatorSim
constructor for starting heightReport error on negative PID gains
Simulation
Unified PWM simulation Speed, Position, and Raw values to be consistent with robot behavior
Expanded DutyCycleEncoderSim API
Added ability to set starting state of mechanism sims
Added mechanism-specific SetState overloads to physics sims
SmartDashboard
Important
SmartDashboard is not supported on Apple Silicon (Arm64) Macs.
Connection to the robot now always occurs after processing the save file. Fixes the problem that Choosers don’t show up if connection to the robot happens before a chooser in the save file is processed
Added LiveWindow widgets to containing subsystem widget when creating them from the save file
Now properly handles putting the Scheduler on SmartDashboard with
SmartDashboard.putData()
Glass / OutlineViewer / Simulation GUI
Include standard field images for Field2D background
Enhanced array support in NetworkTables views
Added background color selector to glass plots
Added tooltips for NT settings
Improved title bar message
Fixed loading a maximized window on second monitor
Fixed crash when clearing existing workspace
Fixed file dialogs not closing after window closes
add ProfiledPIDController support
GradleRIO
Use Java Serial GC by default
Remove AlwaysPreTouch from Java arguments (reduces startup memory usage)
Added support for XRP
Enforces that vendor dependencies set correct frcYear (prevents using prior year vendor dependencies)
Upgraded to Gradle 8.4
Check that project isn’t in OneDrive, as that causes issues
WPILib All in One Installer
Update to VS Code 1.85.1
VS Code extension updates: cpptools 1.19.1, javaext 1.26.0
Use separate zip files for VS Code download/install
Update to use .NET 8
AdvantageScope is now bundlled by the installer
Visual Studio Code Extension
Java source code is now bundled into the deployed jar file. This makes it possible to recover source code from a deployed robot program.
Added XRP support
Check that project isn’t created in OneDrive, as that causes issues
RobotBuilder
Add POVButton
Fixed constants aliasing
Updated PCM references and wiring export for addition of REV PH
SysId
Removed project generation; Replaced with data logging within team robot program