Sommario:

Progetto Arduino di Guitar Hero: 12 passaggi (con immagini)
Progetto Arduino di Guitar Hero: 12 passaggi (con immagini)

Video: Progetto Arduino di Guitar Hero: 12 passaggi (con immagini)

Video: Progetto Arduino di Guitar Hero: 12 passaggi (con immagini)
Video: Quando provi a fare un complimento a una ragazza... 2024, Dicembre
Anonim
Progetto Arduino Guitar Hero
Progetto Arduino Guitar Hero
Progetto Arduino Guitar Hero
Progetto Arduino Guitar Hero
Progetto Arduino Guitar Hero
Progetto Arduino Guitar Hero

Wij zijn Maarten Vrebos, Justin Cavanas e Wannes Stroobandt e studiamo multimedia e tecnologie di comunicazione. Per un progetto di gruppo voor het vak Audiovisual & IT Principles hebben wij een Guitar Hero-gitaar gehackt en gebruikt come behuizing voor onze MIDI-controller. Het was onze bedoeling om de bestaande knoppen op de gitaar intern te vervangen. Il controller onze è molto ampio e può essere visualizzato anche in una normale chitarra. Aangezien we iets hebben gehackt hebben we er niet veel extra material in moeten verwerken.

In de afbeelding kan u onze allereerste schets op papier zien van hoe het eindproduct er zou moeten uitzien met daarnaast een foto van de gitaar die anche behuizing zal worden gebruikt.

Wij hebben ons voor dit project gebaseerd on volgere bronnen:

slapyak.wordpress.com/guitar-hero-midi-con…

www.instructables.com/id/Converting-a-rescu…

gizmodo.com/391834/turn-your-guitar-hero-g…

Benodigdheden voor dit project

  • 6 pulsanti kleine
  • 7 resistenze da 1kohm
  • 1 gel LED 1
  • LED blu
  • 1 Arduino Uno R3
  • 1 LED verde
  • 2 LED montati
  • 1 schuifschakelaar
  • 1 tagliere
  • 1 potenziometro
  • 1 protobord
  • 1 chitarra Guitar Hero
  • Biancheria da letto Voldoende
  • Materiaal om te solderen/dremelen/
  • Schroevendraaier

Passaggio 1: componenti Verzamelen

Componenti Verzamelen
Componenti Verzamelen

Per il prototipo (su breadboard) possiamo completare la progettazione dei componenti:

6 pulsanti

7 resistori da 1 kohm

1 LED giallo

1 LED blu

1 Arduino Uno R3

1 LED verde

2 LED rossi

1 Schuifschakelaar

1 tagliere

1 Potenziometro

Fase 2: Prototipo Bouwen

Prototipo Bouwen
Prototipo Bouwen
Prototipo Bouwen
Prototipo Bouwen
Prototipo Bouwen
Prototipo Bouwen

Tutti i prototipi non sono altro che la creazione di tutti i componenti in base a una breadboard, la stessa breadboard è diversa da altri oggetti di testo che non sono adatti per l'aspetto e il lavoro. Dit prototipo hebben possiamo gedigitaliseerd tramite tinkercad.com, op deze manier hadden we een duidelijk overzicht van ons prototipo dat elk groepslid ook kon bewerken.

Er worden 5 kleine pushbuttons gebruikt die funge da 5 snaren en un grande pulsante die in combinazione con meerdere 'snaren' moet worden ingedrukt om een auditief effect te krijgen. De verschillende LED-lampjes dienen gewoon als visuele controle om er zeker van te zijn dat de interactie succesvol werkt.

Passaggio 3: prototipo del codice

Codice prototipo
Codice prototipo

Variabili globali

In het eerste deel van de code initialiseer je globale variabelen voor de pins van arduino uno waar alle pushbuttons mee verbonden zijn.

