Subversion Repositories FlightCtrl

Rev

Rev 1812 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1813 - 1
/******************************************************************************************************************
2
V0.82b-Arthur-P 2010-12-18
3
------------------------------------------------------------------------------------------------------------------
4
Version includes only support for external HEF4017 for FC1.x hardware, NOT for Twi2Ppm converters for ESCs.
5
 
6
2010-12-18 Transferred changes to v.0.82b-Arthur-P. Remarked out variable i in Mittelwert() as this
7
variable is not used.
8
20100917: Transferred changes to v0.80g-Arthur-Px.
9
20100804: Arthur P.: Modified to use user parameter 7 to determine downstep for motorsmoothing
10
with 0 or 1 defaulting to the default -150% first step followed by upsmoothing and
11
values beyond that resulting in 50% (2), 75% (4), 90% (10), 95% (20), 97.5% (40), 99% (100)
12
downsteps.
13
Within timer0.c user paramater 8 is used to activate an external HEF4017 on FC 1.x hardware,
14
and/or to set the shutter interval timer in steps of 0.1sec (minimum = 1 sec), by using
15
bit 8 (128) as on/off switch, and bits 7 (0..127) for the timer counter.
16
 
17
******************************************************************************************************************/
1 ingob 18
/*#######################################################################################
19
Flight Control
20
#######################################################################################*/
21
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1338 ingob 22
// + Copyright (c) Holger Buss, Ingo Busker
23
// + Nur für den privaten Gebrauch / NON-COMMERCIAL USE ONLY
1 ingob 24
// + www.MikroKopter.com
25
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1051 killagreg 26
// + Es gilt für das gesamte Projekt (Hardware, Software, Binärfiles, Sourcecode und Dokumentation),
27
// + dass eine Nutzung (auch auszugsweise) nur für den privaten (nicht-kommerziellen) Gebrauch zulässig ist.
28
// + Sollten direkte oder indirekte kommerzielle Absichten verfolgt werden, ist mit uns (info@mikrokopter.de) Kontakt
29
// + bzgl. der Nutzungsbedingungen aufzunehmen.
1 ingob 30
// + Eine kommerzielle Nutzung ist z.B.Verkauf von MikroKoptern, Bestückung und Verkauf von Platinen oder Bausätzen,
31
// + Verkauf von Luftbildaufnahmen, usw.
32
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1051 killagreg 33
// + Werden Teile des Quellcodes (mit oder ohne Modifikation) weiterverwendet oder veröffentlicht,
1 ingob 34
// + unterliegen sie auch diesen Nutzungsbedingungen und diese Nutzungsbedingungen incl. Copyright müssen dann beiliegen
35
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
36
// + Sollte die Software (auch auszugesweise) oder sonstige Informationen des MikroKopter-Projekts
37
// + auf anderen Webseiten oder sonstigen Medien veröffentlicht werden, muss unsere Webseite "http://www.mikrokopter.de"
38
// + eindeutig als Ursprung verlinkt werden
39
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
40
// + Keine Gewähr auf Fehlerfreiheit, Vollständigkeit oder Funktion
41
// + Benutzung auf eigene Gefahr
42
// + Wir übernehmen keinerlei Haftung für direkte oder indirekte Personen- oder Sachschäden
43
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1338 ingob 44
// + Die Portierung oder Nutzung der Software (oder Teile davon) auf andere Systeme (ausser der Hardware von www.mikrokopter.de) ist nur
1 ingob 45
// + mit unserer Zustimmung zulässig
46
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
47
// + Die Funktion printf_P() unterliegt ihrer eigenen Lizenz und ist hiervon nicht betroffen
48
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1051 killagreg 49
// + Redistributions of source code (with or without modifications) must retain the above copyright notice,
1 ingob 50
// + this list of conditions and the following disclaimer.
51
// +   * Neither the name of the copyright holders nor the names of contributors may be used to endorse or promote products derived
52
// +     from this software without specific prior written permission.
1051 killagreg 53
// +   * The use of this project (hardware, software, binary files, sources and documentation) is only permittet
1 ingob 54
// +     for non-commercial use (directly or indirectly)
1051 killagreg 55
// +     Commercial use (for excample: selling of MikroKopters, selling of PCBs, assembly, ...) is only permitted
1 ingob 56
// +     with our written permission
1051 killagreg 57
// +   * If sources or documentations are redistributet on other webpages, out webpage (http://www.MikroKopter.de) must be
58
// +     clearly linked as origin
1338 ingob 59
// +   * porting the sources to other systems or using the software on other systems (except hardware from www.mikrokopter.de) is not allowed
1 ingob 60
// +  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
61
// +  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
62
// +  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
63
// +  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
64
// +  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
65
// +  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
66
// +  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
1322 hbuss 67
// +  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
68
// +  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
1 ingob 69
// +  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
1051 killagreg 70
// +  POSSIBILITY OF SUCH DAMAGE.
1 ingob 71
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
72
 
73
#include "main.h"
1320 hbuss 74
#include "mymath.h"
1330 killagreg 75
#include "isqrt.h"
1 ingob 76
 
1352 hbuss 77
unsigned char h,m,s;
78
unsigned int BaroExpandActive = 0;
1153 hbuss 79
int MesswertNick,MesswertRoll,MesswertGier,MesswertGierBias, RohMesswertNick,RohMesswertRoll;
1166 hbuss 80
int TrimNick, TrimRoll;
927 hbuss 81
int AdNeutralNick = 0,AdNeutralRoll = 0,AdNeutralGier = 0,StartNeutralRoll = 0,StartNeutralNick = 0;
1703 holgerb 82
int Mittelwert_AccNick, Mittelwert_AccRoll;
1643 holgerb 83
unsigned int NeutralAccX=0, NeutralAccY=0;
805 hbuss 84
int NaviAccNick, NaviAccRoll,NaviCntAcc = 0;
1639 holgerb 85
int NeutralAccZ = 0;
1683 killagreg 86
unsigned char ControlHeading = 0;// in 2°
693 hbuss 87
long IntegralNick = 0,IntegralNick2 = 0;
88
long IntegralRoll = 0,IntegralRoll2 = 0;
89
long IntegralAccNick = 0,IntegralAccRoll = 0,IntegralAccZ = 0;
90
long Integral_Gier = 0;
91
long Mess_IntegralNick = 0,Mess_IntegralNick2 = 0;
92
long Mess_IntegralRoll = 0,Mess_IntegralRoll2 = 0;
93
long Mess_Integral_Gier = 0,Mess_Integral_Gier2 = 0;
94
long MittelIntegralNick,MittelIntegralRoll,MittelIntegralNick2,MittelIntegralRoll2;
1685 holgerb 95
long SummeNick=0,SummeRoll=0;
1 ingob 96
volatile long Mess_Integral_Hoch = 0;
1153 hbuss 97
int  KompassValue = 0;
98
int  KompassStartwert = 0;
99
int  KompassRichtung = 0;
693 hbuss 100
unsigned int  KompassSignalSchlecht = 500;
855 hbuss 101
unsigned char  MAX_GAS,MIN_GAS;
1 ingob 102
unsigned char HoehenReglerAktiv = 0;
880 hbuss 103
unsigned char TrichterFlug = 0;
395 hbuss 104
long Umschlag180Nick = 250000L, Umschlag180Roll = 250000L;
693 hbuss 105
long  ErsatzKompass;
106
int   ErsatzKompassInGrad; // Kompasswert in Grad
107
int   GierGyroFehler = 0;
1211 hbuss 108
char GyroFaktor,GyroFaktorGier;
109
char IntegralFaktor,IntegralFaktorGier;
1153 hbuss 110
int  DiffNick,DiffRoll;
1377 hbuss 111
//int  Poti1 = 0, Poti2 = 0, Poti3 = 0, Poti4 = 0, Poti5 = 0, Poti6 = 0, Poti7 = 0, Poti8 = 0;
1391 killagreg 112
unsigned char Poti[9] = {0,0,0,0,0,0,0,0};
1 ingob 113
volatile unsigned char SenderOkay = 0;
595 hbuss 114
int StickNick = 0,StickRoll = 0,StickGier = 0,StickGas = 0;
1698 holgerb 115
char MotorenEin = 0,StartTrigger = 0;
1246 killagreg 116
long HoehenWert = 0;
117
long SollHoehe = 0;
1692 holgerb 118
int LageKorrekturRoll = 0,LageKorrekturNick = 0, HoverGas = 0;
1153 hbuss 119
//float Ki =  FAKTOR_I;
1676 holgerb 120
int Ki = 10300 / 33;
395 hbuss 121
unsigned char Looping_Nick = 0,Looping_Roll = 0;
122
unsigned char Looping_Links = 0, Looping_Rechts = 0, Looping_Unten = 0, Looping_Oben = 0;
1 ingob 123
 
124
unsigned char Parameter_Luftdruck_D  = 48;      // Wert : 0-250
125
unsigned char Parameter_MaxHoehe     = 251;      // Wert : 0-250
126
unsigned char Parameter_Hoehe_P      = 16;      // Wert : 0-32
127
unsigned char Parameter_Hoehe_ACC_Wirkung = 58; // Wert : 0-250
128
unsigned char Parameter_KompassWirkung = 64;    // Wert : 0-250
1283 hbuss 129
unsigned char Parameter_Hoehe_GPS_Z = 64;        // Wert : 0-250
1111 hbuss 130
unsigned char Parameter_Gyro_D = 8;             // Wert : 0-250
173 holgerb 131
unsigned char Parameter_Gyro_P = 150;           // Wert : 10-250
1 ingob 132
unsigned char Parameter_Gyro_I = 150;           // Wert : 0-250
1322 hbuss 133
unsigned char Parameter_Gyro_Gier_P = 150;      // Wert : 10-250
134
unsigned char Parameter_Gyro_Gier_I = 150;      // Wert : 10-250
1 ingob 135
unsigned char Parameter_Gier_P = 2;             // Wert : 1-20
136
unsigned char Parameter_I_Faktor = 10;          // Wert : 1-20
137
unsigned char Parameter_UserParam1 = 0;
138
unsigned char Parameter_UserParam2 = 0;
139
unsigned char Parameter_UserParam3 = 0;
140
unsigned char Parameter_UserParam4 = 0;
499 hbuss 141
unsigned char Parameter_UserParam5 = 0;
142
unsigned char Parameter_UserParam6 = 0;
143
unsigned char Parameter_UserParam7 = 0;
144
unsigned char Parameter_UserParam8 = 0;
1 ingob 145
unsigned char Parameter_ServoNickControl = 100;
1232 hbuss 146
unsigned char Parameter_ServoRollControl = 100;
173 holgerb 147
unsigned char Parameter_LoopGasLimit = 70;
1120 hbuss 148
unsigned char Parameter_AchsKopplung1 = 90;
149
unsigned char Parameter_AchsKopplung2 = 65;
150
unsigned char Parameter_CouplingYawCorrection = 64;
151
//unsigned char Parameter_AchsGegenKopplung1 = 0;
499 hbuss 152
unsigned char Parameter_DynamicStability = 100;
921 hbuss 153
unsigned char Parameter_J16Bitmask;             // for the J16 Output
154
unsigned char Parameter_J16Timing;              // for the J16 Output
155
unsigned char Parameter_J17Bitmask;             // for the J17 Output
156
unsigned char Parameter_J17Timing;              // for the J17 Output
157
unsigned char Parameter_NaviGpsModeControl;     // Parameters for the Naviboard
1051 killagreg 158
unsigned char Parameter_NaviGpsGain;
159
unsigned char Parameter_NaviGpsP;
160
unsigned char Parameter_NaviGpsI;
161
unsigned char Parameter_NaviGpsD;
162
unsigned char Parameter_NaviGpsACC;
993 hbuss 163
unsigned char Parameter_NaviOperatingRadius;
164
unsigned char Parameter_NaviWindCorrection;
165
unsigned char Parameter_NaviSpeedCompensation;
921 hbuss 166
unsigned char Parameter_ExternalControl;
1403 hbuss 167
unsigned char Parameter_Servo3,Parameter_Servo4,Parameter_Servo5;
1668 holgerb 168
unsigned char CareFree = 0;
1760 holgerb 169
const signed char sintab[31] = { 0, 2, 4, 6, 7, 8, 8, 8, 7, 6, 4, 2, 0, -2, -4, -6, -7, -8, -8, -8, -7, -6, -4, -2, 0, 2, 4, 6, 7, 8, 8};
1622 killagreg 170
 
492 hbuss 171
signed int ExternStickNick = 0,ExternStickRoll = 0,ExternStickGier = 0, ExternHoehenValue = -20;
614 hbuss 172
int MaxStickNick = 0,MaxStickRoll = 0;
871 hbuss 173
unsigned int  modell_fliegt = 0;
1765 killagreg 174
volatile unsigned char FC_StatusFlags = 0;
1121 hbuss 175
long GIER_GRAD_FAKTOR = 1291;
1153 hbuss 176
signed int KopplungsteilNickRoll,KopplungsteilRollNick;
1209 hbuss 177
signed int tmp_motorwert[MAX_MOTORS];
1591 holgerb 178
char VarioCharacter = ' ';
179
 
1391 killagreg 180
#define LIMIT_MIN(value, min) {if(value <= min) value = min;}
181
#define LIMIT_MAX(value, max) {if(value >= max) value = max;}
182
#define LIMIT_MIN_MAX(value, min, max) {if(value <= min) value = min; else if(value >= max) value = max;}
1155 hbuss 183
 
1622 killagreg 184
 
1639 holgerb 185
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
186
//  Debugwerte zuordnen
187
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
188
void CopyDebugValues(void)
189
{
190
    DebugOut.Analog[0] = IntegralNick / (EE_Parameter.GyroAccFaktor * 4);
191
    DebugOut.Analog[1] = IntegralRoll / (EE_Parameter.GyroAccFaktor * 4);
192
    DebugOut.Analog[2] = Mittelwert_AccNick / 4;
193
    DebugOut.Analog[3] = Mittelwert_AccRoll / 4;
1660 holgerb 194
    DebugOut.Analog[4] = (signed int) AdNeutralGier - AdWertGier;
1639 holgerb 195
    DebugOut.Analog[5] = HoehenWert/5;
1703 holgerb 196
    DebugOut.Analog[6] = AdWertAccHoch;//(Mess_Integral_Hoch / 512);// Aktuell_az;
1639 holgerb 197
    DebugOut.Analog[8] = KompassValue;
198
    DebugOut.Analog[9] = UBat;
199
    DebugOut.Analog[10] = SenderOkay;
200
    DebugOut.Analog[11] = ErsatzKompass / GIER_GRAD_FAKTOR;
1702 holgerb 201
    DebugOut.Analog[12] = Motor[0].SetPoint;
202
    DebugOut.Analog[13] = Motor[1].SetPoint;
203
    DebugOut.Analog[14] = Motor[2].SetPoint;
204
    DebugOut.Analog[15] = Motor[3].SetPoint;
1639 holgerb 205
    DebugOut.Analog[20] = ServoNickValue;
206
    DebugOut.Analog[22] = Capacity.ActualCurrent;
207
    DebugOut.Analog[23] = Capacity.UsedCapacity;
208
//    DebugOut.Analog[22] = FromNaviCtrl_Value.GpsZ;
1682 holgerb 209
//    DebugOut.Analog[29] = FromNaviCtrl_Value.SerialDataOkay;
210
        DebugOut.Analog[29] = Capacity.MinOfMaxPWM;
1639 holgerb 211
    DebugOut.Analog[30] = GPS_Nick;
212
    DebugOut.Analog[31] = GPS_Roll;
1702 holgerb 213
    if(VersionInfo.HardwareError[0] || VersionInfo.HardwareError[1]) DebugOut.Status[1] |= 1; else DebugOut.Status[1] &= 0xfe;
1760 holgerb 214
 
1787 holgerb 215
//if(Capacity.MinOfMaxPWM < 250/* && modell_fliegt > 500*/)  { beeptime = 1000; DebugOut.Analog[25]++; }
1639 holgerb 216
}
217
 
