4
4
# the WPILib BSD license file in the root directory of this project.
5
5
#
6
6
7
- from commands2 import RunCommand , RamseteCommand
8
- from commands2 .button import JoystickButton , Button
9
-
10
7
from wpilib import XboxController
11
8
from wpimath .controller import (
12
9
RamseteController ,
13
10
PIDController ,
14
11
SimpleMotorFeedforwardMeters ,
15
12
)
16
-
17
- from wpimath .kinematics import ChassisSpeeds
18
-
19
- from wpilib .interfaces import GenericHID
20
-
21
- from wpimath .trajectory .constraint import DifferentialDriveVoltageConstraint
22
- from wpimath .trajectory import TrajectoryConfig , TrajectoryGenerator , Trajectory
23
-
24
13
from wpimath .geometry import Pose2d , Rotation2d , Translation2d
14
+ from wpimath .trajectory .constraint import DifferentialDriveVoltageConstraint
15
+ from wpimath .trajectory import TrajectoryConfig , TrajectoryGenerator
25
16
26
- from subsystems .drivetrain import Drivetrain
17
+ from commands2 import InstantCommand , RunCommand , RamseteCommand , cmd
18
+ from commands2 .button import JoystickButton
27
19
20
+ from subsystems .driveSubsystem import DriveSubsystem
28
21
import constants
29
22
30
23
31
24
class RobotContainer :
32
-
33
25
"""
34
- This class hosts the bulk of the robot's functions. Little robot logic needs to be
35
- handled here or in the robot periodic methods, as this is a command-based system.
36
- The structure (commands, subsystems, and button mappings) should be done here.
26
+ This class is where the bulk of the robot should be declared. Since Command-based is a
27
+ "declarative" paradigm, very little robot logic should actually be handled in the {@link Robot}
28
+ periodic methods (other than the scheduler calls). Instead, the structure of the robot (including
29
+ subsystems, commands, and button mappings) should be declared here.
37
30
"""
38
31
39
32
def __init__ (self ):
40
- # Create the driver 's controller.
41
- self .driverController = XboxController ( constants . kDriverControllerPort )
33
+ # The robot 's subsystems
34
+ self .robotDrive = DriveSubsystem ( )
42
35
43
- # Create an instance of the drivetrain subsystem .
44
- self .robotDrive = Drivetrain ( )
36
+ # The driver's controller .
37
+ self .driverController = XboxController ( constants . kDriverControllerPort )
45
38
46
- # Configure and set the button bindings for the driver's controller.
39
+ # Configure the button bindings
47
40
self .configureButtons ()
48
41
49
- # Set the default command for the drive subsystem. It's default command will allow
50
- # the robot to drive with the controller.
51
-
42
+ # Configure default commands
43
+ # Set the default drive command to split-stick arcade drive
52
44
self .robotDrive .setDefaultCommand (
45
+ # A split-stick arcade command, with forward/backward controlled by the left
46
+ # hand, and turning controlled by the right.
53
47
RunCommand (
54
48
lambda : self .robotDrive .arcadeDrive (
55
- - self .driverController .getRawAxis ( 1 ),
56
- self .driverController .getRawAxis ( 2 ) * 0.65 ,
49
+ - self .driverController .getLeftY ( ),
50
+ - self .driverController .getRightX () ,
57
51
),
58
52
self .robotDrive ,
59
53
)
60
54
)
61
55
56
+ def configureButtons (self ):
57
+ """
58
+ Use this method to define your button->command mappings. Buttons can be created by
59
+ instantiating a GenericHID or one of its subclasses (Joystick or XboxController),
60
+ and then calling passing it to a JoystickButton.
61
+ """
62
+
63
+ # Drive at half speed when the right bumper is held
64
+ (
65
+ JoystickButton (self .driverController , XboxController .Button .kRightBumper )
66
+ .onTrue (InstantCommand (lambda : self .robotDrive .setMaxOutput (0.5 )))
67
+ .onFalse (InstantCommand (lambda : self .robotDrive .setMaxOutput (1 )))
68
+ )
69
+
62
70
def getAutonomousCommand (self ):
63
- """Returns the command to be ran during the autonomous period ."""
71
+ """Use this to pass the autonomous command to the main {@link Robot} class ."""
64
72
65
73
# Create a voltage constraint to ensure we don't accelerate too fast.
66
-
67
74
autoVoltageConstraint = DifferentialDriveVoltageConstraint (
68
75
SimpleMotorFeedforwardMeters (
69
76
constants .ksVolts ,
@@ -74,84 +81,54 @@ def getAutonomousCommand(self):
74
81
maxVoltage = 10 , # 10 volts max.
75
82
)
76
83
77
- # Below will generate the trajectory using a set of programmed configurations
78
-
79
- # Create a configuration for the trajctory. This tells the trajectory its constraints
80
- # as well as its resources, such as the kinematics object.
84
+ # Create config for trajectory
81
85
config = TrajectoryConfig (
82
86
constants .kMaxSpeedMetersPerSecond ,
83
87
constants .kMaxAccelerationMetersPerSecondSquared ,
84
88
)
85
-
86
- # Ensures that the max speed is actually obeyed.
89
+ # Add kinematics to ensure max speed is actually obeyed
87
90
config .setKinematics (constants .kDriveKinematics )
88
-
89
- # Apply the previously defined voltage constraint.
91
+ # Apply the voltage constraint
90
92
config .addConstraint (autoVoltageConstraint )
91
93
92
- # Start at the origin facing the +x direction.
93
- initialPosition = Pose2d (0 , 0 , Rotation2d (0 ))
94
-
95
- # Here are the movements we also want to make during this command.
96
- # These movements should make an "S" like curve.
97
- movements = [Translation2d (1 , 1 ), Translation2d (2 , - 1 )]
98
-
99
- # End at this position, three meters straight ahead of us, facing forward.
100
- finalPosition = Pose2d (3 , 0 , Rotation2d (0 ))
101
-
102
94
# An example trajectory to follow. All of these units are in meters.
103
95
self .exampleTrajectory = TrajectoryGenerator .generateTrajectory (
104
- initialPosition ,
105
- movements ,
106
- finalPosition ,
96
+ # Start at the origin facing the +x direction.
97
+ Pose2d (0 , 0 , Rotation2d (0 )),
98
+ # Pass through these two interior waypoints, making an 's' curve path
99
+ [Translation2d (1 , 1 ), Translation2d (2 , - 1 )],
100
+ # End 3 meters straight ahead of where we started, facing forward
101
+ Pose2d (3 , 0 , Rotation2d (0 )),
102
+ # Pass config
107
103
config ,
108
104
)
109
105
110
- # Below creates the RAMSETE command
111
-
112
106
ramseteCommand = RamseteCommand (
113
- # The trajectory to follow.
114
107
self .exampleTrajectory ,
115
- # A reference to a method that will return our position.
116
108
self .robotDrive .getPose ,
117
- # Our RAMSETE controller.
118
109
RamseteController (constants .kRamseteB , constants .kRamseteZeta ),
119
- # A feedforward object for the robot.
120
110
SimpleMotorFeedforwardMeters (
121
111
constants .ksVolts ,
122
112
constants .kvVoltSecondsPerMeter ,
123
113
constants .kaVoltSecondsSquaredPerMeter ,
124
114
),
125
- # Our drive kinematics.
126
115
constants .kDriveKinematics ,
127
- # A reference to a method which will return a DifferentialDriveWheelSpeeds object.
128
116
self .robotDrive .getWheelSpeeds ,
129
- # The turn controller for the left side of the drivetrain.
130
117
PIDController (constants .kPDriveVel , 0 , 0 ),
131
- # The turn controller for the right side of the drivetrain.
132
118
PIDController (constants .kPDriveVel , 0 , 0 ),
133
- # A reference to a method which will set a specified
134
- # voltage to each motor. The command will pass the two parameters.
119
+ # RamseteCommand passes volts to the callback
135
120
self .robotDrive .tankDriveVolts ,
136
- # The subsystems the command should require.
137
121
[self .robotDrive ],
138
122
)
139
123
140
- # Reset the robot's position to the starting position of the trajectory.
141
- self .robotDrive .resetOdometry (self .exampleTrajectory .initialPose ())
142
-
143
- # Return the command to schedule. The "andThen()" will halt the robot after
144
- # the command finishes.
145
- return ramseteCommand .andThen (lambda : self .robotDrive .tankDriveVolts (0 , 0 ))
146
-
147
- def configureButtons (self ):
148
- """Configure the buttons for the driver's controller"""
149
-
150
- # We won't do anything with this button itself, so we don't need to
151
- # define a variable.
152
-
124
+ # Reset odometry to the initial pose of the trajectory, run path following
125
+ # command, then stop at the end.
153
126
(
154
- JoystickButton (self .driverController , XboxController .Button .kRightBumper )
155
- .whenPressed (lambda : self .robotDrive .setSlowMaxOutput (0.5 ))
156
- .whenReleased (lambda : self .robotDrive .setNormalMaxOutput (1 ))
127
+ cmd .runOnce (
128
+ lambda : self .robotDrive .resetOdometry (
129
+ self .exampleTrajectory .initialPose ()
130
+ )
131
+ )
132
+ .andThen (ramseteCommand )
133
+ .andThen (cmd .runOnce (lambda : self .robotDrive .tankDriveVolts (0 , 0 )))
157
134
)
0 commit comments