Je conçois un clavier en VHDL. Tout fonctionne bien lorsqu'une seule touche est enfoncée. J'analyse chaque colonne pour une pression de touche dans une machine d'état et lorsqu'aucune touche n'est enfoncée, ce qui est la condition que pin4pin6pin7pin2 = "0000"
je passe à l'état suivant pour analyser la colonne suivante. J'ai donc défini les colonnes de pin3pin1pin5
manière séquentielle sur "001"
, "010"
et "100"
.
Pendant la numérisation au pin3pin1pin5
fur "001"
et à pin4pin6pin7pin2
mesure, "0100"
il suffit d'appuyer sur "9". Je déclare en VHDL pin4pin6pin7pin2
comme pin3pin1pin5
ports d' entrée et de sortie. Lorsque j'appuie sur 6 et 9 en même temps pin6
et le pin7
sont high
. La première touche enfoncée est lue, la seconde est ignorée. Lorsque j'appuie sur 3 et 7 en même temps, le premier appuyé avec quelques ms avant gagne et la première touche est lue, la deuxième touche est ignorée, pin2
et le pin4
sont high
.
Voici la partie délicate. Quand j'appuie sur 4 et 6 en même temps, je m'attends pin7
à l'être high
mais ça devient low
et pin4pin6pin7pin2 = "0000"
, ce que je ne comprends pas comment et pourquoi. Parce qu'il "0000"
est détecté comme aucune touche enfoncée, la machine d'état passe d'un état à l'autre. Tout en maintenant 4 et 6 si l'on pousse et laisse 4 plusieurs fois, il est détecté comme 6 pressé plusieurs fois, ce qui est un gros bug . Je serais heureux si vous pouviez m'aider à déboguer cela!
La même chose se produit avec "1" et "2", la même chose avec "7" et "8" uniquement pour les touches de la même ligne. Puisqu'il s'agit d'un projet en cours, je ne peux pas mettre mon code VHDL en ligne :( Je serais heureux si vous pouviez me donner des conseils pour surmonter cela!
Ci-dessous, je ne télécharge pas mon code sur la carte, aucun code n'est en cours d'exécution. Connexion Pin5
à la terre, une seule pression sur 1,2,4,5,7,8, *, 0 n'allume pas la Pin3
LED mais si je presse 6 et 4 en même temps, la Pin3
LED est Pin7
allumée et la LED est toujours allumée, mais lorsque mon code s'exécute, cela ne se produit pas. Peut-être que j'ai connecté quelque chose de mal et heureusement Pin7
, je ne sais pas ...
Voici les schémas de la carte du clavier:
la source
Réponses:
La réponse courte:
Inversez votre logique. Conduisez les lignes de sélection de colonne avec open-drain (ou open-collector) logique à où la colonne sélectionnée est tirée vers le bas et les colonnes non sélectionnées flottent. Lorsque vous regardez une ligne, une pression sur une touche est détectée par un «0». Les touches non pressées seront détectées par un «1».
Maintenant, les détails:
Comme le souligne EEIngenuity, lorsque vous appuyez sur 2 boutons dans la même ligne, il en résulte un court-circuit entre leurs colonnes correspondantes. Ce problème (et d'autres problèmes impliquant plusieurs pressions de touches) est généralement résolu dans une matrice de clavier en ajoutant une diode en série avec chaque commutateur.
Étant donné que l'ajout de diodes n'est pas une option pour vous, vous devrez faire flotter les sorties de vos sélections de colonne inactives pour éviter d'essayer de les conduire à la polarité opposée à votre sélection de colonne active. Cela se fait en utilisant une logique à drain ouvert. Si vos sélections de colonne sont directement liées à un CPLD ou FPGA, vous devriez être en mesure de le faire dans votre code VHDL.
La photo dans votre question montre que vous avez une résistance de rappel sur chaque colonne et chaque ligne. Les tractions sur les colonnes sont inutiles, mais ne feront rien de mal. Les tractions sur chaque rangée assureront un état élevé à moins qu'elles ne soient tirées vers le bas par le conducteur à drain ouvert sur les colonnes sélectionnées (via un interrupteur fermé).
J'ai dû faire quelques hypothèses sur votre circuit car vous n'avez pas fourni un schéma complet ou votre code VHDL. Vous dites
pourtant, sur la photo que vous fournissez, des résistances de rappel sont montrées. Cela implique que vous avez déjà une inversion logique quelque part, peut-être dans votre code VHDL ou (moins probablement) des onduleurs entre vos lignes et votre périphérique logique (CPLD ou FPGA).
Éditer:
Selon votre commentaire, vous utilisez une logique négative dans vos descriptions: "0000" indique que les quatre broches sont hautes, etc. suivez mes instructions ci-dessus en utilisant une logique à drain ouvert pour les sorties de sélection de colonne dans votre FPGA.
Je ne suis pas un expert VHDL, mais j'ai trouvé cela chez Xilinx :
Notez également dans votre schéma que toutes les LED sont montrées câblées à l'envers. Les anodes vont aux résistances de limitation de courant et les cathodes aux lignes de signaux. Les LED s'allument lorsque les lignes de signal sont baissées.
la source
pin4pin6pin7pin2 = "0000"
qu'aucune touche n'est en fait1111
. Dans ma question, 1s devrait être 0, 0 devrait être 1, j'ai essayé deout <= 'pin3' when din='1' else '0';
Puisque vous utilisez VHDL et que vous avez une entrée asynchrone, j'écris cette réponse pour vous assurer d'avoir pris une précaution. Je ne sais pas si c'est votre problème, mais cela pourrait très bien l'être.
Voir une question que j'ai posée il y a quelque temps: VHDL: le module de réception échoue de manière aléatoire lors du comptage des bits
Maintenant, vous dites que:
Ce qui est un peu similaire à ce à quoi je faisais face. J'ai eu un problème où ma machine d'état sautait des états, ce qui semblait impossible.
Si vous lisez les réponses à la question liée ci-dessus, vous verrez qu'il est recommandé d'ajouter un synchroniseur à la ligne d'entrée avant qu'il ne soit introduit dans votre machine d'état. Ceci est généralement accompli avec deux tongs D en série:
Ne pas synchroniser l'entrée de votre bouton avec votre matériel provoque des problèmes très bizarres, que j'ai rencontrés avec mon projet N64. Ajouter ce petit morceau de HW était presque comme par magie.
Veuillez donc d'abord vérifier que vos entrées sont synchronisées.
la source
async_in
est retardé de 3 cycles d'horloge mais sa valeur et tout est le même?C'est une question intéressante! La raison pour laquelle vous voyez un minimum sur la broche 7 lorsque vous appuyez sur les touches 4 et 6 est due aux broches 3 et 5.
Pour expliquer davantage, les broches 3 et 5 ne seront jamais élevées en même temps - l'une d'entre elles sera toujours un chemin vers la terre (selon votre conception). Ainsi, lorsque vous appuyez sur les touches 4 et 6, vous créez un chemin vers la terre pour la broche 7.
Voir l'image:
la source