001/* 002 * Copyright (C) Cross The Road Electronics. All rights reserved. 003 * License information can be found in CTRE_LICENSE.txt 004 * For support and suggestions contact support@ctr-electronics.com or file 005 * an issue tracker at https://github.com/CrossTheRoadElec/Phoenix-Releases 006 */ 007package com.ctre.phoenix6.controls; 008 009import com.ctre.phoenix6.StatusCode; 010import com.ctre.phoenix6.controls.jni.ControlJNI; 011 012import java.util.HashMap; 013import java.util.Map; 014 015/** 016 * Request a specified motor duty cycle. 017 * <p> 018 * This control mode will output a proportion of the supplied voltage which is supplied by the user. 019 */ 020public class DutyCycleOut extends ControlRequest implements Cloneable 021{ 022 /** 023 * Proportion of supply voltage to apply in fractional units between -1 and +1 024 */ 025 public double Output; 026 /** 027 * Set to true to use FOC commutation (requires Phoenix Pro), which increases 028 * peak power by ~15%. Set to false to use trapezoidal commutation. FOC 029 * improves motor performance by leveraging torque (current) control. However, 030 * this may be inconvenient for applications that require specifying duty cycle 031 * or voltage. CTR-Electronics has developed a hybrid method that combines the 032 * performances gains of FOC while still allowing applications to provide duty 033 * cycle or voltage demand. This not to be confused with simple sinusoidal 034 * control or phase voltage control which lacks the performance gains. 035 */ 036 public boolean EnableFOC; 037 /** 038 * Set to true to static-brake the rotor when output is zero (or within 039 * deadband). Set to false to use the NeutralMode configuration setting 040 * (default). This flag exists to provide the fundamental behavior of this 041 * control when output is zero, which is to provide 0V to the motor. 042 */ 043 public boolean OverrideBrakeDurNeutral; 044 /** 045 * Set to true to force forward limiting. This allows users to use other limit 046 * switch sensors connected to robot controller. This also allows use of active 047 * sensors that require external power. 048 */ 049 public boolean LimitForwardMotion; 050 /** 051 * Set to true to force reverse limiting. This allows users to use other limit 052 * switch sensors connected to robot controller. This also allows use of active 053 * sensors that require external power. 054 */ 055 public boolean LimitReverseMotion; 056 057 /** 058 * The period at which this control will update at. 059 * This is designated in Hertz, with a minimum of 20 Hz 060 * (every 50 ms) and a maximum of 1000 Hz (every 1 ms). 061 * <p> 062 * If this field is set to 0 Hz, the control request will 063 * be sent immediately as a one-shot frame. This may be useful 064 * for advanced applications that require outputs to be 065 * synchronized with data acquisition. In this case, we 066 * recommend not exceeding 50 ms between control calls. 067 */ 068 public double UpdateFreqHz = 100; // Default to 100Hz 069 070 /** 071 * Request a specified motor duty cycle. 072 * <p> 073 * This control mode will output a proportion of the supplied voltage which is 074 * supplied by the user. 075 * 076 * @param Output Proportion of supply voltage to apply in fractional units 077 * between -1 and +1 078 * @param EnableFOC Set to true to use FOC commutation (requires Phoenix 079 * Pro), which increases peak power by ~15%. Set to false to 080 * use trapezoidal commutation. FOC improves motor 081 * performance by leveraging torque (current) control. 082 * However, this may be inconvenient for applications that 083 * require specifying duty cycle or voltage. 084 * CTR-Electronics has developed a hybrid method that 085 * combines the performances gains of FOC while still 086 * allowing applications to provide duty cycle or voltage 087 * demand. This not to be confused with simple sinusoidal 088 * control or phase voltage control which lacks the 089 * performance gains. 090 * @param OverrideBrakeDurNeutral Set to true to static-brake the rotor when 091 * output is zero (or within deadband). Set 092 * to false to use the NeutralMode 093 * configuration setting (default). This flag 094 * exists to provide the fundamental behavior 095 * of this control when output is zero, which 096 * is to provide 0V to the motor. 097 * @param LimitForwardMotion Set to true to force forward limiting. This 098 * allows users to use other limit switch sensors 099 * connected to robot controller. This also allows 100 * use of active sensors that require external 101 * power. 102 * @param LimitReverseMotion Set to true to force reverse limiting. This 103 * allows users to use other limit switch sensors 104 * connected to robot controller. This also allows 105 * use of active sensors that require external 106 * power. 107 */ 108 public DutyCycleOut(double Output, boolean EnableFOC, boolean OverrideBrakeDurNeutral, boolean LimitForwardMotion, boolean LimitReverseMotion) 109 { 110 super("DutyCycleOut"); 111 this.Output = Output; 112 this.EnableFOC = EnableFOC; 113 this.OverrideBrakeDurNeutral = OverrideBrakeDurNeutral; 114 this.LimitForwardMotion = LimitForwardMotion; 115 this.LimitReverseMotion = LimitReverseMotion; 116 } 117 118 /** 119 * Request a specified motor duty cycle. 120 * <p> 121 * This control mode will output a proportion of the supplied voltage which is 122 * supplied by the user. 123 * 124 * @param Output Proportion of supply voltage to apply in fractional units 125 * between -1 and +1 126 */ 127 public DutyCycleOut(double Output) 128 { 129 this(Output, true, false, false, false); 130 } 131 132 @Override 133 public String toString() 134 { 135 String ss = "class: DutyCycleOut\n"; 136 ss += "Output: " + Output + "\n"; 137 ss += "EnableFOC: " + EnableFOC + "\n"; 138 ss += "OverrideBrakeDurNeutral: " + OverrideBrakeDurNeutral + "\n"; 139 ss += "LimitForwardMotion: " + LimitForwardMotion + "\n"; 140 ss += "LimitReverseMotion: " + LimitReverseMotion + "\n"; 141 return ss; 142 } 143 144 @Override 145 public StatusCode sendRequest(String network, int deviceHash, boolean cancelOtherRequests) 146 { 147 return StatusCode.valueOf(ControlJNI.JNI_RequestControlDutyCycleOut( 148 network, deviceHash, UpdateFreqHz, cancelOtherRequests, Output, EnableFOC, OverrideBrakeDurNeutral, LimitForwardMotion, LimitReverseMotion)); 149 } 150 151 /** 152 * Gets information about this control request. 153 * 154 * @return Map of control parameter names and corresponding applied values 155 */ 156 @Override 157 public Map<String, String> getControlInfo() 158 { 159 var controlInfo = new HashMap<String, String>(); 160 controlInfo.put("Name", getName()); 161 controlInfo.put("Output", String.valueOf(this.Output)); 162 controlInfo.put("EnableFOC", String.valueOf(this.EnableFOC)); 163 controlInfo.put("OverrideBrakeDurNeutral", String.valueOf(this.OverrideBrakeDurNeutral)); 164 controlInfo.put("LimitForwardMotion", String.valueOf(this.LimitForwardMotion)); 165 controlInfo.put("LimitReverseMotion", String.valueOf(this.LimitReverseMotion)); 166 return controlInfo; 167 } 168 169 /** 170 * Modifies this Control Request's Output parameter and returns itself for 171 * method-chaining and easier to use request API. 172 * 173 * @param newOutput Parameter to modify 174 * @return Itself 175 */ 176 public DutyCycleOut withOutput(double newOutput) 177 { 178 Output = newOutput; 179 return this; 180 } 181 182 /** 183 * Modifies this Control Request's EnableFOC parameter and returns itself for 184 * method-chaining and easier to use request API. 185 * 186 * @param newEnableFOC Parameter to modify 187 * @return Itself 188 */ 189 public DutyCycleOut withEnableFOC(boolean newEnableFOC) 190 { 191 EnableFOC = newEnableFOC; 192 return this; 193 } 194 195 /** 196 * Modifies this Control Request's OverrideBrakeDurNeutral parameter and returns itself for 197 * method-chaining and easier to use request API. 198 * 199 * @param newOverrideBrakeDurNeutral Parameter to modify 200 * @return Itself 201 */ 202 public DutyCycleOut withOverrideBrakeDurNeutral(boolean newOverrideBrakeDurNeutral) 203 { 204 OverrideBrakeDurNeutral = newOverrideBrakeDurNeutral; 205 return this; 206 } 207 208 /** 209 * Modifies this Control Request's LimitForwardMotion parameter and returns itself for 210 * method-chaining and easier to use request API. 211 * 212 * @param newLimitForwardMotion Parameter to modify 213 * @return Itself 214 */ 215 public DutyCycleOut withLimitForwardMotion(boolean newLimitForwardMotion) 216 { 217 LimitForwardMotion = newLimitForwardMotion; 218 return this; 219 } 220 221 /** 222 * Modifies this Control Request's LimitReverseMotion parameter and returns itself for 223 * method-chaining and easier to use request API. 224 * 225 * @param newLimitReverseMotion Parameter to modify 226 * @return Itself 227 */ 228 public DutyCycleOut withLimitReverseMotion(boolean newLimitReverseMotion) 229 { 230 LimitReverseMotion = newLimitReverseMotion; 231 return this; 232 } 233 /** 234 * Sets the period at which this control will update at. 235 * This is designated in Hertz, with a minimum of 20 Hz 236 * (every 50 ms) and a maximum of 1000 Hz (every 1 ms). 237 * <p> 238 * If this field is set to 0 Hz, the control request will 239 * be sent immediately as a one-shot frame. This may be useful 240 * for advanced applications that require outputs to be 241 * synchronized with data acquisition. In this case, we 242 * recommend not exceeding 50 ms between control calls. 243 * 244 * @param newUpdateFreqHz Parameter to modify 245 * @return Itself 246 */ 247 public DutyCycleOut withUpdateFreqHz(double newUpdateFreqHz) 248 { 249 UpdateFreqHz = newUpdateFreqHz; 250 return this; 251 } 252 253 @Override 254 public DutyCycleOut clone() 255 { 256 try { 257 return (DutyCycleOut)super.clone(); 258 } catch (CloneNotSupportedException ex) { 259 /* this should never happen */ 260 throw new RuntimeException(ex); 261 } 262 } 263} 264