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.phoenixpro.controls;
008
009import com.ctre.phoenixpro.StatusCode;
010import com.ctre.phoenixpro.controls.jni.ControlJNI;
011import com.ctre.phoenixpro.controls.jni.ControlConfigJNI;
012
013/**
014 * Request PID to target velocity with torque current feedforward.
015 * <p>
016 * This control mode will set the motor's velocity setpoint to the velocity specified by the user. In
017 * addition, it will apply an additional torque current as an arbitrary feedforward value.
018 */
019public class VelocityTorqueCurrentFOC extends ControlRequest
020{
021    private boolean applyConfigsOnRequest;
022    /**
023     * Velocity to drive toward in rotations per second.
024     */
025    public double Velocity;
026    /**
027     * Feedforward to apply in torque current in Amperes.  User can use motor's kT
028     * to scale Newton-meter to Amperes.
029     */
030    public double FeedForward;
031    /**
032     * Select which gains are applied by selecting the slot.  Use the configuration
033     * api to set the gain values for the selected slot before enabling this
034     * feature. Slot must be within [0,2].
035     */
036    public int Slot;
037    /**
038     * Set to true to coast the rotor when output is zero (or within deadband).  Set
039     * to false to use the NeutralMode configuration setting (default). This flag
040     * exists to provide the fundamental behavior of this control when output is
041     * zero, which is to provide 0A (zero torque).
042     */
043    public boolean OverrideCoastDurNeutral;
044
045    
046    /**
047     * The period at which this control will update at.
048     * This is designated in Hertz, with a minimum of 20 Hz
049     * (every 50 ms) and a maximum of 1000 Hz (every 1 ms).
050     * <p>
051     * If this field is set to 0 Hz, the control request will
052     * be sent immediately as a one-shot frame. This may be useful
053     * for advanced applications that require outputs to be
054     * synchronized with data acquisition. In this case, we
055     * recommend not exceeding 50 ms between control calls.
056     */
057    public double UpdateFreqHz = 100; // Default to 100Hz
058
059    /**
060     * The timeout when sending configs associated with this control
061     */
062    public double configTimeout = 0.1;
063
064    /**
065     * Request PID to target velocity with torque current feedforward.
066     * <p>
067     * This control mode will set the motor's velocity setpoint to the velocity
068     * specified by the user. In addition, it will apply an additional torque
069     * current as an arbitrary feedforward value.
070     *
071     * @param Velocity     Velocity to drive toward in rotations per second.
072     * @param FeedForward     Feedforward to apply in torque current in Amperes.
073     *                         User can use motor's kT to scale Newton-meter to
074     *                        Amperes.
075     * @param Slot     Select which gains are applied by selecting the slot. 
076     *                 Use the configuration api to set the gain values for the
077     *                 selected slot before enabling this feature. Slot must be
078     *                 within [0,2].
079     * @param OverrideCoastDurNeutral     Set to true to coast the rotor when
080     *                                    output is zero (or within deadband). 
081     *                                    Set to false to use the NeutralMode
082     *                                    configuration setting (default). This
083     *                                    flag exists to provide the fundamental
084     *                                    behavior of this control when output
085     *                                    is zero, which is to provide 0A (zero
086     *                                    torque).
087     */
088    public VelocityTorqueCurrentFOC(double Velocity, double FeedForward, int Slot, boolean OverrideCoastDurNeutral)
089    {
090        super("VelocityTorqueCurrentFOC");
091        this.Velocity = Velocity;
092        this.FeedForward = FeedForward;
093        this.Slot = Slot;
094        this.OverrideCoastDurNeutral = OverrideCoastDurNeutral;
095    }
096
097    /**
098     * Request PID to target velocity with torque current feedforward.
099     * <p>
100     * This control mode will set the motor's velocity setpoint to the velocity
101     * specified by the user. In addition, it will apply an additional torque
102     * current as an arbitrary feedforward value.
103     *
104     * @param Velocity     Velocity to drive toward in rotations per second.
105     */
106    public VelocityTorqueCurrentFOC(double Velocity)
107    {
108        this(Velocity, 0.0, 0, false);
109    }
110
111    @Override
112    public String toString()
113    {
114        String ss = "class: VelocityTorqueCurrentFOC\n";
115        ss += "Velocity: " + Velocity + "\n";
116        ss += "FeedForward: " + FeedForward + "\n";
117        ss += "Slot: " + Slot + "\n";
118        ss += "OverrideCoastDurNeutral: " + OverrideCoastDurNeutral + "\n";
119        return ss;
120    }
121
122    @Override
123    public StatusCode sendRequest(String network, int deviceHash, boolean cancelOtherRequests)
124    {
125        var ref = requestReference.getNameValues();
126        ref.put("Velocity", String.valueOf(this.Velocity));
127        ref.put("FeedForward", String.valueOf(this.FeedForward));
128        ref.put("Slot", String.valueOf(this.Slot));
129        ref.put("OverrideCoastDurNeutral", String.valueOf(this.OverrideCoastDurNeutral));
130        String ss = "";
131        
132        ControlConfigJNI.JNI_RequestConfigApply(network, deviceHash, configTimeout, ss, applyConfigsOnRequest);
133        applyConfigsOnRequest = false;
134        return StatusCode.valueOf(ControlJNI.JNI_RequestControlVelocityTorqueCurrentFOC(
135                network, deviceHash, UpdateFreqHz, cancelOtherRequests, Velocity, FeedForward, Slot, OverrideCoastDurNeutral));
136    }
137    
138    /**
139     * Modifies this Control Request's Velocity parameter and returns itself for
140     * method-chaining and easier to use request API.
141     *
142     * @param newVelocity Parameter to modify
143     * @return Itself
144     */
145    public VelocityTorqueCurrentFOC withVelocity(double newVelocity)
146    {
147        Velocity = newVelocity;
148        return this;
149    }
150    
151    /**
152     * Modifies this Control Request's FeedForward parameter and returns itself for
153     * method-chaining and easier to use request API.
154     *
155     * @param newFeedForward Parameter to modify
156     * @return Itself
157     */
158    public VelocityTorqueCurrentFOC withFeedForward(double newFeedForward)
159    {
160        FeedForward = newFeedForward;
161        return this;
162    }
163    
164    /**
165     * Modifies this Control Request's Slot parameter and returns itself for
166     * method-chaining and easier to use request API.
167     *
168     * @param newSlot Parameter to modify
169     * @return Itself
170     */
171    public VelocityTorqueCurrentFOC withSlot(int newSlot)
172    {
173        Slot = newSlot;
174        return this;
175    }
176    
177    /**
178     * Modifies this Control Request's OverrideCoastDurNeutral parameter and returns itself for
179     * method-chaining and easier to use request API.
180     *
181     * @param newOverrideCoastDurNeutral Parameter to modify
182     * @return Itself
183     */
184    public VelocityTorqueCurrentFOC withOverrideCoastDurNeutral(boolean newOverrideCoastDurNeutral)
185    {
186        OverrideCoastDurNeutral = newOverrideCoastDurNeutral;
187        return this;
188    }
189    /**
190     * Sets the period at which this control will update at.
191     * This is designated in Hertz, with a minimum of 20 Hz
192     * (every 50 ms) and a maximum of 1000 Hz (every 1 ms).
193     * <p>
194     * If this field is set to 0 Hz, the control request will
195     * be sent immediately as a one-shot frame. This may be useful
196     * for advanced applications that require outputs to be
197     * synchronized with data acquisition. In this case, we
198     * recommend not exceeding 50 ms between control calls.
199     *
200     * @param newUpdateFreqHz Parameter to modify
201     * @return Itself
202     */
203    public VelocityTorqueCurrentFOC withUpdateFreqHz(double newUpdateFreqHz)
204    {
205        UpdateFreqHz = newUpdateFreqHz;
206        return this;
207    }
208    /**
209     * Forces configs to be applied the next time this is used in a setControl.
210     * <p>
211     * This is not necessary in the majority of cases, because Phoenix will make sure configs are
212     * properly set when they are not already set
213     */
214    public void forceApplyConfigs() { applyConfigsOnRequest = true; }
215}
216