Utiliser un PID pour amélioré la stabilisation d'une plateforme

Bonsoir,
Je dois faire une sorte de plateforme afin de stabiliser une caméra à l'aide d'une arduino UNO, d'un servo-moteur et d'un MPU6050.
J'arrive bien à faire en sorte que la "caméra" reste droite mais je dois l'améliorer grâce à l'utilisation d'un PID.
J'ai fais quelque recherches sur internet pour en arriver à ce code, mais je ne pense vraiment pas qu'il soit correct. Je dois tester la stabilisation pour Ki=Kd=0, puis Kp=Kd=0 puis enfin Kp=Ki=0.
Je ne comprend cependant pas quoi mettre comme valeur dans "setpoint"
Pourriez-vous m'éclaircir ?
Merci d'avance

#include <Wire.h>
#include <MPU6050.h>
#include <Servo.h> 
#include <PID_v1.h>
    
#define _DEBUG false  
//-------------Declarations capteur et servo----------------
Servo servo1, servo2;          
int servo1_pin = 11;
int servo2_pin = 10;
MPU6050 sensor ;
int16_t ax, ay, az ;
int16_t gx, gy, gz ;
//---------PID--------------
double input;
double output;
double setpoint;
double Kp=0, Ki=10, Kd=0;

PID myPID(&input, &output, &setpoint, Kp, Ki, Kd, REVERSE);



void setup ( )
{ 
servo1.attach ( servo1_pin );
servo2.attach ( servo2_pin );
Wire.begin ( );
Serial.begin  (9600); 
Serial.println  ( "Initializing the sensor" ); 
sensor.initialize ( ); 
Serial.println (sensor.testConnection ( ) ? "Successfully Connected" : "Connection failed"); 
delay (1000); 
Serial.println ( "Taking Values from the sensor" );
setpoint=90;
myPID.SetMode(AUTOMATIC);
myPID.SetTunings(Kp,Ki,Kd);
myPID.SetOutputLimits(0, 180);

delay (1000);
}




void loop ( ) 
{ 
sensor.getMotion6 (&ax, &ay, &az, &gx, &gy, &gz);
input=map (ay, 17000, -17000, 0, 180) ;
myPID.Compute();
servo1.write(output);
Serial.println(output);

//delay(200);

}

Bonsoir

Setpoint c'est la valeur cible

@+

Le problème c'est que la valeur cible change tout le temps en fonction de l'angle que je donne à ma plateforme donc je ne sais pas quoi mettre

Comment est votre code précédent ? sans le PID.

il va falloir faire 2 PID je pense, 1 pour chaque servo

En me focalisant que sur un seul servo (ay) pour l'instant, j'obtient ce code là qui semble plutôt bien fonctionner

#include <Wire.h>
#include <MPU6050.h>
#include <Servo.h> 
#include <PID_v1.h>
    
#define _DEBUG false  
Servo servo1, servo2;          
int servo1_pin = 11;
int servo2_pin = 10;
MPU6050 sensor ;
int16_t ax, ay, az ;
int16_t gx, gy, gz ;



void setup ( )
{ 
servo1.attach ( servo1_pin );
servo2.attach ( servo2_pin );
Wire.begin ( );
Serial.begin  (9600); 
Serial.println  ( "Initializing the sensor" ); 
sensor.initialize ( ); 
Serial.println (sensor.testConnection ( ) ? "Successfully Connected" : "Connection failed"); 
delay (1000); 
Serial.println ( "Taking Values from the sensor" );

delay (1000);
}




void loop ( ) 
{ 
sensor.getMotion6 (&ax, &ay, &az, &gx, &gy, &gz);
/*ax = map (ax, -17000, 17000, 0, 180) ;
Serial.println (ax);
servo2.write (ax);
 ay = map (ay, 17000, -17000, 0, 180) ;
Serial.println (ay);
servo1.write (ay); */ 
ay=map (ay, 17000, -17000, 0, 180) ;
servo1.write(ay);
delay(200);

}

Tu peux mettre une valeur cible variable, le PID essayera de la suivre.

Justement je ne comprend vraiment pas quoi mettre comme cible variable. Et un autre problème vient quand je lance mon code avec PID : ça stabilise uniquement quand la plateforme est a 0° ou 180°

Lilou7812:
Le problème c'est que la valeur cible change tout le temps en fonction de l'angle que je donne à ma plateforme donc je ne sais pas quoi mettre

Tu sais donc comment la valeur cible change. Il suffit de mettre la nouvelle valeur cible dans la variable setPoint

Je pensais faire setpoint=map (ay, -17000, 17000, 0, 180) ; qui prendrait donc la même valeur que "input" mais bon en testant ça donne rien de bon

Lorsqu'on débute avec un PID, il est recommandé de ne s'occuper que de la composante Proportionnelle, puis de cette composante plus la composante Intégrale. En règle générale, la composante Dérivée est peu ou pas utilisée car bien plus complexe à ajuster.

Il y a ce tutoriel qui explique bien comment fonctionne un PID bien conçu:

http://brettbeauregard.com/blog/2011/04/improving-the-beginners-pid-introduction/

J'ai beau lire plusieurs articles sur le PID j'avoue que je bloque toujours autant sur comment l'implémenter à mon code ...

Bonjour

Exemple pour un chauffage (plus simple a expliquer pour moi):

double input; // c'est la temperature instantanné du volume/piece a chauffé.
double output; // c'est la puissance envoyé au radiateur.
double setpoint; // c'est la température demandé/ à atteindre.

le pid prend en compte le input et le setpoint pour moduler l'output pour réguler au plus prés

@+

Merci pour ces explications mais alors pourquoi quand je fais input=angle, setpoint=90, monServo.write(output), mon servo moteur fait n'importe quoi ?