Reaction Wheel Actuated Satellite Dynamics Test Platform

Dependencies:   mbed

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 ///////////////////////////////////////////////////////////////////////////////////////////////////
00002 ///////////////////////////////////////////////////////////////////////////////////////////////////
00003 // Programm zu Lageregelung der Testplattform mit Hilfe von Reaktionskreiseln.
00004 // Mit UM6-LT IMU als Trägheitsplattform, XBee-Funkmodul zum seriellen Datenübertraggung und mbed
00005 // Mikrokontroller als Regelungs- und Stuerungscomputer.
00006 // Im Programm sind ein PID- und ein PD-Regler implementiert.                                       
00007 //
00008 // Datum: 10.01.2014  Autor: Grübel Dimitri
00009 // 
00010 ///////////////////////////////////////////////////////////////////////////////////////////////////
00011 
00012 
00013 #include "mbed.h"                                // MBED HEADER
00014 #include "MODSERIAL.h"                           // MBED BUFFERED SERIAL HEADER
00015 #include "UM6_usart.h"                           // UM6 USART HEADER
00016 #include "UM6_config.h"                          // UM6 CONFIG HEADER
00017 
00018                                                  // KOMMUNIKATIONSART MIT MBED: USB/XBEE
00019 Serial ios(p28, p27);                            // Serielle Verbi. mit XBee über Pin: tx-28, rx-27
00020 //Serial ios(USBTX, USBRX);                      // Serielle Verbi. über USB Port vom PC
00021 
00022 DigitalOut rst(p11);                             // Digital Reset für the XBee, 200ns für reset
00023 PwmOut x_kreisel(p21);                           // Pin21-PwmOut ist für Drehung um X-Achse
00024 PwmOut y_kreisel(p23);                           // Pin23-PwmOut ist für Drehung um Y-Achse
00025 PwmOut z_kreisel(p22);                           // Pin22-PwmOut ist für Drehung um Z-Achse
00026 
00027                                                  // HIER WIRD PWM EINGESTELLT:
00028 const float pulsweite = 10.0;                    // Pulsweite des Steuersignals in ms
00029 const float pwwork = 2.0;                        // Pulsweite des Arbeitssignals in ms
00030 const float startpw = 0.8;                       // Startpulsweite in ms
00031 const float pwmfakt = (pwwork - startpw)/200.0;  // Pulsweite pro 1% Leistung
00032 const float max_leistung = 75.0;                 // Leistungsbegrenzung global in %
00033 const float min_leistung = 10.0;                 // Notwendige Mindestleistung des Motors in %
00034 
00035 const float x_kp_min = 0.0;                      // min/max - Variablen kp für X/Y/Z-Achse
00036 const float x_kp_max = 3.0;
00037 const float y_kp_min = 0.0;
00038 const float y_kp_max = 3.0;
00039 const float z_kp_min = 0.0;
00040 const float z_kp_max = 3.0;
00041 
00042 const float x_kd_min = 0.0;                      // min/max - Variablen kd für X/Y/Z-Achse
00043 const float x_kd_max = 3.0;
00044 const float y_kd_min = 0.0;
00045 const float y_kd_max = 3.0;
00046 const float z_kd_min = 0.0;
00047 const float z_kd_max = 3.0;
00048 
00049 const float x_ki_min = 0.0;                      // min/max - Variablen ki für X/Y/Z-Achse
00050 const float x_ki_max = 0.5;
00051 const float y_ki_min = 0.0;
00052 const float y_ki_max = 0.5;
00053 const float z_ki_min = 0.0;
00054 const float z_ki_max = 0.5;
00055 
00056 const float x_winkel_min = -45.0;                // Winkelbegrenzung für X/Y/Z-Achse
00057 const float x_winkel_max =  45.0;
00058 const float y_winkel_min = -45.0;
00059 const float y_winkel_max =  45.0;
00060 const float z_winkel_min = -90.0;
00061 const float z_winkel_max =  90.0;
00062 
00063 const float regelgenauigkeit = 1.5;              // Regelgenauigkeit in Grad
00064                                                  
00065 const float x_kp_def = 1.0;                      // DEFAULT REGELPARAMETER FÜR X/Y/Z-ACHSE
00066 const float x_kd_def = 0.4;
00067 const float x_ki_def = 0.01;
00068 const float y_kp_def = 1.0; 
00069 const float y_kd_def = 0.4;
00070 const float y_ki_def = 0.01;
00071 const float z_kp_def = 1.0; 
00072 const float z_kd_def = 0.4;
00073 const float z_ki_def = 0.01;
00074 
00075 DigitalOut uart_activity(LED1);                  // LED1 = UM6 SERIAL für Kommunikation
00076        
00077                                                                    
00078 /// FUNKTIONEN ////////////////////////////////////////////////////////////////////////////////////
00079 ///////////////////////////////////////////////////////////////////////////////////////////////////
00080 
00081 
00082 ///////////////////////////////////////////////////////////////////////////////////////////////////
00083 // rxCallback // FUNKTION FÜR INTERRUPT - ABFRAGE DER DATEN DIE UM6-LT SENDET
00084 
00085 void rxCallback(MODSERIAL_IRQ_INFO *q) 
00086 {
00087     if (um6_uart.rxBufferGetCount() >=  MAX_PACKET_DATA) 
00088     {
00089         uart_activity = !uart_activity;          // LED leuchtet wenn RxBuff hat > 40 Bytes
00090         Process_um6_packet();
00091     }
00092 }
00093 
00094 
00095 ///////////////////////////////////////////////////////////////////////////////////////////////////
00096 // calcStellwert // FUNKTION ZUR STELLWERTBERECHNUNG FÜR MBED-PWM
00097 
00098 float calcStellwert(float leistung) 
00099 {                                
00100     return (startpw + ((leistung + 100) * pwmfakt)) / pulsweite;
00101 }
00102 
00103 
00104 ///////////////////////////////////////////////////////////////////////////////////////////////////
00105 // print_gyro_data // FUNKTION ZUR AUSGABE DER AKTUELLEN WINKEL UND WINKELGESCHWINDIGKEITEN
00106 
00107 void print_gyro_data()
00108 {                                              
00109     ios.printf("Gyro_Proc_X     %+6.1f deg/s\n", data.Gyro_Proc_X);
00110     ios.printf("Gyro_Proc_Y     %+6.1f deg/s\n", data.Gyro_Proc_Y);
00111     ios.printf("Gyro_Proc_Z     %+6.1f deg/s\n", data.Gyro_Proc_Z);
00112     ios.printf("Roll            %+6.1f deg\n", data.Roll);
00113     ios.printf("Pitch           %+6.1f deg\n", data.Pitch);
00114     ios.printf("Yaw             %+6.1f deg\n\n", data.Yaw);
00115 }
00116 
00117 
00118 ///////////////////////////////////////////////////////////////////////////////////////////////////
00119 // print_gyro_angles // FUNKTION ZUR AUSGABE DER AKTUELLEN WINKEL
00120 
00121 void print_gyro_angles()
00122 {                                            
00123     ios.printf("Roll            %+6.1f deg\n", data.Roll);
00124     ios.printf("Pitch           %+6.1f deg\n", data.Pitch);
00125     ios.printf("Yaw             %+6.1f deg\n\n", data.Yaw);
00126 }
00127 
00128 
00129 ///////////////////////////////////////////////////////////////////////////////////////////////////
00130 // LageregelungAchse // FUNKTION ZUR LAGEREGELUNG FÜR EINE ACHSE - STATISCH - PD Regler
00131 
00132 void LageregelungAchse(float kp, float kd, float winkel, const float& gyro_veloc, 
00133                        const float& gyro_angle, PwmOut& kreisel)
00134 {                   
00135     float start_angle = gyro_angle;
00136     float winkel_soll = gyro_angle + winkel;                                                      
00137     float abweichung = gyro_angle - winkel_soll;
00138     float leistung_alt = 0;                           // Variablen für Bremsverfahren
00139     bool start = true;
00140     
00141     while (fabs(abweichung) > regelgenauigkeit) 
00142     {
00143         float leistung = abweichung * kp - gyro_veloc * kd;
00144         if (leistung > max_leistung) leistung = max_leistung;
00145         if (leistung < -max_leistung) leistung = -max_leistung;
00146         if (leistung > -min_leistung && leistung < -0.001) leistung = -min_leistung;
00147         if (leistung < min_leistung && leistung > 0.001) leistung = min_leistung;
00148          
00149         int Bremsrichtung = 0;                        // Vorzeichenbestimmung der Abbremsrichtung
00150          
00151         if (leistung >= 0)
00152             Bremsrichtung = -1;
00153         else 
00154             Bremsrichtung = 1;
00155         
00156         float Stellwert = calcStellwert(leistung);    // Berechnung Stellwert
00157         kreisel.write(Stellwert);                     // Befehl an Motorregler über PWM
00158         wait_ms(20);
00159         abweichung = gyro_angle - winkel_soll;        // Kontrolle der Regelgenauigkeit
00160         
00161         if (start == true) 
00162         {                                             
00163             leistung_alt = leistung;
00164             start = false;
00165         }      
00166         else 
00167         {
00168             if (fabs(winkel) > 5.0) 
00169             {                                     
00170                 if ( fabs(leistung) > min_leistung) 
00171                 { 
00172                     float delta_leistung = fabs(leistung) - fabs(leistung_alt);     // Bestimmung Abfall Delta
00173                     if (delta_leistung < -0.001) 
00174                     {                                 // Abbremsung des Motors bei Leistungsabnahme
00175                         kreisel.write(calcStellwert(Bremsrichtung * min_leistung)); 
00176                         wait_ms(10);
00177                     }
00178                 }
00179             }
00180             
00181             leistung_alt = leistung;
00182         }                                                       // Ende des Bremsverfahrens
00183         
00184         if (fabs(abweichung) <= regelgenauigkeit) 
00185         {             // Vorzeichen für Bremsung wird bestimmt
00186             print_gyro_data();                                  // Funktionsaufruf Gyrodaten ausgeben 
00187             kreisel.write(calcStellwert(Bremsrichtung * 100));  // Vollbremsung
00188             wait_ms(650); 
00189             kreisel.write(calcStellwert(0));                    // Motor aus
00190         }
00191     }
00192        
00193     float end_angle = gyro_angle;        
00194     ios.printf("Plattform wurde gedreht um %+6.1f deg\n\n", end_angle - start_angle);
00195 }
00196 
00197 
00198 ///////////////////////////////////////////////////////////////////////////////////////////////////
00199 // LageregelungAchseDyn // FUNKTION ZUR LAGEREGELUNG FÜR EINE ACHSE - DYNAMISCH - PID Regler
00200 
00201 void LageregelungAchseDyn(float kp, float kd, float ki, float winkel, const float& gyro_veloc, 
00202                           const float& gyro_angle, PwmOut& kreisel, float& dyn_leistung_leerlauf)
00203 {                   
00204     
00205     ios.printf("Start LageregelungAchseDyn\n");
00206     float start_angle = gyro_angle;
00207     float winkel_soll = gyro_angle + winkel;
00208     float abweichung = gyro_angle - winkel_soll;
00209     float abweichung_sum = abweichung;
00210     float leistung_alt = dyn_leistung_leerlauf;
00211     bool  start = true;
00212     float leistung = 0.0;
00213     float i_glied = 0.0;
00214     
00215     int cnt = 0; 
00216     while (fabs(abweichung) > regelgenauigkeit) 
00217     {
00218         cnt += 1;
00219         i_glied = abweichung_sum * 0.001 * ki;
00220         ios.printf("%f\n", i_glied);
00221         if (i_glied > 0.5) i_glied = 0.5;                       // I-Glied Limiter 
00222         if (i_glied < -0.5) i_glied = -0.5;
00223         // Sumierstelle (PID Glieder)
00224         leistung = dyn_leistung_leerlauf + abweichung * kp - gyro_veloc * kd + i_glied;            
00225         if (leistung > max_leistung) leistung = max_leistung;
00226         if (leistung < min_leistung) leistung = min_leistung;
00227         int Bremsrichtung = -1;                                 // Vorzeichen der Abbremsrichtung 
00228 
00229         float Stellwert = calcStellwert(leistung);              // Berechnung Stellwert
00230         kreisel.write(Stellwert);                               // Befehl an Motorregler über Pwm
00231         wait_ms(10);       
00232     
00233         if (start == true) 
00234         {                                   
00235             leistung_alt = leistung;
00236             start = false;
00237         }     
00238         /*else 
00239         {                       
00240             if (leistung > min_leistung) 
00241             { 
00242                 float delta_leistung = leistung - leistung_alt; // Bestimmung Abfall Delta
00243                 
00244                 // bei Abnahme der Leistung - Motor abbremsen
00245                 if (delta_leistung < -0.0001) 
00246                 {                 
00247                     kreisel.write(calcStellwert(Bremsrichtung * min_leistung)); 
00248                     wait_ms(5);
00249                 }
00250             }
00251         }
00252         */
00253         leistung_alt = leistung;
00254         abweichung = gyro_angle - winkel_soll;
00255         abweichung_sum += abweichung;
00256     }
00257     
00258     dyn_leistung_leerlauf = leistung - i_glied;
00259     if (dyn_leistung_leerlauf < min_leistung) dyn_leistung_leerlauf = min_leistung;
00260     if (dyn_leistung_leerlauf > max_leistung) dyn_leistung_leerlauf = max_leistung;
00261     ios.printf("Leerlaufleistung: %f\n", dyn_leistung_leerlauf);  
00262     float end_angle = gyro_angle;      
00263     ios.printf("Plattform wurde gedreht um %+6.1f deg\n\n", end_angle - start_angle);
00264     // Counter für durchlaufene Regelzyklen             
00265     ios.printf("\nEnde LageregelungAchseDyn; Counter: %i\n\n", cnt);                               
00266 }
00267 
00268 
00269 ///////////////////////////////////////////////////////////////////////////////////////////////////
00270 // main // Hauptprogramm
00271 
00272 int main() 
00273 {                                                          
00274     ios.baud(115200);                                                // Baudrate XBee Funkmodul
00275     um6_uart.baud(115200);                                           // Baudrate UM6-lt 
00276     um6_uart.attach(&rxCallback, MODSERIAL::RxIrq);                  // Interrupt Funktion für UART
00277 
00278     rst = 1;                                                         // Reset-Pin von XBee auf ON
00279     
00280     ios.printf("\nBitte warten, Startvorgang der Plattform...\n\n"); // Start-UP Prozedur 
00281     um6_uart.putc(0xAC);                                             // Nulliert die Rate-Gyros
00282     wait_ms(3500);
00283     um6_uart.putc(0xAC);                                             // Nulliert die Rate-Gyros
00284     wait_ms(3500);
00285     um6_uart.putc(0xAC);                                             // Nulliert die Rate-Gyros
00286     wait_ms(3500);
00287 
00288     x_kreisel.period_ms(pulsweite);                                 
00289     y_kreisel.period_ms(pulsweite);
00290     z_kreisel.period_ms(pulsweite);
00291     
00292     ios.printf("\n\nTESTPLATTFORM ZUR SATELLITENLAGEREGELUNG MIT REAKTIONSKREISELN:\n\n");
00293          
00294     int choice1 = 0;
00295     
00296     do 
00297     {
00298         do 
00299         {
00300             ios.printf("\n\nBitte folgende Anweisungen ausfuehren,falls nicht bereits erfolgt!\n"
00301                "Stromversorgung der Testplattform trennen und ohne Druckluft mit X-Achse auf mag."
00302                " Norden ausrichten.\n"
00303                "Testplattform mit Wasserwaage horizontal tarieren.\n"
00304                "Danach Stromversorgung herstellen und mbed Reset-Taste betaetigen.\n\n");
00305             
00306             x_kreisel.write(calcStellwert(0));                       //Initialisierung X-Motorrelger 
00307             y_kreisel.write(calcStellwert(0));                       //Initialisierung Y-Motorrelger
00308             z_kreisel.write(calcStellwert(0));                       //Initialisierung Z-Motorrelger
00309             
00310             ios.printf("Menueauswahl:\n");                          
00311             ios.printf("\t1 - Testplattform um einzelne Achsen drehen\n");
00312             ios.printf("\t2 - Testplattform um drei Achsen drehen\n");
00313             ios.printf("\t3 - Lage der Testplattform aktiv regeln fuer dynamische Fehler\n");
00314             ios.printf("\t4 - Gyrodaten ausgeben [Winkel/Winkelgeschwindigkeiten]\n");
00315             ios.printf("\t5 - Programm beenden\n");
00316             ios.printf("\nEingabe >");
00317             ios.scanf("%i", &choice1);
00318         }while (choice1 < 1 || choice1 > 5);
00319         
00320         if (choice1 == 1)
00321         { 
00322             ios.printf("\nTestplattform ist initialisiert.\n\n");
00323             print_gyro_angles();                                     // Funktionsaufruf Gyrodwinkel ausgeben     
00324             float x_kp = x_kp_def;
00325             float x_kd = x_kd_def;
00326             float x_winkel = 0.0;
00327             float y_kp = y_kp_def; 
00328             float y_kd = y_kd_def;
00329             float y_winkel = 0.0;
00330             float z_kp = z_kp_def; 
00331             float z_kd = z_kd_def;
00332             float z_winkel = 0.0;
00333 
00334             int choice2 = 0;
00335             
00336             do 
00337             {
00338                 do 
00339                 {
00340                     ios.printf("\n\nLAGEREGELUNG EINZELNER ACHSEN:\n\n");                         
00341                     ios.printf("Menueauswahl:\n");
00342                     ios.printf("\t1 - Satellitenplattform rollen (um X-Achse drehen)\n");
00343                     ios.printf("\t2 - Satellitenplattform nicken (um Y-Achse drehen)\n");
00344                     ios.printf("\t3 - Satellitenplattform gieren (um Z-Achse drehen)\n");
00345                     ios.printf("\t4 - Auswahl abbrechen (esc).\n");
00346                     ios.printf("\nEingabe >");
00347                     ios.scanf("%i", &choice2); 
00348                 }while (choice2 < 1 || choice2 > 4);
00349 
00350                 if (choice2 == 1)
00351                 {
00352                     ios.printf("\n Reglerparameter kp eingeben [0 - +3] >");
00353                     ios.scanf("%f", &x_kp);          
00354                     if (x_kp > x_kp_max) x_kp = x_kp_max;                 // Begrenzung X-Achse kp Pos.
00355                     if (x_kp < x_kp_min) x_kp = x_kp_min;                 // Begrenzung X-Achse kp Neg.
00356                     ios.printf("\n Reglerparameter kd eingeben [0 - +3] >");
00357                     ios.scanf("%f", &x_kd); 
00358                     if (x_kd > x_kd_max) x_kd = x_kd_max;                 // Begrenzung X-Achse kd Pos.
00359                     if (x_kd < x_kd_min) x_kd = x_kd_min;                 // Begrenzung X-Achse kd Neg.      
00360                     ios.printf("\n Rollwinkel Phi eingeben [-45 - +45] >");
00361                     ios.scanf("%f", &x_winkel);
00362                     if (x_winkel > x_winkel_max) x_winkel = x_winkel_max; // Begrenzung X-Achse Winkel Pos.
00363                     if (x_winkel < x_winkel_min) x_winkel = x_winkel_min; // Begrenzung X-Achse Winkel Neg.   
00364                     if (fabs(x_winkel) < regelgenauigkeit) ios.printf("\nRegelung ist nicht notwendig!");
00365                     ios.printf("\nParameter kp = %f, Parameter kd = %f, Rollwinkel = %f\n", 
00366                                x_kp, x_kd, x_winkel); 
00367                     print_gyro_angles();
00368                     LageregelungAchse(x_kp, x_kd, x_winkel, data.Gyro_Proc_X, data.Roll, x_kreisel);
00369                 }
00370                 else if (choice2 == 2) 
00371                 {
00372                     ios.printf("\n Reglerparameter kp eingeben [0 - +3] >");
00373                     ios.scanf("%f", &y_kp);
00374                     if (y_kp > y_kp_max) y_kp = y_kp_max;                 // Begrenzung Y-Achse kp Pos.
00375                     if (y_kp < y_kp_min) y_kp = y_kp_min;                 // Begrenzung Y-Achse kp Neg.
00376                     ios.printf("\n Reglerparameter kd eingeben [0 - +3] >");
00377                     ios.scanf("%f", &y_kd);
00378                     if (y_kd > y_kd_max) y_kd = y_kd_max;                 // Begrenzung Y-Achse kd Pos.
00379                     if (y_kd < y_kd_min) y_kd = y_kd_min;                 // Begrenzung Y-Achse kd Neg.
00380                     ios.printf("\n Nickwinkel Theta eingeben [-45 - +45] >");
00381                     ios.scanf("%f", &y_winkel);                             
00382                     if (y_winkel > y_winkel_max) y_winkel = y_winkel_max; // Begrenzung Y-Achse Winkel Pos.
00383                     if (y_winkel < y_winkel_min) y_winkel = y_winkel_min; // Begrenzung Y-Achse Winkel Neg.   
00384                     if (fabs(y_winkel) < regelgenauigkeit) ios.printf("\nRegelung ist nicht notwendig!");
00385                     ios.printf("\nParameter kp = %f, Parameter kd = %f, Nickwinkel = %f\n", 
00386                                 y_kp, y_kd, y_winkel); 
00387                     print_gyro_angles();                                                  
00388                     LageregelungAchse(y_kp, y_kd, y_winkel, data.Gyro_Proc_Y, data.Pitch, y_kreisel);
00389                                      
00390                  } 
00391                  else if (choice2 == 3) 
00392                  {                    
00393                     ios.printf("\n Reglerparameter kp eingeben [0 - +3] >");
00394                     ios.scanf("%f", &z_kp);
00395                     if (z_kp > z_kp_max) z_kp = z_kp_max;                 // Begrenzung Z-Achse kp Pos.
00396                     if (z_kp < z_kp_min) z_kp = z_kp_min;                 // Begrenzung Z-Achse kp Neg.
00397                     ios.printf("\n Reglerparameter kd eingeben [0 - +3] >");
00398                     ios.scanf("%f", &z_kd);
00399                     if (z_kd > z_kd_max) z_kd = z_kd_max;                 // Begrenzung Z-Achse kd Pos.
00400                     if (z_kd < z_kd_min) z_kd = z_kd_min;                 // Begrenzung Z-Achse kd Neg.   
00401                     ios.printf("\n Gierwinkel Psi eingeben [-90 - +90] >");
00402                     ios.scanf("%f", &z_winkel);      
00403                     if (z_winkel > z_winkel_max) z_winkel = z_winkel_max; // Begrenzung Z-Achse Winkel Pos.
00404                     if (z_winkel < z_winkel_min) z_winkel = z_winkel_min; // Begrenzung Z-Achse Winkel Neg.   
00405                     if (fabs(z_winkel) < regelgenauigkeit) ios.printf("\nRegelung ist nicht notwendig!");
00406                     ios.printf("\nParameter kp = %f, Parameter kd = %f, Gierwinkel = %f\n", 
00407                                 z_kp, z_kd, z_winkel); 
00408                     print_gyro_angles();
00409                     LageregelungAchse(z_kp, z_kd, z_winkel, data.Gyro_Proc_Z, data.Yaw, z_kreisel);
00410                 }
00411             }while(choice2 != 4);
00412             
00413         }
00414         else if (choice1 == 2)
00415         {
00416             float x_kp = x_kp_def;
00417             float x_kd = x_kd_def;
00418             float x_winkel = 0.0;
00419             float y_kp = y_kp_def; 
00420             float y_kd = y_kd_def;
00421             float y_winkel = 0.0;
00422             float z_kp = z_kp_def; 
00423             float z_kd = z_kd_def;
00424             float z_winkel = 0.0;
00425        
00426             int choice3 = 0;
00427             
00428             do 
00429             {
00430                 do 
00431                 {
00432                     ios.printf("\n\nLAGEREGELUNG ALLER ACHSEN:\n\n");
00433                     ios.printf("Bitte Plattform in gewuenschte Ausgangsposition bringen.\n");
00434                     ios.printf("Plattform wird in Z-Y-X Reihenfolge gedreht!\n\n");
00435                     ios.printf("Aktuelle Werte fuer Regler X-Achse: kp = %f kd = %f\n\n", x_kp, x_kd);
00436                     ios.printf("Aktuelle Werte fuer Regler Y-Achse: kp = %f kd = %f\n\n", y_kp, y_kd);
00437                     ios.printf("Aktuelle Werte fuer Regler Z-Achse: kp = %f kd = %f\n\n", z_kp, z_kd);
00438                     ios.printf("Menueauswahl:\n");
00439                     ios.printf("\t1 - Regelparameter aendern?\n");
00440                     ios.printf("\t2 - Plattform drehen-Winkel eingeben\n");
00441                     ios.printf("\t3 - Auswahl abbrechen (esc).\n");
00442                     ios.printf("\nEingabe >");
00443                     ios.scanf("%i", &choice3); 
00444                 }while (choice3 < 1 || choice3 > 3);
00445                       
00446                 if (choice3 == 1)
00447                 {
00448                     ios.printf("\n Reglerparameter x_kp eingeben [0 - +3] >");
00449                     ios.scanf("%f", &x_kp);          
00450                     if (x_kp > x_kp_max) x_kp = x_kp_max;                 // Begrenzung X-Achse kp Pos.
00451                     if (x_kp < x_kp_min) x_kp = x_kp_min;                 // Begrenzung X-Achse kp Neg.
00452                     ios.printf("\n Reglerparameter x_kd eingeben [0 - +3] >");
00453                     ios.scanf("%f", &x_kd); 
00454                     if (x_kd > x_kd_max) x_kd = x_kd_max;                 // Begrenzung X-Achse kd Pos.
00455                     if (x_kd < x_kd_min) x_kd = x_kd_min;                 // Begrenzung X-Achse kd Neg.
00456                     ios.printf("\n Reglerparameter y_kp eingeben [0 - +3] >");
00457                     ios.scanf("%f", &y_kp);
00458                     if (y_kp > y_kp_max) y_kp = y_kp_max;                 // Begrenzung Y-Achse kp Pos.
00459                     if (y_kp < y_kp_min) y_kp = y_kp_min;                 // Begrenzung Y-Achse kp Neg.
00460                     ios.printf("\n Reglerparameter y_kd eingeben [0 - +3] >");
00461                     ios.scanf("%f", &y_kd);
00462                     if (y_kd > y_kd_max) y_kd = y_kd_max;                 // Begrenzung Y-Achse kd Pos.
00463                     if (y_kd < y_kd_min) y_kd = y_kd_min;                 // Begrenzung Y-Achse kd Neg.
00464                     ios.printf("\n Reglerparameter z_kp eingeben [0 - +3] >");
00465                     ios.scanf("%f", &z_kp);
00466                     if (z_kp > z_kp_max) z_kp = z_kp_max;                 // Begrenzung Z-Achse kp Pos.
00467                     if (z_kp < z_kp_min) z_kp = z_kp_min;                 // Begrenzung Z-Achse kp Neg.
00468                     ios.printf("\n Reglerparameter z_kd eingeben [0 - +3] >");
00469                     ios.scanf("%f", &z_kd);
00470                     if (z_kd > z_kd_max) z_kd = z_kd_max;                 // Begrenzung Z-Achse kd Pos.
00471                     if (z_kd < z_kd_min) z_kd = z_kd_min;                 // Begrenzung Z-Achse kd Neg. 
00472                     ios.printf("\n\n"); 
00473                     ios.printf("Aktuelle Werte fuer Regler X-Achse: kp = %f kd = %f\n\n", x_kp, x_kd);
00474                     ios.printf("Aktuelle Werte fuer Regler Y-Achse: kp = %f kd = %f\n\n", y_kp, y_kd);
00475                     ios.printf("Aktuelle Werte fuer Regler Z-Achse: kp = %f kd = %f\n\n", z_kp, z_kd);
00476                 }
00477                 else if (choice3 == 2)
00478                 {                                                         // Eingabe der Drehwinkel
00479                     ios.printf("\n Gierwinkel Psi eingeben [-90 - +90] >");
00480                     ios.scanf("%f", &z_winkel);      
00481                     if (z_winkel > z_winkel_max) z_winkel = z_winkel_max; // Begrenzung Z-Achse Winkel Pos.
00482                     if (z_winkel < z_winkel_min) z_winkel = z_winkel_min; // Begrenzung Z-Achse Winkel Neg.
00483                     ios.printf("\n Nickwinkel Theta eingeben [-45 - +45] >");
00484                     ios.scanf("%f", &y_winkel);                             
00485                     if (y_winkel > y_winkel_max) y_winkel = y_winkel_max; // Begrenzung Y-Achse Winkel Pos.
00486                     if (y_winkel < y_winkel_min) y_winkel = y_winkel_min; // Begrenzung Y-Achse Winkel Neg.
00487                     ios.printf("\n Rollwinkel Phi eingeben [-45 - +45] >");
00488                     ios.scanf("%f", &x_winkel);
00489                     if (x_winkel > x_winkel_max) x_winkel = x_winkel_max; // Begrenzung X-Achse Winkel Pos.
00490                     if (x_winkel < x_winkel_min) x_winkel = x_winkel_min; // Begrenzung X-Achse Winkel Neg.
00491                         
00492                     if (fabs(z_winkel) < regelgenauigkeit && 
00493                         fabs(y_winkel) < regelgenauigkeit && 
00494                         fabs(x_winkel) < regelgenauigkeit)
00495                     {
00496                         ios.printf("\nRegelung ist nicht notwendig!");
00497                     }
00498                     else 
00499                     {
00500                         print_gyro_angles();
00501                         LageregelungAchse(z_kp, z_kd, z_winkel, data.Gyro_Proc_Z, data.Yaw, z_kreisel);
00502                         wait_ms(250);   
00503                         LageregelungAchse(y_kp, y_kd, y_winkel, data.Gyro_Proc_Y, data.Pitch, y_kreisel);
00504                         wait_ms(250);
00505                         LageregelungAchse(x_kp, x_kd, x_winkel, data.Gyro_Proc_X, data.Roll, x_kreisel);
00506                         print_gyro_angles();
00507                         ios.printf("\n\nSoll die Plattform wieder in ihre Ausgangslage gefahren werden? "
00508                                    "ja/nein\n");
00509                         char yes_no[50]; 
00510                         ios.scanf("%s", yes_no);
00511                         
00512                         if (strcmp(yes_no, "ja") == 0)    // Plattform in auf Ausgangsposition drehen
00513                         {                       
00514                             LageregelungAchse(x_kp, x_kd, -x_winkel, data.Gyro_Proc_X, data.Roll, x_kreisel);
00515                             wait_ms(250);  
00516                             LageregelungAchse(y_kp, y_kd, -y_winkel, data.Gyro_Proc_Y, data.Pitch, y_kreisel);
00517                             wait_ms(250);
00518                             LageregelungAchse(z_kp, z_kd, -z_winkel, data.Gyro_Proc_Z, data.Yaw, z_kreisel);
00519                             print_gyro_angles();
00520                         }
00521                     }
00522                 }  
00523                             
00524             }while(choice3 != 3);
00525         }
00526         else if (choice1 == 3)
00527         {
00528             float x_kp = x_kp_def;
00529             float x_kd = x_kd_def;
00530             float x_ki = x_ki_def;
00531             float y_kp = y_kp_def; 
00532             float y_kd = y_kd_def;
00533             float y_ki = y_ki_def;
00534             float z_kp = z_kp_def; 
00535             float z_kd = z_kd_def;
00536             float z_ki = z_ki_def;
00537        
00538             int choice4 = 0;
00539             
00540             do 
00541             {
00542                 do 
00543                 {
00544                     ios.printf("\n\nLage der Testplattform aktiv regeln fuer dynamische Fehler"
00545                                " (Position halten):\n\n");
00546                     ios.printf("\n\nBitte Plattform in gewuenschte Ausgangsposition bringen und halten "
00547                                "bis die Kreisel "
00548                                "ihre Leerlaufdrehzahl erreicht haben.\n\n");
00549                     ios.printf("Aktuelle Werte fuer Regler X-Achse: kp = %f kd = %f ki = %f\n", 
00550                                 x_kp, x_kd, x_ki); 
00551                     ios.printf("Aktuelle Werte fuer Regler Y-Achse: kp = %f kd = %f ki = %f\n", 
00552                                 y_kp, y_kd, y_ki);
00553                     ios.printf("Aktuelle Werte fuer Regler Z-Achse: kp = %f kd = %f ki = %f\n\n", 
00554                                 z_kp, z_kd, z_ki);
00555                     ios.printf("Menueauswahl:\n");
00556                     ios.printf("\t1 - Regelparameter aendern?\n");
00557                     ios.printf("\t2 - Plattform aktivieren\n");
00558                     ios.printf("\t3 - Auswahl abbrechen (esc).\n");
00559                     ios.printf("\nEingabe >");
00560                     ios.scanf("%i", &choice4); 
00561                 }while (choice4 < 1 || choice4 > 3);  
00562                        
00563                 if (choice4 == 1)
00564                 {
00565                     /*
00566                     ios.printf("\n Reglerparameter x_kp eingeben [0 - +3] >");
00567                     ios.scanf("%f", &x_kp);          
00568                     if (x_kp > x_kp_max) x_kp = x_kp_max;                 // Begrenzung X-Achse kp Pos.
00569                     if (x_kp < x_kp_min) x_kp = x_kp_min;                 // Begrenzung X-Achse kp Neg.
00570                     ios.printf("\n Reglerparameter x_kd eingeben [0 - +3] >");
00571                     ios.scanf("%f", &x_kd); 
00572                     if (x_kd > x_kd_max) x_kd = x_kd_max;                 // Begrenzung X-Achse kd Pos.
00573                     if (x_kd < x_kd_min) x_kd = x_kd_min;                 // Begrenzung X-Achse kd Neg.
00574                     ios.printf("\n Reglerparameter x_ki eingeben [0 - +0.5] >");
00575                     ios.scanf("%f", &x_ki); 
00576                     if (x_ki > x_ki_max) x_ki = x_ki_max;                 // Begrenzung X-Achse ki Pos.
00577                     if (x_ki < x_ki_min) x_ki = x_ki_min;                 // Begrenzung X-Achse ki Neg.
00578                     ios.printf("\n Reglerparameter y_kp eingeben [0 - +3] >");
00579                     ios.scanf("%f", &y_kp);
00580                     if (y_kp > y_kp_max) y_kp = y_kp_max;                 // Begrenzung Y-Achse kp Pos.
00581                     if (y_kp < y_kp_min) y_kp = y_kp_min;                 // Begrenzung Y-Achse kp Neg.
00582                     ios.printf("\n Reglerparameter y_kd eingeben [0 - +3] >");
00583                     ios.scanf("%f", &y_kd);
00584                     if (y_kd > y_kd_max) y_kd = y_kd_max;                 // Begrenzung Y-Achse kd Pos.
00585                     if (y_kd < y_kd_min) y_kd = y_kd_min;                 // Begrenzung Y-Achse kd Neg.
00586                     ios.printf("\n Reglerparameter y_ki eingeben [0 - +0.5] >");
00587                     ios.scanf("%f", &y_ki); 
00588                     if (y_ki > y_ki_max) y_ki = y_ki_max;                 // Begrenzung Y-Achse ki Pos.
00589                     if (y_ki < y_ki_min) y_ki = y_ki_min;                 // Begrenzung Y-Achse ki Neg.
00590                     */  
00591                     ios.printf("\n Reglerparameter z_kp eingeben [0 - +3] >");
00592                     ios.scanf("%f", &z_kp);
00593                     if (z_kp > z_kp_max) z_kp = z_kp_max;                 // Begrenzung Z-Achse kp Pos.
00594                     if (z_kp < z_kp_min) z_kp = z_kp_min;                 // Begrenzung Z-Achse kp Neg.
00595                     ios.printf("\n Reglerparameter z_kd eingeben [0 - +3] >");
00596                     ios.scanf("%f", &z_kd);
00597                     if (z_kd > z_kd_max) z_kd = z_kd_max;                 // Begrenzung Z-Achse kd Pos.
00598                     if (z_kd < z_kd_min) z_kd = z_kd_min;                 // Begrenzung Z-Achse kd Neg. 
00599                     ios.printf("\n Reglerparameter z_ki eingeben [0 - +0.5] >");
00600                     ios.scanf("%f", &z_ki); 
00601                     if (z_ki > z_ki_max) z_ki = z_ki_max;                 // Begrenzung Z-Achse ki Pos.
00602                     if (z_ki < z_ki_min) z_ki = z_ki_min;                 // Begrenzung Z-Achse ki Neg.
00603                     ios.printf("\n\n"); 
00604                     //ios.printf("Aktuelle Werte fuer Regler X-Achse: kp = %f kd = %f ki = %f\n\n", 
00605                     //            x_kp, x_kd, x_ki); 
00606                     //ios.printf("Aktuelle Werte fuer Regler Y-Achse: kp = %f kd = %f ki = %f\n\n", 
00607                     //            y_kp, y_kd, y_ki);
00608                     ios.printf("Aktuelle Werte fuer Regler Z-Achse: kp = %f kd = %f ki = %f\n\n", 
00609                                 z_kp, z_kd, z_ki);
00610                 }
00611                 else if (choice4 == 2)
00612                 {                                       
00613                     ios.printf("\n\nUm abzubrechen bitte Reset-Taste an mbed betaetigen!\n\n");
00614                     float ziel_x_winkel = data.Roll;
00615                     float ziel_y_winkel = data.Pitch;
00616                     float ziel_z_winkel = data.Yaw;
00617                     
00618                     print_gyro_angles();                                 
00619                     float x_dyn_leistung_leerlauf = (min_leistung + max_leistung)/2; // Leistung im Leerlauf 
00620                     float y_dyn_leistung_leerlauf = (min_leistung + max_leistung)/2; // Leistung im Leerlauf 
00621                     float z_dyn_leistung_leerlauf = (min_leistung + max_leistung)/2; // Leistung im Leerlauf
00622                     
00623                     wait_ms(2000);
00624                     z_kreisel.write(calcStellwert(z_dyn_leistung_leerlauf));
00625                     //y_kreisel.write(calcStellwert(y_dyn_leistung_leerlauf));
00626                     //x_kreisel.write(calcStellwert(x_dyn_leistung_leerlauf));
00627             
00628                     while(1)
00629                     {
00630                         while (fabs(ziel_z_winkel - data.Yaw) > regelgenauigkeit)
00631                         {     
00632                             LageregelungAchseDyn(z_kp, z_kd, z_ki, ziel_z_winkel - data.Yaw, data.Gyro_Proc_Z, 
00633                                                  data.Yaw, z_kreisel, z_dyn_leistung_leerlauf);
00634                         }
00635                         
00636                         /*
00637                         while (fabs(ziel_y_winkel - data.Pitch) > regelgenauigkeit)
00638                         {  
00639                             LageregelungAchseDyn(y_kp, y_kd, y_ki, ziel_y_winkel - data.Roll, data.Gyro_Proc_Y, 
00640                                                  data.Pitch, y_kreisel, y_dyn_leistung_leerlauf);  
00641                         }
00642                         
00643                         while (fabs(ziel_x_winkel - data.Roll) > regelgenauigkeit)
00644                         {
00645                             LageregelungAchseDyn(x_kp, x_kd, x_ki, ziel_x_winkel - data.Pitch, data.Gyro_Proc_X, 
00646                                                  data.Roll, x_kreisel, x_dyn_leistung_leerlauf);
00647                         }
00648                         */
00649                     }
00650                 }
00651             }while(choice4 != 3);
00652         }
00653         else if (choice1 == 4)
00654         { 
00655             print_gyro_data();
00656         }
00657           
00658     }while(choice1 != 5); 
00659  
00660     ios.printf("\n\nProgramm beendet.\n");
00661 }