// zet i numeri dei pin waar mainButton(snaar) e altri pulsanti aan verbonden zijn:const int mainButton = A1; // snaar gitaar const int lightSensor = A0; const int buttonPin1 = 2; //numero van pushbutton1 const int buttonPin2 = 3; //numero van pushbutton2const int buttonPin3 = 4; //numero van pushbutton3const int buttonPin4 = 5; //numero van pushbutton4const int buttonPin5 = 6; // numero pulsante furgone5

Hierna worden er twee arrays aangemaakt voor de namen van de pushbuttons en hun pinnummer.

const int aantalKnoppen = 5;const String namenKnoppen[aantalKnoppen] = {"knop 1", "knop 2", "knop 3", "knop 4", "knop 5"}; const int knopPinnen[aantalKnoppen] = {2, 3, 4, 5, 6};

En dan nog variabelen voor de pins van de LED lichtjes.

const int ledPin1 = 13; // il numero del pin LED 13

const int ledPin2 = 12; // il numero di LED pin 12 const int ledPin3 = 11; // il numero di LED pin 11 const int ledPin4 = 10; // il numero di LED pin 10 const int ledPin5 = 9; // il numero del pin LED 9 const int potPin = A5; // il numero di pin LED A5

De laatste globale variabelen dienen als 'states' voor de sensor (zijn de pushbuttons ingedrukt of niet? potenziometer, lichtsensor).

// initialiseer buttonStates voor de knoppen (ingedrukt of niet)int mainButtonState = 0; int Stato1 = 0; int buttonState2 = 0; int buttonState3 = 0; int buttonState4 = 0; int buttonState5 = 0; int lightSensorState = 0; int potValue = 0; int valoreluce = 0;

Impostare

Nuova funzione di configurazione del vuoto. Deze è van het type void (geeft geen waarde terug) e de instructies hierin worden maar 1 keer uitgevoerd.

Bij elke functie è commentar geschreven wat er concreet gedaan wordt. Extra uitleg over wat een specifieke functie concreet doet is te vinden in de arduino reference

void setup() { // velocità dati al secondo (baud) per la trasmissione dati seriale Serial.begin(9600); // Inizializza la variabile ledPin come output pinMode(ledPin1, OUTPUT); pinMode(ledPin2, OUTPUT); pinMode(ledPin3, OUTPUT); pinMode(ledPin4, OUTPUT); pinMode(ledPin5, OUTPUT); // inizializza tutti i pulsanti come input: pinMode(mainButton, INPUT); pinMode(buttonPin1, INPUT); pinMode(pulsantePin2, INGRESSO); pinMode(buttonPin3, INPUT); pinMode(buttonPin4, INPUT); pinMode(buttonPin5, INPUT); pinMode(potPin, INPUT); pinMode(Sensoreluce, INGRESSO); }

Funzione vuoto

Na de setup() functie volgt de loop() functie, le istruzioni die hierin staan gaan herhaald uitgevoerd worden.

void loop() { // lascia lo stato dei pulsanti uit (ingedrukt of niet) mainButtonState = digitalRead(mainButton); buttonState1 = digitalRead(buttonPin1); buttonState2 = digitalRead(buttonPin2); buttonState3 = digitalRead(buttonPin3); buttonState4 = digitalRead(buttonPin4); buttonState5 = digitalRead(buttonPin5);

// tutti gli stati dei pulsanti in un array

int buttonState = {buttonState1, buttonState2, buttonState3, buttonState4, buttonState5};

// leest de waarde uit van de potenziometer en de lichtsensor

potValue = analogRead(potPin); lightValue = analogRead(lightSensor);

// dichiarante un array mainStates en geef die de standard waarden 0 in.

int mainStates = {0, 0, 0, 0, 0};

// loop sull'array aantalKnoppen

for(int i = 0; i < aantalKnoppen; i++){ pinMode(knopPinnen, INPUT); // inizializza tutti i knopPinnen come input digitalRead(knopPinnen); // lees de waarde van all knoppinnen uit // indien de mainswitch (snaar) ingedrukt is, print all knopnamen, all buttonstates if(mainButtonState == HIGH){ Serial.print(namenKnoppen); Serial.print(", "); Serial.println(buttonStates); } }

Fase 4: Prototipo Uittesten

Il nuovo prototipo è in fase di sviluppo sul modello e il codice di elaborazione è in elaborazione, è così come il prototipo e il test. Op de video is te zien dat alle knoppen een reactie geven op de bijhorende ledjes e dat ook combinaties van knoppen mogelijk zijn.

Nel video di tweede c'è il tremolo che fa per te e la mano con un potenziometro nella chitarra e le parole usate nell'elaborazione.

Passaggio 5: trasformare "ontmantelen" En Kijken Welke Componenten Gebruikt Gaan Worden

behuizing
behuizing
behuizing
behuizing
behuizing
behuizing
behuizing
behuizing

Anche il codice corretto è stato eseguito sul prototipo quando abbiamo iniziato a incontrare gli "ontmantelen" del gioco di Guitar Hero. Abbiamo la possibilità di aprire la macchina fotografica con un schroevendraaier e bekeken Welke Originale componentin che possiamo eventualmente eseguire le modifiche per il controller. Uiteindelijk hebben abbiamo onze eigen pushbuttons in de bestaande buttons gekregen (zie volgende stap). We hebben de tremolo ook gebruikt voor ons eindproduct en voor onze hoofdbutton (pulsante iniziale om als een combinatie af te spelen) hebben ook de originele twee button gebruikt(zie vierde foto). De LEDjes zullen verdwijnen (deze waren enkel ter indicae zodat we zagen dat alle knoppen correct werkten.

Passaggio 6: utilizzo dei pulsanti Originele + Dremelen

Pulsanti Werking Originele + Dremelen
Pulsanti Werking Originele + Dremelen

Op de bijhorende video is de wijze te zien waarop de twee originele knoppen werken anche een soort van schakelaar die wij gebruiken om un effetto te genereren bij combiet van knoppen.

Om onze eigen button te verwerken in de originele knoppen hebben we de binnenkant van de originelen er grotendeels uitgehaald zoals te zien is op de foto.

Passaggio 7: saldatura a letto + bottoni Vastlijmen

Biancheria da letto Solderen + Bottoni Vastlijmen
Biancheria da letto Solderen + Bottoni Vastlijmen
Biancheria da letto Solderen + Bottoni Vastlijmen
Biancheria da letto Solderen + Bottoni Vastlijmen
Biancheria da letto Solderen + Bottoni Vastlijmen
Biancheria da letto Solderen + Bottoni Vastlijmen

Non abbiamo più niente da fare con una breadboard che non contiene più parole gessate o più componenti aggiuntivi con altre parole. Nadat dit gebeurd is kunnen we de button vastlijmen zoals te zien is op de foto's. Una volta che si tratta di gebeurd è possibile che arriviamo a una conclusione successiva.

Passaggio 8: piatti realizzati in De Behuizing

Piatti realizzati in De Behuizing
Piatti realizzati in De Behuizing
Piatti realizzati in De Behuizing
Piatti realizzati in De Behuizing
Piatti realizzati in De Behuizing
Piatti realizzati in De Behuizing

Omdat dit Guitar Hero-model redelijk krap was om mee te werken hebben we extra plaats moeten maken d.m.v. dremelen. Zo hebben we uit de achterkant van de gitaar een hele strook verwijderd zodat er meer plaats ontstaat voor de bedrading in de gitaar. Omdat er overal in de binnenkant obstakels waren, waaronder veel buisjes om de vijzen in te bevestigen, hebben we die ook verwijderd om optimaal van de gegeven ruimte gebruik te kunnen maken. Op de vierde en vijfde foto is te zien dat we in de achterkant van de gitaar een doorgang hebben gecreëerd voor de draden die naar de button gaan omdat de gitaar anders niet meer te sluiten was. L'ultima foto è il motivo per cui si tratta di parole verbali dettagliate con Arduino per essere incluse nella versione originale della chitarra.

Passaggio 9: Bedrading Aansluiten Op Protobord

Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord
Bedrading Aansluiten Op Protobord

Om tutti i componenti con tutti i dettagli e verbinden hebben noi gebruik gemaakt van un protobord. Dit is een bordje dat eigenlijk op net dezelfde manier werkt als een breadbord, maar dan betrouwbaarder en efficiënter. We hebben de bedrading aan het bordje gesoldeerd zoals te zien is op de derde foto. Dit bord is het centrale punt van waaruit al onze verbindingen vertrekken en samenkomen(zie foto 2).

Passaggio 10: Verstevigen

Verstevigen
Verstevigen

Inoltre, il tocco finale è het verstandig om de losse delen te voor extra stabilizzato. Op deze foto is te zien hoe we het deel dat we er hebben uitgehaald d.m.v. dremelen achteraan de button verstevigen met stukjes karton.

Passaggio 11: Code Voor Het Communiceren Met Reaper

Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper
Code Voor Het Communiceren Met Reaper

Questo codice è disponibile in due parti, anche se è in arduino IDE (ambiente di sviluppo interattivo) geschreven. Die code wordt geüpload naar arduino zelf en dient om alle waarden van de sensor van de midi controller uit te lezen en door te sturen naar processing.

L'elaborazione è het tweede gedeelte. Deze code dient om alles wat arduino doorstuurt te ontvangen en door te sturen naar Reaper.

Arduino

/* Questo codice è uno schizzo di base per comunicare con Processing tramite Serial.

È un progetto in cui puoi inserire il tuo codice

specificati per i propri pulsanti, potenziometri o sensori.

Ha una stretta di mano per assicurarsi che abbiamo un contatto

e si decide il formato in cui si comunica

È importante costruire il messaggio allo stesso modo, in modo che Processing sappia come decostruirlo e inviare messaggi OSC corretti alla nostra DAW

realizzato per il Werkcollege AV&IT

ottobre 2017

*

/ velocità di trasmissione

const long baudRate = 115200;

// tempo di attesa in ms tra i sondaggi ai pin

const int loopPauseTime = 200; // milli secondi

// valori di inizio e fine per il messaggio inviato su Serial

const String startString = "*", endString = "#";

const char contactCharacter = '|';

// ID pin

// altre variabili globali

const int aantalKnoppen = 5; const String namenKnoppen[aantalKnoppen] = {"knop 1", "knop 2", "knop 3", "knop 4", "knop 5"}; const int knopPinnen[aantalKnoppen] = {2, 3, 4, 5, 6}; const int mainButton = A1;

int mainButtonState = 0;

int potValue = 0;

// sensori analogici

const int potPin = A5; // pin voor tremolo

// Abbiamo bisogno di questa funzione per stabilire un contatto con lo schizzo Processing

// Tienilo qui void stabilireContact() { while (Serial.available() <= 0) { Serial.print(contactCharacter); // invia un carattere e aspetta una risposta… delay(loopPauseTime); } Serial.read(); }

void setup() {

// imposta i pinModes per tutti i pin for(int i = 0; i < aantalKnoppen; i++){ pinMode(knopPinnen, INPUT); } pinMode(mainButton, INPUT); // decommenta se usi sensori che funzionano a 3V invece che a 5V // dovrai collegare anche il pin 'ext' a 3.3V // analogReference(EXTERNAL);

// inizializza le comunicazioni seriali

Serial.begin(baudRate); mentre (!Seriale); // attendi la stretta di mano stabilireContact(); }

ciclo vuoto() {

// PASSO 1: READ BUTTONS // interroga tutti i pin e mappa la lettura nell'intervallo appropriato int buttonStates[aantalKnoppen]; /* buttonStates[0] = digitalRead(knopPinnen[0]); buttonStates[1] = digitalRead(knopPinnen[1]); buttonStates[2] = digitalRead(knopPinnen[2]); buttonStates[3] = digitalRead(knopPinnen[3]); buttonStates[4] = digitalRead(knopPinnen[4]); */ mainButtonState = digitalRead(mainButton); for(int i = 0; i < aantalKnoppen; i++){ buttonStates = digitalRead(knopPinnen); } potValue = analogRead(potPin); // esempi: // float v0 = map(bpm, 0, 1023, 60, 250); // se vuoi usare un float normalizzato (es. per il volume) // float v1 = map(analogRead(pin2), fromMin, fromMax, 0, 100) / 100.0;

// FASE 2: SCRIVI MESSAGGIO

Serial.print(startString); // avvia una sequenza di messaggi for(int i = 0; i < aantalKnoppen; i++){ if(mainButtonState == HIGH){ Serial.print(namenKnoppen); Serial.print(", "); Serial.print(buttonStates); if(i < aantalKnoppen - 1){ Serial.print(", "); } }else{ buttonStates = 0; Serial.print(nomeKnoppen); Serial.print(", "); Serial.print(buttonStates); if(i < aantalKnoppen - 1){ Serial.print(", "); } } } Serial.print(", "); Serial.print("tremolo"); Serial.print(", "); Serial.print(map(potValue, 0, 1023, 0, 100)); // scrive la fine del messaggio Serial.print(endString);

// aspettare per un po..

delay(loopPauseTime); }

in lavorazione

Dichiarazione di non responsabilità: non tutto il codice van de processing sketch staat hier in geschreven, voor de volledige code zie het bestand: ProcessingSoundControl_handout_v6_1.pde in bijlage

De volgende instructions moeten aangepast worden (indien nodig):

// Baudrate moet hetzelfde zijn zoals in de arduino sketch

baudRate int finale = 115200;

// Visualizza l'indirizzo IP in reaper (schermate di zie in bijlage)

// Processing stuurt naar dit andres en reaper luistert hier naar //

//final String remoteIP = "192.168.1.43"; //per esempio. "127.0.0.1";

final String remoteIP = "10.3.209.60";

// Prendi nota del sendPort e inseriscilo in Reaper.

// Questa è la porta a cui Processing invia e Reaper ascolta.

finale int listenPort = 12000, porta di invio = 12000;

// Il listenPort qui serve per eseguire attivamente il debug.

// anche i portNames sono qui per eseguire il debug.

//final String portName = "/dev/ttyACM0";

final String portName = "COM5"; // "/dev/ttyUSB0";

///////////////////// FINE dei PARAMETRI UTENTE ///////////////////////// ////

import processing.serial.*;

import java.util.*;

importa oscP5.*;

importa netP5.*;

OscP5 oscP5;

NetAddress myRemoteLocation;

Porta di comunicazione seriale; // La porta seriale

boolean messageArrived = false;

Stringa in arrivo = "", IncomingOSCMessage = "";

carattere finale startChar = '*', endChar = '#'; carattere finale contactCharacter = '|';

// Per assicurarci di inviare solo i parametri (valori) che cambiano

// queste variabili globali sono indicate qui ma non dovrebbero // essere inizializzate qui! HashMap oldParams, newParams, toSendParams;

// Dobbiamo dividere il messaggio ad ogni virgola

void processIncoming() { String resVec = incoming.split(", "); // otteniamo le coppie nome + valore // quindi per ogni nome (+2)… try{ for (int i = 0; i< resVec.length; i+=2) { float value = Float.parseFloat(resVec[i+ 1]); // li inserisco nella nuova Hashtable newParams.put(resVec, value); } } // se si verifica un errore, prendiamolo visualizza ed esci. catch(Eccezione ex){ println("Messaggio eccezione: " + ex); printArray(resVec); Uscita(); } }

// Per filtrare i nostri messaggi

/* Ci assicuriamo che ci sia solo un messaggio OSC-out quando * cambia il messaggio di input (Serial) * Cioè: se giriamo/spingiamo il pulsante e cambia valore. * Quindi filtriamo i valori in entrata che effettivamente cambiano * nota: non eviteremo di saltare i valori * come provengono ad esempio da accelerometri o sensori di distanza * dovrai livellarli tu stesso in Arduino */ void filterParams () { toSendParams = new HashMap(); for (String key: newParams.keySet()) { // se la chiave è già presente if (oldParams.containsKey(key)) { // chiave presente e valore diverso, quindi aggiorna if (!oldParams.get(key).equals(newParams.get(key))) { toSendParams.put(key, newParams.get(key)); } } else{ // la chiave non è presente nei vecchi parametri, quindi mettila! toSendParams.put(key, newParams.get(key)); } oldParams.put(key, newParams.get(key)); } }

void makeOSC() {

for (String key: toSendParams.keySet()) { OscMessage myMessage = new OscMessage("/"+ key); myMessage.add(toSendParams.get(key)); /* invia il messaggio */ oscP5.send(myMessage, myRemoteLocation); } }

void translateMessage() {

processIncoming(); filterParams(); makeOSC(); } // Quando vogliamo stampare sulla finestra void ShowIncoming() { // per vedere il messaggio in arrivo, come impostato nel testo HashMap("Incoming from Arduino", 20, 20); int y = 20; for (String key: newParams.keySet()) { y = y+20; testo(chiave, 20, y); text(newParams.get(key), 300, y); } }

void showOsc() {

text(IncomingOSCMessage, 300, 200); IncomingOSCMessage =""; }

void setup() {

dimensione (1000, 800); // Dimensioni dello stage fill(255); sfondo(0); oldParams = new HashMap(); newParams = new HashMap(); //printArray(Serial.list()); comsPort = new Serial(this, portName, baudRate);

/* avvia oscP5, in ascolto dei messaggi in arrivo */

oscP5 = new OscP5(this, listenPort);

/* myRemoteLocation è un NetAddress. un NetAddress accetta 2 parametri, * un indirizzo IP e un numero di porta.myRemoteLocation viene utilizzato come parametro in * oscP5.send() quando si inviano pacchetti osc a un altro computer, dispositivo, * applicazione. utilizzo vedi sotto. a scopo di test, la porta di ascolto * e la porta dell'indirizzo della posizione remota sono le stesse, quindi * invierai messaggi a questo sketch. */ myRemoteLocation = new NetAddress(remoteIP, sendPort); }

disegno vuoto() {

if (messaggioArrivato) { background(0); translateMessage(); MostraIn arrivo(); messaggioArrivato= falso; } showOsc(); }

void serialEvent (porta seriale) {

// legge un byte dalla porta seriale: char inChar = comsPort.readChar(); switch (inChar) { case contactCharacter: commsPort.write(contactCharacter); // chiedi di più println("inizio…"); rottura; case startChar: incoming= ""; rottura; case endChar: messageArrived = true; //println("fine del messaggio"); rottura; default: in entrata += inChar; rottura; } }

/* i messaggi osc in arrivo vengono inoltrati al metodo oscEvent. */

void oscEvent(OscMessage theOscMessage) { float value = theOscMessage.get(0).floatValue(); // ottiene il primo argomento osc

Messaggio OSCMin arrivo += "\n" +

String.format("### ha ricevuto un messaggio osc: " + " addrpattern: " + theOscMessage.addrPattern() + ": %f", valore); println(IncomingOSCMessage); }

Passaggio 12: controllo del controller

Nu alles is aangesloten, tutte le code is geschreven en alles is gedubbelcheckt is het eindelijk tijd om de controller z'n werk te laten doen. Scopri un paio di effetti su Reaper e il genio del controller MIDI di Guitar Hero!

Consigliato: