LC272 - FRC Robot C++ and JAVA (2015)

Download Report

Transcript LC272 - FRC Robot C++ and JAVA (2015)

2015 FRC roboRio
C++ and JAVA
Two languages saying
the same thing but
differently!!!!
Presented By:
Frank Larkin
Lansdale Catholic Robotics,
Team 272
Philadelphia PA, Dec. 2016
Goals
• Get a good understanding of what
the control system can and cannot
do.
• Get a good understanding of how
to program in C++ and JAVA
– Be able to create your own classes to
allow multiple threads for
development.
• See different programming designs
for the FRC robot.
• Learn how to get autonomous
working well.
How will we do it?
• Eat donut holes and then lunch!
• Discuss C++ and JAVA
– No rat holing on theory.
– Exchange cards, get phone numbers
and email
• Review online resources
– Forums, Wiki, bla bla
• Review LC and other code to
explore possibilities
– Get many flavors of the same thing.
– Touches many of the approaches
available to you
– See how other accomplished
– Shamelessly steal their stuff.
• Thought Games
– I ask, you figure it out. Fun!!!!
• Hands On
– Play until it is time to leave.
FRC roboRio Hardware
• Google:FRC robot control
system picture
• https://decibel.ni.com/content/d
ocs/DOC-30419
• http://team358.org/files/progra
mming/ControlSystem20152019/
C++ and JAVA
• Both languages are similar…
– Both are somewhat human readable.
– Both follow a very similar syntax.
– Both are object oriented
• Both allow you to declare variables
– Integer, long, short, float, double
• All numbers that reserve different amounts of space.
– Character, string
• A way to store letters and words. Not really used too
much in robots but we can.
– Google: [language] operators
• A million Internet sites discuss this topic.
• Both are extensible and use something
called a class
– Bundle all of a things, things into a
single thing.
– A class’s “things” can be public or they
can be private. If private you use public
methods to set values to them or get
values from them.
– Classes can inherit other classes
Programming Lexicon
• Object
– Objects are definitions of things you can use in
programming you robot. All objects have state and
behavior. They define behavior with the outside world
through methods.
• Class
– A class is the blueprint from which individual objects are
created.
• Inheritance
– Different kinds of objects often have a certain amount in
common with each other. Object-oriented programming
allows classes to inherit commonly used state and
behavior from other classes.
• Interface (Java only) (just another class in C++)
– In its most common form, an interface is a group of
related methods with empty bodies.
• Variable
– A way to associate some information with a name that we
can use in our programs. Some variables are created as
static and once created cannot be changed.
• Package (Java only) (header file (.h) in C++)
– A package is a namespace that organizes a set of related
classes and interfaces. Conceptually you can think of
packages as being similar to different folders on your
computer.
Class Inheritance
• One class can “inherit”
everything from another class
• People are several inherited
classes.
• class mammal
– Methods: GetAge(), SetAge(),
GetHeartBeat(“bpm”)
• class human extends mammal
– Methods: GetName(), SetName()
• class student extends human
– Methods: SetGrade(),
GetGrade()
– Human.GetAge() still works.
How Many Classes?
• http://www.wbrobotics.com/jav
adoc/index.html?edu/wpi/first/w
pilibj/package-summary.html
• http://wpilib.screenstepslive.co
m/s/3120/m/7912
FRC Class Example
Joystick
• What “things” would you
expect from an object called a
joystick?
– Buttons
• Trigger
• Top
• Other user buttons
– Various Axis controllers
•
•
•
•
X = side to side
Y = forward and back
Z = twist or variable level
Throttle = variable level
KISS
• Class variables
– Public – Everyone can get to them.
– Private – You decide who gets to them
using set and get. (used in real world)
…a dazzling triumph for aerospace
designer and maverick
genius Burt Rutan. ...
SpaceShipOne' s "pressurization"
system is essentially a couple
of corks.
Motor Basics: Java
Examples
import edu.wpi.first.wpilibj.Jaguar;
import edu.wpi.first.wpilibj.Victor;
import edu.wpi.first.wpilibj.Relay;
// creating a Jaguar reference
Jaguar motor1 = new Jaguar(1); // default digital module,
channel 1
// setting the desired speed (range of -1.0 to 1.0)
motor1.set(0.5);
// creating a Victor reference
Victor motor2 = new Victor(2); // default digital module,
channel 2
// setting the desired speed (range of -1.0 to 1.0)
motor2.set(0.25);
// creating a Relay reference
// allowing forward direction only
// default digital module, channel 1
Relay motor3 = new Relay(1, kForward);;
// setting the motor to on and off
motor3.set(kOn);
motor3.set(kOff);
Motor Basics: C++
Examples
#include “WPILib.h”;
#include <Jaguar.h>;
#include <Victor.h>;
#include <Relay.h>;
// creating a Jaguar reference
// default digital module,
Jaguar *motor1 = new Jaguar(1); //channel 1
// setting the desired speed (range of -1.0 to 1.0)
motor1->Set(0.5);
// creating a Victor reference
Victor *motor2 = new Victor(2); //channel 2
// setting the desired speed (range of -1.0 to 1.0)
motor2->Set(0.25);
// creating a Relay reference,
// allowing forward direction only
// default digital module
Relay *motor3 = new Relay(1, Relay::kForward); //
channel 1
// setting the motor to on and off
motor3->Set(Relay::kOn);
motor3->Set(Relay::kOff);
Sensor Basics: Java
Examples
import edu.wpi.first.wpilibj.AnalogChannel;
import edu.wpi.first.wpilibj.DigitalInput;
// Create a reference to an analog sensor
// default analog module, channel 1
AnalogInput ana_sensor1 = new AnalogInput(1);
// Get the average voltage from the analog sensor
double voltage = ana_sensor1.getAverageVoltage();
// Get the average voltage from the analog sensor
double distance = ana_sensor1.getValue();
// Get the average voltage from the analog sensor
double distance = ana_sensor1.getAverageValue();
// Create a reference to a digital sensor
// default digital module, channel 1
DigitalInput dig_sensor2 = new DigitalInput(1);
// Get the value from the sensor
boolean b_SensorState = sensor2.get();
Sensor Basics: C++
Examples
#include <AnalogChannel.h>
#include <DigitalInput.h>
// Create variable pointers for sensors
AnalogChannel *sensor1;
DigitalInput
*sensor2;
// Initialize the analog sensor
// default analog module, channel 1
sensor1 = new AnalogChannel(1);
// Get the average voltage from the analog sensor
float voltage = sensor1->GetAverageVoltage();
// Create a reference to a digital sensor
// default digital module, channel 1
sensor2 = new DigitalInput(1);
// Get the value from the sensor
UINT32 value = sensor2->Get();
Differences between
C++ and JAVA
• Java
– Import
• Brings in external packages or
classes to make it available to your
code.
• C++ Variables must be declared in
constructor and then initialized
• C++
– #include
• Preprocessor directive that brings
in external definitions to make them
available to your code
• Actual code is recompiled into
libraries and linked in later
– What is this ??
• ->
C++
• Pointers vs Local Declarations
– Pointers – References to things in memory
• Possibly looks cleaner
• How most examples are being done.
– Declarations – The things in memory
• No need for pointers but a little more complicated
– Why do I care?
• You will see code described both ways. Do not be afraid
embrace them.
• Declaration Section:
class IterativeDemo : public IterativeRobot
{
// Declare variable for the robot drive system
Servo *p_servo;
}
Note: * means this is a pointer!
• Initialization Section:
IterativeDemo(void)
{
printf("IterativeDemo Constructor Started\n");
p_servo = new Servo(5);
}
• Usage:
p_servo->Set(.50);
p_servo->Set(p_leftStick->GetZ());
Declared Example
• Declaration Section:
class IterativeDemo : public IterativeRobot
{
// Declare variable for the robot drive system
Servo m_servo;
Joystick m_leftStick;
Joystick m_RightStick;
Joystick m_OperatorStick;
}
• Initialization Section:
IterativeDemo(void) : servo(5), leftStick(), rightStick(),
operatorStick()
{
}
• Usage:
m_servo.Set( leftStick.GetZ() );
• How do I keep it all straight?
– Liberal use of variable prefixes can help.
•
•
•
•
•
p_servo, p_leftJoystick; = pointers
i_count = integer (not a pointer)
ip_speed = integer pointer (may never see this).
f_motorPower = floating point variable
M_stuff = member variable (used in many beta
examples)
– This should scare you…..
• p_servo.Set(5);
Death By Pointer
• Java uses pointers under the
covers.
http://javadude.com/articles/passbyvalue.htm
Java makes sure you cannot hurt yourself.
• What happens if you do it wrong?
–
–
–
–
It will compile
The Driver Station will show Ok
It will not run.
“Slow Blinking LED of Doom!”
Death By Pointer
• Startup of program on cRIO
Exception current instruction address: 0x012eb5c8
Machine Status Register: 0x0000b032
Data Access Register: 0x537fb81b
Condition Register: 0x20000048
Data storage interrupt Register: 0x40000000
Task: 0x1307e98 "FRCRobotTask"
0x1307e98 (FRCRobotTask): task 0x1307e98 has had a
failure and has been stopped.
0x1307e98 (FRCRobotTask): fatal kernel task-level
exception!
Welcome to LabVIEW Real-Time 8.5.1
Indicator Mode changed... Slow Blink
• Driver Station shows correctly
• Do not panic over the slow blink of death!
– May be a pointer issue. Do a code review
looking for illegal use of pointers.
p_servo.Set(0.0); // p_ indicates pointer!!!
p_servo->Set(0.0); // correct
Good Boot Up
• Startup of program on cRIO
Resync command from DS...
Resync command from DS...
Enabled!
Booting watchdog!
Indicator Mode changed... Steady On
WPILib was compiled from SVN revision 1330:1345
Spawned FRCRobotTask (0x12f7b70)
RobotIterativeBase Constructor Start
RobotIterativeBase Constructor Finish
IterativeDemo Constructor Started
IterativeDemo Constructor Completed
RobotIterativeBase StartCompetition() Commenced
Teleop_Init() completed
Welcome to LabVIEW Real-Time 8.5.1
Making It All Work
Inputs with Java
// Declaration and Initialization in one step
DriverStation m_Dstation = new
DriverStation.getInstance();
Joystick m_DriverStick = new Joystick(1);
Joystick m_OperatorStick = new Joystick(2);
Analog a_IRSensor = new Analog(0);
// Use
double d_DYAxis = m_DriverStick.getY();
double d_DXAxis = m_DriverStick.getX();
double f_DTrigger = m_DriverStick.getTrigger();
int
i_AutoMode = m_Dstation.getAnalog(1);
Making It All Work
Inputs with C++
// Declaration
DriverStation *p_DStation;
Joystick *p_DriverStick;
Joystick *p_OperatorStick;
int i_AutoMode;
float f_DYAxis, f_DXAxis; f_DTrigger;
// Initialization
p_DriverStick
p_OperatorStick
= new Joystick(1);
= new Joystick(2);
// Use
f_DYAxis = p_DriverStick->GetY();
f_DXAxis = p_DriverStick->GetX();
f_DTrigger = p_DriverStick->GetTrigger();
i_AutoMode = p_Dstation.GetAnalog(1);
Later inputs are fed to outputs.
Making It Work
• Floating point power
ranges
– Percentage of power
• Stated as range is -1.0 to 1.0 with
0.0 being stop.
– Forward and Back are relative
• 2 motors side by side set to (1.0)
are running at full power. But what
direction?
– All relative to the motors position,
gearing, wheels surface top vs. bottom
– Joysticks Y axis
• Backwards to what you might
think?
• Push forward get a value of -1.0.
• Pull back get 1.0
Inputs to Outputs
• Inputs are fed to outputs
– JAVA
m_LeftDriveMotor.set(f_DYaxis)
– C++
p_LeftDriveMotor->Set(f_DYaxis)
• What about the right motor?
Inputs to Outputs
• Right Motor
– opposite side of the robot
– Will normally have to go in
opposite direction to match left
motor.
– JAVA
m_LeftDriveMotor.set(f_DYaxis)
m_RightDriveMotor.set(-f_DYaxis)
– C++
p_LeftDriveMotor->Set(f_DYaxis)
p_RightDriveMotor->Set(-f_DYaxis)
Cooking The Inputs
• Sometimes we “cook” the
inputs
– Joystick gives us percentage of
power. 1.0 to -1.0
float tmp = my_joystick.getY();
– Squaring: multiply input by itself
driverY = tmp * tmp;
– Qubing: multiplying input 3 times
driverY = tmp * tmp * tmp;
• What will this do?
Cooking The Inputs
Discoveries
• Simple math is your friend!
• Joystick “twist” comes in a
GetZ()
– Range 1.0 to -1.0
– What does this do?
my.f_Power = (
(-my.p_LeftDriverStick->GetZ() + 1)
/2);
• Use excel to help figure
out value ranges
Robot Class Types
• SimpleRobot
– A simple robot base class that knows
the standard FRC competition states
(disabled, autonomous, or operator
controlled).
– You can build a simple robot program
off of this by overriding the robotinit(),
disabled(), autonomous() and
operatorControl() methods.
– The startCompetition() method will
calls these methods (sometimes
repeatedly). depending on the state of
the competition.
– Alternatively you can override the
robotMain() method and manage all
aspects of the robot yourself.
• Google: frc2168 FRC robot
Class Types
• Iterative Robot
– Think giant loop that is run 50
times per second.
– System is designed to poll you
different classes for updates or
settings.
– One Method…
•
•
•
•
•
Inputs – Get Driver inputs
Sensors – Read the sensors
Robot Think – Make decisions
RobotBase – Update to the motors
Other Classes
– More to come…
Robot Class Types
• IterativeRobot (JAVA)
– implements a specific type of Robot Program framework,
extending the RobotBase class.
– The IterativeRobot class is intended to be subclassed by
a user creating a robot program. This class is intended to
implement the "old style" default code.
import edu.wpi.first.wpilibj.IterativeRobot;
public class MyRobot extends IterativeRobot {
public void robotInit() { … }
public void disabledInit() { … }
public void disabledPeriodic() { … }
public void autonomousInit() { … }
public void autonomousPeriodic() { … }
public void teleopInit() { … }
public void teleopPeriodic() { … }
}
Robot Class Types
• IterativeRobot (C++)
class My2011Robot : public IterativeRobot
{ // data member declarations …
public:
MyRobot(void) { // constructor }
void RobotInit() { // initialization }
void DisabledInit() { … }
void DisabledContinious() { … }
void DisabledPeriodic() { … }
void AutonomousInit() { … }
void AutonomousContinious () { … }
void AutonomousPeriodic() { … }
void TeleopInit() { … }
void TeleopContinious () { … }
void TeleopPeriodic() { … }
// team-specific methods …
};
START_ROBOT_CLASS(My2011Robot);
Robot Class Types
• IterativeRobot
– FMS tells code which mode be in
at any time, disabled,
autonomous or teleop.
– Code runs in fast loop
• Too fast for sensors
• Continuous routines are called in
every loop, good or bad?
– 50 times per second code drops
into appropriate Periodic
function. (Called polling)
• F-117 only polls 40 times per
second!
– When FMS switches state, init
function is run only once.
– When robot first boots up what
state are we in?
LC Approach
• Variables
– Put all your variables into structure
(C++) or a class (Java).
– Input – All your input variables
– Sensors – All non-driver station
sensors
– Robot - RobotThink make decisions
– Robotbase – all outputs
– Other Classes…
• Major Code sections
– inputs.readInputs()
• Read in and pre-cook DS into
variables
– sensors.GetRobotSensorInputs()
• Read in all non DS sensors. Cook
as necessary
– robot.robotthink()
• Decide what to do. Manipulate
inputs vars to robotBase vars
– robotbase.updateOutputs()
• Update outputs variables
LC Approach
Teleoperated
public void teleopPeriodic() {
inputs.readValues();
sensors.readValues();
robotThink();
robotbase.update();
tower.update(inputs, sensors);
wedge.update(inputs, sensors);
inputs.outputToDashboard();
sensors.outputToDashboard();
robotbase.outputToDashboard();
tower.outputToDashboard();
wedge.outputToDashboard();
auton.outputToDashboard();
}
Autonomous
public void autonomousPeriodic() {
inputs.zeroValues(); //not used in autoon
sensors.readValues();
auton.dispatcher(inputs, sensors, wedge);
robotThink();
robotbase.update();
tower.update(inputs, sensors);
wedge.update(inputs, sensors);
inputs.outputToDashboard();
sensors.outputToDashboard();
auton.outputToDashboard();
robotbase.outputToDashboard();
tower.outputToDashboard();
wedge.outputToDashboard();
}
Look At Other’s Code
• Google: frc399 james-bot
– Many classes
– Autonomous
Batch Files
• Use batch files to quickly
change computer ethernet
connection.
– You must know what your
connection is called.
netsh Command
• netsh – used to set network
parameters
Command: netsh /? To see
parameters
• Example: Set interface to Crio
@echo off
echo Setting the Ip to CRIO network 10.2.72.6.
netsh interface ip set address name="Local Area Connection"
static 10.2.72.6 255.0.0.0
pause
Note: In the example above the netsh
command is on the same line!
Many batches
• Set to camera
netsh interface ip set address name="Local Area Connection"
static 10.2.72.3 255.0.0.0
• Set to DHCP
netsh interface ip set address name="Local Area Connection"
dhcp
Note: All the above commands
are set on the same batch line.
Final Thought
Unlike baseball crying is allowed in
software development… but …
…when you’re done, get back and
make it work!