1760 holgerb 218
 
219
 
1232 hbuss 220
void Piep(unsigned char Anzahl, unsigned int dauer)
1 ingob 221
{
1232 hbuss 222
 if(MotorenEin) return; //auf keinen Fall im Flug!
1 ingob 223
 while(Anzahl--)
224
 {
1232 hbuss 225
  beeptime = dauer;
226
  while(beeptime);
227
  Delay_ms(dauer * 2);
1 ingob 228
 }
229
}
230
 
231
//############################################################################
1622 killagreg 232
// Messwerte beim Ermitteln der Nullage
233
void CalibrierMittelwert(void)
234
//############################################################################
235
{
236
    unsigned char i;
237
    if(PlatinenVersion == 13) SucheGyroOffset();
238
    // ADC auschalten, damit die Werte sich nicht während der Berechnung ändern
239
        ANALOG_OFF;
240
        MesswertNick = AdWertNick;
241
        MesswertRoll = AdWertRoll;
242
        MesswertGier = AdWertGier;
1703 holgerb 243
        Mittelwert_AccNick = ACC_AMPLIFY * AdWertAccNick;
244
        Mittelwert_AccRoll = ACC_AMPLIFY * AdWertAccRoll;
1622 killagreg 245
   // ADC einschalten
246
    ANALOG_ON;
247
   for(i=0;i<8;i++)
248
    {
249
     int tmp;
250
         tmp = PPM_in[EE_Parameter.Kanalbelegung[K_POTI1 + i]] + 110;
251
         LIMIT_MIN_MAX(tmp, 0, 255);
252
     if(Poti[i] > tmp) Poti[i]--;  else  if(Poti[i] < tmp) Poti[i]++;
253
        }
254
        Umschlag180Nick = (long) EE_Parameter.WinkelUmschlagNick * 2500L;
255
        Umschlag180Roll = (long) EE_Parameter.WinkelUmschlagRoll * 2500L;
256
}
257
 
258
//############################################################################
1 ingob 259
//  Nullwerte ermitteln
1622 killagreg 260
void SetNeutral(unsigned char AccAdjustment)
1 ingob 261
//############################################################################
262
{
1622 killagreg 263
        unsigned char i;
264
        unsigned int gier_neutral=0, nick_neutral=0, roll_neutral=0;
1702 holgerb 265
    VersionInfo.HardwareError[0] = 0;
1320 hbuss 266
    HEF4017R_ON;
1051 killagreg 267
        NeutralAccX = 0;
1 ingob 268
        NeutralAccY = 0;
269
        NeutralAccZ = 0;
1622 killagreg 270
 
1051 killagreg 271
    AdNeutralNick = 0;
272
        AdNeutralRoll = 0;
1 ingob 273
        AdNeutralGier = 0;
1622 killagreg 274
 
395 hbuss 275
    Parameter_AchsKopplung1 = 0;
1120 hbuss 276
    Parameter_AchsKopplung2 = 0;
1622 killagreg 277
 
1036 hbuss 278
    ExpandBaro = 0;
1622 killagreg 279
 
1051 killagreg 280
    CalibrierMittelwert();
395 hbuss 281
    Delay_ms_Mess(100);
1622 killagreg 282
 
1 ingob 283
        CalibrierMittelwert();
1622 killagreg 284
 
1 ingob 285
    if((EE_Parameter.GlobalConfig & CFG_HOEHENREGELUNG))  // Höhenregelung aktiviert?
1051 killagreg 286
     {
1 ingob 287
      if((MessLuftdruck > 950) || (MessLuftdruck < 750)) SucheLuftruckOffset();
288
     }
1166 hbuss 289
#define NEUTRAL_FILTER 32
290
    for(i=0; i<NEUTRAL_FILTER; i++)
1111 hbuss 291
         {
292
          Delay_ms_Mess(10);
1216 killagreg 293
          gier_neutral += AdWertGier;
1166 hbuss 294
          nick_neutral += AdWertNick;
295
          roll_neutral += AdWertRoll;
1111 hbuss 296
         }
1173 hbuss 297
     AdNeutralNick= (nick_neutral+NEUTRAL_FILTER/2) / (NEUTRAL_FILTER / 8);
298
         AdNeutralRoll= (roll_neutral+NEUTRAL_FILTER/2) / (NEUTRAL_FILTER / 8);
299
         AdNeutralGier= (gier_neutral+NEUTRAL_FILTER/2) / (NEUTRAL_FILTER);
1622 killagreg 300
 
401 hbuss 301
     StartNeutralRoll = AdNeutralRoll;
302
     StartNeutralNick = AdNeutralNick;
1622 killagreg 303
 
304
     if(AccAdjustment)
305
     {
306
            NeutralAccX = abs(Mittelwert_AccNick) / (2*ACC_AMPLIFY);
307
            NeutralAccY = abs(Mittelwert_AccRoll) / (2*ACC_AMPLIFY);
308
            NeutralAccZ = Aktuell_az;
309
 
310
                // Save ACC neutral settings to eeprom
1639 holgerb 311
                SetParamWord(PID_ACC_NICK, (uint16_t)NeutralAccX);
312
                SetParamWord(PID_ACC_ROLL, (uint16_t)NeutralAccY);
1622 killagreg 313
                SetParamWord(PID_ACC_TOP,  (uint16_t)NeutralAccZ);
513 hbuss 314
    }
1051 killagreg 315
    else
513 hbuss 316
    {
1622 killagreg 317
                // restore from eeprom
318
                NeutralAccX = (int16_t)GetParamWord(PID_ACC_NICK);
319
                NeutralAccY = (int16_t)GetParamWord(PID_ACC_ROLL);
320
                NeutralAccZ = (int16_t)GetParamWord(PID_ACC_TOP);
321
                // strange settings?
1638 holgerb 322
                if(((unsigned int) NeutralAccX > 2048) || ((unsigned int) NeutralAccY > 2048) || ((unsigned int) NeutralAccZ > 1024))
1622 killagreg 323
                {
324
                        printf("\n\rACC not calibrated!\r\n");
325
                        NeutralAccX = abs(Mittelwert_AccNick) / (2*ACC_AMPLIFY);
326
                        NeutralAccY = abs(Mittelwert_AccRoll) / (2*ACC_AMPLIFY);
327
                NeutralAccZ = Aktuell_az;
328
                }
513 hbuss 329
    }
1051 killagreg 330
 
1 ingob 331
    MesswertNick = 0;
332
    MesswertRoll = 0;
333
    MesswertGier = 0;
1111 hbuss 334
    Delay_ms_Mess(100);
1703 holgerb 335
    Mittelwert_AccNick = ACC_AMPLIFY * AdWertAccNick;
336
    Mittelwert_AccRoll = ACC_AMPLIFY * AdWertAccRoll;
1173 hbuss 337
    IntegralNick = EE_Parameter.GyroAccFaktor * (long)Mittelwert_AccNick;
338
    IntegralRoll = EE_Parameter.GyroAccFaktor * (long)Mittelwert_AccRoll;
339
    Mess_IntegralNick2 = IntegralNick;
340
    Mess_IntegralRoll2 = IntegralRoll;
341
    Mess_Integral_Gier = 0;
1 ingob 342
    StartLuftdruck = Luftdruck;
1253 killagreg 343
    VarioMeter = 0;
1 ingob 344
    Mess_Integral_Hoch = 0;
345
    KompassStartwert = KompassValue;
346
    GPS_Neutral();
1051 killagreg 347
    beeptime = 50;
882 hbuss 348
        Umschlag180Nick = ((long) EE_Parameter.WinkelUmschlagNick * 2500L) + 15000L;
349
        Umschlag180Roll = ((long) EE_Parameter.WinkelUmschlagRoll * 2500L) + 15000L;
492 hbuss 350
    ExternHoehenValue = 0;
693 hbuss 351
    ErsatzKompass = KompassValue * GIER_GRAD_FAKTOR;
352
    GierGyroFehler = 0;
723 hbuss 353
    SendVersionToNavi = 1;
921 hbuss 354
    LED_Init();
1765 killagreg 355
    FC_StatusFlags |= FC_STATUS_CALIBRATE;
992 hbuss 356
    FromNaviCtrl_Value.Kalman_K = -1;
1173 hbuss 357
    FromNaviCtrl_Value.Kalman_MaxDrift = 0;
992 hbuss 358
    FromNaviCtrl_Value.Kalman_MaxFusion = 32;
1391 killagreg 359
 
360
   for(i=0;i<8;i++)
1377 hbuss 361
    {
362
     Poti[i] =  PPM_in[EE_Parameter.Kanalbelegung[K_POTI1 + i]] + 110;
363
        }
1171 hbuss 364
    SenderOkay = 100;
1320 hbuss 365
    if(ServoActive)
366
         {
367
                HEF4017R_ON;
368
                DDRD  |=0x80; // enable J7 -> Servo signal
369
     }
1702 holgerb 370
 
1765 killagreg 371
        if((AdNeutralNick < 150 * 16) || (AdNeutralNick > 850 * 16)) { VersionInfo.HardwareError[0] |= FC_ERROR0_GYRO_NICK; };
372
        if((AdNeutralRoll < 150 * 16) || (AdNeutralRoll > 850 * 16)) { VersionInfo.HardwareError[0] |= FC_ERROR0_GYRO_ROLL; };
373
        if((AdNeutralGier < 150 * 2)  || (AdNeutralGier > 850 * 2))  { VersionInfo.HardwareError[0] |= FC_ERROR0_GYRO_YAW; };
374
        if((NeutralAccX < 300) || (NeutralAccX > 750)) { VersionInfo.HardwareError[0] |= FC_ERROR0_ACC_NICK; };
375
        if((NeutralAccY < 300) || (NeutralAccY > 750)) { VersionInfo.HardwareError[0] |= FC_ERROR0_ACC_ROLL; };
376
        if((NeutralAccZ < 512) || (NeutralAccZ > 850)) { VersionInfo.HardwareError[0] |= FC_ERROR0_ACC_TOP; };
1 ingob 377
}
378
 
1702 holgerb 379
 
