Ecam-Eurobot / Eurobot-2017

Main repository containing code for the Eurobot 2017 contest
MIT License
2 stars 9 forks source link

Année 2018 - Amélioration du système de contrôle des moteurs #29

Open AlexisTM opened 7 years ago

AlexisTM commented 7 years ago

Afin d'améliorer le système de contrôle des moteurs, il est nécessaire de calculer la position du robot plutôt que de penser qu'il est arrivé. Il y aura toujours un certain drift, mais il se fera probablement que peu sentir sur 90 secondes.

Voici l'idée:

Variables globales:

double distance_between_wheels = 0.4; // in meters
double x = 0;
double y = 0;
double th = 0; // Th est aussi appelé heading, théta ou yaw
unsigned long last_computation = micros();

Boucle de calcul, à executer toutes les N millisecondes

loop every N milliseconds
    double dt = (micros() -  last_computation)/1000000.0; // Temps depuis le calcul précédent

    // Vitesses en m/s
    double v_right = speed_right_wheel;
    double v_left = speed_left_wheel;

    // vx : Vitesse frontale - m/s
    // vy : Vitesse latérale - m/s 
    // vth : Vitesse angulaire (autour de z) - radians/s
    double vx = (v_right + v_left)/2;
    double vy = 0
    double vth = (v_right - v_left) / distance_between_wheels;

    // Calculons la différence de position du robot (rotation)
    double delta_x = (vx * cos(th) - vy * sin(th)) * dt;
    double delta_y = (vx * sin(th) + vy * cos(th)) * dt;
    double delta_th = vth * dt;

    x = x + delta_x; // m
    y = y + delta_y; // m
    th = th + delta_th; // radians

Il est ensuite facile de calculer l'erreur de position et l'erreur angulaire pour la régulation.

ErrorX = setpoint.x - CurrentPosition.x
ErrorY = setpoint.y - CurrentPosition.y

# Error in forward direction of the robot
ErrorX_f = (cos(CurrentPosition.yaw) * ErrorX) + (sin(CurrentPosition.yaw) * ErrorY);
ErrorY_f = (-sin(CurrentPosition.yaw) * ErrorX) + (cos(CurrentPosition.yaw) * ErrorY);

ErrorTh = ErrorYaw = atan2( ErrorY_f, ErrorX_f)
charlesvdv commented 7 years ago

@AlexisTM quel est l'avantage de cette approche par rapport à l'utilisation des odomètres qui sont pour l'instant sur le robot ? Ton idée est en fait de créer un système INS ?

Les vitesses v_right et v_left ne peuvent être optenue (pour l'instant en tout cas) qu'en dérivant notre valeur de position sur un interval dt et ta manière consiste juste à intégré ces vitesses pour avoir la position. Nous revenons donc à notre point de départ et vu que la régulation change toutes les 10ms les consignes de vitesse, cela signifie que l'on va perdre en précision dans notre positionnement.

AlexisTM commented 7 years ago

C'est exactement ça. Tu utilises les odomètres pour déterminer les vitesses de chaque roue et obtenir la position.

En effet, il y a un drift, qui est inévitable, mais au final, tu gagneras en précision. En effet, en ne se basant que sur les odomètres, tu as une bonne précision localement mais globalement tu perds beaucoup de précision en "estimant être arrivé". Je te propose très simplement de mettre ce code côte à côte avec la régulation actuelle et observe le drift de la position. Sur 90 secondes et de si petites distances, ce sera minime.

De plus, réaliser la régulation de cette façon permet de faire un fusion de senseurs plus simple, par exemple en mettant un IMU et en utilisant un Extended Kalman Filter

Sur l'Arduino, la régulation bas niveau reste primordiale afin d'obtenir une vitesse correcte sur chacun des moteurs.