Indholdsfortegnelse:

Accel Writing (Magic Hand): 4 trin (med billeder)
Accel Writing (Magic Hand): 4 trin (med billeder)

Video: Accel Writing (Magic Hand): 4 trin (med billeder)

Video: Accel Writing (Magic Hand): 4 trin (med billeder)
Video: seeing wife face for first time #shorts 2024, November
Anonim
Accel Writing (magisk hånd)
Accel Writing (magisk hånd)
Accel Writing (magisk hånd)
Accel Writing (magisk hånd)
Accel Writing (magisk hånd)
Accel Writing (magisk hånd)

Introduktion

Den magiske hånd giver mennesker med handicap og motoriske færdigheder mulighed for at nyde kreativiteten ved at tegne og skrive i et simuleret miljø. Den magiske hånd er en bærbar handske, der mærker din pegefingers bevægelse og oversætter det til tegning af linjer på en computerskærm.

Nødvendige materialer

LSM9DOF Breakout Board --- $ 24,95 ---

Adafruit Feather with Wifi --- $ 18,95 ---

Kvinde-/huntråd --- $ 1,95 ---

Tape/velcrobånd --- $ 3

To magneter med samme styrke --- Priserne varierer

Hvordan det virker

Ved at bruge et accelerometer kan vi indsamle accelerationsdata for y-aksen, som hjælper os med at bestemme, hvornår brugerens finger bevæger sig op og ned. På grund af det faktum, at vores accelerometer måler acceleration i forhold til midten af jorden, kan vi ikke bestemme accelerationen af x-aksen (venstre eller højre). Heldigvis indeholder LSM9DOF breakout board også et magnetometer, som giver os mulighed for at indsamle data om magnetiske felter. Vi placerer to magneter med 30 cm mellemrum og har handsken imellem. Hvis de magnetiske data læses positive, ved vi, at handsken bevæger sig til højre og omvendt. Når alle data er indsamlet i accelerometeret/magnetometeret, sender de dataene via ledning til fjeren, som er forbundet til en computer med wifi og videresender derefter dataene til computeren, som vi derefter kan bruge i vores kode.

Trin 1: Fysisk prototype 1

Fysisk prototype 1
Fysisk prototype 1
Fysisk prototype 1
Fysisk prototype 1

Denne prototype er beregnet til at blive handskesyet løst sammen på hånden, så den kan glide over de elektroniske enheder. Den elektroniske enhed vil derefter blive fastgjort med velcro til under armour ærmet base kombineret med en grundlæggende handske på hånden. Så vil den grønne handske glide over basen og de elektroniske enheder ….

Trin i fremstillingen af prototypen handske:

  • Få to stykker stof, der er store nok til at spore hånden
  • Træk hånden på begge stofstykker og skær dem ud
  • Sæt de to håndudskæringer sammen, så de er perfekt tilpasset
  • For at klargøre symaskinen skal du derefter føre tråden gennem de angivne steder på maskinen
  • Når symaskinen er sat op, skal du løfte nålen og placere de to sammensatte stofstykker under nålen
  • Sørg for, at nålen er opstillet på kanten af stoffet, start maskinen, og sy langs stoffets kanter, mens de to stykker ikke er syet ved håndleddet, så en hånd kan passe ind.

Trin 2: Fysisk prototype 2

Fysisk prototype 2
Fysisk prototype 2
Fysisk prototype 2
Fysisk prototype 2

Vores sidste prototype er en almindelig handske kombineret med velcrobånd, der kan justeres til ethvert håndled. Handsken og remmen er syet sammen, og de elektroniske enheder er fastgjort til handsken via velcro.

Trin i fremstillingen af den anden prototype af handsken:

  1. Køb en handske, handskens materiale er ligegyldigt.
  2. Køb en velcro håndledsrem
  3. Køb et bærbart batteri
  4. Køb Sticky Velcro
  5. Med en synål fastgør du velcrobåndsremmen til handskens bund
  6. Håndledsremmen skal kunne justeres til forskellige håndledsstørrelser.
  7. Fastgør tape til bunden af accelerometeret og fastgør det til handskens pegefinger
  8. Fastgør tape til fjer og fastgør den til toppen af handsken.
  9. Brug ledninger til at forbinde 3V3 -stiften i fjer til VIN -stiften i accelerometeret
  10. Brug ledninger til at forbinde GND -stiften i fjer til GND -stiften accelerometeret.
  11. Brug ledninger til at forbinde SCL -stiften i fjer til SCL -ben accelerometeret.
  12. Brug ledninger til at forbinde SDA -stiften i fjeren til SDA -stiften accelerometeret.
  13. Tilslut mindst et 5 volt batteri via usb til fjer for at levere strøm.

Trin 3: Magneter

Magneter
Magneter

Trin 1: Sæt de to magneter med samme styrke over for hinanden.

Trin 2: Mål 30 cm mellemrum mellem de to magneter

Trin 3: Anbring magnetometeret nøjagtigt midt i de to magneter. Du bør modtage data omkring 0, mens det er i midten. Hvis du modtager en aflæsning på nul, skal du gå til trin 5.

Trin 4: Hvis aflæsningen ikke er nul eller tæt på nul, skal du justere afstanden til magneterne. Hvis aflæsningen er negativ, flytt den venstre magnet en cm eller 2 til venstre, eller indtil aflæsningen er nul. Hvis det er positivt, gør det samme undtagen med den rigtige magnet.

Trin 5: Skriv kode, der accepterer data fra magnetometeret og læser, om det er positivt eller negativt. Hvis positiv har koden, tegner du en linje til højre, og hvis negativ, tegner du en linje til venstre.

Trin 4: Kode

Kode
Kode

github.iu.edu/ise-e101-F17/MuscleMemory-Sw…

Introduktion:

For at behandle data fra accelerometeret skal der etableres et klient/server -forhold mellem Adafruit -fjeren og serveren, der behandler dataene (kører på en bærbar/desktop). To kodefiler skal oprettes: en til klienten (Adafruit -fjeren) og den anden til serveren (i dette tilfælde Jarods bærbare computer). Klienten er skrevet i C ++, og serveren er skrevet i python. Det sprog, der bruges til klienten, er vigtigt, da Arduino hovedsageligt er et C ++ - sprog, og det er svært at ændre det til at bruge et andet sprog. Serveren kan skrives på ethvert sprog, så længe den har netværksfunktioner.

Opsætning af klienten:

Først opsætter vi klientkoden. Det meste af WiFi -forbindelseskoden er let tilgængeligt via Adafruit -bibliotekerne. Vi starter med at inkludere relevante klasser.

#include #include #include #include #include

Angiv nogle variabler, hvad der skal bruges i hele koden.

// Opret forbindelse til et netværk const char* ssid = "MMServer"; const char* password = "MMServer-Password"; // IP og port på serveren, der modtager data const char* host = "149.160.251.3"; const int port = 12347; bool tilsluttet = falsk;

// Initialiser bevægelsesdetektor

Adafruit_LSM9DS0 lsm = Adafruit_LSM9DS0 (1000);

WiFiClient -klient;

Opret en setup () -funktion, der køres, så snart fjeren starter.

// Opsæt WiFi -forbindelse, og opret forbindelse til servervoid -opsætningen () {Serial.begin (9600); forsinkelse (100);

Serial.println ();

Serial.println (); Serial.print ("Opretter forbindelse til"); Serial.println (ssid); // Start WiFi WiFi. Begynd (ssid, adgangskode); // Opretter forbindelse … mens (WiFi.status ()! = WL_CONNECTED) {forsinkelse (500); Serial.print ("."); } // Oprettet forbindelse til WiFi Serial.println (""); Serial.println ("WiFi tilsluttet"); Serial.println ("IP -adresse:"); Serial.println (WiFi.localIP ());

#ifndef ESP8266

mens (! Seriel); #endif Serial.begin (9600); Serial.println ("Sensortest");

// Initialiser sensoren

hvis (! lsm.begin ()) {// Der opstod et problem med at registrere LSM9DS0 Serial.print (F ("Ups, ingen LSM9DS0 registreret … Kontroller dine ledninger eller I2C ADDR!")); mens (1); } Serial.println (F ("Fundet LSM9DS0 9DOF")); // Begynd at oprette forbindelse til serveren Serial.print ("Opretter forbindelse til"); Serial.println (vært);

// Kontroller, om forbindelsen er vellykket. Hvis det mislykkes, skal du afbryde

hvis (! client.connect (host, port)) {Serial.println ("forbindelsen mislykkedes"); forbundet = falsk; Vend tilbage; } andet {tilsluttet = sandt; }

// Indstil sensorforstærkning og integrationstid

configureSensor (); }

Vi har derefter brug for en loop -funktion, der gentagne gange vil loopes. I dette tilfælde bruges det til gentagne gange at sende data fra accelerometeret til serveren i form af "[z_accel]: [y_mag]: [z_mag]". Client.print (tal); funktion er det, der sender data til serveren.

void loop () {delay (250); hvis (tilsluttet) {// Dette sender data til serveren sensors_event_t accel, mag, gyro, temp; lsm.getEvent (& accel, & mag, & gyro, & temp); Stringnumre; tal += accel.acceleration.z; tal += ":"; tal += mag.magnetisk.y; tal += ":"; tal += mag.magnetisk.z; Serial.print (tal); client.print (tal); Serial.println (); } ellers {establishmentConnection (); }}

For nogle hjælpefunktioner har vi brug for en til at etablere forbindelsen mellem fjer og server.

void etablConnection () {if (! client.connect (host, port)) {Serial.println ("forbindelse mislykkedes"); forbundet = falsk; Vend tilbage; } andet {tilsluttet = sandt; }}

Vi skal også konfigurere sensoren og give den værdiområdet, den vil læse. For eksempel har acceleration 5 muligheder for området: 2g, 4g, 6g, 8g og 16g.

void configureSensor (void) {// Indstil accelerometerintervallet //lsm.setupAccel(lsm. LSM9DS0_ACCELRANGE_2G); lsm.setupAccel (lsm. LSM9DS0_ACCELRANGE_4G); //lsm.setupAccel(lsm. LSM9DS0_ACCELRANGE_6G); //lsm.setupAccel(lsm. LSM9DS0_ACCELRANGE_8G); //lsm.setupAccel(lsm. LSM9DS0_ACCELRANGE_16G); // Indstil magnetometerfølsomheden //lsm.setupMag(lsm. LSM9DS0_MAGGAIN_2GAUSS); //lsm.setupMag(lsm. LSM9DS0_MAGGAIN_4GAUSS); //lsm.setupMag(lsm. LSM9DS0_MAGGAIN_8GAUSS); lsm.setupMag (lsm. LSM9DS0_MAGGAIN_12GAUSS);

// Opsætning af gyroskopet

lsm.setupGyro (lsm. LSM9DS0_GYROSCALE_245DPS); //lsm.setupGyro(lsm. LSM9DS0_GYROSCALE_500DPS); //lsm.setupGyro(lsm. LSM9DS0_GYROSCALE_2000DPS); }

Opsætning af serveren:

Serveren vil være en python -fil, der kører på kommandolinjen på en computer. For at starte skal du importere de nødvendige klasser.

import socketimport re import pyautogui

stik bruges til netværk. re bruges til regex eller strengmanipulationer. pyautogui er et python -bibliotek, som gør det muligt at tegne (diskuteres senere).

Dernæst bør vi definere nogle variabler. Disse vil være globale variabler, så de får adgang til flere funktioner. De vil blive brugt senere i koden.

i = 0n = 0 linje = 1

data_list =

mag_data =

mag_calib_y = 0 mag_offset_y = 0

z_calib = 0

z_offset = 0 z_moving_offset = 0 z_diff = 0 z_real = 0 z_velo = 0 z_pos = 0

keep_offset = Falsk

first_data = Sandt

Vi har nu brug for en funktion til at oprette en server og åbne den for indgående forbindelser.

def startServer (): global i global first_data # initialize server socket serversocket = socket.socket (socket. AF_INET, socket. SOCK_STREAM) serversocket.setsockopt (socket. SOL_SOCKET, socket. SO_REUSEADDR, 1) # Server IP adresse og port host = " 149.160.251.3 "port = 12347 server_address = (host, port) # Åbn serveren, og lyt efter indgående forbindelser udskriv ('Start server på %s port %s' %server_address) serversocket.bind (server_address) serversocket.listen (5) # Vent på forbindelser … mens True: print ('Venter på forbindelse …') # Accepter en indgående forbindelse (clientsocket, adresse) = serversocket.accept () # Prøv at analysere modtagne data, prøv: print ('Forbindelse etableret fra', adresse) mens True: # Modtag dataene og send dem til behandling af data = clientsocket.recv (25) accel_data = re.split ('[:]', str (data)) accel_data [0] = accel_data [0] [2:] accel_data [1] = accel_data [1] accel_data [2] = accel_data [2] [1: -1] print (accel_data) i+= 1 if (i <51): calibData (accel_data) else: movingAcce l (accel_data [0]) processData (accel_data) first_data = Falsk endelig: # Luk soklen for at forhindre unødvendig datalæk clientsocket.close ()

Vi har nu brug for de funktioner, der behandler alle data. Det første skridt at tage, og den første funktion kaldes, er kalibrering af sensoren til beregningsformål.

def calibData (liste): global z_calib global z_offset global mag_data global mag_calib_y global mag_offset_y z_calib += float (liste [0]) mag_calib_y += float (liste [1]) hvis (i == 50): z_offset = z_calib / 50 mag_offset_ = mag_calib_y / 50 z_calib = 0 mag_calib_y = 0 mag_data.append (mag_offset_y)

Dernæst opretter vi en bevægelig accelerationsforskydning. Dette gør det til, at programmet genkender, når nogen holder op med at flytte deres finger, fordi alle værdierne for acceleration, der sendes til serveren, skal være de samme på det tidspunkt.

def movingAccel (num): global z_calib global z_diff global z_moving_offset global z_offset global data_list global n global keep_offset hvis (n 0.2 eller z_diff <-0.2): # bevægelse registreret i data, genstart keep_offset = True n = 0 z_calib = 0 z_moving_offset = 0 z_diff = 0 data_list = pause hvis ikke keep_offset: # stationær i data, indstil ny z_offset z_offset = z_moving_offset print ("Ny z_offset:") print (z_offset) n = 0 z_calib = 0 z_moving_offset = 0 z_diff = 0 data_list = keep_offset = Falsk keep_offset = Falsk

Dernæst gør vi det største problem med matematikken. Dette indebærer at oversætte accelerationsdataene til en positionsdata, som giver os mulighed for at fortælle den retning, som brugeren bevæger sin finger.

def processData (liste): #[accel.z, mag.y] global z_offset global z_real global z_velo global z_pos global first_data global mag_data

z_real = float (liste [0]) - z_offset

mag_y = liste [1] mag_z = liste [2] venstre = Falsk højre = Falsk # Behandl ikke acceleration, før den er helt sikker på, at den har accelereret # Forhindrer mekanisk støj i at bidrage til position, hvis (z_real -0.20): z_real = 0 #Begin integrationer for at finde position hvis (first_data): mag_data.append (mag_y) z_pos = (0,5 * z_real * 0,25 * 0,25) + (z_velo * 0,25) + z_pos z_velo = z_real * 0,25 pyautogui.moveTo (1500, 1000) ellers: z_pos = (0,5 * z_real * 0,25 * 0,25) + (z_velo * 0,25) + z_pos z_velo = (z_real * 0,25) + z_velo del mag_data [0] mag_data.append (mag_y) if (float (mag_data [1]) - float (mag_data [0])> 0.03): højre = True elif (float (mag_data [1]) - float (mag_data [0]) <-0.03): left = True if (højre): bevægelse (50, int (z_pos* 1000)) elif (venstre): bevægelse (-50, int (z_pos*1000)) z_velo = 0 z_pos = 0

Nu endelig flytter vi markøren! For at gøre dette åbnede vi et malingsvindue og lavede det i fuld skærm. Pyautogui -biblioteket indeholder en funktion kaldet pyautogui.dragRel (x, y); som vi bruger til at trække musemarkøren fra et punkt til det næste. Det bruger relative positionsdata, så bevægelsen er i forhold til markørens sidste position.

def bevægelse (x, y): print ("flytte til", x, -y) pyautogui.dragRel (x, -y)

Endelig er vi nødt til at ringe til hovedfunktionen for selv at tillade hele denne kode at køre.

# Opkalder funktionen for at starte serverstartServer ()

Anbefalede: