Introducing the CCRE!

Team 1540, the Flaming Chickens, is proud to introduce the CCRE: the Common Chicken Runtime Engine. The CCRE, a programming framework, was created to make it easy to write maintainable code for an FRC robot – after too many years of badly structured code, we wanted to do something better. To test it out before build season, we used it on all four of our BunnyBots, and none of them had any major issues.

Here’s an example of how small the CCRE can make something simple like tank drive code with ramping:

 public class Test extends SimpleCore {
       protected void createSimpleControl() {
         DriverImpls.createSynchTankDriver(duringTeleop,
               joystick1.getYChannel(),
               joystick2.getYChannel(),
               makeTalonMotor(1, MOTOR_FORWARD, 0.1f),
               makeTalonMotor(2, MOTOR_REVERSE, 0.1f));
      }
}

The CCRE’s central Git repository can be found at
https://bitbucket.org/col6y/common-chicken-runtime-engine. If you want to give it a try (and we hope you do!), go there, click on source, and then click on DOCUMENTATION.MD to get started.

The CCRE is currently versatile enough for use on almost any competition robot. If there’s something missing that you think should be there, suggest it!

The CCRE has a fully-functional emulator so that almost any robot code can be tested without a real robot.

The CCRE was designed and developed by Team 1540’s student software manager, Colby Skeggs, and is primarily maintained by him as well. You can contact him using this thread or at skeggsc >at< catlin dot< edu if you need help using the CCRE. Team 1540 does not guarantee support for the CCRE, but he’ll do his best to help you out if you have issues.

A side note: The CCRE has support for running most of its infrastructure on standard computers and has hardware support for the BeagleBone Black.

Thanks for reading, and we hope you’ll find it to be easy to use.

Best of luck in build season!

Team 1540

PS if you do end up using it, please let us know!

Looks interesting. How exactly is everything run? Is there an easy way to find documentation?

This link should explain almost everything. A very comprehensive and impressive library for coding a robot using Java. Well done.

Interesting and should be helpful to some teams! Thanks for the share guys!

I’m curious: in what ways do you feel your library structures code in a manner that is superior to alternatives like the Command-Based system from WPILibJ?

Also: Is there a top-level 30,000 ft view executive summary document of the most important features of the framework that set it apart from the other frameworks?

Hi! I’m the primary designer, so I’m probably the best person to answer this.

The best summary document of the CCRE would be the DOCUMENTATION.MD file linked to above.

I don’t have a good enough understanding of Command-Based in order to thoroughly compare the two, but I can point out the main helpful features of the CCRE.

First of all, The CCRE is designed to allow for very easy separation of concerns in the main robot code - the problem in our IterativeRobot code from last year, without the CCRE, was that while we did have multiple modules, there was no easy way to pull anything apart within files, meaning that you had to constantly search and reread the file to understand anything.

Code written with the CCRE, as opposed to code written for IterativeRobot or SimpleRobot, is primarily ran a single time, and pulls together various components (motors, axes, etc) and tells handlers to update them each cycle. This means that a small section of code can, for example, handle shifting and nothing else, and not be interconnected with anything else:


private void setupShifting() {
	BooleanStatus shifter = new BooleanStatus(makeSolenoid(2));
	shifter.setFalseWhen(startedTeleop);
	shifter.setTrueWhen(joystick1.getButtonSource(3));
	shifter.setFalseWhen(joystick1.getButtonSource(1));
}

Since you know for a fact that nothing else could mess with this section of code, by looking at this piece of code you can very quickly determine exactly how EVERYTHING relating to shifting is done.

The second main advantage is that channels are interchangeable.
The CCRE has a handful of interfaces: BooleanOutput, FloatOutput, BooleanInputPoll, FloatInputPoll, BooleanInputProducer, and FloatInputProducer, as well as FloatInput and BooleanInput which are really just combinations of a InputPoll and InputProducer.
Any status data sent anywhere in the CCRE uses one of these, and therefore they are all interchangeable.
For example, there is no “Talon” class that the user interacts with. There is no “Solenoid” class either.
When the user gets access to a Talon motor, they use makeTalonMotor(PORT_ID, MOTOR_DIRECTION, RAMPING_RATE) which gives them a FloatOutput.
This is exactly the same as you could get for a Jaguar, for example.
But then, you can plug any FloatOutput into many of the builtin Mixing methods. Mixing.negate could be ran on any FloatOutput to negate all values sent through it - Mixing.deadzone can be used similarly. And Mixing.limit. And ramping.
The point of that means that you can have generic utility methods to remix anything without special-casing.
So you can change a single line to switch from using a Solenoid to run an actuator:


BooleanOutput actuator = makeSolenoid(1);

To using a servo instead:


BooleanOutput actuator = Mixing.select(makeServo(1, 0, 180), 45, 135);

In addition, the CCRE has a wide variety of prewritten modules that provide useful functionality, but would take too much effort to reimplement during every build season:

  • A logging subsystem - Send messages to the driver station computer, standard console, and anywhere else.
  • A communication subsystem named Cluck - sharing of channels across the network between the robot and driver station (and logging targets and output streams)
  • Concurrency helpers - More robust thread handling, non-synchronizing concurrent lists.
  • Channel remixing tools - A lot
    of these. - Constant tuning - Change constants from the driver station, save them on the robot.
  • A imperative autonomous mode subsystem named Instinct - Used to write autonomous code sequentially. (See below)
  • Phidget controller interfacing on the driver station - Team 1540 uses these for our copilot station.
  • A minimized collections framework - similar to the Java SE collections framework.
  • A robot emulator for testing - (See below)

As well, the CCRE has an emulator that can be launched directly from NetBeans (right click on the project - hit Test) that allows you to try out your code before putting it on the robot.
This doesn’t do anything as cool as put a virtual robot in a 3D field, but it does let you test how the robot gets controlled:

It can display readouts/inputs for everything that the CCRE can interact with. (There’s an extended IO combo box for things like encoders and gyros that pops up other windows.)

As a final useful feature, it allows you to write your autonomous modes as imperative code, instead of using state machines, without pausing the rest of the code:


new InstinctModule() {
	protected void autonomousMain() throws AutonomousModeOverException, InterruptedException {
		leftOut.writeValue(1);
		rightOut.writeValue(1);
		waitForTime(5000);
		leftOut.writeValue(0);
		rightOut.writeValue(0);
	}
}.register(this);

In our code in past years, we had to write finite state machines for autonomous modes, and we haven’t had any luck making these easily understandable or maintainable, which is why imperatively sequenced autonomous is an important feature to us.

TL;DR: Separation of concerns! Interchangeable channels! Prewritten modules! An emulator! Imperative autonomous!

Figured I’d give this a bump. If there’s going to be an endgame sprung on us, having a simple software framework will be a huge advantage.

NEWS! Please at least skim the headlines of these if you’re interested in the CCRE!

>> OUR EXPERIENCES WITH THE CCRE

Recently, our team completed the entire season with the CCRE.
In the season, there was precisely ONE robot-breaking issue with the CCRE, which was fixed in the next twenty minutes and now there are no known bugs in the CCRE. (There are probably plenty, I just don’t know about them. If yuo find any, report them!)

Using the CCRE, we could count the number of matches where there was a software error on one hand. When the mechanics and the control system worked, the software almost always worked too.
This is much better for us than in some previous years, when we’d lose many matches due to software bugs.

With this season, we now have seven robots using the CCRE - our prototype and competition robots this year, four different bunnybots, and our InvenTeams robot.

>> WORLD CHAMPIONSHIP AWARD

As well, we were lucky enough to get to Worlds, where the CCRE won the Innovation in Control award! Specifically, the judges referenced the briefly wide variety of useful features in the system and the new advanced and automatic error-recovery features, which I should make a post about shortly.

>> LIBRARY CHANGES

If you’re intending to try out the CCRE, keep in mind that I’m currently working on some major changes to the core libraries, so your code may spontaneously break and need fixes in the near future.
I will post about these around the time that I push the changes to the core repository.

>> WPILIB

We are currently in talks with Brad Miller, the person in charge of WPILib, and there is a slight chance that some segments of the CCRE will make it into WPILib itself! Stay tuned.

>> 2015 CONTROL SYSTEM

We are doing our best to be a beta team for the 2015 control system, so we’ll be upgrading the CCRE to work on both versions - you’ll be able to use the CCRE to write code for either system, and so you won’t have to worry about having to write different code for the cRIO versus the roboRIO if you have multiple laying around!
Now, there will still be the Java 1.3 versus Java 8 difference, but we can’t do much to help with that, sorry.

This seems really cool. Good job.

Hello, everyone who is interested!

I’ve just pushed what should be the last update to the CCRE that breaks backwards compatibility - we figured that we want to make all of our changes that break backwards compatibility before this gets much use by other teams, which is now.
So if you have code right now using the CCRE, it’s probably now broken. Sorry. See below for a list of the major changes so that it will be easy to fix it.
On the flip-side, it’s now also very good! These changes improve the maintainability of the CCRE by a large amount, and make a lot of things easier to use. As well, it means that we will (hopefully) not have to make any more changes that break backwards compatibility in the near future!

I’ve also set the STABLE branch to this point, and it will remain at this point for the near future, although important bugfixes will still be added to this branch. If you don’t trust the changes that are often pushed, the STABLE branch might be right for you as it changes very infrequently!

I will be working on upgrading the CCRE’s documentation next, as it is several months out of date, so if you’ve experienced any issues with this, they should hopefully be resolved shortly. (If you have any recommendations for how to document this well, please let me know!)

Changes in this final refactoring sprint:

  • EventProducer, Event, and EventConsumer renamed to the more consistent EventInput, EventStatus, and EventOutput.
  • InputProducers are removed, and the functionality is merged into Inputs. This is because it makes little sense to have an Input without a get() method.
  • BooleanOutputs and FloatOutputs now implement set() instead of writeValue().
  • BooleanInputs, BooleanInputPolls, FloatInputs, and FloatInputPolls now implement get() instead of readValue().
  • Inputs now use send() and unsend() instead of addListener/addTarget and removeListener/removeTarget. These all now return void, instead of random ones returning booleans instead.
  • CluckGlobals is renamed to Cluck.
  • CluckNode.publish and CluckNode.subscribe* are now moved to static methods in CluckPublisher, with proxy methods in Cluck. (So instead of CluckGlobals.node.publish or CluckGlobals.getNode().publish, you now use Cluck.publish.)
  • Most of the methods in Mixing are now split into BooleanMixing, FloatMixing, and EventMixing, corresponding to the main focus of the method.
  • Igneous programs now interface with static methods on the Igneous class instead of protected methods inherited from IgneousCore. (Same with fields.)
  • Igneous programs are now initialized in setupRobot() instead of create*() methods, and may now also interface with hardware BEFORE this method is called, if necessary.
  • InstinctRegistrars are removed. Now use Igneous.registerAutonomous(InstinctModule) instead of InstinctModule.register(this) in your Igneous applications.
  • StorageSegments now save in a text-based instead of binary-packed format. This means that any currently-saved values will be lost!
  • Some Igneous event names are changed - startTele instead of startedTeleop, for example. This, as a whole, make the system more regular.
  • Events are moved to the ccre.channel package.
  • ISimpleJoystick is merged into IDispatchJoystick and now called IJoystick for simplicity.
  • FloatTuners are now removed, as their purpose was vestigal.
  • Igneous programs may now implement IgneousApplication instead of extending IgneousCore (although they may continue to do so.)
  • MultiTargetLogger is now removed, as it no longer serves a purpose.
  • Network.Provider is now moved outside of Network and called NetworkProvider.
  • StorageSegments are now implemented once in the CCRE instead of once per platform.
  • PhidgetReader now uses static methods instead of fields.
  • The entire PeripheralTree subsystem has been removed, as its purpose proved irrelevant to the CCRE and bloated the system, besides being completely untested.
  • Correspondingly, the CEL interpreter has been removed. It was never finished, so this shouldn’t impact anyone.
  • Text-based loggers no longer use abbreviations of LogLevel names, but rather the full names, for reasons of clarity.
  • Other minor changes have been made, but they were deemed unimportant enough to be left off of this list.

Hello… again!

While my previous post covered the major upgrades in the CCRE’s codebase, we’ve also upgraded our documentation!

We now have a series of tutorials (eleven so far, out of an estimated 20-25ish) which cover getting started using the CCRE by using the emulator.
The first few tutorials cover everything needed to program a basic robot, including driving, actuators, shifting, and autonomous! Because of the emulator, you can now learn how to program FRC robots without needing to get access to a real one! Also you don’t have to worry about accidentally unplugging a PWM cable when using the emulator, so there’s less standing in your way to learning!

Current list of tutorials:

  1. Setting up the CCRE
  2. Your first Igneous project
  3. Making your robot drive
  4. Making your robot shift and other pneumatics
  5. Organizing your code
  6. Basic Autonomous
  7. The Logging Framework
  8. Control Structures - ExpirationTimer, PauseTimer, MultipleSourceBooleanController, Ticker
  9. The CCRE Collections Framework
  10. The Cluck Communication System - Basic Usage
  11. Constant Tuning

We’re currently posting new tutorials at an average rate of about one tutorial per day, so this list will be very quickly out of date. Check out our main documentation page to see the current listing of tutorials.

As usual, if you have any questions, either post them here on this thread or send me an email at skeggsc [at] catlin [dot] edu.

Would you like a complete example of robot code written using the CCRE?

Look no further! We’ve released our full 2014 robot code.

It demonstrates the majority of the CCRE’s features, although it’s a little bit out-of-date in how it allocates devices in how it works - it still allocates all peripherals from the main class like how it previously had to be done, but now this can be done in each module via the Igneous static methods and that would be much better style.

(We now have fourteen tutorials up! This is less than we’d hoped to have up by now because of schoolwork and getting the robot code ready to post.)