Cours:MindstormStructuresDeControle
Retour à la liste des Tps
Vous trouverez sur la page listant les énoncés de TP un lien vers l'ensemble des fonctions spécifique à la programmation de la brique lego EV3.
Sommaire
Travail préparatoire : affichage de variable
Nous avons vu comment déclarer et donner une valeur à une variable de type entier dans le 1er TP, exemple :
int a = 5;
Il est intéressant d'afficher sa valeur avec la fonction LcdPrintf. Pour cela, on prépare le texte souhaité, et on place %d dans la chaîne de caractère (délimitée par des " ") à l'endroit où on souhaite afficher la valeur de la variable. On ajoute ensuite un paramètre dans l'appel de fonction.
Bon c'est plus simple avec un exemple :
#include <ev3.h>
int main(void)
{
// on déclare une variable prix
int prix = 100;
InitEV3();
LcdPrintf(1, "le produit coute %d euros\n", prix);
Wait(SEC_5);
FreeEV3();
return 0;
}
On peut afficher la valeur de plusieurs variables en ajoutant des %d :
#include <ev3.h>
int main(void)
{
// on déclare 2 variables prixDepart et redution
int prixDepart = 100;
int reduction = 10;
InitEV3();
LcdPrintf(1, "le produit coute %d euros avant reduction, la remise est de %d euros\n", prixDepart, reduction);
Wait(SEC_5);
FreeEV3();
return 0;
}
On peut bien sûr effectuer des opérations sur les variables , par exemple :
...
int prixDepart = 100;
int reduction = 10;
// on n'affecte pas de valeur, on va la calculer par la suite
int prixFinal;
// modification de la valeur de la variable prixFinal :
prixFinal = prixDepart - reduction;
...
Modifier votre programme pour qu'il affiche le prix avant et après réduction.
- déclare 2 variables :
- a de valeur 5
- b de valeur 6
- calcul le produit et met le résultat dans une variable resultat
- affiche le calcul effectué et le résultat
Affichage de l'état d'un capteur
Tout système possède des entrées et des sorties.
Les sorties sont les actionneurs et génèrent donc une action :
- produire un son
- émettre de la lumière
- produire une action mécanique
- ...
Les entrées permettent d’interagir avec l'environnement et l'utilisateur, ils observent/mesurent quelque chose :
- capteur de contact/collision
- microphone
- capteur de couleur
- ...
Sur la brique programmable EV3, le nom des connecteurs donne la fonction :
- 1 2 3 4 : ce sont les entrées
- A B C D : ce sont les sorties
Principe pour 1 capteur
Les capteurs pouvant être connectés sur la brique EV3 étant tous différents, il est nécessaire d'indiquer sur quelle broche nous avons connecté le/les capteur(s) utilisé(s).
Pour cela vous devez utilisez la fonction :
setAllSensorMode
Le détail de cette fonction sera à consulter dans la documentation.
Voici un exemple d'utilisation à suivre pour tester le capteur de contact ( touch sensor in English !) :
#include <ev3.h>
int main(void)
{
// on déclare une variable etatTouchSensor pour "enregistrer" l'état du capteur
int etatTouchSensor = 0;
InitEV3();
// on configure la sortie 1 comme capteur de contact
// et les sorties 2,3,4 sont indiquées sans capteur (NO_SEN)
setAllSensorMode(TOUCH_PRESS, NO_SEN, NO_SEN, NO_SEN);
// on peut alors lire l'état du capteur sur l'entrée 1
// et mettre sa valeur dans la variable etatTouchSensor
etatTouchSensor = readSensor( IN_1 );
// on affiche alors sa valeur
LcdPrintf(1, "valeur du capteur : %d \n", etatTouchSensor);
Wait(SEC_5);
FreeEV3();
return 0;
}
A vous
Vous voici près à lire l'état des différents capteurs.
En vous servant du tableau avec la liste des entrées sur la page des énoncés, modifier votre programme pour observer l'état des différents capteurs
Remarque :
- Pensez à changer le nom de la variable en fonction du nom du capteur
- Vous pouvez bien sûr lire l'état de tous les capteurs dans le même programme
- Vous pouvez lire plusieurs fois l'état du même capteur dans votre programme :
...
etatTouchSensor = readSensor( IN_1 );
LcdPrintf(1, "valeur du capteur : %d \n", etatTouchSensor);
Wait(SEC_5);
// on recommence :
etatTouchSensor = readSensor( IN_1 );
LcdPrintf(1, "valeur du capteur : %d \n", etatTouchSensor);
Wait(SEC_5);
// on recommence :
etatTouchSensor = readSensor( IN_1 );
LcdPrintf(1, "valeur du capteur : %d \n", etatTouchSensor);
Wait(SEC_5);
// on recommence :
...
Structure de contrôle
Structure de répétition
La structure de répétition en informatique s'appelle une boucle. La boucle est le seul moyen de remonter vers le début (plutôt vers le haut) d'un programme ! La boucle permet donc de refaire les choses plusieurs fois.
Lorsque vous désirez faire les choses plusieurs fois vous êtes dans deux situations différentes qui appellent une solution différente :
- vous savez d'avance combien de fois vous voulez répéter la boucle
- vous ne savez pas combien de fois vous voulez exécuter la boucle mais vous connaissez une condition (booléenne) à son arrêt
Nous allons traiter ces deux situations maintenant les unes après les autres.
répéter x fois
Principe
Nous sommes typiquement dans le cas où on connaît le nombre de boucles que l'on veut faire. C'est x. Pour être précis, le nombre en question peut être dans une variable.
- je connais le nombre et je l'écris directement. Regardez le 5 ci-dessous, pour l'écrire il faut le connaître !
int i;
...
for (i=0;i<5;i++) {
// faire quelque chose 5 fois
}
...
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!! Pas de ; après le for !!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
- je sais que le nombre de répétitions est dans une variable
int i,nbIterations;
...
nbIterations=10;
...
for (i=0;i<nbIterations;i++) {
// faire quelque chose nbIterations fois avec nbIterations= 10 dans le cas présent
}
...
Travail à faire
On utilisera dans cette partie le capteur de couleurs (Light sensor dans le mode COL_REFLECT)
Modifier votre programme précédent pour utiliser une "boucle for" à la place de réécrire plusieurs fois la même chose dans votre programme :
#include <ev3.h>
int main(void)
{
// on déclare une variable niveauGris pour "enregistrer" l'état du capteur
int niveauGris = 0;
int i;
InitEV3();
setAllSensorMode(....);
for (i=0;i<???;i++) {
niveauGris = ....;
LcdPrintf(1, ..... );
Wait(SEC_5);
}
FreeEV3();
return 0;
}
Même si le robot ne bouge pas, la valeur retournée par le capteur peut varier (bruit de mesure ....). Il est donc intéressant d'effectuer une moyenne des valeurs retournées :
- initialiser une variable somme
- répéter plusieurs fois
- faire une nouvelle mesure
- ajouter la nouvelle valeur à la variable somme
- calculer la moyenne : somme/nbItérations
Ecrire un programme qui affiche la moyenne de 5 mesures sur le capteur, puis de 10 mesures
faire ... tant que
L'écriture est la suivante :
...
do {
// faire quelque chose plusieurs fois jusqu'à ce que la condition devienne fausse.
// dis autrement
// faire quelque chose plusieurs fois tant que la condition est vraie
} while( condition );
Un exemple plus concret :
....
do {
etatCapteur = ....;
.....
} while ( etatCapteur != 100);
....
On recommence la lecture du capteur tant que sa valeur est différente de 100.
Les opérateurs de comparaisons sont :
Opérateur | Utilisation | Signification |
---|---|---|
== | ( a == b ) | vrai si a et b identiques |
!= | ( a != b ) | vrai si a et b différents |
> | ( a > b ) | vrai si a supérieur strict à b |
< | ( a < b ) | vrai si a inférieur strict à b |
>= | ( a >= b ) | vrai si a supérieur ou égal à b |
<= | ( a <= b ) | vrai si a inférieur ou égal à b |
&& | ( (condition1) && (condition2) ) | vrai si la condition1 et la condition2 sont vraies en même temps |
|| | ( (condition1) || (condition2) ) | vrai si au moins une des 2 conditions est vrai |
Travail à faire
On utilisera ici le capteur de contact.
- affiche le message "demarrage du programme"
- répète en boucle
- lire l'état du capteur de contact
- affiche la valeur du capteur
- attend 0,5s
- tant que le robot ne touche pas un obstacle
- affiche le message "obstacle rencontré
Une fois ce fonctionnement obtenu, modifier votre programme pour que le robot s'arrête lorsqu'il touche un obstacle :
- mettre les moteurs en marche
- répéter
- lire le capteur
- tant qu'il n'y a pas d'obstacles
- arrêter les moteurs
Modifier votre programme pour que le robot avance tant qu'il se trouve sur une surface blanche et s'arrête lorsqu'il se trouve sur du noir.
Remarque : Essayer les 2 modes pour le capteur : COL_COLOR ou COL_REFLECT
Structure de test
if ... else
La structure de test est un élément indispensable en informatique.
Il s'agit, suivant une condition, d'effectuer une action ou une autre :
....
if ( condition ) {
//action si condition est vraie
}
else {
//action si condition est fausse
}
...
On peut éventuellement faire des tests successifs en utilisant un "else if"
....
if ( condition1 ) {
//action si condition1 est vraie
}
else if ( condition2 ) {
//action si condition2 est vraie
}
else if ( condition3 ) {
//action si condition3 est vraie
}
else if....
else {
// action dans tous les autres cas
}
...
Il n'y a pas de limite au nombre de "else if" utilisé
1er test
On souhaite afficher un message indiquant l'état du capteur de contact.
La plupart des programmes que nous écrirons auront la structure suivante :
#include <ev3.h>
int main(void)
{
//variables
InitEV3();
//initialisation capteurs ...
do {
// on répète ces instructions jusqu'à la fermeture du programme
...
} while (condition pour continuer le programme);
FreeEV3();
return 0;
}
Commençons par écrire un programme qui se quitte lorsqu'on appuie sur un bouton.
Il va vous falloir utiliser au choix :
- ButtonIsUp
- ButtonIsDown
Ecrire un programme qui se termine lorsqu'on appuie sur le bouton Center (BTNCENTER)
Maintenant que nous pouvons terminer notre programme facilement, nous allons pouvoir afficher l'état d'un capteur :
Ecrire un programme qui affiche le cas échéant (en fct du capteur de contact :
- obstacle détecté
- pas d'obstacle
Remarque : pensez à mettre un wait pour limiter la vitesse d'affichage
Programme plus avancé
On souhaite utiliser 2 capteurs :
- le capteur d'obstacle qui permettra d'arrêter le programme lorsque le robot touche qqch
- le capteur de couleur
Chaque fois que le capteur arrive sur une ligne noire, il devra faire 1/2tour, sinon il doit avancer en ligne droite.