Matrice 5x5 sur un Joystick

Bonjour à tous,

Je suis actuellement entrain de fabriquer une ButtonBox pour Simracing. Mon projet n'est pas très compliqué, c'est juste que je n'ai aucune notion de code Arduino... J'ai essayé de me documenter à droite à gauche cette semaine...

J'ai donc avec moi une platine avec 25 Boutons poussoirs.
De ce que j'ai pu comprendre, le plus simple était d'utiliser une librairie "Joystick" qui était capable sur Arduino ProMicro d'accueillir 32 boutons.
Du coup je suppose qu'il "suffit" de coder une matrice 5x5 pour obtenir mes 25 actions sur mon "Joystick" non ?

J'ai fouillé à droite a gauche j'en suis arrivé à ce stade :

#include <Joystick.h>

#define NUMROWS 5
#define NUMCOLS 5

byte buttons[NUMROWS][NUMCOLS] = {
  {0,1,2,3,4},
  {5,6,7,8,9},
  {10,11,12,13,14},
  {15,16,17,18,19},
  {20,21,22,23,24},
};

Donc avec ça, si j'ai bien compris, ça "appelle" la librairie Joystick, puis ça fabrique une matrice 5x5.

Désolé si les termes que j'emploi sont pas les bons...

Quelqu'un serait capable de m'aider à finir ce code ? Tout ce que je veux c'est juste un Joystick avec 25 Actions...

Merci d'avance à tous,

Dellta

Je pense (rien de sûr) que ce code est fait pour commander une matrice de boutons de ce type (schéma électrique à gauche) :


Est-ce que ta matrice ressemble (électriquement parlant) à ça ?
Si oui, tu trouveras la bibliothèque ici et les exemples te permettront de comprendre comment l'utiliser. Tu peux commencer par adapter l'exemple HelloKeypad.ino :

#include <Keypad.h>

const byte ROWS = 5; //five rows
const byte COLS = 5; //five columns
char keys[ROWS][COLS] = {
  {'1','2','3','4,'5'},
  {'7','7','8','9','A'},
  {'B','C','D','E','F'},
  {'G','H','I','J','K'}
};
byte rowPins[ROWS] = {6, 5, 4, 3, 2}; //connect to the row pinouts of the keypad
byte colPins[COLS] = {11, 10, 9, 8, 7}; //connect to the column pinouts of the keypad

Keypad keypad = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );

void setup(){
  Serial.begin(9600);
}
  
void loop(){
  char key = keypad.getKey();
  if (key) Serial.println(key);
}

Merci Beaucoup pour votre réponse,

Effectivement on Schéma de branchement ressemble à cela en 5x5 (photo en PJ).

Je voulait éviter de passer par une interface Keypad car j'ai déjà un module sur mon logiciel de simulation qui passe par un pavé numérique.
Et je pense que faire 2 Button-Box avec un Keypad provoque des interférences car les deux essayent de parler avec avec le même code...
Je voulais passer par un Joystick mais je pense que le code reste le même non ?

Je devrais arriver sur cette page (voir photo en PJ) une fois mon code compilé dans mon Arduino.