1 ingob 380
//############################################################################
395 hbuss 381
// Bearbeitet die Messwerte
1 ingob 382
void Mittelwert(void)
383
//############################################################################
1051 killagreg 384
{
1111 hbuss 385
    static signed long tmpl,tmpl2,tmpl3,tmpl4;
386
        static signed int oldNick, oldRoll, d2Roll, d2Nick;
1153 hbuss 387
        signed long winkel_nick, winkel_roll;
1813 - 388
/***********************************************************************************************************
389
Arthur P: Disabbled unsinged char i as this variable is not used.
390
***********************************************************************************************************/
391
//    unsigned char i;
392
/***********************************************************************************************************
393
Arthur P: End of change.
394
***********************************************************************************************************/
1111 hbuss 395
        MesswertGier = (signed int) AdNeutralGier - AdWertGier;
1171 hbuss 396
    MesswertNick = (signed int) AdWertNickFilter / 8;
397
    MesswertRoll = (signed int) AdWertRollFilter / 8;
1153 hbuss 398
    RohMesswertNick = MesswertNick;
399
    RohMesswertRoll = MesswertRoll;
1166 hbuss 400
 
395 hbuss 401
// Beschleunigungssensor  ++++++++++++++++++++++++++++++++++++++++++++++++
1703 holgerb 402
        Mittelwert_AccNick = (Mittelwert_AccNick * 3 + ((ACC_AMPLIFY * AdWertAccNick))) / 4L;
403
        Mittelwert_AccRoll = (Mittelwert_AccRoll * 3 + ((ACC_AMPLIFY * AdWertAccRoll))) / 4L;
395 hbuss 404
    IntegralAccNick += ACC_AMPLIFY * AdWertAccNick;
405
    IntegralAccRoll += ACC_AMPLIFY * AdWertAccRoll;
805 hbuss 406
    NaviAccNick    += AdWertAccNick;
407
    NaviAccRoll    += AdWertAccRoll;
408
    NaviCntAcc++;
1153 hbuss 409
    IntegralAccZ  += Aktuell_az - NeutralAccZ;
410
 
1155 hbuss 411
//++++++++++++++++++++++++++++++++++++++++++++++++
412
// ADC einschalten
1171 hbuss 413
    ANALOG_ON;
1155 hbuss 414
        AdReady = 0;
415
//++++++++++++++++++++++++++++++++++++++++++++++++
416
 
1216 killagreg 417
    if(Mess_IntegralRoll > 93000L) winkel_roll = 93000L;
418
        else if(Mess_IntegralRoll <-93000L) winkel_roll = -93000L;
1153 hbuss 419
        else winkel_roll = Mess_IntegralRoll;
420
 
1216 killagreg 421
    if(Mess_IntegralNick > 93000L) winkel_nick = 93000L;
422
        else if(Mess_IntegralNick <-93000L) winkel_nick = -93000L;
1153 hbuss 423
        else winkel_nick = Mess_IntegralNick;
424
 
1120 hbuss 425
// Gier  ++++++++++++++++++++++++++++++++++++++++++++++++
1153 hbuss 426
   Mess_Integral_Gier += MesswertGier;
427
   ErsatzKompass += MesswertGier;
395 hbuss 428
// Kopplungsanteil  +++++++++++++++++++++++++++++++++++++
429
      if(!Looping_Nick && !Looping_Roll && (EE_Parameter.GlobalConfig & CFG_ACHSENKOPPLUNG_AKTIV))
430
         {
1153 hbuss 431
            tmpl3 = (MesswertRoll * winkel_nick) / 2048L;
1120 hbuss 432
            tmpl3 *= Parameter_AchsKopplung2; //65
1111 hbuss 433
            tmpl3 /= 4096L;
1153 hbuss 434
            tmpl4 = (MesswertNick * winkel_roll) / 2048L;
1216 killagreg 435
            tmpl4 *= Parameter_AchsKopplung2; //65
1111 hbuss 436
            tmpl4 /= 4096L;
1153 hbuss 437
            KopplungsteilNickRoll = tmpl3;
438
            KopplungsteilRollNick = tmpl4;
1111 hbuss 439
            tmpl4 -= tmpl3;
440
            ErsatzKompass += tmpl4;
1166 hbuss 441
            if(!Parameter_CouplingYawCorrection) Mess_Integral_Gier -= tmpl4/2; // Gier nachhelfen
1111 hbuss 442
 
1153 hbuss 443
            tmpl = ((MesswertGier + tmpl4) * winkel_nick) / 2048L;
1111 hbuss 444
            tmpl *= Parameter_AchsKopplung1;  // 90
880 hbuss 445
            tmpl /= 4096L;
1153 hbuss 446
            tmpl2 = ((MesswertGier + tmpl4) * winkel_roll) / 2048L;
395 hbuss 447
            tmpl2 *= Parameter_AchsKopplung1;
1662 killagreg 448
            tmpl2 /= 4096L;
1225 hbuss 449
            if(abs(MesswertGier) > 64) if(labs(tmpl) > 128 || labs(tmpl2) > 128) TrichterFlug = 1;
1153 hbuss 450
            //MesswertGier += (Parameter_CouplingYawCorrection * tmpl4) / 256;
395 hbuss 451
         }
1166 hbuss 452
      else  tmpl = tmpl2 = KopplungsteilNickRoll = KopplungsteilRollNick = 0;
1658 holgerb 453
                        TrimRoll = tmpl - tmpl2 / 100L;
454
                        TrimNick = -tmpl2 + tmpl / 100L;
1111 hbuss 455
// Kompasswert begrenzen  ++++++++++++++++++++++++++++++++++++++++++++++++
456
                    if(ErsatzKompass >= (360L * GIER_GRAD_FAKTOR)) ErsatzKompass -= 360L * GIER_GRAD_FAKTOR;  // 360° Umschlag
457
                    if(ErsatzKompass < 0)                          ErsatzKompass += 360L * GIER_GRAD_FAKTOR;
395 hbuss 458
// Roll  ++++++++++++++++++++++++++++++++++++++++++++++++
1166 hbuss 459
            Mess_IntegralRoll2 += MesswertRoll + TrimRoll;
460
            Mess_IntegralRoll +=  MesswertRoll + TrimRoll - LageKorrekturRoll;
1051 killagreg 461
            if(Mess_IntegralRoll > Umschlag180Roll)
395 hbuss 462
            {
882 hbuss 463
             Mess_IntegralRoll  = -(Umschlag180Roll - 25000L);
395 hbuss 464
             Mess_IntegralRoll2 = Mess_IntegralRoll;
1051 killagreg 465
            }
395 hbuss 466
            if(Mess_IntegralRoll <-Umschlag180Roll)
467
            {
882 hbuss 468
             Mess_IntegralRoll =  (Umschlag180Roll - 25000L);
395 hbuss 469
             Mess_IntegralRoll2 = Mess_IntegralRoll;
1051 killagreg 470
            }
395 hbuss 471
// Nick  ++++++++++++++++++++++++++++++++++++++++++++++++
1166 hbuss 472
            Mess_IntegralNick2 += MesswertNick + TrimNick;
473
            Mess_IntegralNick  += MesswertNick + TrimNick - LageKorrekturNick;
1051 killagreg 474
            if(Mess_IntegralNick > Umschlag180Nick)
882 hbuss 475
             {
476
              Mess_IntegralNick = -(Umschlag180Nick - 25000L);
477
              Mess_IntegralNick2 = Mess_IntegralNick;
1051 killagreg 478
             }
479
            if(Mess_IntegralNick <-Umschlag180Nick)
395 hbuss 480
            {
882 hbuss 481
             Mess_IntegralNick =  (Umschlag180Nick - 25000L);
395 hbuss 482
             Mess_IntegralNick2 = Mess_IntegralNick;
1051 killagreg 483
            }
1111 hbuss 484
 
1 ingob 485
    Integral_Gier  = Mess_Integral_Gier;
486
    IntegralNick = Mess_IntegralNick;
487
    IntegralRoll = Mess_IntegralRoll;
1051 killagreg 488
    IntegralNick2 = Mess_IntegralNick2;
1 ingob 489
    IntegralRoll2 = Mess_IntegralRoll2;
490
 
1166 hbuss 491
#define D_LIMIT 128
492
 
1171 hbuss 493
   MesswertNick = HiResNick / 8;
494
   MesswertRoll = HiResRoll / 8;
1166 hbuss 495
 
1167 hbuss 496
   if(AdWertNick < 15)   MesswertNick = -1000;  if(AdWertNick <  7)   MesswertNick = -2000;
497
   if(PlatinenVersion == 10)  { if(AdWertNick > 1010) MesswertNick = +1000;  if(AdWertNick > 1017) MesswertNick = +2000; }
498
   else  {  if(AdWertNick > 2000) MesswertNick = +1000;  if(AdWertNick > 2015) MesswertNick = +2000; }
499
   if(AdWertRoll < 15)   MesswertRoll = -1000;  if(AdWertRoll <  7)   MesswertRoll = -2000;
500
   if(PlatinenVersion == 10) { if(AdWertRoll > 1010) MesswertRoll = +1000;  if(AdWertRoll > 1017) MesswertRoll = +2000; }
501
   else { if(AdWertRoll > 2000) MesswertRoll = +1000;  if(AdWertRoll > 2015) MesswertRoll = +2000;  }
502
 
1216 killagreg 503
  if(Parameter_Gyro_D)
1111 hbuss 504
  {
1166 hbuss 505
   d2Nick = HiResNick - oldNick;
506
   oldNick = (oldNick + HiResNick)/2;
1111 hbuss 507
   if(d2Nick > D_LIMIT) d2Nick = D_LIMIT;
508
   else if(d2Nick < -D_LIMIT) d2Nick = -D_LIMIT;
1791 holgerb 509
 
1166 hbuss 510
   d2Roll = HiResRoll - oldRoll;
511
   oldRoll = (oldRoll + HiResRoll)/2;
1111 hbuss 512
   if(d2Roll > D_LIMIT) d2Roll = D_LIMIT;
513
   else if(d2Roll < -D_LIMIT) d2Roll = -D_LIMIT;
1791 holgerb 514
 
515
   MesswertNick += (d2Nick * (signed int) Parameter_Gyro_D) / 16;
1166 hbuss 516
   MesswertRoll += (d2Roll * (signed int) Parameter_Gyro_D) / 16;
517
   HiResNick += (d2Nick * (signed int) Parameter_Gyro_D);
518
   HiResRoll += (d2Roll * (signed int) Parameter_Gyro_D);
1216 killagreg 519
  }
1111 hbuss 520
 
1166 hbuss 521
 if(RohMesswertRoll > 0) TrimRoll  += ((long) abs(KopplungsteilNickRoll) * Parameter_CouplingYawCorrection) / 64L;
522
 else                    TrimRoll -= ((long) abs(KopplungsteilNickRoll) * Parameter_CouplingYawCorrection) / 64L;
523
 if(RohMesswertNick > 0) TrimNick += ((long) abs(KopplungsteilRollNick) * Parameter_CouplingYawCorrection) / 64L;
524
 else                    TrimNick -= ((long) abs(KopplungsteilRollNick) * Parameter_CouplingYawCorrection) / 64L;
1153 hbuss 525
 
526
  if(EE_Parameter.GlobalConfig & CFG_DREHRATEN_BEGRENZER && !Looping_Nick && !Looping_Roll)
527
  {
528
    if(RohMesswertNick > 256)       MesswertNick += 1 * (RohMesswertNick - 256);
529
    else if(RohMesswertNick < -256) MesswertNick += 1 * (RohMesswertNick + 256);
530
    if(RohMesswertRoll > 256)       MesswertRoll += 1 * (RohMesswertRoll - 256);
531
    else if(RohMesswertRoll < -256) MesswertRoll += 1 * (RohMesswertRoll + 256);
532
  }
1 ingob 533
}
534
 
535
//############################################################################
536
// Senden der Motorwerte per I2C-Bus
537
void SendMotorData(void)
538
//############################################################################
1051 killagreg 539
{
1209 hbuss 540
 unsigned char i;
921 hbuss 541
    if(!MotorenEin)
1 ingob 542
        {
1765 killagreg 543
         FC_StatusFlags &= ~(FC_STATUS_MOTOR_RUN | FC_STATUS_FLY);
1216 killagreg 544
                 for(i=0;i<MAX_MOTORS;i++)
545
                  {
546
                   if(!PC_MotortestActive)  MotorTest[i] = 0;
1638 holgerb 547
                   Motor[i].SetPoint = MotorTest[i];
548
                   Motor[i].SetPointLowerBits = 0;
549
/*
1760 holgerb 550
 Motor[i].SetPoint = MotorTest[i] / 4;            // testing the high resolution
551
 Motor[i].SetPointLowerBits = MotorTest[i] % 4;
1638 holgerb 552
*/
1216 killagreg 553
                  }
1212 hbuss 554
          if(PC_MotortestActive) PC_MotortestActive--;
1216 killagreg 555
        }
1765 killagreg 556
        else FC_StatusFlags |= FC_STATUS_MOTOR_RUN;
1744 holgerb 557
 
1765 killagreg 558
    if(I2C_TransferActive)
1744 holgerb 559
         {
1760 holgerb 560
          I2C_TransferActive = 0; // enable for the next time
1765 killagreg 561
         }
562
        else
1744 holgerb 563
    {
564
     motor_write = 0;
1760 holgerb 565
     I2C_Start(TWI_STATE_MOTOR_TX); //Start I2C Interrupt Mode
1765 killagreg 566
        }
1 ingob 567
}
568
 
569
 
570
 
571
//############################################################################
572
// Trägt ggf. das Poti als Parameter ein
1051 killagreg 573
void ParameterZuordnung(void)
1 ingob 574
//############################################################################
575
{
1787 holgerb 576
 unsigned char tmp,i;
1391 killagreg 577
 #define CHK_POTI(b,a) {if(a < 248) b = a; else b = Poti[255 - a];}
578
 #define CHK_POTI_MM(b,a,min,max) {CHK_POTI(b,a); LIMIT_MIN_MAX(b, min, max);}
1787 holgerb 579
  for(i=0;i<8;i++)
580
    {
581
     int tmp2;
582
         tmp2 = PPM_in[EE_Parameter.Kanalbelegung[K_POTI1 + i]] + 110;
583
         if(tmp2 > 255) tmp2 = 255; else if(tmp2 < 0) tmp2 = 0;
584
     if(tmp2 != Poti[i])
585
          {
586
           Poti[i] += (tmp2 - Poti[i]) / 4;
587
       if(Poti[i] > tmp2) Poti[i]--;
588
           else Poti[i]++;
589
          }
590
        }
921 hbuss 591
 CHK_POTI_MM(Parameter_Luftdruck_D,EE_Parameter.Luftdruck_D,0,100);
592
 CHK_POTI_MM(Parameter_Hoehe_P,EE_Parameter.Hoehe_P,0,100);
593
 CHK_POTI_MM(Parameter_Gyro_P,EE_Parameter.Gyro_P,10,255);
594
 CHK_POTI_MM(Parameter_J16Timing,EE_Parameter.J16Timing,1,255);
595
 CHK_POTI_MM(Parameter_J17Timing,EE_Parameter.J17Timing,1,255);
1403 hbuss 596
 CHK_POTI(Parameter_Servo3,EE_Parameter.Servo3);
597
 CHK_POTI(Parameter_Servo4,EE_Parameter.Servo4);
598
 CHK_POTI(Parameter_Servo5,EE_Parameter.Servo5);
1377 hbuss 599
 CHK_POTI(Parameter_MaxHoehe,EE_Parameter.MaxHoehe);
1403 hbuss 600
 CHK_POTI(Parameter_MaxHoehe,EE_Parameter.MaxHoehe);
1377 hbuss 601
 CHK_POTI(Parameter_Hoehe_ACC_Wirkung,EE_Parameter.Hoehe_ACC_Wirkung);
602
 CHK_POTI(Parameter_Hoehe_GPS_Z,EE_Parameter.Hoehe_GPS_Z);
603
 CHK_POTI(Parameter_KompassWirkung,EE_Parameter.KompassWirkung);
604
 CHK_POTI(Parameter_Gyro_I,EE_Parameter.Gyro_I);
605
 CHK_POTI(Parameter_Gyro_D,EE_Parameter.Gyro_D);
606
 CHK_POTI(Parameter_Gyro_Gier_P,EE_Parameter.Gyro_Gier_P);
607
 CHK_POTI(Parameter_Gyro_Gier_I,EE_Parameter.Gyro_Gier_I);
608
 CHK_POTI(Parameter_I_Faktor,EE_Parameter.I_Faktor);
609
 CHK_POTI(Parameter_UserParam1,EE_Parameter.UserParam1);
610
 CHK_POTI(Parameter_UserParam2,EE_Parameter.UserParam2);
611
 CHK_POTI(Parameter_UserParam3,EE_Parameter.UserParam3);
612
 CHK_POTI(Parameter_UserParam4,EE_Parameter.UserParam4);
613
 CHK_POTI(Parameter_UserParam5,EE_Parameter.UserParam5);
614
 CHK_POTI(Parameter_UserParam6,EE_Parameter.UserParam6);
615
 CHK_POTI(Parameter_UserParam7,EE_Parameter.UserParam7);
616
 CHK_POTI(Parameter_UserParam8,EE_Parameter.UserParam8);
617
 CHK_POTI(Parameter_ServoNickControl,EE_Parameter.ServoNickControl);
618
 CHK_POTI(Parameter_ServoRollControl,EE_Parameter.ServoRollControl);
619
 CHK_POTI(Parameter_LoopGasLimit,EE_Parameter.LoopGasLimit);
1668 holgerb 620
 CHK_POTI(Parameter_AchsKopplung1,EE_Parameter.AchsKopplung1);
621
 CHK_POTI(Parameter_AchsKopplung2,EE_Parameter.AchsKopplung2);
1377 hbuss 622
 CHK_POTI(Parameter_CouplingYawCorrection,EE_Parameter.CouplingYawCorrection);
623
// CHK_POTI(Parameter_AchsGegenKopplung1,EE_Parameter.AchsGegenKopplung1,0,255);
624
 CHK_POTI(Parameter_DynamicStability,EE_Parameter.DynamicStability);
625
 CHK_POTI(Parameter_ExternalControl,EE_Parameter.ExternalControl);
1676 holgerb 626
 Ki = 10300 / (Parameter_I_Faktor + 1);
1 ingob 627
 MAX_GAS = EE_Parameter.Gas_Max;
1662 killagreg 628
 MIN_GAS = EE_Parameter.Gas_Min;
1668 holgerb 629
 
630
 tmp = EE_Parameter.OrientationModeControl;
1690 holgerb 631
 if(tmp > 50)
1668 holgerb 632
   {
1682 holgerb 633
#ifdef SWITCH_LEARNS_CAREFREE
634
    if(!CareFree) ControlHeading = (((int) EE_Parameter.OrientationAngle * 15 + KompassValue) % 360) / 2;
635
#endif
636
        CareFree = 1;
1668 holgerb 637
    if(tmp >= 248 && Poti[255 - tmp] < 50) CareFree = 0;
1765 killagreg 638
    if(FromNaviCtrl.CompassValue < 0 && CareFree) VersionInfo.HardwareError[0] |= FC_ERROR0_CAREFREE; else VersionInfo.HardwareError[0] &= ~FC_ERROR0_CAREFREE;
1669 killagreg 639
   }
1668 holgerb 640
   else CareFree = 0;
641
 
1691 holgerb 642
 if(FromNaviCtrl.CompassValue < 0 && MotorenEin && CareFree && BeepMuster == 0xffff) // ungültiger Kompasswert
1690 holgerb 643
        {
644
         beeptime = 15000;
645
         BeepMuster = 0xA400;
646
         CareFree = 0;
1765 killagreg 647
    }
1702 holgerb 648
 
1668 holgerb 649
 if(CareFree) {if(Parameter_AchsKopplung1 < 210) Parameter_AchsKopplung1 += 30;}
1 ingob 650
}
651
 
652
//############################################################################
653
//
654
void MotorRegler(void)
655
//############################################################################
656
{
1330 killagreg 657
         int pd_ergebnis_nick,pd_ergebnis_roll,tmp_int, tmp_int2;
1 ingob 658
         int GierMischanteil,GasMischanteil;
659
     static long sollGier = 0,tmp_long,tmp_long2;
395 hbuss 660
     static long IntegralFehlerNick = 0;
661
     static long IntegralFehlerRoll = 0;
1 ingob 662
         static unsigned int RcLostTimer;
663
         static unsigned char delay_neutral = 0;
664
         static unsigned char delay_einschalten = 0,delay_ausschalten = 0;
1622 killagreg 665
         static unsigned char calibration_done = 0;
1 ingob 666
     static char NeueKompassRichtungMerken = 0;
395 hbuss 667
     static long ausgleichNick, ausgleichRoll;
1153 hbuss 668
     int IntegralNickMalFaktor,IntegralRollMalFaktor;
1209 hbuss 669
         unsigned char i;
1051 killagreg 670
        Mittelwert();
1 ingob 671
    GRN_ON;
1051 killagreg 672
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 673
// Gaswert ermitteln
1051 killagreg 674
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
675
        GasMischanteil = StickGas;
831 hbuss 676
    if(GasMischanteil < MIN_GAS + 10) GasMischanteil = MIN_GAS + 10;
1330 killagreg 677
 
1051 killagreg 678
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
693 hbuss 679
// Empfang schlecht
1051 killagreg 680
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 681
   if(SenderOkay < 100)
682
        {
1051 killagreg 683
        if(RcLostTimer) RcLostTimer--;
684
        else
1 ingob 685
         {
686
          MotorenEin = 0;
1765 killagreg 687
          FC_StatusFlags &= ~FC_STATUS_EMERGENCY_LANDING;
1051 killagreg 688
         }
1 ingob 689
        ROT_ON;
693 hbuss 690
        if(modell_fliegt > 1000)  // wahrscheinlich in der Luft --> langsam absenken
1 ingob 691
            {
692
            GasMischanteil = EE_Parameter.NotGas;
1765 killagreg 693
            FC_StatusFlags |= FC_STATUS_EMERGENCY_LANDING;
744 hbuss 694
            PPM_diff[EE_Parameter.Kanalbelegung[K_NICK]] = 0;
1051 killagreg 695
            PPM_diff[EE_Parameter.Kanalbelegung[K_ROLL]] = 0;
1 ingob 696
            PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] = 0;
697
            PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] = 0;
698
            PPM_in[EE_Parameter.Kanalbelegung[K_GIER]] = 0;
173 holgerb 699
            }
1 ingob 700
         else MotorenEin = 0;
701
        }
1051 killagreg 702
        else
703
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 704
// Emfang gut
1051 killagreg 705
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 706
        if(SenderOkay > 140)
707
            {
1765 killagreg 708
                        FC_StatusFlags &= ~FC_STATUS_EMERGENCY_LANDING;
1 ingob 709
            RcLostTimer = EE_Parameter.NotGasZeit * 50;
921 hbuss 710
            if(GasMischanteil > 40 && MotorenEin)
1 ingob 711
                {
712
                if(modell_fliegt < 0xffff) modell_fliegt++;
713
                }
871 hbuss 714
            if((modell_fliegt < 256))
1 ingob 715
                {
716
                SummeNick = 0;
717
                SummeRoll = 0;
1682 holgerb 718
                sollGier = 0;
719
                Mess_Integral_Gier = 0;
1051 killagreg 720
                if(modell_fliegt == 250)
918 hbuss 721
                 {
1051 killagreg 722
                  NeueKompassRichtungMerken = 1;
723
                 }
1765 killagreg 724
                } else FC_StatusFlags |= FC_STATUS_FLY;
1051 killagreg 725
 
595 hbuss 726
            if((PPM_in[EE_Parameter.Kanalbelegung[K_GAS]] > 80) && MotorenEin == 0)
1 ingob 727
                {
1051 killagreg 728
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 729
// auf Nullwerte kalibrieren
1051 killagreg 730
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 731
                if(PPM_in[EE_Parameter.Kanalbelegung[K_GIER]] > 75)  // Neutralwerte
732
                    {
733
                    if(++delay_neutral > 200)  // nicht sofort
734
                        {
735
                        GRN_OFF;
736
                        MotorenEin = 0;
737
                        delay_neutral = 0;
738
                        modell_fliegt = 0;
739
                        if(PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > 70 || abs(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]]) > 70)
740
                        {
304 ingob 741
                         unsigned char setting=1;
1 ingob 742
                         if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] > 70 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] < 70) setting = 1;
743
                         if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] > 70 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > 70) setting = 2;
744
                         if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] < 70 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > 70) setting = 3;
745
                         if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] <-70 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > 70) setting = 4;
746
                         if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] <-70 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] < 70) setting = 5;
1622 killagreg 747
                         SetActiveParamSet(setting);  // aktiven Datensatz merken
1 ingob 748
                        }
1051 killagreg 749
                         if(abs(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]]) < 30 && PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] < -70)
750
                          {
819 hbuss 751
                           WinkelOut.CalcState = 1;
752
                           beeptime = 1000;
753
                          }
754
                          else
1 ingob 755
                          {
1622 killagreg 756
                               ParamSet_ReadFromEEProm(GetActiveParamSet());
1413 killagreg 757
                               LipoDetection(0);
1626 killagreg 758
                                                   LIBFC_ReceiverInit(EE_Parameter.Receiver);
819 hbuss 759
                           if((EE_Parameter.GlobalConfig & CFG_HOEHENREGELUNG))  // Höhenregelung aktiviert?
760
                            {
1 ingob 761
                             if((MessLuftdruck > 950) || (MessLuftdruck < 750)) SucheLuftruckOffset();
1051 killagreg 762
                            }
1330 killagreg 763
                                                   ServoActive = 0;
1622 killagreg 764
                           SetNeutral(0);
1765 killagreg 765
                           calibration_done = 1;
1232 hbuss 766
                                                   ServoActive = 1;
767
                                                   DDRD  |=0x80; // enable J7 -> Servo signal
1622 killagreg 768
                           Piep(GetActiveParamSet(),120);
819 hbuss 769
                         }
1051 killagreg 770
                        }
1 ingob 771
                    }
1051 killagreg 772
                 else
513 hbuss 773
                if(PPM_in[EE_Parameter.Kanalbelegung[K_GIER]] < -75)  // ACC Neutralwerte speichern
774
                    {
775
                    if(++delay_neutral > 200)  // nicht sofort
776
                        {
777
                        GRN_OFF;
778
                        MotorenEin = 0;
779
                        delay_neutral = 0;
780
                        modell_fliegt = 0;
1622 killagreg 781
                        SetNeutral(1);
782
                        calibration_done = 1;
783
                        Piep(GetActiveParamSet(),120);
1051 killagreg 784
                        }
513 hbuss 785
                    }
1 ingob 786
                 else delay_neutral = 0;
787
                }
1051 killagreg 788
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 789
// Gas ist unten
1051 killagreg 790
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1760 holgerb 791
 
595 hbuss 792
            if(PPM_in[EE_Parameter.Kanalbelegung[K_GAS]] < 35-120)
1 ingob 793
                {
1521 killagreg 794
                                        // Motoren Starten
795
                                        if(!MotorenEin)
796
                        {
1760 holgerb 797
                                                if((PPM_in[EE_Parameter.Kanalbelegung[K_GIER]] < -75) && (PPM_in[EE_Parameter.MotorSafetySwitch] < -75 || EE_Parameter.MotorSafetySwitch == 0))
1521 killagreg 798
                                                {
1051 killagreg 799
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 800
// Einschalten
1051 killagreg 801
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1521 killagreg 802
                                                        if(++delay_einschalten > 200)
803
                                                        {
804
                                                                delay_einschalten = 0;
1702 holgerb 805
                                                                if(!VersionInfo.HardwareError[0] && calibration_done)
1622 killagreg 806
                                                                {
807
                                                                        modell_fliegt = 1;
808
                                                                        MotorenEin = 1;
809
                                                                        sollGier = 0;
810
                                                                        Mess_Integral_Gier = 0;
811
                                                                        Mess_Integral_Gier2 = 0;
812
                                                                        Mess_IntegralNick = EE_Parameter.GyroAccFaktor * (long)Mittelwert_AccNick;
813
                                                                        Mess_IntegralRoll = EE_Parameter.GyroAccFaktor * (long)Mittelwert_AccRoll;
814
                                                                        Mess_IntegralNick2 = IntegralNick;
815
                                                                        Mess_IntegralRoll2 = IntegralRoll;
816
                                                                        SummeNick = 0;
817
                                                                        SummeRoll = 0;
1765 killagreg 818
                                                                        FC_StatusFlags |= FC_STATUS_START;
1669 killagreg 819
                                                                        ControlHeading = (((int) EE_Parameter.OrientationAngle * 15 + KompassValue) % 360) / 2;
1622 killagreg 820
                                                                }
821
                                                                else
822
                                                                {
823
                                                                        beeptime = 1500; // indicate missing calibration
824
                                                                }
1521 killagreg 825
                                                        }
826
                                                }
827
                                                else delay_einschalten = 0;
828
                                        }
1051 killagreg 829
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 830
// Auschalten
1051 killagreg 831
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1521 killagreg 832
                                        else // only if motors are running
833
                                        {
1760 holgerb 834
                                                if((PPM_in[EE_Parameter.Kanalbelegung[K_GIER]] > 75) && (PPM_in[EE_Parameter.MotorSafetySwitch] < -75 || EE_Parameter.MotorSafetySwitch == 0))
1521 killagreg 835
                                                {
836
                                                        if(++delay_ausschalten > 200)  // nicht sofort
837
                                                        {
838
                                                                MotorenEin = 0;
839
                                                                delay_ausschalten = 0;
840
                                                                modell_fliegt = 0;
841
                                                        }
842
                                                }
843
                                                else delay_ausschalten = 0;
844
                                        }
1 ingob 845
                }
846
            }
1051 killagreg 847
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 848
// neue Werte von der Funke
1051 killagreg 849
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1216 killagreg 850
 
1765 killagreg 851
 if(!NewPpmData-- || (FC_StatusFlags & FC_STATUS_EMERGENCY_LANDING))
1 ingob 852
  {
604 hbuss 853
        static int stick_nick,stick_roll;
1 ingob 854
    ParameterZuordnung();
1051 killagreg 855
    stick_nick = (stick_nick * 3 + PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] * EE_Parameter.Stick_P) / 4;
723 hbuss 856
    stick_nick += PPM_diff[EE_Parameter.Kanalbelegung[K_NICK]] * EE_Parameter.Stick_D;
857
    stick_roll = (stick_roll * 3 + PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] * EE_Parameter.Stick_P) / 4;
858
    stick_roll += PPM_diff[EE_Parameter.Kanalbelegung[K_ROLL]] * EE_Parameter.Stick_D;
859
 
1707 holgerb 860
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
861
// CareFree und freie Wahl der vorderen Richtung
862
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1668 holgerb 863
if(CareFree)
1658 holgerb 864
 {
1664 holgerb 865
    signed int nick, roll;
866
        nick = stick_nick / 4;
867
        roll = stick_roll / 4;
868
    StickNick = ((FromNC_Rotate_C * nick) + (FromNC_Rotate_S * roll)) / (32 / 4);
869
    StickRoll = ((FromNC_Rotate_C * roll) - (FromNC_Rotate_S * nick)) / (32 / 4);
1658 holgerb 870
 }
1662 killagreg 871
 else
1658 holgerb 872
 {
1668 holgerb 873
        FromNC_Rotate_C = sintab[EE_Parameter.OrientationAngle + 6];
874
        FromNC_Rotate_S = sintab[EE_Parameter.OrientationAngle];
875
    StickNick = ((FromNC_Rotate_C * stick_nick) + (FromNC_Rotate_S * stick_roll)) / 8;
876
    StickRoll = ((FromNC_Rotate_C * stick_roll) - (FromNC_Rotate_S * stick_nick)) / 8;
1658 holgerb 877
 }
1662 killagreg 878
 
1 ingob 879
    StickGier = -PPM_in[EE_Parameter.Kanalbelegung[K_GIER]];
1120 hbuss 880
        if(StickGier > 2) StickGier -= 2;       else
881
        if(StickGier < -2) StickGier += 2; else StickGier = 0;
882
 
1658 holgerb 883
    StickNick -= (GPS_Nick + GPS_Nick2);
884
    StickRoll -= (GPS_Roll + GPS_Roll2);
1350 hbuss 885
        StickGas  = PPM_in[EE_Parameter.Kanalbelegung[K_GAS]] + 120;
1330 killagreg 886
 
1153 hbuss 887
    GyroFaktor     = (Parameter_Gyro_P + 10.0);
888
    IntegralFaktor = Parameter_Gyro_I;
1322 hbuss 889
    GyroFaktorGier     = (Parameter_Gyro_Gier_P + 10.0);
890
    IntegralFaktorGier = Parameter_Gyro_Gier_I;
1 ingob 891
 
595 hbuss 892
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
893
//+ Analoge Steuerung per Seriell
894
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
921 hbuss 895
   if(ExternControl.Config & 0x01 && Parameter_ExternalControl > 128)
595 hbuss 896
    {
897
         StickNick += (int) ExternControl.Nick * (int) EE_Parameter.Stick_P;
898
         StickRoll += (int) ExternControl.Roll * (int) EE_Parameter.Stick_P;
899
         StickGier += ExternControl.Gier;
900
     ExternHoehenValue =  (int) ExternControl.Hight * (int)EE_Parameter.Hoehe_Verstaerkung;
901
     if(ExternControl.Gas < StickGas) StickGas = ExternControl.Gas;
902
    }
855 hbuss 903
    if(StickGas < 0) StickGas = 0;
1330 killagreg 904
 
1 ingob 905
    if(EE_Parameter.GlobalConfig & CFG_HEADING_HOLD) IntegralFaktor =  0;
723 hbuss 906
 
1051 killagreg 907
    if(abs(StickNick/STICK_GAIN) > MaxStickNick)
928 hbuss 908
     {
1051 killagreg 909
      MaxStickNick = abs(StickNick)/STICK_GAIN;
928 hbuss 910
      if(MaxStickNick > 100) MaxStickNick = 100;
1051 killagreg 911
     }
928 hbuss 912
     else MaxStickNick--;
1051 killagreg 913
    if(abs(StickRoll/STICK_GAIN) > MaxStickRoll)
928 hbuss 914
     {
1051 killagreg 915
      MaxStickRoll = abs(StickRoll)/STICK_GAIN;
928 hbuss 916
      if(MaxStickRoll > 100) MaxStickRoll = 100;
1051 killagreg 917
     }
928 hbuss 918
     else MaxStickRoll--;
1765 killagreg 919
    if(FC_StatusFlags & FC_STATUS_EMERGENCY_LANDING)  {MaxStickNick = 0; MaxStickRoll = 0;}
723 hbuss 920
 
1051 killagreg 921
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
173 holgerb 922
// Looping?
1051 killagreg 923
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
993 hbuss 924
  if((PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] > EE_Parameter.LoopThreshold) && EE_Parameter.BitConfig & CFG_LOOP_LINKS)  Looping_Links = 1;
1051 killagreg 925
  else
926
   {
395 hbuss 927
     {
1051 killagreg 928
      if((PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] < (EE_Parameter.LoopThreshold - EE_Parameter.LoopHysterese))) Looping_Links = 0;
929
     }
930
   }
993 hbuss 931
  if((PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] < -EE_Parameter.LoopThreshold) && EE_Parameter.BitConfig & CFG_LOOP_RECHTS) Looping_Rechts = 1;
1051 killagreg 932
   else
395 hbuss 933
   {
934
   if(Looping_Rechts) // Hysterese
935
     {
936
      if(PPM_in[EE_Parameter.Kanalbelegung[K_ROLL]] > -(EE_Parameter.LoopThreshold - EE_Parameter.LoopHysterese)) Looping_Rechts = 0;
937
     }
1051 killagreg 938
   }
173 holgerb 939
 
993 hbuss 940
  if((PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > EE_Parameter.LoopThreshold) && EE_Parameter.BitConfig & CFG_LOOP_OBEN) Looping_Oben = 1;
1051 killagreg 941
  else
942
   {
395 hbuss 943
    if(Looping_Oben)  // Hysterese
944
     {
1051 killagreg 945
      if((PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] < (EE_Parameter.LoopThreshold - EE_Parameter.LoopHysterese))) Looping_Oben = 0;
946
     }
947
   }
993 hbuss 948
  if((PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] < -EE_Parameter.LoopThreshold) && EE_Parameter.BitConfig & CFG_LOOP_UNTEN) Looping_Unten = 1;
1051 killagreg 949
   else
395 hbuss 950
   {
951
    if(Looping_Unten) // Hysterese
952
     {
953
      if(PPM_in[EE_Parameter.Kanalbelegung[K_NICK]] > -(EE_Parameter.LoopThreshold - EE_Parameter.LoopHysterese)) Looping_Unten = 0;
954
     }
1051 killagreg 955
   }
395 hbuss 956
 
957
   if(Looping_Links || Looping_Rechts)   Looping_Roll = 1; else Looping_Roll = 0;
1153 hbuss 958
   if(Looping_Oben  || Looping_Unten) {  Looping_Nick = 1; Looping_Roll = 0; Looping_Links = 0; Looping_Rechts = 0;} else Looping_Nick = 0;
395 hbuss 959
  } // Ende neue Funken-Werte
960
 
961
  if(Looping_Roll || Looping_Nick)
962
   {
173 holgerb 963
    if(GasMischanteil > EE_Parameter.LoopGasLimit) GasMischanteil = EE_Parameter.LoopGasLimit;
1153 hbuss 964
        TrichterFlug = 1;
173 holgerb 965
   }
966
 
1051 killagreg 967
 
968
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
969
// Bei Empfangsausfall im Flug
970
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1765 killagreg 971
   if(FC_StatusFlags & FC_STATUS_EMERGENCY_LANDING)
1 ingob 972
    {
973
     StickGier = 0;
974
     StickNick = 0;
975
     StickRoll = 0;
1211 hbuss 976
     GyroFaktor     = 90;
977
     IntegralFaktor = 120;
978
     GyroFaktorGier     = 90;
979
     IntegralFaktorGier = 120;
173 holgerb 980
     Looping_Roll = 0;
981
     Looping_Nick = 0;
1051 killagreg 982
    }
395 hbuss 983
 
984
 
1051 killagreg 985
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 986
// Integrale auf ACC-Signal abgleichen
1051 killagreg 987
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
395 hbuss 988
#define ABGLEICH_ANZAHL 256L
989
 
990
 MittelIntegralNick  += IntegralNick;    // Für die Mittelwertbildung aufsummieren
991
 MittelIntegralRoll  += IntegralRoll;
992
 MittelIntegralNick2 += IntegralNick2;
993
 MittelIntegralRoll2 += IntegralRoll2;
994
 
995
 if(Looping_Nick || Looping_Roll)
996
  {
997
    IntegralAccNick = 0;
998
    IntegralAccRoll = 0;
999
    MittelIntegralNick = 0;
1000
    MittelIntegralRoll = 0;
1001
    MittelIntegralNick2 = 0;
1002
    MittelIntegralRoll2 = 0;
1003
    Mess_IntegralNick2 = Mess_IntegralNick;
1004
    Mess_IntegralRoll2 = Mess_IntegralRoll;
1005
    ZaehlMessungen = 0;
498 hbuss 1006
    LageKorrekturNick = 0;
1007
    LageKorrekturRoll = 0;
395 hbuss 1008
  }
1009
 
1051 killagreg 1010
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1224 hbuss 1011
  if(!Looping_Nick && !Looping_Roll && (Aktuell_az > 512 || MotorenEin))
469 hbuss 1012
  {
1013
   long tmp_long, tmp_long2;
1171 hbuss 1014
   if(FromNaviCtrl_Value.Kalman_K != -1 /*&& !TrichterFlug*/)
992 hbuss 1015
     {
1016
      tmp_long = (long)(IntegralNick / EE_Parameter.GyroAccFaktor - (long)Mittelwert_AccNick);
1051 killagreg 1017
      tmp_long2 = (long)(IntegralRoll / EE_Parameter.GyroAccFaktor - (long)Mittelwert_AccRoll);
1018
      tmp_long  = (tmp_long  * FromNaviCtrl_Value.Kalman_K) / (32 * 16);
1019
      tmp_long2 = (tmp_long2 * FromNaviCtrl_Value.Kalman_K) / (32 * 16);
992 hbuss 1020
     if((MaxStickNick > 64) || (MaxStickRoll > 64))
1021
      {
1022
      tmp_long  /= 2;
1023
      tmp_long2 /= 2;
1024
      }
1025
     if(abs(PPM_in[EE_Parameter.Kanalbelegung[K_GIER]]) > 25)
1026
      {
1027
      tmp_long  /= 3;
1028
      tmp_long2 /= 3;
1029
      }
1030
      if(tmp_long >  (long) FromNaviCtrl_Value.Kalman_MaxFusion)  tmp_long  = (long) FromNaviCtrl_Value.Kalman_MaxFusion;
1031
      if(tmp_long <  (long)-FromNaviCtrl_Value.Kalman_MaxFusion)  tmp_long  = (long)-FromNaviCtrl_Value.Kalman_MaxFusion;
1032
      if(tmp_long2 > (long) FromNaviCtrl_Value.Kalman_MaxFusion)  tmp_long2 = (long) FromNaviCtrl_Value.Kalman_MaxFusion;
1033
      if(tmp_long2 < (long)-FromNaviCtrl_Value.Kalman_MaxFusion)  tmp_long2 = (long)-FromNaviCtrl_Value.Kalman_MaxFusion;
1034
     }
1051 killagreg 1035
     else
992 hbuss 1036
     {
1037
      tmp_long = (long)(IntegralNick / EE_Parameter.GyroAccFaktor - (long)Mittelwert_AccNick);
1051 killagreg 1038
      tmp_long2 = (long)(IntegralRoll / EE_Parameter.GyroAccFaktor - (long)Mittelwert_AccRoll);
992 hbuss 1039
      tmp_long /= 16;
1040
      tmp_long2 /= 16;
1041
     if((MaxStickNick > 64) || (MaxStickRoll > 64))
1042
      {
1043
      tmp_long  /= 3;
1044
      tmp_long2 /= 3;
1216 killagreg 1045
      }
1046
     if(abs(PPM_in[EE_Parameter.Kanalbelegung[K_GIER]]) > 25)
992 hbuss 1047
      {
1048
      tmp_long  /= 3;
1049
      tmp_long2 /= 3;
1050
      }
1155 hbuss 1051
 
1052
#define AUSGLEICH  32
992 hbuss 1053
      if(tmp_long >  AUSGLEICH)  tmp_long  = AUSGLEICH;
1054
      if(tmp_long < -AUSGLEICH)  tmp_long  =-AUSGLEICH;
1055
      if(tmp_long2 > AUSGLEICH)  tmp_long2 = AUSGLEICH;
1056
      if(tmp_long2 <-AUSGLEICH)  tmp_long2 =-AUSGLEICH;
1057
     }
1166 hbuss 1058
 
1111 hbuss 1059
   Mess_IntegralNick -= tmp_long;
1060
   Mess_IntegralRoll -= tmp_long2;
469 hbuss 1061
  }
1051 killagreg 1062
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
395 hbuss 1063
 if(ZaehlMessungen >= ABGLEICH_ANZAHL)
1064
 {
1065
  static int cnt = 0;
1066
  static char last_n_p,last_n_n,last_r_p,last_r_n;
1067
  static long MittelIntegralNick_Alt,MittelIntegralRoll_Alt;
1173 hbuss 1068
  if(!Looping_Nick && !Looping_Roll && !TrichterFlug && EE_Parameter.Driftkomp)
173 holgerb 1069
  {
395 hbuss 1070
    MittelIntegralNick  /= ABGLEICH_ANZAHL;
1071
    MittelIntegralRoll  /= ABGLEICH_ANZAHL;
1072
        IntegralAccNick = (EE_Parameter.GyroAccFaktor * IntegralAccNick) / ABGLEICH_ANZAHL;
1073
        IntegralAccRoll = (EE_Parameter.GyroAccFaktor * IntegralAccRoll) / ABGLEICH_ANZAHL;
1074
    IntegralAccZ    = IntegralAccZ / ABGLEICH_ANZAHL;
1707 holgerb 1075
#define MAX_I 0
395 hbuss 1076
// Nick ++++++++++++++++++++++++++++++++++++++++++++++++
1077
    IntegralFehlerNick = (long)(MittelIntegralNick - (long)IntegralAccNick);
1078
    ausgleichNick = IntegralFehlerNick / EE_Parameter.GyroAccAbgleich;
1051 killagreg 1079
// Roll ++++++++++++++++++++++++++++++++++++++++++++++++
1080
    IntegralFehlerRoll = (long)(MittelIntegralRoll - (long)IntegralAccRoll);
395 hbuss 1081
    ausgleichRoll = IntegralFehlerRoll / EE_Parameter.GyroAccAbgleich;
614 hbuss 1082
 
1083
    LageKorrekturNick = ausgleichNick / ABGLEICH_ANZAHL;
498 hbuss 1084
    LageKorrekturRoll = ausgleichRoll / ABGLEICH_ANZAHL;
395 hbuss 1085
 
992 hbuss 1086
   if(((MaxStickNick > 64) || (MaxStickRoll > 64) || (abs(PPM_in[EE_Parameter.Kanalbelegung[K_GIER]]) > 25)) && (FromNaviCtrl_Value.Kalman_K == -1))
614 hbuss 1087
    {
1088
     LageKorrekturNick /= 2;
720 ingob 1089
     LageKorrekturRoll /= 2;
614 hbuss 1090
    }
498 hbuss 1091
 
1051 killagreg 1092
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
395 hbuss 1093
// Gyro-Drift ermitteln
1051 killagreg 1094
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
395 hbuss 1095
    MittelIntegralNick2 /= ABGLEICH_ANZAHL;
1096
    MittelIntegralRoll2 /= ABGLEICH_ANZAHL;
1051 killagreg 1097
    tmp_long  = IntegralNick2 - IntegralNick;
1098
    tmp_long2 = IntegralRoll2 - IntegralRoll;
395 hbuss 1099
 
1100
    IntegralFehlerNick = tmp_long;
1101
    IntegralFehlerRoll = tmp_long2;
1102
    Mess_IntegralNick2 -= IntegralFehlerNick;
1103
    Mess_IntegralRoll2 -= IntegralFehlerRoll;
1104
 
1111 hbuss 1105
  if(EE_Parameter.Driftkomp)
1106
   {
1622 killagreg 1107
    if(GierGyroFehler > ABGLEICH_ANZAHL/2) { AdNeutralGier++; }
1108
    if(GierGyroFehler <-ABGLEICH_ANZAHL/2) { AdNeutralGier--; }
1111 hbuss 1109
   }
693 hbuss 1110
    GierGyroFehler = 0;
720 ingob 1111
 
1243 killagreg 1112
#define FEHLER_LIMIT  (ABGLEICH_ANZAHL / 2)
1113
#define FEHLER_LIMIT1 (ABGLEICH_ANZAHL * 2) //4
1225 hbuss 1114
#define FEHLER_LIMIT2 (ABGLEICH_ANZAHL * 16) //16
492 hbuss 1115
#define BEWEGUNGS_LIMIT 20000
395 hbuss 1116
// Nick +++++++++++++++++++++++++++++++++++++++++++++++++
1117
        cnt = 1;// + labs(IntegralFehlerNick) / 4096;
1225 hbuss 1118
        if(labs(IntegralFehlerNick) > FEHLER_LIMIT1) cnt = 4;
1173 hbuss 1119
        if(labs(MittelIntegralNick_Alt - MittelIntegralNick) < BEWEGUNGS_LIMIT || (FromNaviCtrl_Value.Kalman_MaxDrift > 3*8))
492 hbuss 1120
        {
1051 killagreg 1121
        if(IntegralFehlerNick >  FEHLER_LIMIT2)
395 hbuss 1122
         {
1051 killagreg 1123
           if(last_n_p)
395 hbuss 1124
           {
1173 hbuss 1125
            cnt += labs(IntegralFehlerNick) / (FEHLER_LIMIT2 / 8);
492 hbuss 1126
            ausgleichNick = IntegralFehlerNick / 8;
401 hbuss 1127
            if(ausgleichNick > 5000) ausgleichNick = 5000;
498 hbuss 1128
            LageKorrekturNick += ausgleichNick / ABGLEICH_ANZAHL;
1051 killagreg 1129
           }
395 hbuss 1130
           else last_n_p = 1;
1131
         } else  last_n_p = 0;
1051 killagreg 1132
        if(IntegralFehlerNick < -FEHLER_LIMIT2)
395 hbuss 1133
         {
1134
           if(last_n_n)
1051 killagreg 1135
            {
1173 hbuss 1136
             cnt += labs(IntegralFehlerNick) / (FEHLER_LIMIT2 / 8);
492 hbuss 1137
             ausgleichNick = IntegralFehlerNick / 8;
401 hbuss 1138
             if(ausgleichNick < -5000) ausgleichNick = -5000;
498 hbuss 1139
             LageKorrekturNick += ausgleichNick / ABGLEICH_ANZAHL;
1051 killagreg 1140
            }
395 hbuss 1141
           else last_n_n = 1;
1142
         } else  last_n_n = 0;
1051 killagreg 1143
        }
1144
        else
847 hbuss 1145
        {
1146
         cnt = 0;
921 hbuss 1147
         KompassSignalSchlecht = 1000;
1051 killagreg 1148
        }
499 hbuss 1149
        if(cnt > EE_Parameter.Driftkomp) cnt = EE_Parameter.Driftkomp;
1173 hbuss 1150
                if(FromNaviCtrl_Value.Kalman_MaxDrift) if(cnt > FromNaviCtrl_Value.Kalman_MaxDrift) cnt = FromNaviCtrl_Value.Kalman_MaxDrift;
395 hbuss 1151
        if(IntegralFehlerNick >  FEHLER_LIMIT)   AdNeutralNick += cnt;
1152
        if(IntegralFehlerNick < -FEHLER_LIMIT)   AdNeutralNick -= cnt;
401 hbuss 1153
 
395 hbuss 1154
// Roll +++++++++++++++++++++++++++++++++++++++++++++++++
1695 holgerb 1155
        cnt = 1;// + labs(IntegralFehlerRoll) / 4096;
1225 hbuss 1156
        if(labs(IntegralFehlerRoll) > FEHLER_LIMIT1) cnt = 4;
1173 hbuss 1157
        if(labs(MittelIntegralRoll_Alt - MittelIntegralRoll) < BEWEGUNGS_LIMIT || (FromNaviCtrl_Value.Kalman_MaxDrift > 3*8))
492 hbuss 1158
        {
1051 killagreg 1159
        if(IntegralFehlerRoll >  FEHLER_LIMIT2)
395 hbuss 1160
         {
1051 killagreg 1161
           if(last_r_p)
395 hbuss 1162
           {
1173 hbuss 1163
            cnt += labs(IntegralFehlerRoll) / (FEHLER_LIMIT2 / 8);
492 hbuss 1164
            ausgleichRoll = IntegralFehlerRoll / 8;
401 hbuss 1165
            if(ausgleichRoll > 5000) ausgleichRoll = 5000;
498 hbuss 1166
            LageKorrekturRoll += ausgleichRoll / ABGLEICH_ANZAHL;
1051 killagreg 1167
           }
395 hbuss 1168
           else last_r_p = 1;
1169
         } else  last_r_p = 0;
1051 killagreg 1170
        if(IntegralFehlerRoll < -FEHLER_LIMIT2)
395 hbuss 1171
         {
1051 killagreg 1172
           if(last_r_n)
395 hbuss 1173
           {
1173 hbuss 1174
            cnt += labs(IntegralFehlerRoll) / (FEHLER_LIMIT2 / 8);
492 hbuss 1175
            ausgleichRoll = IntegralFehlerRoll / 8;
401 hbuss 1176
            if(ausgleichRoll < -5000) ausgleichRoll = -5000;
498 hbuss 1177
            LageKorrekturRoll += ausgleichRoll / ABGLEICH_ANZAHL;
395 hbuss 1178
           }
1179
           else last_r_n = 1;
1180
         } else  last_r_n = 0;
1051 killagreg 1181
        } else
492 hbuss 1182
        {
1183
         cnt = 0;
921 hbuss 1184
         KompassSignalSchlecht = 1000;
1051 killagreg 1185
        }
499 hbuss 1186
        if(cnt > EE_Parameter.Driftkomp) cnt = EE_Parameter.Driftkomp;
1173 hbuss 1187
                if(FromNaviCtrl_Value.Kalman_MaxDrift) if(cnt > FromNaviCtrl_Value.Kalman_MaxDrift) cnt = FromNaviCtrl_Value.Kalman_MaxDrift;
395 hbuss 1188
        if(IntegralFehlerRoll >  FEHLER_LIMIT)   AdNeutralRoll += cnt;
1189
        if(IntegralFehlerRoll < -FEHLER_LIMIT)   AdNeutralRoll -= cnt;
173 holgerb 1190
  }
1051 killagreg 1191
  else
498 hbuss 1192
  {
1193
   LageKorrekturRoll = 0;
1194
   LageKorrekturNick = 0;
880 hbuss 1195
   TrichterFlug = 0;
498 hbuss 1196
  }
1051 killagreg 1197
 
498 hbuss 1198
  if(!IntegralFaktor) { LageKorrekturRoll = 0; LageKorrekturNick = 0;} // z.B. bei HH
1051 killagreg 1199
// +++++++++++++++++++++++++++++++++++++++++++++++++++++
1200
   MittelIntegralNick_Alt = MittelIntegralNick;
1201
   MittelIntegralRoll_Alt = MittelIntegralRoll;
1202
// +++++++++++++++++++++++++++++++++++++++++++++++++++++
395 hbuss 1203
    IntegralAccNick = 0;
1204
    IntegralAccRoll = 0;
1205
    IntegralAccZ = 0;
1206
    MittelIntegralNick = 0;
1207
    MittelIntegralRoll = 0;
1208
    MittelIntegralNick2 = 0;
1209
    MittelIntegralRoll2 = 0;
1210
    ZaehlMessungen = 0;
1173 hbuss 1211
 } //  ZaehlMessungen >= ABGLEICH_ANZAHL
