From 1083e3747de7e1fe95c8e69aca1a05e229b4994b Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Fri, 28 Jun 2019 15:51:35 -0500 Subject: [PATCH 01/10] Began commenting and implementing HyperComponents. [General] - Added TODO list to README.md - Added Kauai Labs dependency to build.gradle. [SuperComponents] - Moved to subsystems.supercomponents package. - SuperTalon and SuperVictor now have proper commenting. [HyperComponents] - HyperComponents added, essentially wrappers for FRC objects. - HyperTalon and HyperVictor fully implemented. [Util] - Fully commented MotorUtils SuperInterface. - Renamed Direction to MoveDirection to avoid conflict. --- .vscode/settings.json | 3 + README.md | 20 ++ build.gradle | 6 + .../subsystem/components/SuperTalon.java | 76 ------- .../subsystem/components/SuperVictor.java | 70 ------ .../subsystem/hypercomponents/HyperTalon.java | 72 ++++++ .../hypercomponents/HyperVictor.java | 72 ++++++ .../SuperCompressor.java | 2 +- .../SuperDigitalInput.java | 2 +- .../SuperEncoder.java | 2 +- .../SuperPDP.java | 2 +- .../SuperSolenoid.java | 2 +- .../subsystem/supercomponents/SuperTalon.java | 98 ++++++++ .../SuperUltrasonic.java | 2 +- .../supercomponents/SuperVictor.java | 94 ++++++++ .../org/usfirst/lib6647/util/Direction.java | 8 - .../org/usfirst/lib6647/util/MotorUtils.java | 213 ++++++++++++------ .../usfirst/lib6647/util/MoveDirection.java | 11 + 18 files changed, 529 insertions(+), 226 deletions(-) create mode 100644 .vscode/settings.json delete mode 100644 src/main/java/org/usfirst/lib6647/subsystem/components/SuperTalon.java delete mode 100644 src/main/java/org/usfirst/lib6647/subsystem/components/SuperVictor.java create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperCompressor.java (97%) rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperDigitalInput.java (97%) rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperEncoder.java (97%) rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperPDP.java (97%) rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperSolenoid.java (97%) create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java rename src/main/java/org/usfirst/lib6647/subsystem/{components => supercomponents}/SuperUltrasonic.java (97%) create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java delete mode 100644 src/main/java/org/usfirst/lib6647/util/Direction.java create mode 100644 src/main/java/org/usfirst/lib6647/util/MoveDirection.java diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..de2a843 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,3 @@ +{ + "java.configuration.updateBuildConfiguration": "automatic" +} \ No newline at end of file diff --git a/README.md b/README.md index 6525af3..af8bb0b 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,22 @@ # lib6647 Team 6647's library to allow JSON-oriented object building and initialization. + +## TODO + +- [ ] Implement every HyperComponent Wrapper. + - [ ] HyperAHRS + - [ ] HyperAnalogPotentiometer + - [ ] HyperCompressor + - [ ] HyperDigitalInput + - [ ] HyperEncoder + - [ ] HyperPDP + - [ ] HyperSolenoid + - [X] HyperTalon + - [ ] HyperUltrasonic + - [X] HyperVictor +- [ ] Implement missing SuperComponents. + - [ ] SuperAHRS + - [ ] SuperAnalogPotentiometer +- [ ] Add more flexibility and configuration options. +- [ ] Document everything properly. +- [ ] Blame mechanical. \ No newline at end of file diff --git a/build.gradle b/build.gradle index 006a0c0..f9c27a2 100644 --- a/build.gradle +++ b/build.gradle @@ -21,6 +21,9 @@ repositories { maven { url "http://devsite.ctr-electronics.com/maven/release" } + maven { + url "https://repo1.maven.org/maven2/" + } } dependencies { @@ -46,6 +49,9 @@ dependencies { //Phoenix dependencies. compile group: 'com.ctre.phoenix', name: 'api-java', version: '5.14.1' compile group: 'com.ctre.phoenix', name: 'wpiapi-java', version: '5.14.1' + + //Kauai Labs dependencies. + compile group: 'com.kauailabs.navx.frc', name: 'navx-java', version: '3.1.367' } // Setting up my Jar File. In this case, adding all libraries into the main jar ('fat jar') diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/components/SuperTalon.java deleted file mode 100644 index ca37d64..0000000 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperTalon.java +++ /dev/null @@ -1,76 +0,0 @@ -package org.usfirst.lib6647.subsystem.components; - -import java.util.Arrays; -import java.util.HashMap; - -import com.ctre.phoenix.motorcontrol.can.WPI_TalonSRX; - -import org.json.simple.JSONArray; -import org.json.simple.JSONObject; -import org.usfirst.lib6647.util.MotorUtils; - -import edu.wpi.first.wpilibj.DriverStation; - -/** - * Interface to allow Talon initialization via JSON file. Subsystem needs to - * extend SuperSubsystem. - */ -public interface SuperTalon extends MotorUtils { - /** - * HashMap storing the SuperSubsystem's Talons. - */ - public HashMap talons = new HashMap(); - - /** - * Method to initialize Talons declared in JSON file, and add them to the - * HashMap using its name as its key. ALWAYS declare and initialize masters - * before followers in the JSON file. - * - * @param robotMap - * @param subsystemName - */ - default void initTalons(JSONObject robotMap, String subsystemName) { - try { - JSONArray talonArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("talons"); - Arrays.stream(talonArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - WPI_TalonSRX talon = new WPI_TalonSRX(Integer.parseInt(json.get("port").toString())); - - if (json.containsKey("inverted")) - setInverted(json, talon); - - if (json.containsKey("neutralMode")) - setNeutralMode(json, talon); - - if (json.containsKey("loopRamp")) - setLoopRamp(json, talon); - - if (json.containsKey("sensor")) - setSensors(json, talon); - - if (json.containsKey("pid")) - setPIDValues(json, talon); - - talons.put(json.get("name").toString(), talon); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); - System.exit(1); - } finally { - json.clear(); - } - }); - talonArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), false); - System.out - .println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); - System.exit(1); - } - } -} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/components/SuperVictor.java deleted file mode 100644 index 05a5d0c..0000000 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperVictor.java +++ /dev/null @@ -1,70 +0,0 @@ -package org.usfirst.lib6647.subsystem.components; - -import java.util.Arrays; -import java.util.HashMap; - -import com.ctre.phoenix.motorcontrol.can.WPI_VictorSPX; - -import org.json.simple.JSONArray; -import org.json.simple.JSONObject; -import org.usfirst.lib6647.util.MotorUtils; - -import edu.wpi.first.wpilibj.DriverStation; - -/** - * Interface to allow Victor initialization via JSON file. Subsystem needs to - * extend SuperSubsystem. - */ -public interface SuperVictor extends MotorUtils { - /** - * HashMap storing the SuperSubsystem's Victors. - */ - public HashMap victors = new HashMap(); - - /** - * Method to initialize Victors declared in JSON file, and add them to the - * HashMap using its name as its key. ALWAYS declare and initialize masters - * before followers! - * - * @param robotMap - * @param subsystemName - */ - default void initVictors(JSONObject robotMap, String subsystemName) { - try { - JSONArray victorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("victors"); - Arrays.stream(victorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - WPI_VictorSPX victor = new WPI_VictorSPX(Integer.parseInt(json.get("port").toString())); - - if (json.containsKey("inverted")) - setInverted(json, victor); - - if (json.containsKey("neutralMode")) - setNeutralMode(json, victor); - - if (json.containsKey("loopRamp")) - setLoopRamp(json, victor); - - victors.put(json.get("name").toString(), victor); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); - System.exit(1); - } finally { - json.clear(); - } - }); - victorArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); - System.exit(1); - } - } -} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java new file mode 100644 index 0000000..bc56285 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java @@ -0,0 +1,72 @@ +package org.usfirst.lib6647.subsystem.hypercomponents; + +import com.ctre.phoenix.motorcontrol.ControlMode; +import com.ctre.phoenix.motorcontrol.can.WPI_TalonSRX; + +/** + * HyperComponent for {@link WPI_TalonSRX}. + */ +public class HyperTalon extends WPI_TalonSRX { + + /** + * Limits how fast the Talon can go if using {@link #setTalonWithRamp(double)} + * or {@link #setTalon(double, boolean)} if true. + */ + private double limiter = 1; + + /** + * Wrapper for {@link WPI_TalonSRX}. + * + * @param port + */ + public HyperTalon(int port) { + super(port); + } + + /** + * Sets {@link #limiter} for Talon speed. + */ + public void setLimiter(double limiter) { + this.limiter = limiter; + } + + /** + * Raises {@link #limiter} by a given amount. + * + * @param amount + */ + public void raiseLimiter(double amount) { + limiter += amount; + } + + /** + * Sets {@link HyperTalon} to a given speed, in {@link ControlMode#PercentOutput + * PercentOutput}. + * + * @param speed + * @param limited + */ + public void setTalon(double speed, boolean limited) { + if (speed >= limiter && limited) + super.set(ControlMode.PercentOutput, limiter); + else + super.set(ControlMode.PercentOutput, speed); + } + + /** + * Sets {@link HyperTalon} to a given amount multiplied by {@link #limiter}, in + * {@link ControlMode#PercentOutput PercentOutput}. + * + * @param speed + */ + public void setTalonWithRamp(double speed) { + super.set(ControlMode.PercentOutput, speed * limiter); + } + + /** + * Stops {@link HyperTalon} dead in its tracks. + */ + public void stopTalon() { + setTalon(0, false); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java new file mode 100644 index 0000000..0d58126 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java @@ -0,0 +1,72 @@ +package org.usfirst.lib6647.subsystem.hypercomponents; + +import com.ctre.phoenix.motorcontrol.ControlMode; +import com.ctre.phoenix.motorcontrol.can.WPI_VictorSPX; + +/** + * HyperComponent for {@link WPI_VictorSPX}. + */ +public class HyperVictor extends WPI_VictorSPX { + + /** + * Limits how fast the Victor can go if using {@link #setVictorWithRamp(double)} + * or {@link #setVictor(double, boolean)} if true. + */ + private double limiter = 1; + + /** + * Wrapper for {@link WPI_VictorSPX}. + * + * @param port + */ + public HyperVictor(int port) { + super(port); + } + + /** + * Sets {@link #limiter limiter} for Victor speed. + */ + public void setLimiter(double limiter) { + this.limiter = limiter; + } + + /** + * Raises {@link #limiter} by a given amount. + * + * @param amount + */ + public void raiseLimiter(double amount) { + limiter += amount; + } + + /** + * Sets {@link HyperVictor} to a given speed, in + * {@link ControlMode#PercentOutput PercentOutput}. + * + * @param speed + * @param limited + */ + public void setVictor(double speed, boolean limited) { + if (speed >= limiter && limited) + super.set(ControlMode.PercentOutput, limiter); + else + super.set(ControlMode.PercentOutput, speed); + } + + /** + * Sets {@link HyperVictor} to a given amount multiplied by {@link #limiter}, in + * {@link ControlMode#PercentOutput PercentOutput}. + * + * @param speed + */ + public void setVictorWithRamp(double speed) { + super.set(ControlMode.PercentOutput, speed * limiter); + } + + /** + * Stops {@link HyperVictor} dead in its tracks. + */ + public void stopVictor() { + setVictor(0, false); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperCompressor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperCompressor.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java index 2a473e7..24e46a7 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperCompressor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperDigitalInput.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperDigitalInput.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java index f7906e7..db994f5 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperDigitalInput.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperEncoder.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperEncoder.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java index a9ef080..997012d 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperEncoder.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperPDP.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperPDP.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java index 5f50f91..6512e5c 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperPDP.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperSolenoid.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java index 8a2c637..3c64e76 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperSolenoid.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java new file mode 100644 index 0000000..d23ab42 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java @@ -0,0 +1,98 @@ +package org.usfirst.lib6647.subsystem.supercomponents; + +import java.util.Arrays; +import java.util.HashMap; + +import org.json.simple.JSONArray; +import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; +import org.usfirst.lib6647.util.MotorUtils; + +import edu.wpi.first.wpilibj.DriverStation; + +/** + * Interface to allow {@link HyperTalon} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link HyperTalon + * HyperTalons} declared in {@link SuperSubsystem#robotMap robotMap}. + */ +public interface SuperTalon extends MotorUtils { + /** + * HashMap storing the {@link SuperSubsystem}'s {@link HyperTalon HyperTalons}. + */ + public HashMap talons = new HashMap(); + + /** + * Method to initialize {@link HyperTalon HyperTalons} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #talons} HashMap using its declared name as its key. + * + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} + * + * @Note ALWAYS declare and initialize masters before followers! + */ + default void initTalons(JSONObject robotMap, String subsystemName) { + try { + // Create a JSONArray out of the declared objects. + JSONArray talonArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("talons"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(talonArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + // Create an object out of one index in the JSONArray. + HyperTalon talon = new HyperTalon(Integer.parseInt(json.get("port").toString())); + + talon.setName(json.get("name").toString()); + + if (json.containsKey("limiter")) + setLimiter(json, talon); + + if (json.containsKey("neutralMode")) + setNeutralMode(json, talon); + + if (json.containsKey("inverted")) + setInverted(json, talon); + + if (json.containsKey("loopRamp")) + setLoopRamp(json, talon); + + if (json.containsKey("sensor")) + setSensors(json, talon); + + if (json.containsKey("pid")) + setPIDValues(json, talon); + + talon.stopMotor(); + + // Put object in HashMap with its declared name as key after initialization and + // configuration. + talons.put(json.get("name").toString(), talon); + } catch (Exception e) { + DriverStation.reportError( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), + false); + System.out.println( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); + System.exit(1); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + talonArray.clear(); + } catch (Exception e) { + DriverStation.reportError( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), false); + System.out + .println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); + System.exit(1); + } + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperUltrasonic.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java similarity index 97% rename from src/main/java/org/usfirst/lib6647/subsystem/components/SuperUltrasonic.java rename to src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java index a80ed62..0d90fb4 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/components/SuperUltrasonic.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java @@ -1,4 +1,4 @@ -package org.usfirst.lib6647.subsystem.components; +package org.usfirst.lib6647.subsystem.supercomponents; import java.util.Arrays; import java.util.HashMap; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java new file mode 100644 index 0000000..3d2d9a4 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java @@ -0,0 +1,94 @@ +package org.usfirst.lib6647.subsystem.supercomponents; + +import java.util.Arrays; +import java.util.HashMap; + +import org.json.simple.JSONArray; +import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperVictor; +import org.usfirst.lib6647.util.MotorUtils; + +import edu.wpi.first.wpilibj.DriverStation; + +/** + * Interface to allow {@link HyperVictor} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link HyperTalon + * HyperVictors} declared in {@link SuperSubsystem#robotMap robotMap}. + */ +public interface SuperVictor extends MotorUtils { + /** + * HashMap storing the {@link SuperSubsystem}'s {@link HyperVictor + * HyperVictors}. + */ + public HashMap victors = new HashMap(); + + /** + * Method to initialize {@link HyperVictor HyperVictors} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #victors} HashMap using its declared name as its key. + * + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} + * + * @Note ALWAYS declare and initialize masters before followers! + */ + default void initVictors(JSONObject robotMap, String subsystemName) { + try { + // Create a JSONArray out of the declared objects. + JSONArray victorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("victors"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(victorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + // Create an object out of one index in the JSONArray. + HyperVictor victor = new HyperVictor(Integer.parseInt(json.get("port").toString())); + + victor.setName(json.get("name").toString()); + + if (json.containsKey("limiter")) + setLimiter(json, victor); + + if (json.containsKey("neutralMode")) + setNeutralMode(json, victor); + + if (json.containsKey("inverted")) + setInverted(json, victor); + + if (json.containsKey("loopRamp")) + setLoopRamp(json, victor); + + victor.stopMotor(); + + // Put object in HashMap with its declared name as key after initialization and + // configuration. + victors.put(json.get("name").toString(), victor); + } catch (Exception e) { + DriverStation.reportError( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), + false); + System.out.println( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); + System.exit(1); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + victorArray.clear(); + } catch (Exception e) { + DriverStation.reportError( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), false); + System.out.println( + "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); + System.exit(1); + } + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/util/Direction.java b/src/main/java/org/usfirst/lib6647/util/Direction.java deleted file mode 100644 index 94edb31..0000000 --- a/src/main/java/org/usfirst/lib6647/util/Direction.java +++ /dev/null @@ -1,8 +0,0 @@ -package org.usfirst.lib6647.util; - -/** - * Enum listing possible movement directions, for readability purposes. - */ -public enum Direction { - UP, DOWN, FRONT, BACK, LEFT, RIGHT, FORWARD, BACKWARD, IN, OUT, NONE -} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/util/MotorUtils.java b/src/main/java/org/usfirst/lib6647/util/MotorUtils.java index 9761b51..4d9efe5 100644 --- a/src/main/java/org/usfirst/lib6647/util/MotorUtils.java +++ b/src/main/java/org/usfirst/lib6647/util/MotorUtils.java @@ -2,43 +2,84 @@ import com.ctre.phoenix.motorcontrol.FeedbackDevice; import com.ctre.phoenix.motorcontrol.NeutralMode; -import com.ctre.phoenix.motorcontrol.can.WPI_TalonSRX; -import com.ctre.phoenix.motorcontrol.can.WPI_VictorSPX; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperVictor; /** - * Interface for converting String values to CTRE Objects. + * SuperInterface for converting String values from a {@link JSONObject} to + * configure a {@link HyperTalon} or a {@link HyperVictor}. */ public interface MotorUtils { /** - * Sets a given Talon's inverted status from the JSON configuration. + * Sets a given {@link HyperTalon}'s limiter value from a {@link JSONObject}. + * Max value is 1, min value is 0 (which would make the {@link HyperTalon} + * stop). * - * @param json - * @param talon - * @throws Exception + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} key does not exist or is + * empty. + * @throws NumberFormatException if {@link JSONObject} is not a number. */ - default void setInverted(JSONObject json, WPI_TalonSRX talon) throws Exception { - talon.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + default void setLimiter(JSONObject json, HyperTalon talon) throws NullPointerException, NumberFormatException { + double limiter = Double.parseDouble(json.get("limiter").toString()); + talon.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); } /** - * Sets a given Victor's inverted status from the JSON configuration. + * Sets a given {@link HyperVictor}'s limiter value from a {@link JSONObject}. + * Max value is 1, min value is 0 (which would make the {@link HyperVictor} + * stop). * - * @param json - * @param victor - * @throws Exception + * @param JSONObject + * @param HyperVictor + * @throws NullPointerException if {@link JSONObject} key does not exist or is + * empty. + * @throws NumberFormatException if {@link JSONObject} is not a number. */ - default void setInverted(JSONObject json, WPI_VictorSPX victor) throws Exception { - victor.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + default void setLimiter(JSONObject json, HyperVictor victor) throws NullPointerException, NumberFormatException { + double limiter = Double.parseDouble(json.get("limiter").toString()); + victor.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); } /** - * Method to convert a String to its respective NeutralMode. + * Sets a given {@link HyperTalon}'s inverted value from a {@link JSONObject}. * - * @param neutralMode + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} key does not exist or is + * empty. + */ + default void setInverted(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { + HyperTalon.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + } + + /** + * Sets a given {@link HyperVictor}'s inverted value from a {@link JSONObject} + * key. + * + * @param JSONObject + * @param HyperVictor + * @throws NullPointerException if {@link JSONObject} key does not exist or is + * empty. + */ + default void setInverted(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { + HyperVictor.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + } + + /** + * Method to convert a String value to its respective {@link NeutralMode}. + * + * @param String * @return NeutralMode + * + * @note There are three types of {@link NeutralMode NeutralModes}: + * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and + * {@link NeutralMode#EEPROMSetting}. All of which should share the same + * name in the {@link JSONObject}. */ default NeutralMode getNeutralMode(String neutralMode) { switch (neutralMode) { @@ -54,76 +95,106 @@ default NeutralMode getNeutralMode(String neutralMode) { } /** - * Sets a given Talon's inverted status from the JSON configuration. + * Sets a given {@link HyperTalon}'s {@link NeutralMode} from a + * {@link JSONObject} key. * - * @param json - * @param talon - * @throws Exception + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} key does not exist, is + * empty, or is not valid. + * + * @note There are three types of {@link NeutralMode NeutralModes}: + * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and + * {@link NeutralMode#EEPROMSetting}. All of which should share the same + * name in the {@link JSONObject}. */ - default void setNeutralMode(JSONObject json, WPI_TalonSRX talon) throws Exception { - talon.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); + default void setNeutralMode(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { + HyperTalon.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); } /** - * Sets a given Victor's inverted status from the JSON configuration. + * Sets a given {@link HyperVictor}'s {@link NeutralMode} from a + * {@link JSONObject} key. + * + * @param JSONObject + * @param HyperVictor + * @throws NullPointerException if {@link JSONObject} key does not exist, is + * empty, or is not valid. * - * @param json - * @param victor - * @throws Exception + * @note There are three types of {@link NeutralMode NeutralModes}: + * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and + * {@link NeutralMode#EEPROMSetting}. All of which should share the same + * name in the {@link JSONObject}. */ - default void setNeutralMode(JSONObject json, WPI_VictorSPX victor) throws Exception { - victor.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); + default void setNeutralMode(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { + HyperVictor.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); } /** - * Sets a given Talon's loopramp from the JSON configuration. + * Sets a given {@link HyperTalon}'s loopramp from a {@link JSONObject} key. * - * @param json - * @param talon - * @throws Exception + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} keys do not exist or are + * empty. + * @throws NumberFormatException if {@link JSONObject} keys are not numbers. */ - default void setLoopRamp(JSONObject json, WPI_TalonSRX talon) throws Exception { + default void setLoopRamp(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"), open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); if (closed.containsKey("timeoutMs") && open.containsKey("timeoutMs")) { - talon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), + HyperTalon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), Integer.parseInt(closed.get("timeoutMs").toString())); - talon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), + HyperTalon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), Integer.parseInt(open.get("timeoutMs").toString())); } else { - talon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); - talon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); + HyperTalon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); + HyperTalon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); } } /** - * Sets a given Victor's loopramp from the JSON configuration. + * Sets a given {@link HyperVictor}'s loopramp from the JSON configuration. * - * @param json - * @param victor - * @throws Exception + * @param JSONObject + * @param HyperVictor + * @throws NullPointerException if {@link JSONObject} keys do not exist or are + * empty. + * @throws NumberFormatException if {@link JSONObject} keys are not numbers. */ - default void setLoopRamp(JSONObject json, WPI_VictorSPX victor) throws Exception { + default void setLoopRamp(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"), open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); if (closed.containsKey("timeoutMs") && open.containsKey("timeoutMs")) { - victor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), + HyperVictor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), Integer.parseInt(closed.get("timeoutMs").toString())); - victor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), + HyperVictor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), Integer.parseInt(open.get("timeoutMs").toString())); } else { - victor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); - victor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); + HyperVictor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); + HyperVictor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); } } /** - * Method to convert a String to its respective FeedbackDevice. + * Method to convert a String to its respective {@link FeedbackDevice}. * * @param feedbackDevice * @return FeedbackDevice + * + * @note There are eleven types of {@link FeedbackDevice FeedbackDevices}: + * {@link FeedbackDevice#QuadEncoder}, {@link FeedbackDevice#Analog}, + * {@link FeedbackDevice#Tachometer}, + * {@link FeedbackDevice#PulseWidthEncodedPosition}, + * {@link FeedbackDevice#SensorSum}, + * {@link FeedbackDevice#SensorDifference}, + * {@link FeedbackDevice#RemoteSensor0}, + * {@link FeedbackDevice#RemoteSensor1}, + * {@link FeedbackDevice#SoftwareEmulatedSensor}, + * {@link FeedbackDevice#CTRE_MagEncoder_Absolute}, + * {@link FeedbackDevice#CTRE_MagEncoder_Relative} */ default FeedbackDevice getFeedbackDevice(String feedbackDevice) { switch (feedbackDevice) { @@ -155,41 +226,51 @@ default FeedbackDevice getFeedbackDevice(String feedbackDevice) { } /** - * Sets a given Talon's sensors from the JSON configuration (fairly limited in - * terms of customizability at the moment). + * Sets a given {@link HyperTalon}'s sensors from a {@link JSONObject} key + * (fairly limited in terms of configuration at the moment). * - * @param json - * @param talon - * @throws Exception + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} keys do not exist or are + * empty. + * @throws NumberFormatException if some {@link JSONObject} keys are not + * numbers. */ - default void setSensors(JSONObject json, WPI_TalonSRX talon) throws Exception { + default void setSensors(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { JSONObject sensor = (JSONObject) json.get("sensor"); JSONObject feedback = (JSONObject) sensor.get("feedback"); - talon.configSelectedFeedbackSensor(getFeedbackDevice(feedback.get("feedbackDevice").toString()), + HyperTalon.configSelectedFeedbackSensor(getFeedbackDevice(feedback.get("feedbackDevice").toString()), Integer.parseInt(feedback.get("pidIdx").toString()), Integer.parseInt(feedback.get("timeoutMs").toString())); - talon.setSensorPhase(Boolean.parseBoolean(sensor.get("phase").toString())); + HyperTalon.setSensorPhase(Boolean.parseBoolean(sensor.get("phase").toString())); - talon.setSelectedSensorPosition(Integer.parseInt(sensor.get("sensorPos").toString()), + HyperTalon.setSelectedSensorPosition(Integer.parseInt(sensor.get("sensorPos").toString()), Integer.parseInt(sensor.get("pidIdx").toString()), Integer.parseInt(sensor.get("timeoutMs").toString())); } /** - * Sets a given Talon's PID values from the JSON configuration. + * Sets a given {@link HyperTalon}'s PID values from a {@link JSONObject} key. * - * @param json - * @param talon - * @throws Exception + * @param JSONObject + * @param HyperTalon + * @throws NullPointerException if {@link JSONObject} keys do not exist or are + * empty. + * @throws NumberFormatException if some {@link JSONObject} keys are not + * numbers. */ - default void setPIDValues(JSONObject json, WPI_TalonSRX talon) throws Exception { + default void setPIDValues(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { JSONObject pid = (JSONObject) json.get("pid"); - talon.config_kP(Integer.parseInt(pid.get("slotIdx").toString()), Double.parseDouble(pid.get("p").toString())); - talon.config_kI(Integer.parseInt(pid.get("slotIdx").toString()), Double.parseDouble(pid.get("i").toString())); - talon.config_kD(Integer.parseInt(pid.get("slotIdx").toString()), Double.parseDouble(pid.get("d").toString())); - talon.config_kF(Integer.parseInt(pid.get("slotIdx").toString()), Double.parseDouble(pid.get("f").toString())); + HyperTalon.config_kP(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("p").toString())); + HyperTalon.config_kI(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("i").toString())); + HyperTalon.config_kD(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("d").toString())); + HyperTalon.config_kF(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("f").toString())); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/util/MoveDirection.java b/src/main/java/org/usfirst/lib6647/util/MoveDirection.java new file mode 100644 index 0000000..974f63f --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/util/MoveDirection.java @@ -0,0 +1,11 @@ +package org.usfirst.lib6647.util; + +import edu.wpi.first.wpilibj.command.Command; + +/** + * Enum listing possible movement directions, useful for commands. Mostly useful + * for {@link Command Commands}. + */ +public enum MoveDirection { + UP, DOWN, FRONT, BACK, LEFT, RIGHT, FORWARD, BACKWARD, IN, OUT, NONE +} \ No newline at end of file From 7ce27a84f08d260f2f817446d28417493c75ab07 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Fri, 28 Jun 2019 16:46:46 -0500 Subject: [PATCH 02/10] Added some default methods to interfaces. [SuperComponents] - Added default methods for getting HashMaps. --- .../subsystem/supercomponents/SuperCompressor.java | 4 ++++ .../subsystem/supercomponents/SuperDigitalInput.java | 4 ++++ .../lib6647/subsystem/supercomponents/SuperEncoder.java | 4 ++++ .../lib6647/subsystem/supercomponents/SuperPDP.java | 4 ++++ .../lib6647/subsystem/supercomponents/SuperSolenoid.java | 4 ++++ .../lib6647/subsystem/supercomponents/SuperTalon.java | 8 ++++++++ .../subsystem/supercomponents/SuperUltrasonic.java | 4 ++++ .../lib6647/subsystem/supercomponents/SuperVictor.java | 8 ++++++++ 8 files changed, 40 insertions(+) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java index 24e46a7..ee566c6 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java @@ -54,4 +54,8 @@ default void initCompressors(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + default HashMap getCompressor() { + return compressors; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java index db994f5..2921f97 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java @@ -54,4 +54,8 @@ default void initDigitalInputs(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + default HashMap getDigitalInputs() { + return digitalInputs; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java index 997012d..c853689 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java @@ -73,4 +73,8 @@ default EncodingType getEncodingType(String encodingType) { return null; } } + + default HashMap getEncoders() { + return encoders; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java index 6512e5c..4c55c91 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java @@ -54,4 +54,8 @@ default void initPDPs(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + default HashMap getPDPs() { + return PDPs; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java index 3c64e76..46b8380 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java @@ -58,4 +58,8 @@ default void initSolenoids(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + default HashMap getSolenoids() { + return solenoids; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java index d23ab42..8a16032 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java @@ -95,4 +95,12 @@ default void initTalons(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + /** + * Gets {@link HyperTalon} HashMap. + * @return {@link HyperTalon} HashMap + */ + default HashMap getVictors() { + return talons; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java index 0d90fb4..fea58fd 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java @@ -55,4 +55,8 @@ default void initUltrasonics(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + default HashMap getUltrasonics() { + return ultrasonics; + } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java index 3d2d9a4..8eb7394 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java @@ -91,4 +91,12 @@ default void initVictors(JSONObject robotMap, String subsystemName) { System.exit(1); } } + + /** + * Gets {@link HyperVictor} HashMap. + * @return {@link HyperVictor} HashMap + */ + default HashMap getVictors() { + return victors; + } } \ No newline at end of file From 502286ff749f79c25ccc8480bd67850017113174 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Fri, 28 Jun 2019 16:56:41 -0500 Subject: [PATCH 03/10] Literally changed one word. [SuperComponents] - SuperTalon's getVictors() method renamed to getTalons(). --- .../usfirst/lib6647/subsystem/supercomponents/SuperTalon.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java index 8a16032..1364667 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java @@ -100,7 +100,7 @@ default void initTalons(JSONObject robotMap, String subsystemName) { * Gets {@link HyperTalon} HashMap. * @return {@link HyperTalon} HashMap */ - default HashMap getVictors() { + default HashMap getTalons() { return talons; } } \ No newline at end of file From 2d57080ec32a6cc38a286ea1d7f25ced4b40538e Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Fri, 28 Jun 2019 17:25:28 -0500 Subject: [PATCH 04/10] Changed SuperComponents slightly. [SuperComponents] - Changed getX() method to return object instead of HashMap. --- .../subsystem/supercomponents/SuperCompressor.java | 10 ++++++++-- .../subsystem/supercomponents/SuperDigitalInput.java | 10 ++++++++-- .../subsystem/supercomponents/SuperEncoder.java | 10 ++++++++-- .../lib6647/subsystem/supercomponents/SuperPDP.java | 10 ++++++++-- .../subsystem/supercomponents/SuperSolenoid.java | 10 ++++++++-- .../lib6647/subsystem/supercomponents/SuperTalon.java | 10 ++++++---- .../subsystem/supercomponents/SuperUltrasonic.java | 10 ++++++++-- .../lib6647/subsystem/supercomponents/SuperVictor.java | 10 ++++++---- 8 files changed, 60 insertions(+), 20 deletions(-) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java index ee566c6..f49b66d 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java @@ -55,7 +55,13 @@ default void initCompressors(JSONObject robotMap, String subsystemName) { } } - default HashMap getCompressor() { - return compressors; + /** + * Gets specified {@link Compressor}. + * + * @return {@link Compressor} + * @param compressorName + */ + default Compressor getCompressor(String compressorName) { + return compressors.get(compressorName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java index 2921f97..b030eeb 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java @@ -55,7 +55,13 @@ default void initDigitalInputs(JSONObject robotMap, String subsystemName) { } } - default HashMap getDigitalInputs() { - return digitalInputs; + /** + * Gets specified {@link DigitalInput}. + * + * @return {@link DigitalInput} + * @param digitalInputName + */ + default DigitalInput getDigitalInput(String digitalInputName) { + return digitalInputs.get(digitalInputName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java index c853689..06a6df5 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java @@ -74,7 +74,13 @@ default EncodingType getEncodingType(String encodingType) { } } - default HashMap getEncoders() { - return encoders; + /** + * Gets specified {@link Encoder}. + * + * @return {@link Encoder} + * @param encoderName + */ + default Encoder getEncoder(String encoderName) { + return encoders.get(encoderName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java index 4c55c91..b5b2b11 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java @@ -55,7 +55,13 @@ default void initPDPs(JSONObject robotMap, String subsystemName) { } } - default HashMap getPDPs() { - return PDPs; + /** + * Gets specified {@link PowerDistributionPanel}. + * + * @return {@link PowerDistributionPanel} + * @param pdpName + */ + default PowerDistributionPanel getPDP(String pdpName) { + return PDPs.get(pdpName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java index 46b8380..c0bc330 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java @@ -59,7 +59,13 @@ default void initSolenoids(JSONObject robotMap, String subsystemName) { } } - default HashMap getSolenoids() { - return solenoids; + /** + * Gets specified {@link Solenoid}. + * + * @return {@link Solenoid} + * @param solenoidName + */ + default Solenoid getSolenoid(String solenoidName) { + return solenoids.get(solenoidName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java index 1364667..88587fb 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java @@ -97,10 +97,12 @@ default void initTalons(JSONObject robotMap, String subsystemName) { } /** - * Gets {@link HyperTalon} HashMap. - * @return {@link HyperTalon} HashMap + * Gets specified {@link HyperTalon}. + * + * @return {@link HyperTalon} + * @param talonName */ - default HashMap getTalons() { - return talons; + default HyperTalon getTalon(String talonName) { + return talons.get(talonName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java index fea58fd..0d0df07 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java @@ -56,7 +56,13 @@ default void initUltrasonics(JSONObject robotMap, String subsystemName) { } } - default HashMap getUltrasonics() { - return ultrasonics; + /** + * Gets specified {@link Ultrasonic}. + * + * @return {@link Ultrasonic} + * @param ultrasonicName + */ + default Ultrasonic getUltrasonic(String ultrasonicName) { + return ultrasonics.get(ultrasonicName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java index 8eb7394..559f624 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java @@ -93,10 +93,12 @@ default void initVictors(JSONObject robotMap, String subsystemName) { } /** - * Gets {@link HyperVictor} HashMap. - * @return {@link HyperVictor} HashMap + * Gets specified {@link HyperVictor}. + * + * @return {@link HyperVictor} + * @param victorName */ - default HashMap getVictors() { - return victors; + default HyperVictor getVictor(String victorName) { + return victors.get(victorName); } } \ No newline at end of file From f995f113e076adfc150c1552eb54b664c822e352 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Fri, 28 Jun 2019 17:33:28 -0500 Subject: [PATCH 05/10] Quick addition to HyperTalon and HyperVictor. [HyperComponents] - getLimiter() getter added to HyperTalon and HyperVictor. --- .../lib6647/subsystem/hypercomponents/HyperTalon.java | 8 ++++++++ .../lib6647/subsystem/hypercomponents/HyperVictor.java | 9 +++++++++ 2 files changed, 17 insertions(+) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java index bc56285..40fadfa 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java @@ -23,6 +23,14 @@ public HyperTalon(int port) { super(port); } + /** + * Returns {@link #limiter} value for Talon speed. + * @return + */ + public double getLimiter() { + return limiter; + } + /** * Sets {@link #limiter} for Talon speed. */ diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java index 0d58126..f1f841d 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java @@ -23,6 +23,15 @@ public HyperVictor(int port) { super(port); } + /** + * Returns {@link #limiter} value for Victor speed. + * + * @return + */ + public double getLimiter() { + return limiter; + } + /** * Sets {@link #limiter limiter} for Victor speed. */ From 0771e575406b18731644eeef476ad78b54777210 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Sat, 29 Jun 2019 06:28:01 -0500 Subject: [PATCH 06/10] Quick change to some HyperComponent methods. [HyperComponents] - setTalon() and setVictor() now have default limiter values. --- .../lib6647/subsystem/hypercomponents/HyperTalon.java | 11 +++++++++++ .../subsystem/hypercomponents/HyperVictor.java | 10 ++++++++++ 2 files changed, 21 insertions(+) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java index 40fadfa..7c9a51f 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java @@ -25,6 +25,7 @@ public HyperTalon(int port) { /** * Returns {@link #limiter} value for Talon speed. + * * @return */ public double getLimiter() { @@ -47,6 +48,16 @@ public void raiseLimiter(double amount) { limiter += amount; } + /** + * Sets {@link HyperTalon} to a given speed, in {@link ControlMode#PercentOutput + * PercentOutput}. + * + * @param speed + */ + public void setTalon(double speed) { + setTalon(speed, false); + } + /** * Sets {@link HyperTalon} to a given speed, in {@link ControlMode#PercentOutput * PercentOutput}. diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java index f1f841d..bf4332b 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java @@ -48,6 +48,16 @@ public void raiseLimiter(double amount) { limiter += amount; } + /** + * Sets {@link HyperVictor} to a given speed, in + * {@link ControlMode#PercentOutput PercentOutput}. + * + * @param speed + */ + public void setVictor(double speed) { + setVictor(speed, false); + } + /** * Sets {@link HyperVictor} to a given speed, in * {@link ControlMode#PercentOutput PercentOutput}. From d5aff0f97b66bc308e8ac025b3672eda7960dbb4 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Sat, 29 Jun 2019 13:52:21 -0500 Subject: [PATCH 07/10] Comments overhaul! [General] - License added. - Everything is now properly commented! --- BSD_License_for_WPILib_code.txt | 24 +++++++ .../org/usfirst/lib6647/oi/ButtonHelper.java | 46 +++++++++---- .../org/usfirst/lib6647/oi/JController.java | 65 ++++++++++++++----- .../lib6647/subsystem/PIDSuperSubsystem.java | 40 ++++++++---- .../lib6647/subsystem/SuperSubsystem.java | 18 +++-- .../supercomponents/SuperCompressor.java | 29 +++++++-- .../supercomponents/SuperDigitalInput.java | 30 +++++++-- .../supercomponents/SuperEncoder.java | 29 +++++++-- .../subsystem/supercomponents/SuperPDP.java | 31 +++++++-- .../supercomponents/SuperSolenoid.java | 29 +++++++-- .../supercomponents/SuperUltrasonic.java | 29 +++++++-- 11 files changed, 278 insertions(+), 92 deletions(-) create mode 100644 BSD_License_for_WPILib_code.txt diff --git a/BSD_License_for_WPILib_code.txt b/BSD_License_for_WPILib_code.txt new file mode 100644 index 0000000..3a7f798 --- /dev/null +++ b/BSD_License_for_WPILib_code.txt @@ -0,0 +1,24 @@ +* Copyright (c) 2009 FIRST +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the FIRST nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY FIRST AND CONTRIBUTORS``AS IS'' AND ANY +* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY NONINFRINGEMENT AND FITNESS FOR A PARTICULAR +* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL FIRST OR CONTRIBUTORS BE LIABLE FOR +* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java b/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java index 421bf7b..c334daf 100644 --- a/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java +++ b/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java @@ -13,14 +13,22 @@ import edu.wpi.first.wpilibj.buttons.Button; /** - * Helper class for registering button input. + * Helper class for registering {@link Button} input. */ public class ButtonHelper { + + /** + * HashMap where declared {@link JController joysticks} are stored. + */ public HashMap joysticks; - String fileName; /** - * Constructor for the class. + * Location of the JSON file for {@link Button} nicknames. + */ + private String fileName; + + /** + * Helper class for registering {@link Button} input. * * @param fileName */ @@ -31,26 +39,32 @@ public ButtonHelper(String fileName) { } /** - * Method for getting a button with a JSON name from a given joystick. Returns - * null if no button is found. + * Method for getting a {@link Button} with a friendly name (declared in the + * JSON configuration) from a given {@link #joysticks joystick}. Returns null if + * no {@link Button} is found at that key. * - * @param joystick + * @param joystickName * @param buttonName - * @return button from the given joystick + * @return {@link Button} */ public Button oiButton(String joystickName, String buttonName) { try { + // Create a new JSONParser and JSONObject with the given key. JSONParser parser = new JSONParser(); Reader file = new FileReader(fileName); JSONObject jsonJoystick = (JSONObject) ((JSONObject) parser.parse(file)) .get(joysticks.get(joystickName).getName()); + // Create Button object and initialize it with values from the JSONObject. Button button = joysticks.get(joystickName).buttons.get(jsonJoystick.get(buttonName).toString()); + // Clear JSONObject and JSONParser after use, and close Reader. Not sure if it + // does anything, but it might free some unused memory. jsonJoystick.clear(); file.close(); parser.reset(); + // Finally, return Button object from the friendly name. return button; } catch (IOException e) { DriverStation.reportError("[!] OIBUTTON " + buttonName + " IO ERROR: " + e.getMessage(), false); @@ -69,37 +83,41 @@ public Button oiButton(String joystickName, String buttonName) { } /** - * Method for getting a button from a given joystick. + * Method for getting a {@link Button} from a given {@link JController#joysticks + * joystick}. * * @param joystickName * @param button - * @return button from the given joystick + * @return button from the given {@link JController#joysticks joystick} */ public Button oiButton(String joystickName, int button) { return joysticks.get(joystickName).buttons.get("Button" + button); } /** - * Method for getting an axisButton from a given joystick. + * Method for getting a {@link Button} from an axisButton or dPadButton, from a + * given {@link JController#joysticks joystick}. * * @param joystickName * @param type * @param axis - * @return axisButton from the given joystick, for the given axis + * @return {@link Button} from the given {@link JController#joysticks joystick}, + * for the given axis or dPad */ public Button oiButton(String joystickName, String type, int axis) { return joysticks.get(joystickName).buttons.get(type + axis); } /** - * Method for getting an axisButton from a given joystick, at a specific angle. + * Method for getting a {@link Button} from an axisButton or dPadButton, from a + * given {@link JController#joysticks joystick}, at a specific angle. * * @param joystickName * @param type * @param axis * @param angle - * @return axisButton from the given joystick, for the given axis, for the given - * angle + * @return {@link Button} from the given {@link JController#joysticks joystick}, + * for the given axis or dPad, for the given angle or value */ public Button oiButton(String joystickName, String type, int axis, int angle) { return joysticks.get(joystickName).buttons.get(type + axis + "_" + angle); diff --git a/src/main/java/org/usfirst/lib6647/oi/JController.java b/src/main/java/org/usfirst/lib6647/oi/JController.java index 0da4a14..ec50d39 100644 --- a/src/main/java/org/usfirst/lib6647/oi/JController.java +++ b/src/main/java/org/usfirst/lib6647/oi/JController.java @@ -8,28 +8,39 @@ import edu.wpi.first.wpilibj.buttons.JoystickButton; /** - * Joystick wrapper for initializing buttons. + * Wrapper for the {@link Joystick} class for easy {@link Button} + * initialization, and more. */ public class JController extends Joystick { + /** + * HashMap storing the {@link JController}'s {@link Button Buttons}. + */ public HashMap buttons = new HashMap(); + + /** + * Left or right axis of the {@link JController} (assuming it's a gamepad). + */ private int leftAxis = 1, rightAxis = 5; /** - * Constructor for the controller. + * Constructor for {@link JController}. * - * Initializes each and every button from the joystick found at the given port. - * Also initializes buttons for certain angles for each of the axis buttons. + * Initializes each and every {@link Button} from the {@link Joystick} found at + * the given port. Also initializes {@link Button Buttons} for each of the axes + * and POVs. * * @param port */ public JController(int port) { super(port); + // Button initialization. Starting at 1. for (int i = 1; i <= this.getButtonCount(); i++) { buttons.put("Button" + i, new JoystickButton(this, i)); } + // dPadButton initialization. Starting at 0. for (int i = 0; i < this.getPOVCount(); i++) { buttons.put("dPad" + i, buttonFromPOV(this, i)); for (int j = 0; j <= 315; j += 45) { @@ -37,17 +48,19 @@ public JController(int port) { } } + // axisButton initialization. Starting at 0. for (int i = 0; i < this.getAxisCount(); i++) { + buttons.put("Stick" + i, buttonFromAxis(this, i)); buttons.put("Stick" + i + "_1", buttonFromAxisPositive(this, i)); buttons.put("Stick" + i + "_-1", buttonFromAxisNegative(this, i)); } } /** - * Method to set left and right axis. + * Method to set {@link #leftAxis} and {@link #rightAxis}. * - * @param leftAxis - * @param rightAxis + * @param {@link #leftAxis} + * @param {@link #rightAxis} */ public void setLeftRightAxis(int leftAxis, int rightAxis) { this.leftAxis = leftAxis; @@ -55,29 +68,29 @@ public void setLeftRightAxis(int leftAxis, int rightAxis) { } /** - * Method to get left-most Stick raw value. + * Method to get {@link #leftAxis} raw value. * - * @return leftAxis + * @return {@link #leftAxis} */ public double getLeftAxis() { return getRawAxis(leftAxis); } /** - * Method to get right-most Stick raw value. + * Method to get {@link #rightAxis} raw value. * - * @return rightAxis + * @return {@link #rightAxis} */ public double getRightAxis() { return getRawAxis(rightAxis); } /** - * Method for getting a pov button at any angle. + * Method for getting a dPadButton input for any angle. * * @param controller * @param pov - * @return axisButton + * @return dPadButton */ private Button buttonFromPOV(GenericHID controller, int pov) { return new Button() { @@ -89,7 +102,7 @@ public boolean get() { } /** - * Method for getting a pov button at a specific angle. + * Method for getting a dPadButton input for a specific angle. * * @param controller * @param pov @@ -106,7 +119,26 @@ public boolean get() { } /** - * Method for getting a negative input from an axis. + * Method for getting an axisButton input for any value, with 0.15 as tolerance + * (so as to avoid accidental input due to improper {@link JController} + * calibration). + * + * @param controller + * @param axis + * @return axisButton + */ + private Button buttonFromAxis(GenericHID controller, int axis) { + return new Button() { + @Override + public boolean get() { + return Math.abs(controller.getRawAxis(axis)) < 0.15; + } + }; + } + + /** + * Method for getting a negative axisButton input, with 0.15 as tolerance (to + * avoid accidental input due to improper {@link JController} calibration). * * @param controller * @param axis @@ -122,7 +154,8 @@ public boolean get() { } /** - * Method for getting a positive input from an axis. + * Method for getting a positive axisButton input, with 0.15 as tolerance (to + * avoid accidental input due to improper {@link JController} calibration). * * @param controller * @param axis diff --git a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java index e39dd98..0c346a1 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java @@ -11,18 +11,24 @@ import edu.wpi.first.wpilibj.smartdashboard.SmartDashboard; /** - * Class to allow usage of JSON files for PIDSubsystem creation. + * Abstract class to allow usage of {@link #robotMap JSON files} for + * {@link PIDSubsystem} creation, with additional PID initialization. */ public abstract class PIDSuperSubsystem extends PIDSubsystem { + /** + * Bread and butter of {@link PIDSuperSubsystem}. + */ protected JSONObject robotMap; protected float p = 0.0f, i = 0.0f, d = 0.0f; /** - * Constructor for the class. + * Constructor for {@link PIDSuperSubsystem}. Initializes the + * {@link PIDSubsystem} with 0.0f, 0.0f, and 0.0f as PID values, then replaces + * them with the values declared in {@link #robotMap} * - * @param name - * @param fileName (of JSON) + * @param name (of the {@link PIDSubsystem}) + * @param fileName (to {@link #robotMap JSON file}) */ public PIDSuperSubsystem(String name, String fileName) { super(name, 0.0f, 0.0f, 0.0f); @@ -33,9 +39,9 @@ public PIDSuperSubsystem(String name, String fileName) { } /** - * Method to initialize JSON at the given path. + * Method to initialize {@link #robotMap} at the given path. * - * @param fileName + * @param fileName (to {@link #robotMap JSON file}) */ private void initJSON(String fileName) { try { @@ -52,17 +58,21 @@ private void initJSON(String fileName) { } /** - * Method to initialize subsystem PID values and configuration. + * Method to initialize and set {@link PIDSuperSubsystem}'s PID values and + * configuration. */ private void initPID() { try { + // Create a JSONObject out of the 'pid' key. JSONObject pid = (JSONObject) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(getName())) .get("pid"); + // Update current PID values. p = Float.parseFloat(pid.get("p").toString()); i = Float.parseFloat(pid.get("i").toString()); d = Float.parseFloat(pid.get("d").toString()); + // Update PIDSubsystem PID values and configuration. getPIDController().setPID(p, i, d); setInputRange(Double.parseDouble(pid.get("inputMin").toString()), Double.parseDouble(pid.get("inputMax").toString())); @@ -71,6 +81,8 @@ private void initPID() { setAbsoluteTolerance(Double.parseDouble(pid.get("absoluteTolerance").toString())); getPIDController().setContinuous(Boolean.parseBoolean(pid.get("continuous").toString())); + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. pid.clear(); } catch (Exception e) { DriverStation.reportError( @@ -81,19 +93,20 @@ private void initPID() { } /** - * Method to clear JSONObject. + * Method to clear {@link #robotMap}. */ public void finishedJSONInit() { robotMap.clear(); } /** - * Method to output PID values to the SmartDashboard. + * Method to output {@link #p}, {@link #i}, and {@link #d} values from the + * {@link PIDSuperSubsystem} to the {@link SmartDashboard}. * * @param subsystemName - * @param p - * @param i - * @param d + * @param {@link #p} + * @param {@link #i} + * @param {@link #d} */ private void outputPIDValues(String subsystemName, float p, float i, float d) { SmartDashboard.putString(subsystemName + "P", p + ""); @@ -102,7 +115,8 @@ private void outputPIDValues(String subsystemName, float p, float i, float d) { } /** - * Method to update PID values from the SmartDashboard. + * Method to update {@link #p}, {@link #i}, and {@link #d} values as float from + * the {@link SmartDashboard}. */ public void updatePIDValues() { p = Float.parseFloat(SmartDashboard.getString(getName() + "P", p + "")); diff --git a/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java index ee90f3a..f8f0ea4 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java @@ -10,17 +10,21 @@ import edu.wpi.first.wpilibj.command.Subsystem; /** - * Class to allow usage of JSON files for Subsystem creation. + * Abstract class to allow usage of {@link #robotMap JSON files} for + * {@link Subsystem} creation. */ public abstract class SuperSubsystem extends Subsystem { + /** + * Bread and butter of {@link SuperSubsystem}. + */ protected JSONObject robotMap; /** - * Constructor for the class. + * Constructor for {@link SuperSubsystem}. * - * @param name - * @param fileName (of JSON) + * @param name (of the {@link Subsystem}) + * @param fileName (to {@link #robotMap JSON file}) */ public SuperSubsystem(String name, String fileName) { super(name); @@ -29,9 +33,9 @@ public SuperSubsystem(String name, String fileName) { } /** - * Method to initialize JSON at the given path. + * Method to initialize {@link #robotMap} at the given path. * - * @param fileName + * @param fileName (to {@link #robotMap JSON file}) */ private void initJSON(String fileName) { try { @@ -48,7 +52,7 @@ private void initJSON(String fileName) { } /** - * Method to clear JSONObject. + * Method to clear {@link #robotMap}. */ public void finishedJSONInit() { robotMap.clear(); diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java index f49b66d..6104c0c 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java @@ -5,34 +5,45 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.Compressor; import edu.wpi.first.wpilibj.DriverStation; /** - * Interface to allow Compressor initialization via JSON file. Subsystem needs - * to extend SuperSubsystem. + * Interface to allow {@link Compressor} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link Compressor + * Compressors} declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperCompressor { /** - * HashMap storing the SuperSubsystem's Compressors. + * HashMap storing the {@link SuperSubsystem}'s {@link Compressor Compressors}. */ public HashMap compressors = new HashMap(); /** - * Method to initialize Compressors declared in JSON file, and add them to the - * HashMap using its name as its key. + * Method to initialize {@link Compressor Compressors} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #compressors} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initCompressors(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray compressorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) .get(subsystemName)).get("compressors"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(compressorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. Compressor compressor = new Compressor(Integer.parseInt(json.get("module").toString())); + // Put object in HashMap with its declared name as key after initialization and + // configuration. compressors.put(json.get("name").toString(), compressor); } catch (Exception e) { DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() @@ -41,9 +52,13 @@ default void initCompressors(JSONObject robotMap, String subsystemName) { + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. compressorArray.clear(); } catch (Exception e) { DriverStation.reportError( diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java index b030eeb..501f845 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java @@ -5,34 +5,46 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.DigitalInput; import edu.wpi.first.wpilibj.DriverStation; /** - * Interface to allow DigitalInput initialization via JSON file. Subsystem needs - * to extend SuperSubsystem. + * Interface to allow {@link DigitalInput} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link DigitalInput + * DigitalInputs} declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperDigitalInput { /** - * HashMap storing the SuperSubsystem's DigitalInputs. + * HashMap storing the {@link SuperSubsystem}'s {@link DigitalInput + * DigitalInputs}. */ public HashMap digitalInputs = new HashMap(); /** - * Method to initialize DigitalInputs declared in JSON file, and add them to the - * HashMap using its name as its key. + * Method to initialize {@link DigitalInput DigitalInputs} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #digitalInputs} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initDigitalInputs(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray digitalInputArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) .get(subsystemName)).get("digitalInputs"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(digitalInputArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. DigitalInput digitalInput = new DigitalInput(Integer.parseInt(json.get("channel").toString())); + // Put object in HashMap with its declared name as key after initialization and + // configuration. digitalInputs.put(json.get("name").toString(), digitalInput); } catch (Exception e) { DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() @@ -41,9 +53,13 @@ default void initDigitalInputs(JSONObject robotMap, String subsystemName) { + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. digitalInputArray.clear(); } catch (Exception e) { DriverStation.reportError( diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java index 06a6df5..0830dc7 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java @@ -5,40 +5,51 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.CounterBase.EncodingType; import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.Encoder; /** - * Interface to allow Encoder initialization via JSON file. Subsystem needs to - * extend SuperSubsystem. + * Interface to allow {@link Encoder} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link Encoder Encoders} + * declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperEncoder { /** - * HashMap storing the SuperSubsystem's Encoders. + * HashMap storing the {@link SuperSubsystem}'s {@link Encoder Encoders}. */ public HashMap encoders = new HashMap(); /** - * Method to initialize Encoders declared in JSON file, and add them to the - * HashMap using its name as its key. + * Method to initialize {@link Encoder Encoders} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #encoders} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initEncoders(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray encoderArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) .get(subsystemName)).get("encoders"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(encoderArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. Encoder encoder = new Encoder(Integer.parseInt(json.get("channelA").toString()), Integer.parseInt(json.get("channelB").toString()), Boolean.parseBoolean(json.get("reverse").toString()), getEncodingType(json.get("encodingType").toString())); encoder.reset(); + // Put object in HashMap with its declared name as key after initialization and + // configuration. encoders.put(json.get("name").toString(), encoder); } catch (Exception e) { DriverStation.reportError( @@ -48,9 +59,13 @@ default void initEncoders(JSONObject robotMap, String subsystemName) { + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. encoderArray.clear(); } catch (Exception e) { DriverStation.reportError( diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java index b5b2b11..e7b831a 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java @@ -5,35 +5,48 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.PowerDistributionPanel; /** - * Interface to allow PowerDistributionPanel initialization via JSON file. - * Subsystem needs to extend SuperSubsystem. + * Interface to allow {@link PowerDistributionPanel} initialization via JSON. + * Subsystems declared need to extend {@link SuperSubsystem} or + * {@link PIDSuperSubsystem} and implement this interface in order to initialize + * {@link PowerDistributionPanel PDPs} declared in + * {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperPDP { /** - * HashMap storing the SuperSubsystem's PowerDistributionPanel objects. + * HashMap storing the {@link SuperSubsystem}'s {@link PowerDistributionPanel + * PDPs}. */ public HashMap PDPs = new HashMap(); /** - * Method to initialize PDPs declared in JSON file, and add them to the HashMap - * using its name as its key. + * Method to initialize {@link PowerDistributionPanel PDPs} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #PDPs} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initPDPs(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray PDPArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) .get("PDPs"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(PDPArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. PowerDistributionPanel pdp = new PowerDistributionPanel( Integer.parseInt(json.get("module").toString())); + // Put object in HashMap with its declared name as key after initialization and + // configuration. PDPs.put(json.get("name").toString(), pdp); } catch (Exception e) { DriverStation.reportError( @@ -43,9 +56,13 @@ default void initPDPs(JSONObject robotMap, String subsystemName) { "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' PDP INIT ERROR: " + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. PDPArray.clear(); } catch (Exception e) { DriverStation.reportError( diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java index c0bc330..02ad4ce 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java @@ -5,38 +5,49 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.Solenoid; /** - * Interface to allow Solenoid initialization via JSON file. Subsystem needs to - * extend SuperSubsystem. + * Interface to allow {@link Solenoid} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link Solenoid + * Solenoids} declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperSolenoid { /** - * HashMap storing the SuperSubsystem's Solenoids. + * HashMap storing the {@link SuperSubsystem}'s {@link Solenoid Solenoids}. */ public HashMap solenoids = new HashMap(); /** - * Method to initialize Solenoids declared in JSON file, and add them to the - * HashMap using its name as its key. + * Method to initialize {@link Solenoid Solenoids} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #solenoids} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initSolenoids(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray solenoidArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) .get(subsystemName)).get("solenoids"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(solenoidArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. Solenoid solenoid = new Solenoid(Integer.parseInt(json.get("channel").toString())); if (json.containsKey("initialValue")) solenoid.set(Boolean.parseBoolean(json.get("initialValue").toString())); + // Put object in HashMap with its declared name as key after initialization and + // configuration. solenoids.put(json.get("name").toString(), solenoid); } catch (Exception e) { DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() @@ -45,9 +56,13 @@ default void initSolenoids(JSONObject robotMap, String subsystemName) { + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. solenoidArray.clear(); } catch (Exception e) { DriverStation.reportError( diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java index 0d0df07..6dc93cc 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java @@ -5,35 +5,46 @@ import org.json.simple.JSONArray; import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.Ultrasonic; /** - * Interface to allow Ultrasonic initialization via JSON file. Subsystem needs - * to extend SuperSubsystem. + * Interface to allow {@link Ultrasonic} initialization via JSON. Subsystems + * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} + * and implement this interface in order to initialize {@link Ultrasonic + * Ultrasonics} declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperUltrasonic { /** - * HashMap storing the SuperSubsystem's Ultrasonics. + * HashMap storing the {@link SuperSubsystem}'s {@link Ultrasonic Ultrasonics}. */ public HashMap ultrasonics = new HashMap(); /** - * Method to initialize Ultrasonics declared in JSON file, and add them to the - * HashMap using its name as its key. + * Method to initialize {@link Ultrasonic Ultrasonics} declared in the + * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the + * {@link #ultrasonics} HashMap using its declared name as its key. * - * @param robotMap - * @param subsystemName + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} */ default void initUltrasonics(JSONObject robotMap, String subsystemName) { try { + // Create a JSONArray out of the declared objects. JSONArray ultrasonicArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) .get(subsystemName)).get("ultrasonics"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. Arrays.stream(ultrasonicArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { try { + // Create an object out of one index in the JSONArray. Ultrasonic ultrasonic = new Ultrasonic(Integer.parseInt(json.get("pingChannel").toString()), Integer.parseInt(json.get("echoChannel").toString())); + // Put object in HashMap with its declared name as key after initialization and + // configuration. ultrasonics.put(json.get("name").toString(), ultrasonic); } catch (Exception e) { DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() @@ -42,9 +53,13 @@ default void initUltrasonics(JSONObject robotMap, String subsystemName) { + e.getMessage()); System.exit(1); } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. json.clear(); } }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. ultrasonicArray.clear(); } catch (Exception e) { DriverStation.reportError( From d253449a110a3f3ca3c3543a0f51a9b90519a97f Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Sun, 30 Jun 2019 14:05:23 -0500 Subject: [PATCH 08/10] Added a variable to PIDSuperSubsystem. [Subsystems] - Added pidOutput, just to store it if needed. --- .../java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java | 1 + 1 file changed, 1 insertion(+) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java index 0c346a1..2a13e61 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java @@ -21,6 +21,7 @@ public abstract class PIDSuperSubsystem extends PIDSubsystem { */ protected JSONObject robotMap; protected float p = 0.0f, i = 0.0f, d = 0.0f; + protected double pidOutput; /** * Constructor for {@link PIDSuperSubsystem}. Initializes the From 3ce145437785e8804df12e8559fdb02f5d5a28e1 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Sun, 30 Jun 2019 14:15:09 -0500 Subject: [PATCH 09/10] Added getter in PIDSuperSubsystem. [Subsystems] - Added getter for pidOutput. --- .../usfirst/lib6647/subsystem/PIDSuperSubsystem.java | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java index 2a13e61..649107e 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java @@ -126,4 +126,14 @@ public void updatePIDValues() { getPIDController().setPID(p, i, d); } + + /** + * Method to return {@link #pidOutput}, must be updated in a PID loop in order + * to be useful. + * + * @return pidOutput + */ + public double getPIDOutput() { + return pidOutput; + } } \ No newline at end of file From bdd1d98355d78067590e51e348eccd4aee19e363 Mon Sep 17 00:00:00 2001 From: pacoito123 Date: Sat, 6 Jul 2019 10:51:14 -0500 Subject: [PATCH 10/10] Exception overhaul, and some other changes. [General] - Heavily updated README.md. - Exception Handling is now finally a thing I did! - Removed DS warnings, now you must select +Prints to see messages. [HyperComponents] - HyperTalon now configs to factory default when instantiated. - Removed Talon-only methods in MotorUtils, moved to SuperTalon. - HyperVictor now configs to factory default when instantiated. - Removed Victor-only methods in MotorUtils, moved to SuperVictor. - HyperSolenoid and HyperDoubleSolenoid added. [SuperComponents] - Added SuperDoubleSolenoid. [OI] - JController axisButton tolerance doubled. --- README.md | 99 ++++++- .../org/usfirst/lib6647/oi/ButtonHelper.java | 7 - .../org/usfirst/lib6647/oi/JController.java | 6 +- .../lib6647/subsystem/PIDSuperSubsystem.java | 5 - .../lib6647/subsystem/SuperSubsystem.java | 3 - .../hypercomponents/HyperDoubleSolenoid.java | 50 ++++ .../hypercomponents/HyperSolenoid.java | 25 ++ .../subsystem/hypercomponents/HyperTalon.java | 11 +- .../hypercomponents/HyperVictor.java | 7 +- .../supercomponents/SuperCompressor.java | 64 +++-- .../supercomponents/SuperDigitalInput.java | 64 +++-- .../supercomponents/SuperDoubleSolenoid.java | 87 ++++++ .../supercomponents/SuperEncoder.java | 87 +++--- .../subsystem/supercomponents/SuperPDP.java | 67 ++--- .../supercomponents/SuperSolenoid.java | 107 ++++---- .../subsystem/supercomponents/SuperTalon.java | 250 +++++++++++++++--- .../supercomponents/SuperUltrasonic.java | 69 ++--- .../supercomponents/SuperVictor.java | 191 ++++++++++--- .../lib6647/util/ComponentInitException.java | 21 ++ .../org/usfirst/lib6647/util/MotorUtils.java | 216 ++------------- 20 files changed, 906 insertions(+), 530 deletions(-) create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperDoubleSolenoid.java create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperSolenoid.java create mode 100644 src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDoubleSolenoid.java create mode 100644 src/main/java/org/usfirst/lib6647/util/ComponentInitException.java diff --git a/README.md b/README.md index af8bb0b..65edcf4 100644 --- a/README.md +++ b/README.md @@ -1,22 +1,103 @@ # lib6647 -Team 6647's library to allow JSON-oriented object building and initialization. -## TODO +Team 6647's library for JSON-oriented object initialization, among other things. +