(je n'arrive pas a insérer de photo dans mon post...)

Salutations,

Dellta

Cablage.PNG

Joystick.PNG

Cablage.PNG

Joystick.PNG

C'est quoi pour toi un joystick ?

Une fois compilé dans mon arduino, mon pc reconnaît un game controller.

Il y a un exemple ici :

Je crois qu'il y a méprise. L'Arduino Leonardo et le Micro peuvent communiquer avec un PC via le port USB et sont reconnus par le PC comme un périphérique USB. C'est cette capacité qui est utilisée ici pour que l'Arduino envoie des informations (par exemple le numéro d'un bouton poussoir enfoncé) au PC.

Que veux-tu faire exactement ?
L'Arduino sera t-il juste une interface entre la matrice de boutons et le PC, qui fera tourner un autre programme ? Et ce programme agira en fonction des boutons enfoncés ?

Merci pour ton aide,

Effectivement, l'arduino sera une interface entre la matrice et le PC. Le but est de pouvoir utiliser une action sur mon Arduino pour la transmettre à un simulateur.

En faite j'associe dans mon simulateur : une action (ex : allumer les phares) à une touche
Je pourrais l'associer à une touche de clavier mais ce n'est pas pratique...
Du coup je fabrique un contrôleur de jeu a partir d'un Arduino pour pouvoir associer mon action a un bouton poussoirs branché sur un Arduino.

J'utilise une matrice seulement car je n'ai pas assez d'entrés sur mon Arduino pour en avoir 1 par boutons.

J'ai un peu regardé à droite à gauche, j'ai réussi à avoir un code qui se compile super bien et qui fonctionne pour 25 boutons poussoirs et 4 encodeurs rotatifs.

#include <Keypad.h>
#include <Joystick.h>

#define ENABLE_PULLUPS
#define NUMROTARIES 4
#define NUMBUTTONS 25
#define NUMROWS 5
#define NUMCOLS 5


byte buttons[NUMROWS][NUMCOLS] = {
  {0,1,2,3,4},
  {5,6,7,8,9},
  {10,11,12,13,14},
  {15,16,17,18,19},
  {20,21,22,23,24},
};

struct rotariesdef {
  byte pin1;
  byte pin2;
  int ccwchar;
  int cwchar;
  volatile unsigned char state;
};

rotariesdef rotaries[NUMROTARIES] {
  {0,1,24,25,0},
  {2,3,26,27,0},
  {4,5,28,29,0},
  {6,7,30,31,0},
};

#define DIR_CCW 0x10
#define DIR_CW 0x20
#define R_START 0x0

#ifdef HALF_STEP
#define R_CCW_BEGIN 0x1
#define R_CW_BEGIN 0x2
#define R_START_M 0x3
#define R_CW_BEGIN_M 0x4
#define R_CCW_BEGIN_M 0x5
const unsigned char ttable[6][4] = {
  // R_START (00)
  {R_START_M,            R_CW_BEGIN,     R_CCW_BEGIN,  R_START},
  // R_CCW_BEGIN
  {R_START_M | DIR_CCW, R_START,        R_CCW_BEGIN,  R_START},
  // R_CW_BEGIN
  {R_START_M | DIR_CW,  R_CW_BEGIN,     R_START,      R_START},
  // R_START_M (11)
  {R_START_M,            R_CCW_BEGIN_M,  R_CW_BEGIN_M, R_START},
  // R_CW_BEGIN_M
  {R_START_M,            R_START_M,      R_CW_BEGIN_M, R_START | DIR_CW},
  // R_CCW_BEGIN_M
  {R_START_M,            R_CCW_BEGIN_M,  R_START_M,    R_START | DIR_CCW},
};
#else
#define R_CW_FINAL 0x1
#define R_CW_BEGIN 0x2
#define R_CW_NEXT 0x3
#define R_CCW_BEGIN 0x4
#define R_CCW_FINAL 0x5
#define R_CCW_NEXT 0x6

const unsigned char ttable[7][4] = {
  // R_START
  {R_START,    R_CW_BEGIN,  R_CCW_BEGIN, R_START},
  // R_CW_FINAL
  {R_CW_NEXT,  R_START,     R_CW_FINAL,  R_START | DIR_CW},
  // R_CW_BEGIN
  {R_CW_NEXT,  R_CW_BEGIN,  R_START,     R_START},
  // R_CW_NEXT
  {R_CW_NEXT,  R_CW_BEGIN,  R_CW_FINAL,  R_START},
  // R_CCW_BEGIN
  {R_CCW_NEXT, R_START,     R_CCW_BEGIN, R_START},
  // R_CCW_FINAL
  {R_CCW_NEXT, R_CCW_FINAL, R_START,     R_START | DIR_CCW},
  // R_CCW_NEXT
  {R_CCW_NEXT, R_CCW_FINAL, R_CCW_BEGIN, R_START},
};
#endif

byte rowPins[NUMROWS] = {21,20,19,18,15}; 
byte colPins[NUMCOLS] = {14,16,10,9,8}; 

Keypad buttbx = Keypad( makeKeymap(buttons), rowPins, colPins, NUMROWS, NUMCOLS); 

Joystick_ Joystick(JOYSTICK_DEFAULT_REPORT_ID, 
  JOYSTICK_TYPE_JOYSTICK, 32, 0,
  false, false, false, false, false, false,
  false, false, false, false, false);

void setup() {
  Joystick.begin();
  rotary_init();}

void loop() { 

  CheckAllEncoders();

  CheckAllButtons();

}

void CheckAllButtons(void) {
      if (buttbx.getKeys())
    {
       for (int i=0; i<LIST_MAX; i++)   
        {
           if ( buttbx.key[i].stateChanged )   
            {
            switch (buttbx.key[i].kstate) {  
                    case PRESSED:
                    case HOLD:
                              Joystick.setButton(buttbx.key[i].kchar, 1);
                              break;
                    case RELEASED:
                    case IDLE:
                              Joystick.setButton(buttbx.key[i].kchar, 0);
                              break;
            }
           }   
         }
     }
}


void rotary_init() {
  for (int i=0;i<NUMROTARIES;i++) {
    pinMode(rotaries[i].pin1, INPUT);
    pinMode(rotaries[i].pin2, INPUT);
    #ifdef ENABLE_PULLUPS
      digitalWrite(rotaries[i].pin1, HIGH);
      digitalWrite(rotaries[i].pin2, HIGH);
    #endif
  }
}


unsigned char rotary_process(int _i) {
   unsigned char pinstate = (digitalRead(rotaries[_i].pin2) << 1) | digitalRead(rotaries[_i].pin1);
  rotaries[_i].state = ttable[rotaries[_i].state & 0xf][pinstate];
  return (rotaries[_i].state & 0x30);
}

void CheckAllEncoders(void) {
  for (int i=0;i<NUMROTARIES;i++) {
    unsigned char result = rotary_process(i);
    if (result == DIR_CCW) {
      Joystick.setButton(rotaries[i].ccwchar, 1); delay(50); Joystick.setButton(rotaries[i].ccwchar, 0);
    };
    if (result == DIR_CW) {
      Joystick.setButton(rotaries[i].cwchar, 1); delay(50); Joystick.setButton(rotaries[i].cwchar, 0);
    };
  }
}

Le code est surement pas parfait mais ça fait le travail largement...

Merci encore pour ton aide,

Dellta

Ok bonne continuation