Teensy (post nerd e scacciafiga)

Tra i tanti progetti che porto avanti contemporaneamente, uno è quello della tastiera USB per macro universale.
Ricordate che di tanto in tanto faccio sottotitoli?
Ricordate che nel mio rozzissimo tutoriali per VSS decantavo l’utilità di una tastiera esterna con le macro?
Bene, quelle in commercio o non sono programmabili, o sono care impestate, o hanno troppi pochi tasti, o sono dispositivi per gaming troppo ingombranti.
Quindi ne ho messi in cantiere (sei mesi fa, credo, ormai) due modelli, uno molto piatto (una volta finito sarà poco più alto del circuito di comando, la cui altezza è influenzata soprattutto dalla presa USB) e uno pieghevole.
Com’è come non è (tagliare e forare il plexiglass è un lavoro di fino) il primo è rimasto indietro, ed ho terminato il secondo, più grezzo.
Sono partito da Arduino, nello sviluppo del progetto, ma ho ripiegato immediatamente su Teensy, molto più piccola, economica, e soprattutto ai tempi era l’unica a fornire una HID USB nativa.
Ne ho studiato la documentazione, ho rotto le scatole a diversi amici per un’estate sulla modificabilità di codici e librerie trovati online, ho provveduto all’acquisto.

Per la tastiera, il modello flat è una matrice di pulsanti su millefori (vedrete), per quello pieghevole, come vedete, sono quattro tastierini pseudo-telefonici acquistati su ebay collegati in matrice:

Come si può vedere, il fatto che colonne e righe avessero i pin mescolati e non in ordine non ha facilitato la cablatura.

C’è una sola vite per cerniera perché, fisicamente, l’altro occhiello andava in corrispondenza di una pista: mettere le altre quattro viti avrebbe significato danneggiare la tastiera, cosa che ho evitato per il resto del fissaggio inserendo le viti nei “montanti” plastici più esterni.

Ovviamente a lavoro finito ho rivestito il lato posteriore con una gomma antiscivolo, ho messo dei piedini alti quanto il chip+USB in modo da dare stabilità e ho lasciato una finestra trasparente per il LED e il pulsante di reboot (che serve per il caricamento del codice).

Già, il codice. Ho copiato e attinto da codice di diverse applicazioni, ho chiesto aiuto su un paio di forum quando la mia bozza non funzionava. M’hanno fatto levare gli apici dai case dello switch -boh?- e rileggendo le specifiche della libreria ho visto che dovevo togliere una colonna dal pin del LED (ebeh, RTFM).

È legnoso, ridondante, ma funziona.

#include < Keypad.h>

   int led = 11;
  const byte ROWS = 6;
  const byte COLS = 8; 
  char keys[ROWS][COLS] = {
    {38, 37, 36, 35, 14, 13, 12, 11},  
    {28, 27, 26, 25, 24, 23, 22, 21},
    {18, 17, 16, 15, 34, 33, 32, 31},
    {48, 47, 46, 45, 64, 63, 62, 61},
    {58, 57, 56, 55, 54, 53, 52, 51},
    {68, 67, 66, 65, 44, 43, 42, 41},
   
  };
  
  byte rowPins[ROWS] = {10, 12, 13, 14, 15, 16}; //connect to the row pinouts of the keypad
  byte colPins[COLS] = {1, 2, 3, 4, 5, 6, 7, 8}; //connect to the column pinouts of the keypad
  
  // Create the Keypad
Keypad kpd = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );

void setup ()
{
  // initialize control over the keyboard:
  Keyboard.begin();
}  // end of setup

void loop () 
  {   
   
   
  digitalWrite(led, HIGH); 
    
    
    
   byte key =  kpd.getKey();
   if (!key)
     return;
     
  switch (key)
    {
    case 11: Keyboard.set_key1(KEY_F5); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//start -100
    case 12: Keyboard.set_key1(KEY_F6); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//start -10
    case 13: Keyboard.set_key1(KEY_F7); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//start +10
    case 14: Keyboard.set_key1(KEY_F8); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//start +100
    case 15: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //70%
             Keyboard.set_key1(KEY_7); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 16: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //80%
             Keyboard.set_key1(KEY_8); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 17: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //90%
             Keyboard.set_key1(KEY_9); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 18: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //100%
             Keyboard.set_key1(KEY_0); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 21: Keyboard.set_key1(KEY_F12); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//stop -100
    case 22: Keyboard.set_key1(KEY_F11); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//stop -10
    case 23: Keyboard.set_key1(KEY_F10); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//stop +10
    case 24: Keyboard.set_key1(KEY_F9); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now(); break;//stop +100
    case 25: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //show pipe
             Keyboard.set_key1(KEY_H); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 26: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //Replace from pipe
             Keyboard.set_key1(KEY_R); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 27: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //Save
             Keyboard.set_key1(KEY_S); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 28: Keyboard.set_modifier(MODIFIERKEY_ALT);  Keyboard.send_now(); //play pause VLC
             Keyboard.set_key1(KEY_TAB); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_key1(KEY_LEFT); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now();
             Keyboard.set_key1(KEY_LEFT); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now();
             Keyboard.set_key1(KEY_SPACE); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(MODIFIERKEY_ALT); Keyboard.send_now();
             Keyboard.set_key1(KEY_TAB); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 31: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //wav display left
             Keyboard.set_key1(KEY_O); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 32: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //goto
             Keyboard.set_key1(KEY_G); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 33: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //find
             Keyboard.set_key1(KEY_F); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 34: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //wav display right
             Keyboard.set_key1(KEY_P); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 35: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //delay
             Keyboard.set_key1(KEY_D); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 36: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //redo
             Keyboard.set_key1(KEY_Y); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 37: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //strip tags
             Keyboard.set_key1(KEY_T); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 38: Keyboard.set_modifier(MODIFIERKEY_ALT); Keyboard.send_now(); //È
      Keyboard.set_key1(KEYPAD_0); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
      Keyboard.set_key1(KEYPAD_2); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
      Keyboard.set_key1(KEYPAD_0); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
      Keyboard.set_key1(KEYPAD_0); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
      Keyboard.set_modifier(0);  Keyboard.send_now(); Keyboard.print(" "); break;
    case 41: Keyboard.print ("Signor"); break; 
    case 42: Keyboard.print ("Professor"); break;
    case 43: Keyboard.print ("Dottor"); break;
    case 44: Keyboard.print ("Perché "); break;
    case 45: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //pause
             Keyboard.set_key1(KEY_P); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 46: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //previous sub
             Keyboard.set_key1(KEY_B); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 47: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //next sub
             Keyboard.set_key1(KEY_N); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 48: Keyboard.set_modifier(MODIFIERKEY_ALT);  Keyboard.send_now(); // play to end
             Keyboard.set_key1(KEY_RIGHT); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 51: Keyboard.print ("signor"); break;
    case 52: Keyboard.print ("professor"); break;
    case 53: Keyboard.print ("dottor"); break;
    case 54: Keyboard.print ("perché "); break;
    case 55: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //split
             Keyboard.set_key1(KEY_S); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;Keyboard.println ("55"); break;
    case 56: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //merge with next
             Keyboard.set_key1(KEY_M); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 57: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //merge dialog
             Keyboard.set_key1(KEY_D); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 58: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //loop
             Keyboard.set_key1(KEY_L); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 61: Keyboard.set_modifier(MODIFIERKEY_CTRL );  Keyboard.send_now(); //spell check
             Keyboard.set_key1(KEY_H); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 62: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //check error
             Keyboard.set_key1(KEY_K); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 63: Keyboard.set_modifier(MODIFIERKEY_CTRL | MODIFIERKEY_ALT);  Keyboard.send_now(); //error fix
             Keyboard.set_key1(KEY_F); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 64: Keyboard.set_modifier(MODIFIERKEY_ALT);  Keyboard.send_now(); //next error
             Keyboard.set_key1(KEY_N); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 65: Keyboard.print("- "); //dialogo
             Keyboard.set_key1(KEY_ENTER);Keyboard.send_now();Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.print("- ");
             Keyboard.set_key1(KEY_UP);Keyboard.send_now();Keyboard.set_key1(0); Keyboard.send_now();
             break;
    case 66: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); // Undo   
             Keyboard.set_key1(KEY_Z); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 67: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //text in italic
             Keyboard.set_key1(KEY_I); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    case 68: Keyboard.set_modifier(MODIFIERKEY_CTRL);  Keyboard.send_now(); //add subtitle
             Keyboard.set_key1(KEY_W); Keyboard.send_now(); Keyboard.set_key1(0); Keyboard.send_now();
             Keyboard.set_modifier(0);  Keyboard.send_now(); break;
    
    
    
    
      
    } // end of switch
  } // end of loop

Questo è il risultato finito:

E funziona, pure. Ne sono tanto stupito che questo post è grossomodo per chiedere “cosa ho sbagliato due volte per farla giusta?”.

6 thoughts on “Teensy (post nerd e scacciafiga)”

  1. Bravo! 🙂 Ed il fatto che abbia capito il codice mi rassicura sul fatto che il mio 18 in fondamenti-informaticaII almeno è meritato ^^;;;

    Vuoi un simulatore di macchinetta del caffè in C++ che funziona anche se non dovrebbe? 🙂

  2. Complimenti!
    Che ti abbiano fatto rimuovere gli apici dai “case” è perché i codici che stai usando (KEY_S, KEY_N, etc.) sono parte di una “enum” (enumerazione) e sono di fatto degli interi, non dei caratteri e nemmeno delle stringhe.

Leave a Reply