-- [ ] Implement every HyperComponent Wrapper. +## Getting Started + +### Usage + +Team 6647 encourages the usage of this library by any team that may find it useful, period. Giving us credit is optional, but greatly appreciated. Please feel free to request anything your team might need that could be added to this library. + +### Compiling lib6647 to your Robot + +**lib6647** must be added as a dependency in your Robot's _build.gradle_ file, as well as the **json-simple** library that it requires. + +First, add the following url to your Maven repositories in _build.gradle_: https://jitpack.io. This is to effortlessly compile code from any github project release or commit into your code. + +Your _build.gradle_ file should look like this (if no other Maven repositories are present): + +``` + repositories { + mavenCentral() + maven { + url 'https://jitpack.io' + } + } +``` + +Then, add **lib6647** and **json-simple** as a dependency in your _build.gradle_'s dependencies like so: + +``` + // https://mvnrepository.com/artifact/com.googlecode.json-simple/json-simple + compile group: 'com.googlecode.json-simple', name: 'json-simple', version: '1.1.1' + + // lib6647 + compile group: 'com.github.pacoito123', name: 'lib6647', version: '-SNAPSHOT' +``` + +Your dependencies in should look like this (again, if none other than WPILib's dependencies are present): + +``` + dependencies { + // WPILib dependencies. + compile wpi.deps.wpilib() + compile wpi.deps.vendor.java() + nativeZip wpi.deps.vendor.jni(wpi.platforms.roborio) + nativeDesktopZip wpi.deps.vendor.jni(wpi.platforms.desktop) + testCompile 'junit:junit:4.12' + + // https://mvnrepository.com/artifact/com.googlecode.json-simple/json-simple + compile group: 'com.googlecode.json-simple', name: 'json-simple', version: '1.1.1' + + // lib6647 + compile group: 'com.github.pacoito123', name: 'lib6647', version: '-SNAPSHOT' + } +``` + +Of course, you can change the version of the library to any specific commit in any branch, just make sure that your code is compatible with it. + +Now you're ready to begin instantiating and initializing objects through JSON! + +## To do (for now) + +- [ ] Implement every HyperComponent Wrapper (if needed). - [ ] HyperAHRS - [ ] HyperAnalogPotentiometer - [ ] HyperCompressor - [ ] HyperDigitalInput + - [ ] HyperDoubleSolenoid - [ ] HyperEncoder - [ ] HyperPDP - - [ ] HyperSolenoid - - [X] HyperTalon + - [x] HyperSolenoid + - [x] HyperTalon - [ ] HyperUltrasonic - - [X] HyperVictor -- [ ] Implement missing SuperComponents. + - [x] HyperVictor +- [ ] Implement SuperComponents. - [ ] SuperAHRS - [ ] SuperAnalogPotentiometer + - [x] SuperCompressor + - [x] SuperDigitalInput + - [x] SuperDoubleSolenoid + - [x] SuperEncoder + - [x] SuperPDP + - [x] SuperSolenoid + - [x] SuperTalon + - [x] SuperUltrasonic + - [x] SuperVictor +- [x] Improve Controller initialization. + - [x] Create JController class, for initializing Buttons along with a Controller. + - [x] Add Buttons for each POV and axis found for the Controller. - [ ] Add more flexibility and configuration options. -- [ ] Document everything properly. -- [ ] Blame mechanical. \ No newline at end of file +- [x] Document everything properly. +- [x] Do proper Exception handling. +- [ ] Write proper documentation for this library. +- [x] Blame mechanical. + +## Authors + +* **Francisco Rubio** - [pacoito123](https://github.com/pacoito123) + +## License + +This project is under the BSD License for WPILib code, see: [BSD_License_for_WPILib_code.txt](BSD_License_for_WPILib_code.txt). \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java b/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java index c334daf..f32f4d9 100644 --- a/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java +++ b/src/main/java/org/usfirst/lib6647/oi/ButtonHelper.java @@ -9,7 +9,6 @@ import org.json.simple.parser.JSONParser; import org.json.simple.parser.ParseException; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.buttons.Button; /** @@ -67,17 +66,11 @@ public Button oiButton(String joystickName, String buttonName) { // Finally, return Button object from the friendly name. return button; } catch (IOException e) { - DriverStation.reportError("[!] OIBUTTON " + buttonName + " IO ERROR: " + e.getMessage(), false); System.out.println("[!] OIBUTTON " + buttonName + " IO ERROR: " + e.getMessage()); - System.exit(1); } catch (ParseException e) { - DriverStation.reportError("[!] OIBUTTON " + buttonName + " PARSE ERROR: " + e.getMessage(), false); System.out.println("[!] OIBUTTON " + buttonName + " PARSE ERROR: " + e.getMessage()); - System.exit(1); } catch (Exception e) { - DriverStation.reportError("[!] OIBUTTON " + buttonName + " ERROR: " + e.getMessage(), false); System.out.println("[!] OIBUTTON " + buttonName + " ERROR: " + e.getMessage()); - System.exit(1); } return null; } diff --git a/src/main/java/org/usfirst/lib6647/oi/JController.java b/src/main/java/org/usfirst/lib6647/oi/JController.java index ec50d39..441bb14 100644 --- a/src/main/java/org/usfirst/lib6647/oi/JController.java +++ b/src/main/java/org/usfirst/lib6647/oi/JController.java @@ -131,7 +131,7 @@ private Button buttonFromAxis(GenericHID controller, int axis) { return new Button() { @Override public boolean get() { - return Math.abs(controller.getRawAxis(axis)) < 0.15; + return Math.abs(controller.getRawAxis(axis)) < 0.30; } }; } @@ -148,7 +148,7 @@ private Button buttonFromAxisNegative(GenericHID controller, int axis) { return new Button() { @Override public boolean get() { - return controller.getRawAxis(axis) < -0.15; + return controller.getRawAxis(axis) < -0.30; } }; } @@ -165,7 +165,7 @@ private Button buttonFromAxisPositive(GenericHID controller, int axis) { return new Button() { @Override public boolean get() { - return controller.getRawAxis(axis) > 0.15; + return controller.getRawAxis(axis) > 0.30; } }; } diff --git a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java index 649107e..dbf2f1b 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/PIDSuperSubsystem.java @@ -6,7 +6,6 @@ import org.json.simple.JSONObject; import org.json.simple.parser.JSONParser; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.command.PIDSubsystem; import edu.wpi.first.wpilibj.smartdashboard.SmartDashboard; @@ -51,8 +50,6 @@ private void initJSON(String fileName) { robotMap = (JSONObject) parser.parse(file); file.close(); } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + getName().toUpperCase() + "' JSON INIT ERROR: " + e.getMessage(), false); System.out.println("[!] SUBSYSTEM '" + getName().toUpperCase() + "' JSON INIT ERROR: " + e.getMessage()); System.exit(1); } @@ -86,8 +83,6 @@ private void initPID() { // some unused memory. pid.clear(); } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + getName().toUpperCase() + "' PID INIT ERROR: " + e.getMessage(), false); System.out.println("[!] SUBSYSTEM '" + getName().toUpperCase() + "' PID INIT ERROR: " + e.getMessage()); System.exit(1); } diff --git a/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java b/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java index f8f0ea4..b1bdc4b 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/SuperSubsystem.java @@ -6,7 +6,6 @@ import org.json.simple.JSONObject; import org.json.simple.parser.JSONParser; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.command.Subsystem; /** @@ -44,8 +43,6 @@ private void initJSON(String fileName) { robotMap = (JSONObject) parser.parse(file); file.close(); } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + getName().toUpperCase() + "' JSON INIT ERROR: " + e.getMessage(), false); System.out.println("[!] SUBSYSTEM '" + getName().toUpperCase() + "' JSON INIT ERROR: " + e.getMessage()); System.exit(1); } diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperDoubleSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperDoubleSolenoid.java new file mode 100644 index 0000000..eab1afb --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperDoubleSolenoid.java @@ -0,0 +1,50 @@ +package org.usfirst.lib6647.subsystem.hypercomponents; + +import edu.wpi.first.wpilibj.Solenoid; + +/** + * HyperComponent for a {@link Solenoid DoubleSolenoid}. + */ +public class HyperDoubleSolenoid { + + /** + * {@link Solenoid Solenoids} for . + */ + private Solenoid forward, reverse; + + /** + * Wrapper for a {@link Solenoid DoubleSolenoid}. + * + * @param forwardChannel + * @param reverseChannel + */ + public HyperDoubleSolenoid(int forwardChannel, int reverseChannel) { + forward = new Solenoid(forwardChannel); + reverse = new Solenoid(reverseChannel); + } + + /** + * Set {@link Solenoid DoubleSolenoid} to a specific value. + * + * @param value + */ + public void set(boolean value) { + forward.set(value); + reverse.set(!value); + } + + /** + * Toggle {@link Solenoid DoubleSolenoid}. + */ + public void toggle() { + set(!forward.get()); + } + + /** + * Stop any {@link Solenoid DoubleSolenoid} movement. + */ + public void stop() { + forward.set(false); + reverse.set(false); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperSolenoid.java new file mode 100644 index 0000000..5078411 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperSolenoid.java @@ -0,0 +1,25 @@ +package org.usfirst.lib6647.subsystem.hypercomponents; + +import edu.wpi.first.wpilibj.Solenoid; + +/** + * HyperComponent for {@link Solenoid}. + */ +public class HyperSolenoid extends Solenoid { + + /** + * Wrapper for {@link Solenoid}. + * + * @param channel + */ + public HyperSolenoid(int channel) { + super(channel); + } + + /** + * Toggle {@link Solenoid}. + */ + public void toggle() { + set(!get()); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java index 7c9a51f..4a8e1e1 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperTalon.java @@ -9,8 +9,9 @@ public class HyperTalon extends WPI_TalonSRX { /** - * Limits how fast the Talon can go if using {@link #setTalonWithRamp(double)} - * or {@link #setTalon(double, boolean)} if true. + * Limits how fast the Talon can go as a percentage if using + * {@link #setTalonWithRamp(double)} or {@link #setTalon(double, boolean)} if + * true. */ private double limiter = 1; @@ -21,10 +22,12 @@ public class HyperTalon extends WPI_TalonSRX { */ public HyperTalon(int port) { super(port); + + configFactoryDefault(); } /** - * Returns {@link #limiter} value for Talon speed. + * Returns {@link #limiter} value for {@link WPI_TalonSRX} speed. * * @return */ @@ -33,7 +36,7 @@ public double getLimiter() { } /** - * Sets {@link #limiter} for Talon speed. + * Sets {@link #limiter} for {@link WPI_TalonSRX} speed. */ public void setLimiter(double limiter) { this.limiter = limiter; diff --git a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java index bf4332b..f4c4911 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/hypercomponents/HyperVictor.java @@ -9,8 +9,9 @@ public class HyperVictor extends WPI_VictorSPX { /** - * Limits how fast the Victor can go if using {@link #setVictorWithRamp(double)} - * or {@link #setVictor(double, boolean)} if true. + * Limits how fast the Victor can go as a percentage if using + * {@link #setVictorWithRamp(double)} or {@link #setVictor(double, boolean)} if + * true. */ private double limiter = 1; @@ -21,6 +22,8 @@ public class HyperVictor extends WPI_VictorSPX { */ public HyperVictor(int port) { super(port); + + configFactoryDefault(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java index 6104c0c..1cfa659 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperCompressor.java @@ -7,9 +7,9 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.util.ComponentInitException; import edu.wpi.first.wpilibj.Compressor; -import edu.wpi.first.wpilibj.DriverStation; /** * Interface to allow {@link Compressor} initialization via JSON. Subsystems @@ -32,42 +32,40 @@ public interface SuperCompressor { * @param {@link SuperSubsystem#getName} */ default void initCompressors(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray compressorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("compressors"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(compressorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - Compressor compressor = new Compressor(Integer.parseInt(json.get("module").toString())); + // Create a JSONArray out of the declared objects. + JSONArray compressorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("compressors"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(compressorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("module")) { + + Compressor compressor; + try { + // Try to initialize an object from an index in the JSONArray. + compressor = new Compressor(Integer.parseInt(json.get("module").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format( + "[!] INVALID OR EMPTY MODULE VALUE FOR COMPRESSOR '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } + // Put object in HashMap with its declared name as key after initialization and // configuration. compressors.put(json.get("name").toString(), compressor); - } catch (Exception e) { - DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() - + "' COMPRESSOR INIT ERROR: " + e.getMessage(), false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' COMPRESSOR INIT ERROR: " - + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - compressorArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' COMPRESSOR INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' COMPRESSOR INIT ERROR: " + e.getMessage()); - System.exit(1); - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + compressorArray.clear(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java index 501f845..7a502ea 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDigitalInput.java @@ -7,9 +7,9 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.util.ComponentInitException; import edu.wpi.first.wpilibj.DigitalInput; -import edu.wpi.first.wpilibj.DriverStation; /** * Interface to allow {@link DigitalInput} initialization via JSON. Subsystems @@ -33,42 +33,40 @@ public interface SuperDigitalInput { * @param {@link SuperSubsystem#getName} */ default void initDigitalInputs(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray digitalInputArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("digitalInputs"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(digitalInputArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - DigitalInput digitalInput = new DigitalInput(Integer.parseInt(json.get("channel").toString())); + // Create a JSONArray out of the declared objects. + JSONArray digitalInputArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("digitalInputs"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(digitalInputArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("channel")) { + + DigitalInput digitalInput; + try { + // Try to initialize an object from an index in the JSONArray. + digitalInput = new DigitalInput(Integer.parseInt(json.get("channel").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format( + "[!] INVALID OR EMPTY CHANNEL VALUE FOR DIGITALINPUT '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } + // Put object in HashMap with its declared name as key after initialization and // configuration. digitalInputs.put(json.get("name").toString(), digitalInput); - } catch (Exception e) { - DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() - + "' DIGITAL INPUT INIT ERROR: " + e.getMessage(), false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' DIGITAL INPUT INIT ERROR: " - + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - digitalInputArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' DIGITAL INPUT INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' DIGITAL INPUT INIT ERROR: " + e.getMessage()); - System.exit(1); - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + digitalInputArray.clear(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDoubleSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDoubleSolenoid.java new file mode 100644 index 0000000..ca444e4 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperDoubleSolenoid.java @@ -0,0 +1,87 @@ +package org.usfirst.lib6647.subsystem.supercomponents; + +import java.util.Arrays; +import java.util.HashMap; + +import org.json.simple.JSONArray; +import org.json.simple.JSONObject; +import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; +import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperDoubleSolenoid; +import org.usfirst.lib6647.util.ComponentInitException; + +/** + * Interface to allow {@link HyperDoubleSolenoid} initialization via JSON. + * Subsystems declared need to extend {@link SuperSubsystem} or + * {@link PIDSuperSubsystem} and implement this interface in order to initialize + * {@link HyperDoubleSolenoid HyperDoubleSolenoids} declared in + * {@link SuperSubsystem#robotMap robotMap}. + */ +public interface SuperDoubleSolenoid { + /** + * HashMap storing the {@link SuperSubsystem}'s {@link HyperDoubleSolenoid + * HyperDoubleSolenoids}. + */ + public HashMap solenoids = new HashMap(); + + /** + * Method to initialize {@link HyperDoubleSolenoid HyperDoubleSolenoids} + * declared in the {@link SuperSubsystem#robotMap robotMap} JSON file, and add + * them to the {@link #solenoids} HashMap using its declared name as its key. + * + * @param {@link SuperSubsystem#robotMap} + * @param {@link SuperSubsystem#getName} + */ + default void initSolenoids(JSONObject robotMap, String subsystemName) { + // Create a JSONArray out of the declared objects. + JSONArray solenoidArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("doubleSolenoids"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(solenoidArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("forwardChannel") + && json.containsKey("reverseChannel")) { + + HyperDoubleSolenoid solenoid; + try { + // Try to initialize an object from an index in the JSONArray. + solenoid = new HyperDoubleSolenoid(Integer.parseInt(json.get("forwardChannel").toString()), + Integer.parseInt(json.get("reverseChannel").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format( + "[!] INVALID OR EMPTY CHANNEL VALUE(S) FOR DOUBLESOLENOID '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } + solenoid.stop(); + + // Put object in HashMap with its declared name as key after initialization and + // configuration. + solenoids.put(json.get("name").toString(), solenoid); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY DOUBLESOLENOID ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); + } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + solenoidArray.clear(); + } + + /** + * Gets specified {@link HyperDoubleSolenoid}. + * + * @return {@link HyperDoubleSolenoid} + * @param solenoidName + */ + default HyperDoubleSolenoid getSolenoid(String solenoidName) { + return solenoids.get(solenoidName); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java index 0830dc7..4cfdb86 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperEncoder.java @@ -7,9 +7,9 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.util.ComponentInitException; +import org.usfirst.lib6647.util.MotorUtils; -import edu.wpi.first.wpilibj.CounterBase.EncodingType; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.Encoder; /** @@ -18,7 +18,7 @@ * and implement this interface in order to initialize {@link Encoder Encoders} * declared in {@link SuperSubsystem#robotMap robotMap}. */ -public interface SuperEncoder { +public interface SuperEncoder extends MotorUtils { /** * HashMap storing the {@link SuperSubsystem}'s {@link Encoder Encoders}. */ @@ -33,60 +33,45 @@ public interface SuperEncoder { * @param {@link SuperSubsystem#getName} */ default void initEncoders(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray encoderArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("encoders"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(encoderArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - Encoder encoder = new Encoder(Integer.parseInt(json.get("channelA").toString()), - Integer.parseInt(json.get("channelB").toString()), - Boolean.parseBoolean(json.get("reverse").toString()), - getEncodingType(json.get("encodingType").toString())); + // Create a JSONArray out of the declared objects. + JSONArray encoderArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) + .get("encoders"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(encoderArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("channelA") && json.containsKey("channelB") + && json.containsKey("reverse") && json.containsKey("encodingType")) { + + Encoder encoder; + try { + // Try to initialize an object from an index in the JSONArray. + encoder = new Encoder(Integer.parseInt(json.get("channelA").toString()), + Integer.parseInt(json.get("channelB").toString()), + Boolean.parseBoolean(json.get("reverse").toString()), + getEncodingType(json.get("encodingType").toString())); + } catch (NullPointerException | NumberFormatException e) { + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY VALUE(S) FOR ENCODER '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } encoder.reset(); // Put object in HashMap with its declared name as key after initialization and // configuration. encoders.put(json.get("name").toString(), encoder); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ENCODER INIT ERROR: " + e.getMessage(), - false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ENCODER INIT ERROR: " - + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - encoderArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ENCODER INIT ERROR: " + e.getMessage(), false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ENCODER INIT ERROR: " + e.getMessage()); - System.exit(1); - } - } - - default EncodingType getEncodingType(String encodingType) { - switch (encodingType) { - case "k1X": - return EncodingType.k1X; - case "k2X": - return EncodingType.k2X; - case "k4X": - return EncodingType.k4X; - default: - return null; - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + encoderArray.clear(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java index e7b831a..19b93f2 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperPDP.java @@ -7,8 +7,8 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.util.ComponentInitException; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.PowerDistributionPanel; /** @@ -34,42 +34,43 @@ public interface SuperPDP { * @param {@link SuperSubsystem#getName} */ default void initPDPs(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray PDPArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) - .get("PDPs"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(PDPArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - PowerDistributionPanel pdp = new PowerDistributionPanel( - Integer.parseInt(json.get("module").toString())); + // Create a JSONArray out of the declared objects. + JSONArray PDPArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) + .get("PDPs"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(PDPArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("module")) { + + PowerDistributionPanel pdp; + try { + // Try to initialize an object from an index in the JSONArray. + pdp = new PowerDistributionPanel(Integer.parseInt(json.get("module").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY PORT VALUE FOR PDP '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } + // Put object in HashMap with its declared name as key after initialization and // configuration. PDPs.put(json.get("name").toString(), pdp); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' PDP INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' PDP INIT ERROR: " + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY PDP ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - PDPArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' PDP INIT ERROR: " + e.getMessage(), false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' PDP INIT ERROR: " + e.getMessage()); - System.exit(1); - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + PDPArray.clear(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java index 02ad4ce..9381a49 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperSolenoid.java @@ -7,24 +7,24 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; - -import edu.wpi.first.wpilibj.DriverStation; -import edu.wpi.first.wpilibj.Solenoid; +import org.usfirst.lib6647.subsystem.hypercomponents.HyperSolenoid; +import org.usfirst.lib6647.util.ComponentInitException; /** - * Interface to allow {@link Solenoid} initialization via JSON. Subsystems + * Interface to allow {@link HyperSolenoid} initialization via JSON. Subsystems * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} - * and implement this interface in order to initialize {@link Solenoid - * Solenoids} declared in {@link SuperSubsystem#robotMap robotMap}. + * and implement this interface in order to initialize {@link HyperSolenoid + * HyperSolenoids} declared in {@link SuperSubsystem#robotMap robotMap}. */ public interface SuperSolenoid { /** - * HashMap storing the {@link SuperSubsystem}'s {@link Solenoid Solenoids}. + * HashMap storing the {@link SuperSubsystem}'s {@link HyperSolenoid + * HyperSolenoids}. */ - public HashMap solenoids = new HashMap(); + public HashMap solenoids = new HashMap(); /** - * Method to initialize {@link Solenoid Solenoids} declared in the + * Method to initialize {@link HyperSolenoid HyperSolenoids} declared in the * {@link SuperSubsystem#robotMap robotMap} JSON file, and add them to the * {@link #solenoids} HashMap using its declared name as its key. * @@ -32,55 +32,72 @@ public interface SuperSolenoid { * @param {@link SuperSubsystem#getName} */ default void initSolenoids(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray solenoidArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("solenoids"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(solenoidArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - Solenoid solenoid = new Solenoid(Integer.parseInt(json.get("channel").toString())); + // Create a JSONArray out of the declared objects. + JSONArray solenoidArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("solenoids"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(solenoidArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("channel")) { + + HyperSolenoid solenoid; + try { + // Create an object out of one index in the JSONArray. + solenoid = new HyperSolenoid(Integer.parseInt(json.get("channel").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format( + "[!] INVALID OR EMPTY CHANNEL VALUE(S) FOR SOLENOID '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } if (json.containsKey("initialValue")) - solenoid.set(Boolean.parseBoolean(json.get("initialValue").toString())); + setInitialValue(json, solenoid); // Put object in HashMap with its declared name as key after initialization and // configuration. solenoids.put(json.get("name").toString(), solenoid); - } catch (Exception e) { - DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() - + "' SOLENOID INIT ERROR: " + e.getMessage(), false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' SOLENOID INIT ERROR: " - + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY SOLENOID ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - solenoidArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' SOLENOID INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' SOLENOID INIT ERROR: " + e.getMessage()); - System.exit(1); - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + solenoidArray.clear(); + } + + /** + * Sets a given {@link HyperSolenoid}'s inverted value from a + * {@link JSONObject}. + * + * @param {@link JSONObject} + * @param {@link HyperSolenoid} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty. + */ + default void setInitialValue(JSONObject json, HyperSolenoid solenoid) throws ComponentInitException { + if (json.get("initialValue").toString().isEmpty()) + throw new ComponentInitException(String.format("[!] EMPTY INITIAL VALUE FOR SOLENOID '%s'.", + json.get("name").toString().toUpperCase())); + + solenoid.set(Boolean.parseBoolean(json.get("initialValue").toString())); } /** - * Gets specified {@link Solenoid}. + * Gets specified {@link HyperSolenoid}. * - * @return {@link Solenoid} + * @return {@link HyperSolenoid} * @param solenoidName */ - default Solenoid getSolenoid(String solenoidName) { + default HyperSolenoid getSolenoid(String solenoidName) { return solenoids.get(solenoidName); } } \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java index 88587fb..88a6c42 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperTalon.java @@ -3,15 +3,16 @@ import java.util.Arrays; import java.util.HashMap; +import com.ctre.phoenix.motorcontrol.NeutralMode; + import org.json.simple.JSONArray; import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; +import org.usfirst.lib6647.util.ComponentInitException; import org.usfirst.lib6647.util.MotorUtils; -import edu.wpi.first.wpilibj.DriverStation; - /** * Interface to allow {@link HyperTalon} initialization via JSON. Subsystems * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} @@ -31,21 +32,26 @@ public interface SuperTalon extends MotorUtils { * * @param {@link SuperSubsystem#robotMap} * @param {@link SuperSubsystem#getName} - * - * @Note ALWAYS declare and initialize masters before followers! */ default void initTalons(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray talonArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("talons"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(talonArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - HyperTalon talon = new HyperTalon(Integer.parseInt(json.get("port").toString())); + // Create a JSONArray out of the declared objects. + JSONArray talonArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) + .get("talons"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(talonArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("port")) { + HyperTalon talon; + try { + // Try to initialize an object from an index in the JSONArray. + talon = new HyperTalon(Integer.parseInt(json.get("port").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY PORT VALUE FOR TALON '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } talon.setName(json.get("name").toString()); if (json.containsKey("limiter")) @@ -57,8 +63,10 @@ default void initTalons(JSONObject robotMap, String subsystemName) { if (json.containsKey("inverted")) setInverted(json, talon); - if (json.containsKey("loopRamp")) - setLoopRamp(json, talon); + if (json.containsKey("loopRamp")) { + setClosedloopRamp(json, talon); + setOpenloopRamp(json, talon); + } if (json.containsKey("sensor")) setSensors(json, talon); @@ -71,28 +79,196 @@ default void initTalons(JSONObject robotMap, String subsystemName) { // Put object in HashMap with its declared name as key after initialization and // configuration. talons.put(json.get("name").toString(), talon); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY TALON ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - talonArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage(), false); - System.out - .println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' TALON INIT ERROR: " + e.getMessage()); - System.exit(1); + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + talonArray.clear(); + } + + /** + * Sets a given {@link HyperTalon}'s {@link HyperTalon#limiter limiter} value + * from a {@link JSONObject}. Max value is 1, min value is 0 (which would make + * the {@link HyperTalon} stop). + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty or not a number. + */ + default void setLimiter(JSONObject json, HyperTalon talon) throws ComponentInitException { + try { + double limiter = Double.parseDouble(json.get("limiter").toString()); + talon.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY LIMITER VALUE FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID LIMITER VALUE FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperTalon}'s inverted value from a {@link JSONObject}. + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty. + */ + default void setInverted(JSONObject json, HyperTalon talon) throws ComponentInitException { + if (json.get("inverted").toString().isEmpty()) + throw new ComponentInitException(String.format("[!] EMPTY INVERTED VALUE FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + + talon.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + } + + /** + * Sets a given {@link HyperTalon}'s {@link NeutralMode} from a + * {@link JSONObject} key. + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty or invalid. + * + * @note There are three types of {@link NeutralMode NeutralModes}: + * {@link NeutralMode#Coast Coast}, {@link NeutralMode#Brake Brake}, and + * {@link NeutralMode#EEPROMSetting EEPROMSetting}. All of which must + * share the same name in the {@link JSONObject}. + */ + default void setNeutralMode(JSONObject json, HyperTalon talon) throws ComponentInitException { + if (getNeutralMode(json.get("neutralMode").toString()) == null) + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY NEUTRAL MODE CONFIGURATION FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + + talon.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); + } + + /** + * Sets a given {@link HyperTalon}'s ClosedloopRamp from a {@link JSONObject} + * key. + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setClosedloopRamp(JSONObject json, HyperTalon talon) throws ComponentInitException { + try { + JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"); + + if (closed.containsKey("timeoutMs")) + talon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), + Integer.parseInt(closed.get("timeoutMs").toString())); + else + talon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY CLOSEDLOOP RAMP VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID CLOSEDLOOP RAMP VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperTalon}'s OpenloopRamp from a {@link JSONObject} key. + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setOpenloopRamp(JSONObject json, HyperTalon talon) throws ComponentInitException { + try { + JSONObject open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); + + if (open.containsKey("timeoutMs")) + talon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), + Integer.parseInt(open.get("timeoutMs").toString())); + else + talon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY OPENLOOP RAMP VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID OPENLOOP RAMP VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperTalon}'s sensors from a {@link JSONObject} key + * (fairly limited in terms of configuration at the moment). + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setSensors(JSONObject json, HyperTalon talon) throws ComponentInitException { + try { + JSONObject sensor = (JSONObject) json.get("sensor"); + JSONObject feedback = (JSONObject) sensor.get("feedback"); + + talon.configSelectedFeedbackSensor(getFeedbackDevice(feedback.get("feedbackDevice").toString()), + Integer.parseInt(feedback.get("pidIdx").toString()), + Integer.parseInt(feedback.get("timeoutMs").toString())); + + talon.setSensorPhase(Boolean.parseBoolean(sensor.get("phase").toString())); + + talon.setSelectedSensorPosition(Integer.parseInt(sensor.get("sensorPos").toString()), + Integer.parseInt(sensor.get("pidIdx").toString()), + Integer.parseInt(sensor.get("timeoutMs").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY SENSOR VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID SENSOR VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperTalon}'s PID values from a {@link JSONObject} key. + * + * @param {@link JSONObject} + * @param {@link HyperTalon} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setPIDValues(JSONObject json, HyperTalon talon) throws ComponentInitException { + try { + JSONObject pid = (JSONObject) json.get("pid"); + + talon.config_kP(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("p").toString())); + talon.config_kI(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("i").toString())); + talon.config_kD(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("d").toString())); + talon.config_kF(Integer.parseInt(pid.get("slotIdx").toString()), + Double.parseDouble(pid.get("f").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException( + String.format("[!] EMPTY PID VALUE(S) FOR TALON '%s'.", json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID PID VALUE(S) FOR TALON '%s'.", + json.get("name").toString().toUpperCase())); } } diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java index 6dc93cc..f68c9bf 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperUltrasonic.java @@ -7,8 +7,8 @@ import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; +import org.usfirst.lib6647.util.ComponentInitException; -import edu.wpi.first.wpilibj.DriverStation; import edu.wpi.first.wpilibj.Ultrasonic; /** @@ -32,43 +32,44 @@ public interface SuperUltrasonic { * @param {@link SuperSubsystem#getName} */ default void initUltrasonics(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray ultrasonicArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("ultrasonics"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(ultrasonicArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - Ultrasonic ultrasonic = new Ultrasonic(Integer.parseInt(json.get("pingChannel").toString()), - Integer.parseInt(json.get("echoChannel").toString())); + // Create a JSONArray out of the declared objects. + JSONArray ultrasonicArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) + .get(subsystemName)).get("ultrasonics"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(ultrasonicArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("pingChannel") && json.containsKey("echoChannel")) { + + Ultrasonic ultrasonic; + try { + // Create an object out of one index in the JSONArray. + ultrasonic = new Ultrasonic(Integer.parseInt(json.get("pingChannel").toString()), + Integer.parseInt(json.get("echoChannel").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY VALUE(S) FOR ULTRASONIC '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } + // Put object in HashMap with its declared name as key after initialization and // configuration. ultrasonics.put(json.get("name").toString(), ultrasonic); - } catch (Exception e) { - DriverStation.reportError("[!] SUBSYSTEM '" + subsystemName.toUpperCase() - + "' ULTRASONIC INIT ERROR: " + e.getMessage(), false); - System.out.println("[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ULTRASONIC INIT ERROR: " - + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY ULTRASONIC ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - ultrasonicArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ULTRASONIC INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' ULTRASONIC INIT ERROR: " + e.getMessage()); - System.exit(1); - } + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + ultrasonicArray.clear(); } /** diff --git a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java index 559f624..98dff37 100644 --- a/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java +++ b/src/main/java/org/usfirst/lib6647/subsystem/supercomponents/SuperVictor.java @@ -3,16 +3,16 @@ import java.util.Arrays; import java.util.HashMap; +import com.ctre.phoenix.motorcontrol.NeutralMode; + import org.json.simple.JSONArray; import org.json.simple.JSONObject; import org.usfirst.lib6647.subsystem.PIDSuperSubsystem; import org.usfirst.lib6647.subsystem.SuperSubsystem; -import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; import org.usfirst.lib6647.subsystem.hypercomponents.HyperVictor; +import org.usfirst.lib6647.util.ComponentInitException; import org.usfirst.lib6647.util.MotorUtils; -import edu.wpi.first.wpilibj.DriverStation; - /** * Interface to allow {@link HyperVictor} initialization via JSON. Subsystems * declared need to extend {@link SuperSubsystem} or {@link PIDSuperSubsystem} @@ -33,21 +33,26 @@ public interface SuperVictor extends MotorUtils { * * @param {@link SuperSubsystem#robotMap} * @param {@link SuperSubsystem#getName} - * - * @Note ALWAYS declare and initialize masters before followers! */ default void initVictors(JSONObject robotMap, String subsystemName) { - try { - // Create a JSONArray out of the declared objects. - JSONArray victorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")) - .get(subsystemName)).get("victors"); - // Create a stream to cast each entry in the JSONArray into a JSONObject, in - // order to configure it using the values declared in the robotMap file. - Arrays.stream(victorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { - try { - // Create an object out of one index in the JSONArray. - HyperVictor victor = new HyperVictor(Integer.parseInt(json.get("port").toString())); + // Create a JSONArray out of the declared objects. + JSONArray victorArray = (JSONArray) ((JSONObject) ((JSONObject) robotMap.get("subsystems")).get(subsystemName)) + .get("victors"); + // Create a stream to cast each entry in the JSONArray into a JSONObject, in + // order to configure it using the values declared in the robotMap file. + Arrays.stream(victorArray.toArray()).map(json -> (JSONObject) json).forEach(json -> { + try { + if (json.containsKey("name") && json.containsKey("port")) { + HyperVictor victor; + try { + // Create an object out of one index in the JSONArray. + victor = new HyperVictor(Integer.parseInt(json.get("port").toString())); + } catch (NumberFormatException e) { + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY PORT VALUE FOR VICTOR '%1$s' IN SUBSYSTEM '%2$s'", + json.get("name").toString(), subsystemName)); + } victor.setName(json.get("name").toString()); if (json.containsKey("limiter")) @@ -59,36 +64,146 @@ default void initVictors(JSONObject robotMap, String subsystemName) { if (json.containsKey("inverted")) setInverted(json, victor); - if (json.containsKey("loopRamp")) - setLoopRamp(json, victor); + if (json.containsKey("loopRamp")) { + setClosedloopRamp(json, victor); + setOpenloopRamp(json, victor); + } victor.stopMotor(); // Put object in HashMap with its declared name as key after initialization and // configuration. victors.put(json.get("name").toString(), victor); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), - false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); - System.exit(1); - } finally { - // Clear JSONObject after use, not sure if it does anything, but it might free - // some unused memory. - json.clear(); + } else { + System.out.println(String.format("[!] UNDECLARED OR EMPTY VICTOR ENTRY IN SUBSYSTEM '%s'", + subsystemName.toUpperCase())); } - }); - // Clear JSONArray after use, not sure if it does anything, but it might free - // some unused memory. - victorArray.clear(); - } catch (Exception e) { - DriverStation.reportError( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage(), false); - System.out.println( - "[!] SUBSYSTEM '" + subsystemName.toUpperCase() + "' VICTOR INIT ERROR: " + e.getMessage()); - System.exit(1); + } catch (ComponentInitException e) { + System.out.println(e.getMessage()); + } finally { + // Clear JSONObject after use, not sure if it does anything, but it might free + // some unused memory. + json.clear(); + } + }); + // Clear JSONArray after use, not sure if it does anything, but it might free + // some unused memory. + victorArray.clear(); + } + + /** + * Sets a given {@link HyperVictor}'s {@link HyperVictor#limiter limiter} value + * from a {@link JSONObject}. Max value is 1, min value is 0 (which would make + * the {@link HyperVictor} stop). + * + * @param {@link JSONObject} + * @param {@link HyperVictor} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty or not a number. + */ + default void setLimiter(JSONObject json, HyperVictor victor) throws ComponentInitException { + try { + double limiter = Double.parseDouble(json.get("limiter").toString()); + victor.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY LIMITER VALUE FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID LIMITER VALUE FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperVictor}'s inverted value from a {@link JSONObject}. + * + * @param {@link JSONObject} + * @param {@link HyperVictor} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty. + */ + default void setInverted(JSONObject json, HyperVictor victor) throws ComponentInitException { + if (json.get("inverted").toString().isEmpty()) + throw new ComponentInitException(String.format("[!] EMPTY INVERTED VALUE FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + + victor.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); + } + + /** + * Sets a given {@link HyperVictor}'s {@link NeutralMode} from a + * {@link JSONObject} key. + * + * @param {@link JSONObject} + * @param {@link HyperVictor} + * @throws ComponentInitException if {@link JSONObject} key is defined, but + * empty or invalid. + * + * @note There are three types of {@link NeutralMode NeutralModes}: + * {@link NeutralMode#Coast Coast}, {@link NeutralMode#Brake Brake}, and + * {@link NeutralMode#EEPROMSetting EEPROMSetting}. All of which must + * share the same name in the {@link JSONObject}. + */ + default void setNeutralMode(JSONObject json, HyperVictor victor) throws ComponentInitException { + if (getNeutralMode(json.get("neutralMode").toString()) == null) + throw new ComponentInitException( + String.format("[!] INVALID OR EMPTY NEUTRAL MODE CONFIGURATION FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + + victor.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); + } + + /** + * Sets a given {@link HyperVictor}'s ClosedloopRamp from a {@link JSONObject} + * key. + * + * @param {@link JSONObject} + * @param {@link HyperVictor} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setClosedloopRamp(JSONObject json, HyperVictor victor) throws ComponentInitException { + try { + JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"); + + if (closed.containsKey("timeoutMs")) + victor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), + Integer.parseInt(closed.get("timeoutMs").toString())); + else + victor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY CLOSEDLOOP RAMP VALUE(S) FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID CLOSEDLOOP RAMP VALUE(S) FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + } + } + + /** + * Sets a given {@link HyperVictor}'s OpenloopRamp from a {@link JSONObject} + * key. + * + * @param {@link JSONObject} + * @param {@link HyperVictor} + * @throws ComponentInitException if {@link JSONObject} key is not found, or its + * subkeys are invalid or empty. + */ + default void setOpenloopRamp(JSONObject json, HyperVictor victor) throws ComponentInitException { + try { + JSONObject open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); + + if (open.containsKey("timeoutMs")) + victor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), + Integer.parseInt(open.get("timeoutMs").toString())); + else + victor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); + } catch (NullPointerException e) { + throw new ComponentInitException(String.format("[!] EMPTY OPENLOOP RAMP VALUE(S) FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); + } catch (NumberFormatException e) { + throw new ComponentInitException(String.format("[!] INVALID OPENLOOP RAMP VALUE(S) FOR VICTOR '%s'.", + json.get("name").toString().toUpperCase())); } } diff --git a/src/main/java/org/usfirst/lib6647/util/ComponentInitException.java b/src/main/java/org/usfirst/lib6647/util/ComponentInitException.java new file mode 100644 index 0000000..5cff574 --- /dev/null +++ b/src/main/java/org/usfirst/lib6647/util/ComponentInitException.java @@ -0,0 +1,21 @@ +package org.usfirst.lib6647.util; + +/** + * {@link Exception} for errors while initializing Super/HyperComponents. + */ +public class ComponentInitException extends Exception { + + /** + * Serial Version UID. + */ + private static final long serialVersionUID = 7668209987656891489L; + + /** + * {@link Exception} for errors while initializing Super/HyperComponents. + * + * @param message + */ + public ComponentInitException(String message) { + super(message); + } +} \ No newline at end of file diff --git a/src/main/java/org/usfirst/lib6647/util/MotorUtils.java b/src/main/java/org/usfirst/lib6647/util/MotorUtils.java index 4d9efe5..4d11d68 100644 --- a/src/main/java/org/usfirst/lib6647/util/MotorUtils.java +++ b/src/main/java/org/usfirst/lib6647/util/MotorUtils.java @@ -1,80 +1,23 @@ package org.usfirst.lib6647.util; +import org.json.simple.JSONObject; + +import edu.wpi.first.wpilibj.CounterBase.EncodingType; + import com.ctre.phoenix.motorcontrol.FeedbackDevice; import com.ctre.phoenix.motorcontrol.NeutralMode; -import org.json.simple.JSONObject; -import org.usfirst.lib6647.subsystem.hypercomponents.HyperTalon; -import org.usfirst.lib6647.subsystem.hypercomponents.HyperVictor; - /** - * SuperInterface for converting String values from a {@link JSONObject} to - * configure a {@link HyperTalon} or a {@link HyperVictor}. + * SuperInterface for converting String values from a {@link JSONObject} to enum + * types. */ public interface MotorUtils { - /** - * Sets a given {@link HyperTalon}'s limiter value from a {@link JSONObject}. - * Max value is 1, min value is 0 (which would make the {@link HyperTalon} - * stop). - * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} key does not exist or is - * empty. - * @throws NumberFormatException if {@link JSONObject} is not a number. - */ - default void setLimiter(JSONObject json, HyperTalon talon) throws NullPointerException, NumberFormatException { - double limiter = Double.parseDouble(json.get("limiter").toString()); - talon.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); - } - - /** - * Sets a given {@link HyperVictor}'s limiter value from a {@link JSONObject}. - * Max value is 1, min value is 0 (which would make the {@link HyperVictor} - * stop). - * - * @param JSONObject - * @param HyperVictor - * @throws NullPointerException if {@link JSONObject} key does not exist or is - * empty. - * @throws NumberFormatException if {@link JSONObject} is not a number. - */ - default void setLimiter(JSONObject json, HyperVictor victor) throws NullPointerException, NumberFormatException { - double limiter = Double.parseDouble(json.get("limiter").toString()); - victor.setLimiter(limiter < 0.0 ? 0.0 : limiter > 1.0 ? 1.0 : limiter); - } - - /** - * Sets a given {@link HyperTalon}'s inverted value from a {@link JSONObject}. - * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} key does not exist or is - * empty. - */ - default void setInverted(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { - HyperTalon.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); - } - - /** - * Sets a given {@link HyperVictor}'s inverted value from a {@link JSONObject} - * key. - * - * @param JSONObject - * @param HyperVictor - * @throws NullPointerException if {@link JSONObject} key does not exist or is - * empty. - */ - default void setInverted(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { - HyperVictor.setInverted(Boolean.parseBoolean(json.get("inverted").toString())); - } - /** * Method to convert a String value to its respective {@link NeutralMode}. * - * @param String - * @return NeutralMode + * @param neutralMode + * @return {@link NeutralMode} * * @note There are three types of {@link NeutralMode NeutralModes}: * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and @@ -94,95 +37,11 @@ default NeutralMode getNeutralMode(String neutralMode) { } } - /** - * Sets a given {@link HyperTalon}'s {@link NeutralMode} from a - * {@link JSONObject} key. - * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} key does not exist, is - * empty, or is not valid. - * - * @note There are three types of {@link NeutralMode NeutralModes}: - * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and - * {@link NeutralMode#EEPROMSetting}. All of which should share the same - * name in the {@link JSONObject}. - */ - default void setNeutralMode(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { - HyperTalon.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); - } - - /** - * Sets a given {@link HyperVictor}'s {@link NeutralMode} from a - * {@link JSONObject} key. - * - * @param JSONObject - * @param HyperVictor - * @throws NullPointerException if {@link JSONObject} key does not exist, is - * empty, or is not valid. - * - * @note There are three types of {@link NeutralMode NeutralModes}: - * {@link NeutralMode#Coast}, {@link NeutralMode#Brake}, and - * {@link NeutralMode#EEPROMSetting}. All of which should share the same - * name in the {@link JSONObject}. - */ - default void setNeutralMode(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { - HyperVictor.setNeutralMode(getNeutralMode(json.get("neutralMode").toString())); - } - - /** - * Sets a given {@link HyperTalon}'s loopramp from a {@link JSONObject} key. - * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} keys do not exist or are - * empty. - * @throws NumberFormatException if {@link JSONObject} keys are not numbers. - */ - default void setLoopRamp(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { - JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"), - open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); - - if (closed.containsKey("timeoutMs") && open.containsKey("timeoutMs")) { - HyperTalon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), - Integer.parseInt(closed.get("timeoutMs").toString())); - HyperTalon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), - Integer.parseInt(open.get("timeoutMs").toString())); - } else { - HyperTalon.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); - HyperTalon.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); - } - } - - /** - * Sets a given {@link HyperVictor}'s loopramp from the JSON configuration. - * - * @param JSONObject - * @param HyperVictor - * @throws NullPointerException if {@link JSONObject} keys do not exist or are - * empty. - * @throws NumberFormatException if {@link JSONObject} keys are not numbers. - */ - default void setLoopRamp(JSONObject json, HyperVictor HyperVictor) throws NullPointerException { - JSONObject closed = (JSONObject) ((JSONObject) json.get("loopRamp")).get("closed"), - open = (JSONObject) ((JSONObject) json.get("loopRamp")).get("open"); - - if (closed.containsKey("timeoutMs") && open.containsKey("timeoutMs")) { - HyperVictor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString()), - Integer.parseInt(closed.get("timeoutMs").toString())); - HyperVictor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString()), - Integer.parseInt(open.get("timeoutMs").toString())); - } else { - HyperVictor.configClosedloopRamp(Double.parseDouble(closed.get("secondsFromNeutralToFull").toString())); - HyperVictor.configOpenloopRamp(Double.parseDouble(open.get("secondsFromNeutralToFull").toString())); - } - } - /** * Method to convert a String to its respective {@link FeedbackDevice}. * * @param feedbackDevice - * @return FeedbackDevice + * @return {@link FeedbackDevice} * * @note There are eleven types of {@link FeedbackDevice FeedbackDevices}: * {@link FeedbackDevice#QuadEncoder}, {@link FeedbackDevice#Analog}, @@ -226,51 +85,22 @@ default FeedbackDevice getFeedbackDevice(String feedbackDevice) { } /** - * Sets a given {@link HyperTalon}'s sensors from a {@link JSONObject} key - * (fairly limited in terms of configuration at the moment). + * Method to convert a String to its respective {@link EncodingType}. * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} keys do not exist or are - * empty. - * @throws NumberFormatException if some {@link JSONObject} keys are not - * numbers. + * @param encodingType + * @return {@link EncodingType} */ - default void setSensors(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { - JSONObject sensor = (JSONObject) json.get("sensor"); - JSONObject feedback = (JSONObject) sensor.get("feedback"); - - HyperTalon.configSelectedFeedbackSensor(getFeedbackDevice(feedback.get("feedbackDevice").toString()), - Integer.parseInt(feedback.get("pidIdx").toString()), - Integer.parseInt(feedback.get("timeoutMs").toString())); - - HyperTalon.setSensorPhase(Boolean.parseBoolean(sensor.get("phase").toString())); - - HyperTalon.setSelectedSensorPosition(Integer.parseInt(sensor.get("sensorPos").toString()), - Integer.parseInt(sensor.get("pidIdx").toString()), - Integer.parseInt(sensor.get("timeoutMs").toString())); + default EncodingType getEncodingType(String encodingType) { + switch (encodingType) { + case "k1X": + return EncodingType.k1X; + case "k2X": + return EncodingType.k2X; + case "k4X": + return EncodingType.k4X; + default: + return null; + } } - /** - * Sets a given {@link HyperTalon}'s PID values from a {@link JSONObject} key. - * - * @param JSONObject - * @param HyperTalon - * @throws NullPointerException if {@link JSONObject} keys do not exist or are - * empty. - * @throws NumberFormatException if some {@link JSONObject} keys are not - * numbers. - */ - default void setPIDValues(JSONObject json, HyperTalon HyperTalon) throws NullPointerException { - JSONObject pid = (JSONObject) json.get("pid"); - - HyperTalon.config_kP(Integer.parseInt(pid.get("slotIdx").toString()), - Double.parseDouble(pid.get("p").toString())); - HyperTalon.config_kI(Integer.parseInt(pid.get("slotIdx").toString()), - Double.parseDouble(pid.get("i").toString())); - HyperTalon.config_kD(Integer.parseInt(pid.get("slotIdx").toString()), - Double.parseDouble(pid.get("d").toString())); - HyperTalon.config_kF(Integer.parseInt(pid.get("slotIdx").toString()), - Double.parseDouble(pid.get("f").toString())); - } } \ No newline at end of file