395 hbuss 1212
 
1051 killagreg 1213
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1214
//  Gieren
1051 killagreg 1215
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1216
    if(abs(StickGier) > 15) // war 35
1 ingob 1217
     {
921 hbuss 1218
      KompassSignalSchlecht = 1000;
1051 killagreg 1219
      if(!(EE_Parameter.GlobalConfig & CFG_KOMPASS_FIX))
1220
       {
1221
         NeueKompassRichtungMerken = 1;
824 hbuss 1222
        };
1 ingob 1223
     }
395 hbuss 1224
    tmp_int  = (long) EE_Parameter.Gier_P * ((long)StickGier * abs(StickGier)) / 512L; // expo  y = ax + bx²
1051 killagreg 1225
    tmp_int += (EE_Parameter.Gier_P * StickGier) / 4;
173 holgerb 1226
    sollGier = tmp_int;
1051 killagreg 1227
    Mess_Integral_Gier -= tmp_int;
395 hbuss 1228
    if(Mess_Integral_Gier > 50000) Mess_Integral_Gier = 50000;  // begrenzen
1229
    if(Mess_Integral_Gier <-50000) Mess_Integral_Gier =-50000;
1051 killagreg 1230
 
1231
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1232
//  Kompass
1051 killagreg 1233
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1234
    if(KompassValue && (EE_Parameter.GlobalConfig & CFG_KOMPASS_AKTIV))
1 ingob 1235
     {
819 hbuss 1236
       int w,v,r,fehler,korrektur;
1 ingob 1237
       w = abs(IntegralNick /512); // mit zunehmender Neigung den Einfluss drosseln
1238
       v = abs(IntegralRoll /512);
1239
       if(v > w) w = v; // grösste Neigung ermitteln
1658 holgerb 1240
       korrektur = w / 8 + 2;
921 hbuss 1241
       fehler = ((540 + KompassValue - (ErsatzKompass/GIER_GRAD_FAKTOR)) % 360) - 180;
1664 holgerb 1242
           //fehler += MesswertGier / 12;
1662 killagreg 1243
 
921 hbuss 1244
       if(!KompassSignalSchlecht && w < 25)
1245
        {
1246
        GierGyroFehler += fehler;
1051 killagreg 1247
        if(NeueKompassRichtungMerken)
1248
         {
1171 hbuss 1249
                  ErsatzKompass = KompassValue * GIER_GRAD_FAKTOR;
921 hbuss 1250
          KompassStartwert = (ErsatzKompass/GIER_GRAD_FAKTOR);
1251
          NeueKompassRichtungMerken = 0;
1252
         }
1 ingob 1253
        }
1658 holgerb 1254
       ErsatzKompass += (fehler * 16) / korrektur;
921 hbuss 1255
       w = (w * Parameter_KompassWirkung) / 32;           // auf die Wirkung normieren
1 ingob 1256
       w = Parameter_KompassWirkung - w;                  // Wirkung ggf drosseln
921 hbuss 1257
       if(w >= 0)
1 ingob 1258
        {
1051 killagreg 1259
          if(!KompassSignalSchlecht)
693 hbuss 1260
          {
1051 killagreg 1261
           v = 64 + ((MaxStickNick + MaxStickRoll)) / 8;
847 hbuss 1262
           r = ((540 + (ErsatzKompass/GIER_GRAD_FAKTOR) - KompassStartwert) % 360) - 180;
819 hbuss 1263
           v = (r * w) / v;  // nach Kompass ausrichten
1264
           w = 3 * Parameter_KompassWirkung;
693 hbuss 1265
           if(v > w) v = w; // Begrenzen
1051 killagreg 1266
           else
693 hbuss 1267
           if(v < -w) v = -w;
1268
           Mess_Integral_Gier += v;
1051 killagreg 1269
          }
693 hbuss 1270
          if(KompassSignalSchlecht) KompassSignalSchlecht--;
1051 killagreg 1271
        }
921 hbuss 1272
        else KompassSignalSchlecht = 500; // so lange das Signal taub stellen --> ca. 1 sek
1051 killagreg 1273
     }
1 ingob 1274
 
1051 killagreg 1275
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1276
//  Drehgeschwindigkeit und -winkel zu einem Istwert zusammenfassen
1051 killagreg 1277
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1216 killagreg 1278
  if(TrichterFlug)  { SummeRoll = 0; SummeNick = 0;};
604 hbuss 1279
 
1171 hbuss 1280
  if(!Looping_Nick) IntegralNickMalFaktor = (IntegralNick * IntegralFaktor) /  (44000 / STICK_GAIN); else IntegralNickMalFaktor = 0;
1281
  if(!Looping_Roll) IntegralRollMalFaktor = (IntegralRoll * IntegralFaktor) /  (44000 / STICK_GAIN); else IntegralRollMalFaktor = 0;
1153 hbuss 1282
 
1167 hbuss 1283
#define TRIM_MAX 200
1166 hbuss 1284
 if(TrimNick > TRIM_MAX) TrimNick = TRIM_MAX; else  if(TrimNick <-TRIM_MAX) TrimNick =-TRIM_MAX;
1285
 if(TrimRoll > TRIM_MAX) TrimRoll = TRIM_MAX; else  if(TrimRoll <-TRIM_MAX) TrimRoll =-TRIM_MAX;
1153 hbuss 1286
 
1166 hbuss 1287
    MesswertNick = IntegralNickMalFaktor + (long)((long)MesswertNick * GyroFaktor + (long)TrimNick * 128L) / (256L / STICK_GAIN);
1288
    MesswertRoll = IntegralRollMalFaktor + (long)((long)MesswertRoll * GyroFaktor + (long)TrimRoll * 128L) / (256L / STICK_GAIN);
1211 hbuss 1289
    MesswertGier = (long)(MesswertGier * 2 * (long)GyroFaktorGier) / (256L / STICK_GAIN) + (long)(Integral_Gier * IntegralFaktorGier) / (2 * (44000 / STICK_GAIN));
1166 hbuss 1290
 
1 ingob 1291
    // Maximalwerte abfangen
1153 hbuss 1292
//    #define MAX_SENSOR  (4096*STICK_GAIN)
1685 holgerb 1293
    #define MAX_SENSOR  (4096)
1216 killagreg 1294
    if(MesswertNick >  MAX_SENSOR) MesswertNick =  MAX_SENSOR;
1 ingob 1295
    if(MesswertNick < -MAX_SENSOR) MesswertNick = -MAX_SENSOR;
1296
    if(MesswertRoll >  MAX_SENSOR) MesswertRoll =  MAX_SENSOR;
1297
    if(MesswertRoll < -MAX_SENSOR) MesswertRoll = -MAX_SENSOR;
1298
    if(MesswertGier >  MAX_SENSOR) MesswertGier =  MAX_SENSOR;
1299
    if(MesswertGier < -MAX_SENSOR) MesswertGier = -MAX_SENSOR;
1300
 
1051 killagreg 1301
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1302
// Höhenregelung
1303
// Die Höhenregelung schwächt lediglich das Gas ab, erhöht es allerdings nicht
1051 killagreg 1304
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1374 hbuss 1305
  if(UBat > BattLowVoltageWarning) GasMischanteil = ((unsigned int)GasMischanteil * BattLowVoltageWarning) / UBat; // Gas auf das aktuelle Spannungvieveau beziehen
855 hbuss 1306
  GasMischanteil *= STICK_GAIN;
1309 hbuss 1307
        // if height control is activated
1322 hbuss 1308
 if((EE_Parameter.GlobalConfig & CFG_HOEHENREGELUNG) && !(Looping_Roll || Looping_Nick))  // Höhenregelung
1309 hbuss 1309
        {
1698 holgerb 1310
                #define HOVER_GAS_AVERAGE 16384L                // 16384 * 2ms = 32s averaging
1332 hbuss 1311
                #define HC_GAS_AVERAGE 4                        // 4 * 2ms= 8ms averaging
1638 holgerb 1312
 
1313
#if (defined(__AVR_ATmega1284__) || defined(__AVR_ATmega1284P__))
1314
#define OPA_OFFSET_STEP 15
1642 killagreg 1315
#else
1638 holgerb 1316
#define OPA_OFFSET_STEP 10
1317
#endif
1697 holgerb 1318
                int HCGas, HeightDeviation = 0,GasReduction = 0;
1309 hbuss 1319
                static int HeightTrimming = 0;  // rate for change of height setpoint
1320
                static int FilterHCGas = 0;
1692 holgerb 1321
                static int StickGasHover = 120, HoverGasMin = 0, HoverGasMax = 1023;
1587 killagreg 1322
                static unsigned long HoverGasFilter = 0;
1322 hbuss 1323
                static unsigned char delay = 100, BaroAtUpperLimit = 0, BaroAtLowerLimit = 0;
1320 hbuss 1324
            int CosAttitude;    // for projection of hoover gas
1330 killagreg 1325
 
1309 hbuss 1326
                // get the current hooverpoint
1587 killagreg 1327
                DebugOut.Analog[21] = HoverGas;
1642 killagreg 1328
 
1322 hbuss 1329
        // Expand the measurement
1330
                // measurement of air pressure close to upper limit and no overflow in correction of the new OCR0A value occurs
1331
          if(!BaroExpandActive)
1332
                   {
1333
                        if(MessLuftdruck > 920)
1334
                        {   // increase offset
1330 killagreg 1335
             if(OCR0A < (255 - OPA_OFFSET_STEP))
1322 hbuss 1336
                           {
1337
                                ExpandBaro -= 1;
1338
                                OCR0A = DruckOffsetSetting - OPA_OFFSET_STEP * ExpandBaro; // increase offset to shift ADC down
1339
                                beeptime = 300;
1352 hbuss 1340
                                BaroExpandActive = 350;
1330 killagreg 1341
                           }
1342
                           else
1322 hbuss 1343
                           {
1344
                            BaroAtLowerLimit = 1;
1345
               }
1346
                        }
1347
                        // measurement of air pressure close to lower limit and
1330 killagreg 1348
                        else
1322 hbuss 1349
                        if(MessLuftdruck < 100)
1350
                        {   // decrease offset
1330 killagreg 1351
                          if(OCR0A > OPA_OFFSET_STEP)
1322 hbuss 1352
                           {
1353
                                ExpandBaro += 1;
1354
                                OCR0A = DruckOffsetSetting - OPA_OFFSET_STEP * ExpandBaro; // decrease offset to shift ADC up
1355
                                beeptime = 300;
1352 hbuss 1356
                                BaroExpandActive = 350;
1330 killagreg 1357
                           }
1358
                           else
1322 hbuss 1359
                           {
1360
                            BaroAtUpperLimit = 1;
1361
               }
1362
                        }
1330 killagreg 1363
                        else
1322 hbuss 1364
                        {
1365
                            BaroAtUpperLimit = 0;
1366
                                BaroAtLowerLimit = 0;
1367
                        }
1368
                   }
1369
                   else // delay, because of expanding the Baro-Range
1370
                   {
1371
                    // now clear the D-values
1372
                          SummenHoehe = HoehenWert * SM_FILTER;
1373
                          VarioMeter = 0;
1374
                          BaroExpandActive--;
1375
                   }
1328 hbuss 1376
 
1377
                // if height control is activated by an rc channel
1378
        if(EE_Parameter.GlobalConfig & CFG_HOEHEN_SCHALTER)  // Regler wird über Schalter gesteuert
1379
                {       // check if parameter is less than activation threshold
1380
                        if(Parameter_MaxHoehe < 50) // for 3 or 2-state switch height control is disabled in lowest position
1381
                        {   //height control not active
1382
                                if(!delay--)
1383
                                {
1384
                                        HoehenReglerAktiv = 0; // disable height control
1385
                                        SollHoehe = HoehenWert;  // update SetPoint with current reading
1386
                                        delay = 1;
1387
                                }
1388
                        }
1389
                        else
1390
                        {       //height control is activated
1391
                                HoehenReglerAktiv = 1; // enable height control
1334 killagreg 1392
                                delay = 200;
1328 hbuss 1393
                        }
1051 killagreg 1394
                }
1309 hbuss 1395
                else // no switchable height control
1396
                {
1397
                        SollHoehe = ((int16_t) ExternHoehenValue + (int16_t) Parameter_MaxHoehe) * (int)EE_Parameter.Hoehe_Verstaerkung;
1398
                        HoehenReglerAktiv = 1;
1051 killagreg 1399
                }
1322 hbuss 1400
 
1320 hbuss 1401
                // calculate cos of nick and roll angle used for projection of the vertical hoover gas
1330 killagreg 1402
                tmp_int  = (int)(IntegralNick/GIER_GRAD_FAKTOR);  // nick angle in deg
1403
                tmp_int2 = (int)(IntegralRoll/GIER_GRAD_FAKTOR);  // roll angle in deg
1404
                CosAttitude = (int16_t)ihypot(tmp_int, tmp_int2); // phytagoras gives effective attitude angle in deg
1320 hbuss 1405
                LIMIT_MAX(CosAttitude, 60); // limit effective attitude angle
1406
                CosAttitude = c_cos_8192(CosAttitude);  // cos of actual attitude
1591 holgerb 1407
                VarioCharacter = ' ';
1765 killagreg 1408
                if(HoehenReglerAktiv && !(FC_StatusFlags & FC_STATUS_EMERGENCY_LANDING))
1309 hbuss 1409
                {
1330 killagreg 1410
                        #define HEIGHT_CONTROL_STICKTHRESHOLD 15
1309 hbuss 1411
                // Holger original version
1412
                // start of height control algorithm
1413
                // the height control is only an attenuation of the actual gas stick.
1414
                // I.e. it will work only if the gas stick is higher than the hover gas
1415
                // and the hover height will be allways larger than height setpoint.
1314 killagreg 1416
        if((EE_Parameter.ExtraConfig & CFG2_HEIGHT_LIMIT) || !(EE_Parameter.GlobalConfig & CFG_HOEHEN_SCHALTER))  // Regler wird über Schalter gesteuert)
1417
              {  // old version
1309 hbuss 1418
                        HCGas = GasMischanteil; // take current stick gas as neutral point for the height control
1419
                        HeightTrimming = 0;
1773 killagreg 1420
                        // set both flags to indicate no vario mode
1421
                        FC_StatusFlags |= (FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN);
1309 hbuss 1422
          }
1314 killagreg 1423
                  else
1309 hbuss 1424
                  {
1425
                // alternative height control
1426
                // PD-Control with respect to hoover point
1427
                // the thrust loss out of horizontal attitude is compensated
1428
                // the setpoint will be fine adjusted with the gas stick position
1765 killagreg 1429
                        if(FC_StatusFlags & FC_STATUS_FLY) // trim setpoint only when flying
1309 hbuss 1430
                        {   // gas stick is above hoover point
1587 killagreg 1431
                                if(StickGas > (StickGasHover + HEIGHT_CONTROL_STICKTHRESHOLD) && !BaroAtUpperLimit)
1309 hbuss 1432
                                {
1767 killagreg 1433
                                        if(FC_StatusFlags & FC_STATUS_VARIO_TRIM_DOWN)
1309 hbuss 1434
                                        {
1767 killagreg 1435
                                                FC_StatusFlags &= ~FC_STATUS_VARIO_TRIM_DOWN;
1309 hbuss 1436
                                                SollHoehe = HoehenWert; // update setpoint to current heigth
1437
                                        }
1767 killagreg 1438
                                        FC_StatusFlags |= FC_STATUS_VARIO_TRIM_UP;
1587 killagreg 1439
                                        HeightTrimming += abs(StickGas - (StickGasHover + HEIGHT_CONTROL_STICKTHRESHOLD));
1591 holgerb 1440
                                        VarioCharacter = '+';
1309 hbuss 1441
                                } // gas stick is below hoover point
1587 killagreg 1442
                                else if(StickGas < (StickGasHover - HEIGHT_CONTROL_STICKTHRESHOLD) && !BaroAtLowerLimit )
1309 hbuss 1443
                                {
1767 killagreg 1444
                                        if(FC_StatusFlags & FC_STATUS_VARIO_TRIM_UP)
1309 hbuss 1445
                                        {
1767 killagreg 1446
                                                FC_StatusFlags &= ~FC_STATUS_VARIO_TRIM_UP;
1309 hbuss 1447
                                                SollHoehe = HoehenWert; // update setpoint to current heigth
1448
                                        }
1767 killagreg 1449
                                        FC_StatusFlags |= FC_STATUS_VARIO_TRIM_DOWN;
1587 killagreg 1450
                                        HeightTrimming -= abs(StickGas - (StickGasHover - HEIGHT_CONTROL_STICKTHRESHOLD));
1591 holgerb 1451
                                        VarioCharacter = '-';
1309 hbuss 1452
                                }
1587 killagreg 1453
                                else // Gas Stick in Hover Range
1309 hbuss 1454
                                {
1767 killagreg 1455
                                        if(FC_StatusFlags & (FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN))
1309 hbuss 1456
                                        {
1767 killagreg 1457
                                                FC_StatusFlags &= ~(FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN);
1309 hbuss 1458
                                                HeightTrimming = 0;
1459
                                                SollHoehe = HoehenWert; // update setpoint to current height
1460
                                                if(EE_Parameter.ExtraConfig & CFG2_VARIO_BEEP) beeptime = 500;
1698 holgerb 1461
                                                if(!StartTrigger && HoehenWert > 50)
1462
                                                {
1463
                                                 StartTrigger = 1;
1765 killagreg 1464
                                                }
1309 hbuss 1465
                                        }
1591 holgerb 1466
                                        VarioCharacter = '=';
1309 hbuss 1467
                                }
1468
                                // Trim height set point
1334 killagreg 1469
                                if(abs(HeightTrimming) > 512)
1309 hbuss 1470
                                {
1332 hbuss 1471
                                        SollHoehe += (HeightTrimming * EE_Parameter.Hoehe_Verstaerkung)/(5 * 512 / 2); // move setpoint
1309 hbuss 1472
                                        HeightTrimming = 0;
1587 killagreg 1473
                    LIMIT_MIN_MAX(SollHoehe, (HoehenWert-1024), (HoehenWert+1024)); // max. 10m Unterschied
1720 holgerb 1474
                                        if(EE_Parameter.ExtraConfig & CFG2_VARIO_BEEP) beeptime = 100;
1320 hbuss 1475
                                        //update hoover gas stick value when setpoint is shifted
1332 hbuss 1476
                       if(!EE_Parameter.Hoehe_StickNeutralPoint)
1477
                       {
1587 killagreg 1478
                           StickGasHover = HoverGas/STICK_GAIN; //rescale back to stick value
1479
                           StickGasHover = (StickGasHover * UBat) / BattLowVoltageWarning;
1480
                           if(StickGasHover < 70) StickGasHover = 70;
1481
                           else if(StickGasHover > 150) StickGasHover = 150;
1332 hbuss 1482
                       }
1309 hbuss 1483
                                }
1352 hbuss 1484
              if(BaroExpandActive) SollHoehe = HoehenWert; // update setpoint to current altitude if Expanding is active
1420 killagreg 1485
                        } //if FCFlags & MKFCFLAG_FLY
1330 killagreg 1486
                        else
1487
                        {
1322 hbuss 1488
                         SollHoehe = HoehenWert - 400;
1587 killagreg 1489
                         if(EE_Parameter.Hoehe_StickNeutralPoint) StickGasHover = EE_Parameter.Hoehe_StickNeutralPoint;
1490
                         else StickGasHover = 120;
1698 holgerb 1491
                         HoverGas = GasMischanteil;
1320 hbuss 1492
                         }
1590 killagreg 1493
                        HCGas = HoverGas;      // take hover gas (neutral point)
1494
                   }
1314 killagreg 1495
         if(HoehenWert > SollHoehe || !(EE_Parameter.ExtraConfig & CFG2_HEIGHT_LIMIT))
1283 hbuss 1496
                 {
1590 killagreg 1497
                        // from this point the Heigth Control Algorithm is identical for both versions
1498
                        if(BaroExpandActive) // baro range expanding active
1499
                        {
1500
                                HCGas = HoverGas; // hover while expanding baro adc range
1501
                                HeightDeviation = 0;
1502
                        } // EOF // baro range expanding active
1503
                        else // valid data from air pressure sensor
1504
                        {
1505
                                // ------------------------- P-Part ----------------------------
1506
                                tmp_long = (HoehenWert - SollHoehe); // positive when too high
1507
                                LIMIT_MIN_MAX(tmp_long, -32767L, 32767L);       // avoid overflov when casting to int16_t
1508
                                HeightDeviation = (int)(tmp_long); // positive when too high
1695 holgerb 1509
                                tmp_long = (tmp_long * (long)Parameter_Hoehe_P) / 32L; // p-part
1698 holgerb 1510
                                LIMIT_MIN_MAX(tmp_long, -127 * STICK_GAIN, 256 * STICK_GAIN); // more than the full range makes no sense
1511
                                GasReduction = tmp_long;
1590 killagreg 1512
                                // ------------------------- D-Part 1: Vario Meter ----------------------------
1513
                                tmp_int = VarioMeter / 8;
1765 killagreg 1514
                                LIMIT_MIN_MAX(tmp_int, -127, 128);
1705 holgerb 1515
                                tmp_int = (tmp_int * (long)Parameter_Luftdruck_D) / 4L; // scale to d-gain parameter
1516
                                LIMIT_MIN_MAX(tmp_int,-64 * STICK_GAIN, 64 * STICK_GAIN);
1767 killagreg 1517
                                if(FC_StatusFlags & (FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN)) tmp_int /= 4; // reduce d-part while trimming setpoint
1765 killagreg 1518
                                else
1722 holgerb 1519
                                if(EE_Parameter.ExtraConfig & CFG2_HEIGHT_LIMIT) tmp_int /= 8; // reduce d-part in "Deckel" mode
1698 holgerb 1520
                                GasReduction += tmp_int;
1590 killagreg 1521
                        } // EOF no baro range expanding
1309 hbuss 1522
                        // ------------------------ D-Part 2: ACC-Z Integral  ------------------------
1698 holgerb 1523
            if(Parameter_Hoehe_ACC_Wirkung)
1524
                         {
1525
                          tmp_long = ((Mess_Integral_Hoch / 128L) * (int32_t) Parameter_Hoehe_ACC_Wirkung) / (128L / STICK_GAIN);
1526
                          LIMIT_MIN_MAX(tmp_long, -32 * STICK_GAIN, 64 * STICK_GAIN);
1527
                          GasReduction += tmp_long;
1765 killagreg 1528
                         }
1587 killagreg 1529
                        // ------------------------ D-Part 3: GpsZ  ----------------------------------
1588 killagreg 1530
                        tmp_int = (Parameter_Hoehe_GPS_Z * (int)FromNaviCtrl_Value.GpsZ)/128L;
1531
            LIMIT_MIN_MAX(tmp_int, -32 * STICK_GAIN, 64 * STICK_GAIN);
1698 holgerb 1532
                        GasReduction += tmp_int;
1701 holgerb 1533
            GasReduction = (long)((long)GasReduction * HoverGas) / 512; // scale to the gas value
1534
                        // ------------------------                  ----------------------------------
1535
                        HCGas -= GasReduction;
1309 hbuss 1536
                        // limit deviation from hoover point within the target region
1692 holgerb 1537
                        if(!HeightTrimming && HoverGas > 0) // height setpoint is not changed and hoover gas not zero
1309 hbuss 1538
                        {
1765 killagreg 1539
                         unsigned int tmp;
1705 holgerb 1540
                         tmp = abs(HeightDeviation);
1541
                         if(tmp <= 60)
1542
                         {
1543
                          LIMIT_MIN_MAX(HCGas, HoverGasMin, HoverGasMax); // limit gas around the hoover point
1544
                         }
1545
                         else
1765 killagreg 1546
                         {
1705 holgerb 1547
                                tmp = (tmp - 60) / 32;
1692 holgerb 1548
                                if(tmp > 15) tmp = 15;
1705 holgerb 1549
                           if(HeightDeviation > 0)
1693 holgerb 1550
                                {
1705 holgerb 1551
                                tmp = (HoverGasMin * (16 - tmp)) / 16;
1552
                                LIMIT_MIN_MAX(HCGas, tmp, HoverGasMax); // limit gas around the hoover point
1693 holgerb 1553
                                }
1705 holgerb 1554
                                else
1555
                                {
1556
                                tmp = (HoverGasMax * (tmp + 16)) / 16;
1557
                                LIMIT_MIN_MAX(HCGas, HoverGasMin, tmp); // limit gas around the hoover point
1558
                                }
1559
                          }
1309 hbuss 1560
                        }
1322 hbuss 1561
                        // strech control output by inverse attitude projection 1/cos
1562
            // + 1/cos(angle)  ++++++++++++++++++++++++++
1330 killagreg 1563
                        tmp_long2 = (int32_t)HCGas;
1564
                        tmp_long2 *= 8192L;
1565
                        tmp_long2 /= CosAttitude;
1566
                        HCGas = (int16_t)tmp_long2;
1309 hbuss 1567
                        // update height control gas averaging
1568
                        FilterHCGas = (FilterHCGas * (HC_GAS_AVERAGE - 1) + HCGas) / HC_GAS_AVERAGE;
1569
                        // limit height control gas pd-control output
1570
                        LIMIT_MIN_MAX(FilterHCGas, EE_Parameter.Hoehe_MinGas * STICK_GAIN, (MAX_GAS - 20) * STICK_GAIN);
1571
                        // set GasMischanteil to HeightControlGasFilter
1314 killagreg 1572
            if(EE_Parameter.ExtraConfig & CFG2_HEIGHT_LIMIT)
1587 killagreg 1573
                        {  // old version
1574
                                LIMIT_MAX(FilterHCGas, GasMischanteil); // nicht mehr als Gas
1719 holgerb 1575
                                GasMischanteil = FilterHCGas;
1765 killagreg 1576
                        }
1719 holgerb 1577
                        else GasMischanteil = FilterHCGas + (GasMischanteil - HoverGas) / 4; // only in Vario-Mode
1314 killagreg 1578
                  }
1309 hbuss 1579
                }// EOF height control active
1320 hbuss 1580
                else // HC not active
1581
                {
1582
                        //update hoover gas stick value when HC is not active
1587 killagreg 1583
                        if(!EE_Parameter.Hoehe_StickNeutralPoint)
1584
                        {
1585
                                StickGasHover = HoverGas/STICK_GAIN; // rescale back to stick value
1586
                                StickGasHover = (StickGasHover * UBat) / BattLowVoltageWarning;
1322 hbuss 1587
                        }
1587 killagreg 1588
                        else StickGasHover = EE_Parameter.Hoehe_StickNeutralPoint;
1589
            LIMIT_MIN_MAX(StickGasHover, 70, 150); // reserve some range for trim up and down
1328 hbuss 1590
                        FilterHCGas = GasMischanteil;
1773 killagreg 1591
                        // set both flags to indicate no vario mode
1592
                        FC_StatusFlags |= (FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN);
1330 killagreg 1593
                }
1283 hbuss 1594
 
1587 killagreg 1595
                // Hover gas estimation by averaging gas control output on small z-velocities
1309 hbuss 1596
                // this is done only if height contol option is selected in global config and aircraft is flying
1765 killagreg 1597
                if((FC_StatusFlags & FC_STATUS_FLY))// && !(FC_SatusFlags & FC_STATUS_EMERGENCY_LANDING))
1309 hbuss 1598
                {
1698 holgerb 1599
                        if(HoverGasFilter == 0 || StartTrigger == 1)  HoverGasFilter = HOVER_GAS_AVERAGE * (unsigned long)(GasMischanteil); // init estimation
1600
                        if(StartTrigger == 1) StartTrigger = 2;
1330 killagreg 1601
                                tmp_long2 = (int32_t)GasMischanteil; // take current thrust
1602
                                tmp_long2 *= CosAttitude;            // apply attitude projection
1603
                                tmp_long2 /= 8192;
1309 hbuss 1604
                                // average vertical projected thrust
1698 holgerb 1605
                            if(modell_fliegt < 4000) // the first 8 seconds
1606
                                {   // reduce the time constant of averaging by factor of 4 to get much faster a stable value
1607
                                        HoverGasFilter -= HoverGasFilter/(HOVER_GAS_AVERAGE/16L);
1608
                                        HoverGasFilter += 16L * tmp_long2;
1309 hbuss 1609
                                }
1698 holgerb 1610
                if(modell_fliegt < 8000) // the first 16 seconds
1611
                                {   // reduce the time constant of averaging by factor of 2 to get much faster a stable value
1590 killagreg 1612
                                        HoverGasFilter -= HoverGasFilter/(HOVER_GAS_AVERAGE/4L);
1587 killagreg 1613
                                        HoverGasFilter += 4L * tmp_long2;
1309 hbuss 1614
                                }
1698 holgerb 1615
                          else //later
1616
                          if(abs(VarioMeter) < 100) // only on small vertical speed
1309 hbuss 1617
                                {
1590 killagreg 1618
                                        HoverGasFilter -= HoverGasFilter/HOVER_GAS_AVERAGE;
1587 killagreg 1619
                                        HoverGasFilter += tmp_long2;
1309 hbuss 1620
                                }
1590 killagreg 1621
                                HoverGas = (int16_t)(HoverGasFilter/HOVER_GAS_AVERAGE);
1309 hbuss 1622
                                if(EE_Parameter.Hoehe_HoverBand)
1623
                                {
1624
                                        int16_t band;
1587 killagreg 1625
                                        band = HoverGas / EE_Parameter.Hoehe_HoverBand; // the higher the parameter the smaller the range
1626
                                        HoverGasMin = HoverGas - band;
1627
                                        HoverGasMax = HoverGas + band;
1309 hbuss 1628
                                }
1629
                                else
1630
                                {       // no limit
1587 killagreg 1631
                                        HoverGasMin = 0;
1632
                                        HoverGasMax = 1023;
1309 hbuss 1633
                                }
1765 killagreg 1634
                }
1635
                 else
1698 holgerb 1636
                  {
1637
                   StartTrigger = 0;
1638
                   HoverGasFilter = 0;
1639
                   HoverGas = 0;
1765 killagreg 1640
                  }
1309 hbuss 1641
        }// EOF ParamSet.GlobalConfig & CFG_HEIGHT_CONTROL
1773 killagreg 1642
        else
1643
        {
1644
                // set undefined state to indicate vario off
1645
                FC_StatusFlags |= (FC_STATUS_VARIO_TRIM_UP|FC_STATUS_VARIO_TRIM_DOWN);
1646
        } // EOF no height control
1647
 
1309 hbuss 1648
        // limit gas to parameter setting
1320 hbuss 1649
  LIMIT_MIN(GasMischanteil, (MIN_GAS + 10) * STICK_GAIN);
855 hbuss 1650
  if(GasMischanteil > (MAX_GAS - 20) * STICK_GAIN) GasMischanteil = (MAX_GAS - 20) * STICK_GAIN;
1111 hbuss 1651
 
1051 killagreg 1652
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1320 hbuss 1653
// all BL-Ctrl connected?
1654
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1675 holgerb 1655
  if(MissingMotor || Capacity.MinOfMaxPWM != 255)
1320 hbuss 1656
  if(modell_fliegt > 1 && modell_fliegt < 50 && GasMischanteil > 0)
1657
   {
1658
    modell_fliegt = 1;
1675 holgerb 1659
        GasMischanteil = (MIN_GAS + 10) * STICK_GAIN;
1320 hbuss 1660
   }
1661
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1662
// + Mischer und PI-Regler
1051 killagreg 1663
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
173 holgerb 1664
  DebugOut.Analog[7] = GasMischanteil;
1051 killagreg 1665
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1666
// Gier-Anteil
1051 killagreg 1667
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
855 hbuss 1668
    GierMischanteil = MesswertGier - sollGier * STICK_GAIN;     // Regler für Gier
1669
#define MIN_GIERGAS  (40*STICK_GAIN)  // unter diesem Gaswert trotzdem Gieren
693 hbuss 1670
   if(GasMischanteil > MIN_GIERGAS)
1671
    {
1051 killagreg 1672
     if(GierMischanteil > (GasMischanteil / 2)) GierMischanteil = GasMischanteil / 2;
1673
     if(GierMischanteil < -(GasMischanteil / 2)) GierMischanteil = -(GasMischanteil / 2);
693 hbuss 1674
    }
1051 killagreg 1675
    else
693 hbuss 1676
    {
1051 killagreg 1677
     if(GierMischanteil > (MIN_GIERGAS / 2))  GierMischanteil = MIN_GIERGAS / 2;
1678
     if(GierMischanteil < -(MIN_GIERGAS / 2)) GierMischanteil = -(MIN_GIERGAS / 2);
693 hbuss 1679
    }
855 hbuss 1680
    tmp_int = MAX_GAS*STICK_GAIN;
1051 killagreg 1681
    if(GierMischanteil > ((tmp_int - GasMischanteil))) GierMischanteil = ((tmp_int - GasMischanteil));
855 hbuss 1682
    if(GierMischanteil < -((tmp_int - GasMischanteil))) GierMischanteil = -((tmp_int - GasMischanteil));
513 hbuss 1683
 
1051 killagreg 1684
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 ingob 1685
// Nick-Achse
1051 killagreg 1686
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
723 hbuss 1687
    DiffNick = MesswertNick - StickNick;        // Differenz bestimmen
1153 hbuss 1688
    if(IntegralFaktor) SummeNick += IntegralNickMalFaktor - StickNick; // I-Anteil bei Winkelregelung
1051 killagreg 1689
    else  SummeNick += DiffNick; // I-Anteil bei HH
855 hbuss 1690
    if(SummeNick >  (STICK_GAIN * 16000L)) SummeNick =  (STICK_GAIN * 16000L);
1691
    if(SummeNick < -(16000L * STICK_GAIN)) SummeNick = -(16000L * STICK_GAIN);
1791 holgerb 1692
 
1693
    if(EE_Parameter.Gyro_Stability <= 8)        pd_ergebnis_nick = (EE_Parameter.Gyro_Stability * DiffNick) / 8; // PI-Regler für Nick
1694
    else                                                                        pd_ergebnis_nick = ((EE_Parameter.Gyro_Stability / 2) * DiffNick) / 4; // Überlauf verhindern
1695
    pd_ergebnis_nick +=  SummeNick / Ki;
1696
 
1676 holgerb 1697
    tmp_int = (long)((long)Parameter_DynamicStability * (long)(GasMischanteil + abs(GierMischanteil)/2)) / 64;
1153 hbuss 1698
    if(pd_ergebnis_nick >  tmp_int) pd_ergebnis_nick =  tmp_int;
1699
    if(pd_ergebnis_nick < -tmp_int) pd_ergebnis_nick = -tmp_int;
173 holgerb 1700
 
1153 hbuss 1701
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1702
// Roll-Achse
1703
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1704
        DiffRoll = MesswertRoll - StickRoll;    // Differenz bestimmen
1705
    if(IntegralFaktor) SummeRoll += IntegralRollMalFaktor - StickRoll;// I-Anteil bei Winkelregelung
1706
    else                 SummeRoll += DiffRoll;  // I-Anteil bei HH
1707
    if(SummeRoll >  (STICK_GAIN * 16000L)) SummeRoll =  (STICK_GAIN * 16000L);
1708
    if(SummeRoll < -(16000L * STICK_GAIN)) SummeRoll = -(16000L * STICK_GAIN);
1791 holgerb 1709
 
1710
    if(EE_Parameter.Gyro_Stability <= 8)        pd_ergebnis_roll = (EE_Parameter.Gyro_Stability * DiffRoll) / 8;        // PI-Regler für Roll
1711
        else                                                                    pd_ergebnis_roll = ((EE_Parameter.Gyro_Stability / 2) * DiffRoll) / 4;  // Überlauf verhindern
1712
    pd_ergebnis_roll += SummeRoll / Ki;
1713
 
1676 holgerb 1714
    tmp_int = (long)((long)Parameter_DynamicStability * (long)(GasMischanteil + abs(GierMischanteil)/2)) / 64;
1153 hbuss 1715
    if(pd_ergebnis_roll >  tmp_int) pd_ergebnis_roll =  tmp_int;
1716
    if(pd_ergebnis_roll < -tmp_int) pd_ergebnis_roll = -tmp_int;
1717
 
1718
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1209 hbuss 1719
// Universal Mixer
1155 hbuss 1720
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1642 killagreg 1721
        for(i=0; i<MAX_MOTORS; i++)
1722
        {
1723
                signed int tmp_int;
1724
                if(Mixer.Motor[i][0] > 0)
1725
                {
1652 holgerb 1726
                        // Gas
1676 holgerb 1727
                        if(Mixer.Motor[i][0] == 64) tmp_int = GasMischanteil; else tmp_int =  ((long)GasMischanteil * Mixer.Motor[i][0]) / 64L;
1652 holgerb 1728
                        // Nick
1729
                        if(Mixer.Motor[i][1] == 64) tmp_int += pd_ergebnis_nick;
1730
                        else if(Mixer.Motor[i][1] == -64) tmp_int -= pd_ergebnis_nick;
1731
                        else tmp_int += ((long)pd_ergebnis_nick * Mixer.Motor[i][1]) / 64L;
1732
            // Roll
1733
                        if(Mixer.Motor[i][2] == 64) tmp_int += pd_ergebnis_roll;
1734
                        else if(Mixer.Motor[i][2] == -64) tmp_int -= pd_ergebnis_roll;
1735
                        else tmp_int += ((long)pd_ergebnis_roll * Mixer.Motor[i][2]) / 64L;
1736
            // Gier
1676 holgerb 1737
                        if(Mixer.Motor[i][3] == 64) tmp_int += GierMischanteil;
1738
                        else if(Mixer.Motor[i][3] == -64) tmp_int -= GierMischanteil;
1739
                        else tmp_int += ((long)GierMischanteil * Mixer.Motor[i][3]) / 64L;
1675 holgerb 1740
 
1813 - 1741
/******************************************************************************************************************
1742
Arthur P: the original code allowed the motor value to drop to 0 or negative values
1743
straight off, i.e. could amplify an intended decrease excessively while upregulation
1744
is dampened. The modification would still allow immediate drop below intended value
1745
but would dampen this. This would still allow for airbraking of the prop to have effect
1746
but it might lead to less sudden excessive drops in rpm with only gradual recovery.
1747
090807 Arthur P: Due to problems with uart.c which still refers to user parameter 1 and 2 and
1748
possible timing issues with the shutter interval load, removed the shutter interval functions
1749
and switched to use of userparam6 for the motor smoothing.
1750
091114 Inserted modification into 0.76g source code.
1751
20100804 Modified v.0.80d code where motorsmoothing is no longer a separate function.
1752
Downsmoothing either uses default v.0.7x+ 150% downstep (user para 7 == 0),
1753
50% downstep (user para 7 == 1 or 2), or downsteps of x% (userpara7 ==):
1754
66.6% (3), 75% (4), 80% (5), 90% (10), 95% (20), 97.5% (40), 98% (50), 99% (100).
1755
******************************************************************************************************************/
1756
 
1680 holgerb 1757
                        if(tmp_int > tmp_motorwert[i]) tmp_int = (tmp_motorwert[i] + tmp_int) / 2;      // MotorSmoothing
1813 - 1758
/******************************************************************************************************************
1759
Arthur P: Start of changes in fc.c. Next line is disabled and replaced by modified routine.
1760
******************************************************************************************************************/
1761
//                      else tmp_int = 2 * tmp_int - tmp_motorwert[i];                                                              // MotorSmoothing
1762
                        else
1763
                        {
1764
                                if(Parameter_UserParam7 < 2)
1765
                                { // Original function
1766
                                        tmp_int = 2 * tmp_int - tmp_motorwert[i];
1767
                                }
1768
                                else
1769
                                {
1770
                                        // If userpara7 >= 2 then allow >= 50% of the intended step down to rapidly reach the intended value.
1771
                                        tmp_int = tmp_int + ((tmp_motorwert[i] - tmp_int)/Parameter_UserParam7);
1772
                                }
1773
                        }
1774
/******************************************************************************************************************
1775
Arthur P: End of changes in fc.c.
1776
******************************************************************************************************************/
1693 holgerb 1777
 
1760 holgerb 1778
                        LIMIT_MIN_MAX(tmp_int,(int) MIN_GAS * 4,(int) MAX_GAS * 4);
1676 holgerb 1779
                        Motor[i].SetPoint = tmp_int / 4;
1677 killagreg 1780
                        Motor[i].SetPointLowerBits = (tmp_int % 4)<<1; // (3 bits total)
1652 holgerb 1781
            tmp_motorwert[i] = tmp_int;
1642 killagreg 1782
                }
1783
                else
1784
                {
1785
                        Motor[i].SetPoint = 0;
1786
                        Motor[i].SetPointLowerBits = 0;
1787
                }
1788
        }
1111 hbuss 1789
}