Help...

Toutes les discussions sur l'Arduino !

Modérateur : MOD

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Help...

Message par papou89 » ven. 05 déc. 2014, 16:32

J'ai commencé à travailler sur mon pgm (commande d'un pont tournant).
La commande sera faite par un code-disque (0-15).
J'ai prévu une wait loop où on attend une nouvelle commande, différente de l'actuelle position du pont (0-15).
J'ai fait un montage de test avec 2 poussoirs qui me permettent de coder la commande (0-3). Ça marche, j'affiche bien ces 4 valeurs.
Où ça ne va plus, c'est quand je veux créer ma boucle :
Pour les valeurs 0, 1, 2, on sort du while, même quand pont=CMDE, et on édite pont=2 CMDE=2, ou 0, ou 1...
Il n'y a que pour la valeur 3 que ça marche et que j'édite les =...

Code : Tout sélectionner

#define CMDE ~PINB & 0X03       //Port B, on = LOW
byte pont=0;

void setup() {
 DDRD=B00111111;                // pins 8 & 9 input
 Serial.begin (9600);
}

void loop() {
 while (CMDE==pont) {Serial.println ("= ");delay (500);};

 Serial.print ("Pont = ");Serial.print (pont);  
 Serial.print ("   CMDE = ");Serial.println (CMDE);
 pont=CMDE; 
 delay (500);
 }

J'ai du me planter quelque part, mais je ne vois pas où. Quelqu'un à une idée ?

(Le basique, c'était plus simple !.. :gne: )

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Re: Help...

Message par papou89 » ven. 05 déc. 2014, 16:48

Correction : dans la 1ère ligne du set-up, lire DDRB=11111100...
Mais c'est pareil !.. :cry:

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » ven. 05 déc. 2014, 17:17

Hello,

Je ne saisi pas l'utilité du ";" a la fin de la phrase suivante ?

while (CMDE==pont) {Serial.println ("= ");delay (500);};

:roll:

Si je traduis le While :

Tant que CMDE égale la pont :

j'écrit, j'attend, j'écrit encore plein de chose ....

Et CMDE prend la valeur de pont ???????
Cordialement,

Christian.

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Re: Help...

Message par papou89 » ven. 05 déc. 2014, 18:29

Oui, t'as raison, le ; est de trop... Mais c'est pareil sans...

Le principe, c'est de dire que tant que pont=CMDE, on attend. Pour visualiser, j'édite des =.
Quand CMDE change au panneau de commande (code disque) on exécute les instructions du bas, qui plus tard commanderont la rotation du pont, jusqu'à ce que le pont atteigne la voie portant le code du code disque, soit pont=CMDE et on retourne dans la boucle while. Etc...
Mais, en test, on ne retourne dans la boucle que si pont=CMDE=3 ! :gne:

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » ven. 05 déc. 2014, 18:42

:gne:

Sur le bout de programme que tu a mis, "pont" a la valeur de 0

Mais quel est la valeur de CMDE au début de la boucle ?
Cordialement,

Christian.

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Re: Help...

Message par papou89 » ven. 05 déc. 2014, 19:10

La valeur de CMDE est donnée par les 2 bits du port B, pins 8&9. Pour le montage de test ce sont 2 poussoirs (off=5v, on=0v).
Donc au départ, CMDE=0 tant que l'on a pas appuyé sur un poussoir.

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » ven. 05 déc. 2014, 19:21

Ok, mais où initialise tu CMDE a 0 ?
Cordialement,

Christian.

Avatar du membre
jlb
Fécond
Messages : 694
Enregistré le : jeu. 04 oct. 2012, 16:38
Echelle pratiquée : N
Prénom : Jean-Luc
Site Internet : http://modelleisenbahn.triskell.org

Re: Help...

Message par jlb » ven. 05 déc. 2014, 19:57

Bonsoir,

Je ne comprends pas tout à fait ce que tu veux faire

Tu as deux broches qui te servent à donner une valeur de 0 à 3. Mais tu parles également de poussoirs raccordées à ces deux broches.

Or les poussoirs donnent une commande fugace. Par conséquent il est normal qu'après une pression qui donne une valeur différente de 3 (valeur qui est la valeur de repos et donc la seule stable), on sorte de la boucle dès que le ou les poussoirs sont relâchés. Par ailleurs il est probables que les rebonds donnent des comportement erratiques.

À mon humble avis l'interface homme machine n'est pas adaptée à un pont tournant.

Concernant le ; seul, ça ne gêne en rien, le ; étant un séparateur d'instructions, la présence d'un ; supplémentaire engendre une instruction vide que le compilateur retire car sans objet.
Modifié en dernier par jlb le ven. 05 déc. 2014, 21:04, modifié 2 fois.

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » ven. 05 déc. 2014, 21:01

C'est ce que je pensais aussi, c'est pourquoi je passe toujours par une variable et un delay(50). :siffle:
Cordialement,

Christian.

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Re: Help...

Message par papou89 » ven. 05 déc. 2014, 21:16

Ce que je veux faire est simple :
Une wait loop où l'Arduino attend une nouvelle commande (while loop). Quand le pont est arrêté, c'est que son adresse est égale à celle de commande (pont=CMDE).
Quand quelqu'un (moi?) tourne le bouton de commande, le code disque présente une nouvelle adresse : CMDE != pont, on sort de la while loop et on effectue les instructions suivantes (rotation du pont).

Pour le moment, en test, je n'utilise que les CMDE 0-3. J'ai mis des poussoirs parce que c'est plus pratique. J'édite les résultats pour voir si ma boucle se comporte comme je le veux. S'il y a des rebonds, c'est pas grave, j'éditerai quelques lignes à tort, mais avec le delay que j'ai mis...

Mon problème est que la boucle ne se comporte pas comme je le veux :
Au démarrage, j'édite plein de lignes pont=0 CMDE=0... Je devrais rester dans la while loop et éditer des =.
Si j'appuie sur le 1er poussoir, j'édite pont=0 CMDE=1, puis pont=1 CMDE=1, et là je devrais revenir dans la while loop et éditer des =... Que nenni, je continue à éditer la même ligne !
2ème poussoir pareil : pont=2 CMDE=2.
Il n'y a que quand j’appuie sur les 2 poussoirs en même temps que j'ai pont=2 CMDE=3, suivi d'une flopée de = .
Si je relâche le 1er poussoir, j'ai pont=3 CMDE=2, puis pont=2 CMDE=2, et je continue à éditer cette ligne au lieu de retourner dans la while loop...

Y'a quelque chose que je n'ai pas compris...

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » ven. 05 déc. 2014, 21:27

Et si tu essayait, tout simplement, avec l'instruction IF ?

Tu incrémente ou décrémente une variable selon ton besoin (n° de la voie que tu veut comme destination) tu calcule le nombre de voies que tu doit passer et op, en route mimille tourne la plaque. :roll:
Cordialement,

Christian.

Avatar du membre
jlb
Fécond
Messages : 694
Enregistré le : jeu. 04 oct. 2012, 16:38
Echelle pratiquée : N
Prénom : Jean-Luc
Site Internet : http://modelleisenbahn.triskell.org

Re: Help...

Message par jlb » ven. 05 déc. 2014, 21:47

ok je vois

C'est encore un coup du pré processeur C. J'avais signalé les pb de l'utilisation des #define à tort et à travers il y a quelques semaines. Le cours de COURSERA est passé par là entre-temps. Ce qu'on y apprends est en général bien sauf en ce qui concerne les bonnes pratiques de programmation en C.

Tu as utilisé un #define pour rendre équivalent CMDE à ~PINB & 0x03

Dans ton while tu utilises la condition CMDE == pont

Le pré processeur expanse CMDE en ~PINB & 0x03. La condition est donc :

~PINB & 0x03 == pont

Or l'opérateur == est plus prioritaire que l'opérateur &.

Donc 0x03 == pont est évalué en premier. Si pont vaut 3 cette expression vaut 1 sinon elle vaut 0. Ensuite le & est fait entre ce résultat et ~PINB.

C'est un piège classique. À cause du pré processeur, ce que tu écris semble avoir un sens différent de ce qui est en réalité.

Pour résoudre ton problème, ajoute des parenthèses :

#define CMDE (~PINB & 0x03)

De cette manière tu forces l'exécution du & avant l'exécution du ==

papou89
Papotier
Messages : 199
Enregistré le : lun. 29 nov. 2010, 20:58

Re: Help...

Message par papou89 » sam. 06 déc. 2014, 08:44

:applause: et merci JLB, ça marche !...

Pour ce genre de problème, tu ne peux pas trouver si tu ne connais pas les subtilités du pré-processeur... :gne:

A suivre.

Avatar du membre
likiki
Éloquent
Messages : 302
Enregistré le : dim. 29 avr. 2012, 15:21
Echelle pratiquée : H0 3R
Prénom : Christian
Site Internet : http://passionnement.forumactif.org
Localisation : Corbeil Essonne
Âge : 52

Re: Help...

Message par likiki » sam. 06 déc. 2014, 09:29

C'est juste une priorité mathématique en faite.

Moi j'ai une petite question messieurs, que veut dire littéralement ceci :

" ~PINB & 0x03 " ???

Parce que là je sèche.

:ange:
Cordialement,

Christian.

Avatar du membre
jlb
Fécond
Messages : 694
Enregistré le : jeu. 04 oct. 2012, 16:38
Echelle pratiquée : N
Prénom : Jean-Luc
Site Internet : http://modelleisenbahn.triskell.org

Re: Help...

Message par jlb » sam. 06 déc. 2014, 09:39

PINB est la valeur sur 8 bits correspondant à l'état des broches du port B de l'ATMega 328, ce qui correspond aux broches 8 à 13 sur les 6 bits de poids faible (8 sur le bit 0, 13 sur le bit 5). Les 2 bits de poids fort (6 et 7) ne sont pas utilisables.

le ~ est l'opérateur de complémentation, le not

le & est l'opérateur de ET bit à bit

0x03 est la valeur 3 en hexa, 3 en décimal aussi. En binaire ça correspond à 00000011

Donc ont lit les bits des broches du port B, on les inverse et on masque en ne gardant que les deux bits de poids faible. On récupère donc une valeur de 0 à 3 qui reflète l'état des broches 8 et 9 de l'Arduino.

Répondre