Table des matières:

Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC : 5 étapes
Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC : 5 étapes

Vidéo: Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC : 5 étapes

Vidéo: Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC : 5 étapes
Vidéo: Ne JAMAIS partir SANS SA COPINE 🫢 #humour #blague #drole #couplegoals #internationalcouple #shorts 2024, Novembre
Anonim
Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC
Comment interpréter le sens de rotation d'un commutateur rotatif numérique avec un PIC

L'objectif de ce Instructable est d'illustrer comment interfacer un commutateur rotatif numérique (codé en quadrature) avec un microcontrôleur. Ne vous inquiétez pas, je vais vous expliquer ce que le code en quadrature signifie pour nous. Cette interface et le logiciel qui l'accompagne permettront au microcontrôleur de reconnaître le sens de rotation à chaque passage d'un cran à un autre. crans au lieu des boutons haut/bas. L'idée était de permettre à l'utilisateur de « composer » la pression souhaitée. En conséquence, nous avons dû développer une routine logicielle pour obtenir les informations de position du commutateur et en déduire le sens de rotation afin d'incrémenter ou de décrémenter le point de consigne de pression pour le système principal. Dans ce Instructable, je vais couvrir l'interface physique au microcontrôleur, la théorie de fonctionnement du commutateur rotatif, la théorie de fonctionnement du logiciel ainsi que la routine de déduction. Enfin, je vais vous montrer mon application de la routine de déduction. Au fur et à mesure que nous progressons, j'essaierai de garder les choses un peu génériques afin que l'idée puisse être appliquée sur autant de plateformes que possible, mais je partagerai également ce que j'ai fait pour que vous puissiez voir une application spécifique.

Étape 1: Pièces

les pièces
les pièces

Pour mettre en œuvre cela, vous aurez besoin de:Un commutateur rotatif (codé en quadrature)Résistances de rappelPlateforme de microcontrôleur appropriéePour mon projet, j'ai utilisé un encodeur optique Grayhill 61C22-01-04-02. La fiche technique du commutateur rotatif demande des résistances de rappel de 8,2 k ohms sur les deux lignes de données provenant du commutateur. Vous voudrez vérifier la fiche technique de l'encodeur que vous choisissez d'utiliser. Le commutateur rotatif que j'ai utilisé peut également être commandé avec un bouton-poussoir axial. C'est une fonctionnalité utile pour valider des sélections qui ont été composées, etc. mais je ne parlerai pas de son interface ici. J'ai répertorié une "plate-forme de microcontrôleur appropriée" car (je pense) cela peut être implémenté sur plusieurs plates-formes. J'ai vu beaucoup de gens utiliser d'autres microcontrôleurs pour Instructables, donc je veux aussi montrer l'approche générale. J'ai écrit tout le code dans PIC Basic Pro pour une utilisation avec un Microchip PIC16F877A. Vraiment, l'élément clé dont vous avez besoin sur le microcontrôleur est la possibilité d'interrompre lorsqu'il y a un changement logique sur l'une des deux broches. Sur le PIC16F877A, cela s'appelle l'interruption de changement de PORTB. Il peut y avoir d'autres noms pour cela sur d'autres contrôleurs. Cette fonction d'interruption du microcontrôleur fait partie de ce qui rend cette implémentation si élégante.

Étape 2: Interface matérielle

Interface matérielle
Interface matérielle

Une solution "simple" serait d'avoir un interrupteur "unipolaire à 16 jets" avec 16 connexions au microcontrôleur. Chaque sortie de commutateur serait alors liée à une broche sur le microcontrôleur afin que chaque position de cadran puisse être vérifiée par le microcontrôleur. Il s'agit d'une utilisation excessive des broches d'E/S. Les choses empirent encore si nous voulons plus de 16 positions (détentes) à notre disposition sur le commutateur. Chaque position supplémentaire sur le commutateur nécessiterait une entrée supplémentaire pour le microcontrôleur. Cela devient rapidement une utilisation très inefficace des entrées sur un microcontrôleur. Entrez dans la beauté du commutateur rotatif. Le commutateur rotatif n'a que deux sorties vers le microcontrôleur répertoriées comme A et B sur la fiche technique. Il n'y a que quatre niveaux logiques possibles que ces lignes peuvent prendre: AB = 00, 01, 10 et 11. Cela réduit considérablement le nombre de lignes d'entrée que vous devez utiliser pour connecter le commutateur au microcontrôleur. Nous avons donc réduit le nombre de lignes d'entrée à seulement deux. Maintenant quoi? Il semble que nous ayons vraiment besoin de 16 états différents, mais ce nouveau commutateur n'en a que quatre. Est-ce qu'on s'est tiré une balle dans le pied ? Nan. Continuer à lire. Nous allons couvrir un peu la théorie derrière le fonctionnement du commutateur rotatif pour expliquer.

Étape 3: Théorie de fonctionnement du matériel

Théorie de fonctionnement du matériel
Théorie de fonctionnement du matériel
Théorie de fonctionnement du matériel
Théorie de fonctionnement du matériel
Théorie de fonctionnement du matériel
Théorie de fonctionnement du matériel

La détection du sens de rotation est possible à l'aide du commutateur "unipolaire à 16 jets" susmentionné, mais il utilise beaucoup d'entrées sur le microcontrôleur. L'utilisation du commutateur rotatif réduit le nombre d'entrées du microcontrôleur, mais nous devons maintenant interpréter les signaux provenant du commutateur et les traduire dans un sens de rotation. J'ai mentionné plus tôt que le commutateur était codé en quadrature. C'est aussi l'une des élégances clés de cette solution. Cela signifie qu'il y a un code à 2 bits que le commutateur donne qui correspond à la position du commutateur. Vous pensez peut-être: « S'il y a une entrée à deux bits dans le microcontrôleur, comment représentons-nous les 16 positions ? » C'est une bonne question. Nous ne les représentons pas tous. Il suffit de connaître les positions relatives du bouton pour pouvoir déterminer le sens de rotation. La position absolue du bouton n'a pas d'importance. Pour une rotation dans le sens des aiguilles d'une montre, le code que le commutateur donne se répète tous les quatre crans et est codé en gris. Le code gris signifie qu'il n'y a qu'un seul changement de bit pour chaque changement de position. Au lieu que l'entrée AB compte pour une rotation dans le sens des aiguilles d'une montre en binaire comme ceci: 00, 01, 10, 11, elle change comme ceci: 00, 10, 11, 01. Notez que pour ce dernier modèle, il n'y a qu'une seule entrée changeant entre ensembles. Les valeurs dans le sens inverse des aiguilles d'une montre pour l'entrée AB du microcontrôleur ressembleront à ceci: 00, 01, 11, 10. C'est simplement l'inverse du schéma dans le sens des aiguilles d'une montre avec AB = 00 répertorié en premier. Jetez un œil aux diagrammes pour une explication plus visuelle.

Étape 4: Théorie de fonctionnement du logiciel

Théorie de fonctionnement du logiciel
Théorie de fonctionnement du logiciel

La routine qui déduit le sens de rotation est pilotée par interruption. Le microcontrôleur que vous sélectionnez doit pouvoir interrompre chaque fois qu'il y a un changement sur l'une des (au moins) deux broches lorsque l'interruption est activée. C'est ce qu'on appelle l'interruption de changement de PORTB sur le PIC16F877A. Chaque fois que le commutateur est tourné, le microcontrôleur sera interrompu et l'exécution du programme sera envoyée à la routine de service d'interruption (ISR). L'ISR déterminera rapidement dans quel sens le commutateur a été tourné, définira un indicateur de manière appropriée et reviendra rapidement au programme principal. Nous avons besoin que cela se produise rapidement au cas où l'utilisateur tournerait le commutateur très rapidement. Nous savons que le motif AB codé en gris se répète toutes les quatre positions, donc si nous faisons fonctionner la routine pour les transitions entre ces quatre positions, cela fonctionnera pour toutes les autres. Notez que dans un cycle à quatre positions, il y a quatre arêtes. Un front montant et un front descendant pour l'entrée A ainsi que l'entrée B. Le microprocesseur sera interrompu à chaque fois qu'il y a un front, ce qui signifie que le microcontrôleur sera interrompu à chaque fois que le bouton est tourné. En conséquence, l'ISR doit déterminer dans quel sens le bouton a été tourné. Pour nous aider à comprendre comment procéder, nous nous tournons vers la forme d'onde pour une rotation dans le sens des aiguilles d'une montre. Notez que chaque fois que A a un front, sa nouvelle valeur est toujours différente de celle de B. Lorsque le bouton passe de la position 1 à 2, A passe de logique-0 à logique-1. B est toujours à 0 pour cette transition et ne correspond pas à la nouvelle valeur de A. Lorsque le bouton passe de la position 3 à 4, A a un front descendant tandis que B reste au niveau logique-1. Notez à nouveau que B et la nouvelle valeur de A sont différentes. À l'heure actuelle, nous pouvons voir qu'à chaque fois que A provoque l'interruption pendant la rotation dans le sens horaire, sa nouvelle valeur est différente de celle de B. Vérifions B pour voir ce qui se passe. B a un front montant lorsque le commutateur passe de la position 2 à 3. Ici, la nouvelle valeur de B est la même que A. En regardant le dernier front restant pour la rotation dans le sens des aiguilles d'une montre, B a un front descendant se déplaçant de la position 4 à 5. (La position 5 est la même que la position 1.) La nouvelle valeur de B est la même que A ici aussi ! Nous pouvons maintenant faire quelques déductions! Si A provoque l'interruption et que la nouvelle valeur de A est différente de celle de B, la rotation était dans le sens des aiguilles d'une montre. De plus, si B provoque l'interruption et que la nouvelle valeur de B est la même que A, alors la rotation était dans le sens des aiguilles d'une montre. Examinons rapidement le cas de la rotation dans le sens inverse des aiguilles d'une montre. Tout comme la rotation dans le sens horaire, la rotation dans le sens antihoraire provoquera quatre interruptions en un cycle: deux pour l'entrée A et deux pour l'entrée B. L'entrée A a un front montant lorsque le bouton passe de la position 4 à 3 et un front descendant passant de la position 2 à 1. Lorsque le bouton se déplace de la position 4 à 3, la nouvelle valeur de A est la même que la valeur de B. Notez que lorsque A se déplace de la position 2 à 1, sa nouvelle valeur est également la même que celle de B. Maintenant, nous pouvons voir que lorsque A provoque l'interruption et que sa nouvelle valeur correspond à celle de B, la rotation était dans le sens inverse des aiguilles d'une montre. Rapidement, nous allons regarder l'entrée B pour tout vérifier. B provoquera une interruption lorsque le bouton passera de la position 5 (qui est la même que 1) à 4 et lorsque le bouton passera de la position 3 à 2. Dans ces deux cas, la nouvelle valeur de B ne correspond pas à la valeur existante de A qui est le contraire des cas où B provoque l'interruption pour la rotation dans le sens horaire. C'est une bonne nouvelle. Tout se passe comme il se doit. Pour résumer, si A provoque l'interruption et que sa nouvelle valeur ne correspond pas à la valeur de B ou si B provoque l'interruption et que la nouvelle valeur de B correspond à la valeur de A, nous savons qu'il y a eu une rotation dans le sens des aiguilles d'une montre. Nous pouvons vérifier les autres cas de rotation dans le sens antihoraire dans le logiciel ou nous pouvons supposer que parce que ce n'était pas une rotation dans le sens horaire, c'était dans le sens antihoraire. Ma routine a simplement fait l'hypothèse.

Étape 5: Logiciel

Logiciel
Logiciel
Logiciel
Logiciel

Je n'ai pas utilisé les interruptions intégrées dans PIC Basic Pro. J'ai utilisé quelques fichiers que j'ai inclus dans mon code de Darrel Taylor pour piloter la routine. C'est là qu'un énorme crédit à Darrel appartient ! Les fichiers sont gratuits. Il suffit de visiter son site Web pour plus d'informations, d'autres applications et pour télécharger les fichiers. Vous pouvez ignorer cette partie si vous n'utilisez pas de PIC avec des interruptions Darrel Taylor. Configurez simplement les interruptions selon les besoins sur la plate-forme que vous utilisez. Pour configurer les interruptions Darrel Taylor (DT), il y a deux choses à faire: 1.) Incluez les fichiers DT_INTS-14.bas et ReEnterPBP.bas dans votre code.2.) Copiez et collez ceci dans votre macro code. ASMINT_LIST;IntSource, Label, Type, ResetFlag ? INT_Handler RBC_INT, _ISR, PBP, oui endm INT_CREATEENDASMInsérez des onglets et des espaces comme le graphique à la fin de l'Instructable afin que vous puissiez voir les choses un peu plus facilement dans votre code. Vous devrez le modifier légèrement pour l'adapter à vos besoins. Sous Étiquette, remplacez ISR par le nom du sous-programme qui est votre ISR. N'oubliez pas le soulignement ! Vous en avez besoin ! Pour que les interruptions fonctionnent, il y a deux autres choses à faire: 1.) Écrivez l'ISR. Vous allez écrire ceci comme vous alliez écrire un sous-programme PBP, sauf que vous devrez insérer @ INT_RETURN à la fin du sous-programme au lieu de RETURN. Cela accusera réception de l'interruption et ramènera l'exécution du programme là où elle s'était arrêtée dans la boucle principale. À l'intérieur de l'ISR, vous devez effacer l'indicateur d'interruption afin que votre programme ne soit pas pris dans une interruption récursive. Il suffit de lire PORTB pour effacer l'indicateur d'interruption sur le PIC16F877A. Chaque microcontrôleur différent a une manière différente d'effacer les drapeaux d'interruption. Consultez la fiche technique de votre microcontrôleur.2.) Lorsque vous atteignez le point dans votre code que vous souhaitez activer l'interruption, utilisez cette ligne de code:@ INT_ENABLE RBC_INTLorsque vous souhaitez désactiver l'interruption, utilisez simplement:@ INT_DISABLE RBC_INTIl y a beaucoup de choses emballées dans ce que je viens de couvrir, je vais donc résumer rapidement. Jusqu'à présent, votre programme devrait ressembler à ceci:; Toute configuration ou code INCLUDE "DT_INTS-14.bas" INCLUDE "ReEnterPBP.bas" macro ASMINT_LIST; IntSource, Label, Type, ResetFlag ? INT_Handler RBC_INT, _myISR, PBP, oui endm INT_CREATEENDASM; Toute autre configuration ou code nécessaire@ INT_ENABLE RBC_INT; Code qui doit savoir dans quel sens le bouton tourne@ INT_DISABLE RBC_INT; Autre codeEND; Fin du programme monISR:;Code ISR ici@ INT_RETURN (Table de configuration du gestionnaire d'interruptions) Je pense que c'est là que toute personne qui n'utilise pas d'interruptions PIC ou DT peut se joindre à nouveau. Maintenant, nous devons réellement écrire l'ISR pour que le microcontrôleur sache dans quel sens le bouton tourne. Rappelons de la section théorie du logiciel que nous pouvons déduire le sens de rotation si nous connaissons l'entrée qui a provoqué l'interruption, sa nouvelle valeur et la valeur de l'autre entrée. Voici le pseudocode: Lisez PORTB dans une variable scratch pour effacer l'indicateur d'interruption Vérifiez si A a causé l'interruption. Si vrai, comparez A et B. Vérifiez si différent, si différent, c'était la rotation dans le sens des aiguilles d'une montre Sinon, c'était dans le sens inverse des aiguilles d'une montre EndifVérifiez si B a causé l'interruption. Si vrai, comparez A et B Vérifiez si différent, si identique, c'était la rotation dans le sens horaire Sinon, c'était dans le sens antihoraire EndifReturn from interruptComment savons-nous si un changement sur A ou B a causé l'interruption ? Découvrir la nouvelle valeur de l'entrée modifiée et de l'autre entrée (inchangée) est facile car nous pouvons les lire à l'intérieur de l'ISR. Nous devons connaître l'état de chacun avant que l'exécution ne soit envoyée aux ISR. Cela se produit dans la routine principale. La routine principale s'assoit et attend qu'une variable d'octet que nous avons appelée CWflag soit définie sur 1 ou remise à 0 par l'ISR. Après chaque changement de bouton acquitté ou s'il n'y a pas d'activité de bouton, la variable est mise à 5 pour indiquer un état de repos. Si le drapeau est défini ou est effacé, la routine principale incrémente ou décrémente immédiatement la pression du point de consigne de manière appropriée en fonction de la rotation, puis remet la variable CWflag à 5 car le bouton est maintenant à nouveau inactif. Comme la routine principale vérifie le CWflag, elle documente également l'état des valeurs des commutateurs rotatifs A et B. C'est vraiment simple et ressemble à ceci:oldA = AoldB = BIl n'y a vraiment rien de super chic ici. Incluez simplement ces deux lignes au début de la boucle qui vérifie la rotation du drapeau CW. Nous mettons simplement à jour les valeurs logiques des entrées du bouton rotatif à l'intérieur de la boucle d'incrémentation/décrémentation dans la routine principale afin que nous puissions voir quelle entrée a causé l'interruption lorsque l'ISR est exécuté. Voici le code ISR: ABchange: scratch = PORTB ' Lire PORTB pour effacer le drapeau d'interruption ' Si A provoque l'interruption, vérifiez le sens de rotation de B SI oldA != A ALORS ' Si A et B sont différents, c'était la rotation dans le sens des aiguilles d'une montre SI A != B THEN GOTO CW ' Sinon, c'était une rotation dans le sens antihoraire ELSE GOTO CCW ENDIF ENDIF ' Si B provoque l'interruption, vérifiez le sens de rotation de A IF oldB != B THEN ' Si A et B sont identiques, il était une rotation dans le sens horaire IF A == B THEN GOTO CW ' Sinon, c'était une rotation dans le sens antihoraire ELSE GOTO CCW ENDIF ENDIFCW: CWflag = 1@ INT_RETURNCCW: CWflag = 0@ INT_RETURNI j'ai inclus le code ISR dans un fichier AB_ISR.bas parce que le les onglets dans le code ne s'affichent pas comme ils le devraient. Maintenant, parce que l'ISR a les anciennes valeurs pour les entrées A et B, il peut déterminer quelle entrée a causé l'interruption, la comparer à l'autre entrée (inchangée) et déterminer la direction de rotation. Tout ce que la routine principale a à faire est de vérifier le CWflag pour voir dans quelle direction le bouton a tourné (si c'est le cas) et d'incrémenter ou de décrémenter un compteur, un point de consigne ou tout ce que vous aimez ou avez besoin. J'espère que cela vous aide et que cela n'a pas été trop déroutant. Ce type d'interface est particulièrement utile si votre système utilise déjà des interruptions car ce n'est qu'une interruption de plus à ajouter. Prendre plaisir!

Conseillé: