mirror of
https://github.com/betaflight/betaflight.git
synced 2025-07-16 04:45:24 +03:00
iTermRelaxFactor now only attenuates amount added
The original setpoint based iTerm Relax code attenuated the amount of iTerm added per loop by a relax factor based on an HPF of setpoint. At some point the code was re-factored and the relax factor multiplied the accumulating iterm error itself, such that almost any relax factor below 1.0 would quickly zero out iTerm. This was bad for racing because when making sustained tight turns, I would abrubtly be zeroed when the setpoint for the starting of some relax was close to the threshold. This was never the intent of the original proposal, which was for a smoother attenuation of iTerm, and for retention of some accumulation of iTerm during spirals around poles etc. This PR fixes that error. It also changes the default threshold up from 30 deg/s to 40 deg/s which better suits racing. Also included us a form of simple cutoff independence. In the initial form, lowering cutoff would reduce the effectiveness but draw out the duration. Now cutoff only really affects duration. Lower cutoff values are better for quads with greater motor delay, faster values are better for quicker quads. For most of my quads a cutoff of 30 works best. I've also removed newlines. set to current cutoff maybe fix unit test default cutoff set to current value in unit test add itermRelaxSetpointThreshold as float in unit test add itermRelaxSetpointThreshold as float, because ITERM_RELAX_SETPOINT_THRESHOLD doesn't exist any more Move itermRelaxFactor limit, remove from fast ram remove unncessary max, revert unit test changes, restore original defaults. remove max from debug restore old defaults and revert unit test changes temporarily to see if will pass unit test with defaults whoops lets see if unit test passes when cutoff is 20 lets see if unit test passes when cutoff is 20
This commit is contained in:
parent
750e7c30cf
commit
1d998ea404
3 changed files with 9 additions and 8 deletions
|
@ -267,7 +267,8 @@ static FAST_RAM_ZERO_INIT pt1Filter_t ptermYawLowpass;
|
|||
static FAST_RAM_ZERO_INIT pt1Filter_t windupLpf[XYZ_AXIS_COUNT];
|
||||
static FAST_RAM_ZERO_INIT uint8_t itermRelax;
|
||||
static FAST_RAM_ZERO_INIT uint8_t itermRelaxType;
|
||||
static FAST_RAM_ZERO_INIT uint8_t itermRelaxCutoff;
|
||||
static uint8_t itermRelaxCutoff;
|
||||
static FAST_RAM_ZERO_INIT float itermRelaxSetpointThreshold;
|
||||
#endif
|
||||
|
||||
#if defined(USE_ABSOLUTE_CONTROL)
|
||||
|
@ -615,10 +616,12 @@ void pidInitConfig(const pidProfile_t *pidProfile)
|
|||
#if defined(USE_SMART_FEEDFORWARD)
|
||||
smartFeedforward = pidProfile->smart_feedforward;
|
||||
#endif
|
||||
|
||||
#if defined(USE_ITERM_RELAX)
|
||||
itermRelax = pidProfile->iterm_relax;
|
||||
itermRelaxType = pidProfile->iterm_relax_type;
|
||||
itermRelaxCutoff = pidProfile->iterm_relax_cutoff;
|
||||
itermRelaxSetpointThreshold = ITERM_RELAX_SETPOINT_THRESHOLD * 20.0f / itermRelaxCutoff;
|
||||
#endif
|
||||
|
||||
#ifdef USE_ACRO_TRAINER
|
||||
|
@ -1107,16 +1110,13 @@ STATIC_UNIT_TESTED void applyItermRelax(const int axis, const float iterm,
|
|||
const float setpointLpf = pt1FilterApply(&windupLpf[axis], *currentPidSetpoint);
|
||||
const float setpointHpf = fabsf(*currentPidSetpoint - setpointLpf);
|
||||
|
||||
if (itermRelax &&
|
||||
(axis < FD_YAW || itermRelax == ITERM_RELAX_RPY ||
|
||||
itermRelax == ITERM_RELAX_RPY_INC)) {
|
||||
const float itermRelaxFactor = 1 - setpointHpf / ITERM_RELAX_SETPOINT_THRESHOLD;
|
||||
|
||||
if (itermRelax && (axis < FD_YAW || itermRelax == ITERM_RELAX_RPY || itermRelax == ITERM_RELAX_RPY_INC)) {
|
||||
const float itermRelaxFactor = MAX(0, 1 - setpointHpf / itermRelaxSetpointThreshold);
|
||||
const bool isDecreasingI =
|
||||
((iterm > 0) && (*itermErrorRate < 0)) || ((iterm < 0) && (*itermErrorRate > 0));
|
||||
if ((itermRelax >= ITERM_RELAX_RP_INC) && isDecreasingI) {
|
||||
// Do Nothing, use the precalculed itermErrorRate
|
||||
} else if (itermRelaxType == ITERM_RELAX_SETPOINT && setpointHpf < ITERM_RELAX_SETPOINT_THRESHOLD) {
|
||||
} else if (itermRelaxType == ITERM_RELAX_SETPOINT) {
|
||||
*itermErrorRate *= itermRelaxFactor;
|
||||
} else if (itermRelaxType == ITERM_RELAX_GYRO ) {
|
||||
*itermErrorRate = fapplyDeadband(setpointLpf - gyroRate, setpointHpf);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue