Computer Science
Gilmour AcademyLancerTech
  • Our Curriculum and Department
  • Intro to Programming
    • 1: Parts of a Computer
    • 2: Parts of Python
    • 3: DRY Turtle
    • 4: Turtle Design App
    • Wordle with Turtles
    • 5: Interactive Turtles
    • OLD 5: Replit, GitHub, and repositories (Oh my!)
    • 6: Raspberry Pi / GoPiGo
    • 7: Kivy
  • Intro to Web Design
    • 1: Internet?
    • 2: Websites?
    • 3: Bootstrap Template
    • 4: Graphics and Branding
    • 5: Collaboration
    • 6: Advanced Editing
    • Publish Static HTML
  • AP Computer Science
    • 1: Logic & Instances
    • 2: How Java Works
    • 3: Data Types & Flow
    • 4: Strings
    • 5: Objects & References
    • 6: Inheritance & Algorithms
    • 7: Data Structures
    • 8: Sorting
    • 9: Review
    • Data Science
  • Web App Dev
    • 1: Core Concepts
    • 2: MVT Pattern
    • 3: Hello Flask
    • 4: Install Flaskinni
    • 5: Tour Flaskinni
    • 6: Visualize Your App
    • 7: Theme & Blueprint
    • 8: Standup Your DB
    • 9: Advanced Topics
    • 10: Deployment
  • 2D Game Design
    • Class Overview
    • Gamemaker Studio 2 and Github Setup
    • Game 1: Bouncing Ball
    • Turning in your games
    • Game 2: Maze
    • Game 3: Ping Pong
    • Game 4: Breakout
    • Game 5: Tank Battle
    • Game 6 Highlights
    • DO NOT DO:
    • Game 7: Final Project
    • Publish to Opera
    • FAQ
  • 3D Game Design
    • 1: Class Overview
    • 2: Installation
    • 3: Exploring the Unity UI
    • Game 1: Rolling Ball
    • Game 2: Tanks
    • Game 3: Third Person Platformer
    • Game 4: Final project
    • FAQs
    • OLD: Distance Learning Setup
    • OLD: GIT
  • 3D Modeling & Fabrication
    • Installation
    • Fusion 360 Interface and Sketch Modeling
    • Primitive Modeling
    • Patterns
    • Appearances and Rendering
    • Building Community Gallery Page 2023
    • Parametric Modeling
    • 3D Printing Concerns
    • Assemblies and Mechanical Design
    • Laser Cutting
    • Sculpt Tools
    • Milling Concerns
  • Robotics 7
    • Software Installation
    • Python basics (trinket.io)
    • Python Turtle
    • Programming for the Ev3
    • Setting up for clarity
  • Robotics 8
    • Replit
    • Python review
    • Kivy Basics
    • Calculator
  • Competitive Robotics
    • Hardware Team
      • CAD Examples
      • Elevators
    • Software Team
      • Command Pattern
      • Example Command
      • Subsystem
      • Running Your Code
      • Under the Hood
      • RoadRunner
      • Vision Processing
  • Archives
    • Adiletta Archives
      • Old Web
        • Ex: WordPress CMS
      • ItP
        • OLD: Parts of Python (old -- Mr. A)
        • OLD: 5: Raspberry Pi
        • OLD: 6: Deploying Code
        • OLD 7: Nav Algorithm
    • Vanek Archives
      • OLD Robotics 8
        • OLD: End of Class Project
      • OLD Competitive Robotics
        • Untitled
        • Webots Videos
      • OLD Robotics 7
        • Trinket Introduction
        • Lists: x/y position
        • Functions: Math program
        • Lists: Grocery List
        • Study Guide Program
        • Tic Tac Toe Game
        • Dice Roller Program
        • Visualization
        • Dice Roller + Visualization
        • OpenSCAD: Installation
        • OpenSCAD: Command Sheet and Intro
        • OpenSCAD: Difference
        • OpenSCAD: Variables
        • OpenSCAD: Union
        • OpenSCAD: For Loops
        • OpenSCAD: Final Project
      • OLD Art I - Blender Sculpting
        • Class Overview
        • Installation
        • Lesson 1 - Tools
        • Lesson 2 - Detail
        • Lesson 3 - Base Mesh: Metaballs
        • Lesson 4: Converting metaballs and adding detail
        • Lesson 5: Masking, Hiding, and Working with Multiple Objects
        • Lesson 6: Joining Objects & Basing
        • Lesson 7: Sculpture Painting
        • Student Gallery: Animal Sculpts
        • Lesson 8: 3D Compositon
        • Lesson 9: The Project - Putting it all together
        • Lesson 10: Developing the image further
        • Lesson 11: Layout the base metaball mesh.
        • Lesson 12: Final Detail
        • Lesson 13: Basing and Painting
        • Final Project Gallery
      • OLD Fab
        • OLD Building Community Project Gallery
        • Copy of Building Community Project Gallery
        • old Building Community Project Gallery
      • OLD: Turtle Design App
      • OLD Arduino Robotics 8
        • Arduino Basic Commands Cheat Sheet
        • Logging into Tinkercad
        • Arduino, Circuits, LEDs and Resistors
        • Functions and Variables
        • Serial Monitor
        • Buttons and Interrupts
        • Traffic Light Project
        • Potentiometers + Servos
        • Piezo Buzzer and Tone();
        • Sequencer Project
        • Arrays and for loops
        • Extra Loop Practice
        • Refining the Sequencer
        • Servos
        • Ultrasonic Sensors
        • Final Project
Powered by GitBook
On this page
  • Robot.java
  • Beyond isDisabled: Expanding State Variables
  • CommandOpMode
  • Lifecycle Integration
  • Reset

Was this helpful?

Export as PDF
  1. Competitive Robotics
  2. Software Team

Under the Hood

The files that drive FTCLib

PreviousRunning Your CodeNextRoadRunner

Last updated 12 months ago

Was this helpful?

Before looking under the hood of our code, programmers should study the Command pattern's goals of organized, non-blocking code. We've done that ✅. You don't need to go past this point. We hardly ever need to touch these files. Programmers can contribute to a team by knowing how Command and Subsystem work together and how to run their code. Proceeding on means you want the next level. You're comfortable and open-minded about how this all works.

Robot.java

The secret to understanding how we turned FTC's code into a Command pattern is how the following two files connect. They sit in our utils folder, working their magic--we may never need to touch them. Let's start with Robot.java.

public abstract class Robot {

    public static boolean isDisabled = false;

    /**
     * Cancels all previous commands
     */
    public void reset() {
        CommandScheduler.getInstance().reset();
    }

    /**
     * Runs the {@link CommandScheduler} instance
     */
    public void run() {
        CommandScheduler.getInstance().run();
    }

    /**
     * Schedules {@link com.arcrobotics.ftclib.command.Command} objects to the scheduler
     */
    public void schedule(Command... commands) {
        CommandScheduler.getInstance().schedule(commands);
    }

    /**
     * Registers {@link com.arcrobotics.ftclib.command.Subsystem} objects to the scheduler
     */
    public void register(Subsystem... subsystems) {
        CommandScheduler.getInstance().registerSubsystem(subsystems);
    }

    public static void disable() {
        isDisabled = true;
    }

    public static void enable() {
        isDisabled = false;
    }

}

This file acts as an invisible layer, providing essential functionalities:

  • Shared State: The isDisabled static variable is a central flag accessible throughout your code, indicating robot state (enabled/disabled). The disable() and enable() methods allow external control over the robot's state during transitions between autonomous and teleop periods.

  • Command Control Center: Methods like reset(), run(), schedule(), and register() grant access to the CommandScheduler, the mastermind behind command execution and resource management. Think of it as the conductor of your robot's actions.

Beyond isDisabled: Expanding State Variables

Remember, the way the isDisabled variable controls state is not how we need to track our robot's current status. It doesn't need a static variable; we'll have easy access to the instance of our robot. We're not restricted to booleans. We'll use custom state variables of all sorts--here's an example that uses enums to represent various robot conditions:

public class MyRobot extends Robot {
    // ... other code
    public enum AprilTagToAlign {
        LEFT, CENTER, RIGHT, NONE
    }
    public AprilTagToAlign target;

    // ... any other subsystem will have access to check which target we want
}

CommandOpMode

Here's the most straightforward connection point between Command and FTC. This file is our translator.

public abstract class CommandOpMode extends LinearOpMode {
    /**
     * Cancels all previous commands
     */
    public void reset() {
        CommandScheduler.getInstance().reset();
    }

    /**
     * Runs the {@link CommandScheduler} instance
     */
    public void run() {
        CommandScheduler.getInstance().run();
    }

    /**
     * Schedules {@link com.arcrobotics.ftclib.command.Command} objects to the scheduler
     */
    public void schedule(Command... commands) {
        CommandScheduler.getInstance().schedule(commands);
    }

    /**
     * Registers {@link com.arcrobotics.ftclib.command.Subsystem} objects to the scheduler
     */
    public void register(Subsystem... subsystems) {
        CommandScheduler.getInstance().registerSubsystem(subsystems);
    }

    @Override
    public void runOpMode() throws InterruptedException {
        telemetry = new MultipleTelemetry(telemetry, FtcDashboard.getInstance().getTelemetry());
        initialize();

        waitForStart();

        // run the scheduler
        while (!isStopRequested() && opModeIsActive()) {
            run();
            telemetry.addData("hi", "hi");
            telemetry.update();
        }
        reset();
    }

    public abstract void initialize();

    public static void disable() {
        Robot.disable();
    }

    public static void enable() {
        Robot.enable();
    }

}

Lifecycle Integration

CommandOpMode runs LinearOpMode's critical method runOpMode()method. That's it 🤯. Sure, we can also post telemetry updates, but the real essential bit is just that stupid run() call. That keeps our CommandScheduler working while satisfying the requirements for FTC gameplay.

Reset

The reset() method within both Robot and CommandOpMode plays a crucial role in managing Commands during various FTC gameplay scenarios. Here are some practical examples of when you might utilize it:

1. Autonomous Period Transitions:

  • Switching Strategies: During autonomous, imagine your robot first performs a pre-determined path using a pre-scheduled set of Commands. If external sensors detect an unexpected obstacle, you can call reset() in Robot or CommandOpMode to clear all running Commands and initiate a new set of Commands for obstacle avoidance or adaptation.

  • Recovering from Errors: If a sensor reading is deemed unreliable or a Command encounters an error, resetting can clear the current action and allow you to initiate a new Command for recovery or safe shutdown.

2. Teleop Period:

  • Button-Triggered Resets: Consider a button press on your gamepad that triggers reset() in CommandOpMode. This could be used to:

    • Cancel an ongoing movement Command if the driver wants to stop abruptly.

    • Reset arm or claw positions to known starting points for precise manipulation.

    • Restart a specific Command sequence for a repeated action.

3. Testing and Debugging:

  • Isolating Command Behavior: During testing, you might use reset() after each test run to isolate specific Commands and verify their functionality without interference from previous actions.

  • Reproducing Issues: If your robot exhibits unexpected behavior, strategically placing reset() calls can help reproduce the issue for easier debugging and troubleshooting.