Industrielle Fertigung
Industrielles Internet der Dinge | Industrielle Materialien | Gerätewartung und Reparatur | Industrielle Programmierung |
home  MfgRobots >> Industrielle Fertigung >  >> Manufacturing Technology >> Herstellungsprozess

FlickMote: Gestensteuerung per Ultraschall & IR für Smart Home (Arduino 101)

Komponenten

Bauteil Anzahl
Arduino 101 (oder UNO) 1
HC-SR04 Ultraschall-Entfernungsmesser 1
IR-Sende-LED (940 nm) 1
Widerstand 220 Ω (für IR-LED) 1
RGB-LED (Common Cathode) 1
Steckbrett & Kabel 1 Set

Software

Funktionsprinzip

Der HC-SR04 misst die Distanz zur Hand. Aus Distanzänderungen (Swipes, Halten) werden Gesten erkannt und entsprechende IR-Codes (Sony-TV-Protokoll) gesendet. Eine RGB-LED gibt visuelles Feedback.

Gesten-Mapping

Geste Distanz Aktion IR-Code (Sony, 12 Bit)
Hand abdecken (< 3 cm / ~1,2″) < 3 Zoll Power Toggle (Ein/Aus) 0xA90
Swipe niedrig (3–10 Zoll / ~7–25 cm) 3–10 Zoll Channel Down 0x890
Swipe hoch (10–20 Zoll / ~25–50 cm) 10–20 Zoll Channel Up 0x090
Halten niedrig (3–10 Zoll) 3–10 Zoll Volume Down (wiederholend) 0xC90
Halten hoch (10–20 Zoll) 10–20 Zoll Volume Up (wiederholend) 0x490

Power-Bestätigung: Erstes Abdecken → LED blinkt lila (Bestätigung). Zweites Abdecken innerhalb 5 s → IR-Code wird gesendet. Verhindert versehentliches Ausschalten.

Verdrahtung

Arduino-Code (Vollständig)

#include <IRremote.h>

#define CONTROL_CH 1
#define CONTROL_VOL 2
#define CONTROL_POW 3
#define CONTROL_UP 1
#define CONTROL_DOWN -1
#define DIST_MAX 20
#define DIST_DOWN 10
#define DIST_POW 3

const int irPin = 3; // fixed in library
const int pingPin = 8;
const int echoPin = 7;
const int led = 13;
const int ledR = 11, ledG = 10, ledB = 9;

unsigned long timer = 0;
IRsend irsend;
bool powerConfirmed = false;

void setup() {
  Serial.begin(9600);
  pinMode(led, OUTPUT);
  pinMode(ledR, OUTPUT);
  pinMode(ledG, OUTPUT);
  pinMode(ledB, OUTPUT);
  pinMode(pingPin, OUTPUT);
  pinMode(echoPin, INPUT);
}

void loop() {
  long duration = doPing();
  long inches = microsecondsToInches(duration);

  // Timer-Reset nach 5 s
  if (timer && millis() - timer > 5000) {
    timer = 0;
    Serial.println("timer reset");
  }

  digitalWrite(led, LOW);
  setColor(0, 0, 0);

  if (inches < DIST_MAX) {
    Serial.print(inches); Serial.println("in");

    if (inches < DIST_POW) { // Power-Geste
      if (timer) {
        doIR(CONTROL_POW, 0);
        timer = 0;
        delay(2000);
      } else {
        Serial.println("power flag set");
        timer = millis();
        setColor(255, 50, 50); // Lila
        delay(500);
      }
    } else { // Channel oder Volume
      int value = handleDist(inches);
      delay(300);
      long inches2 = microsecondsToInches(doPing());
      if (inches2 > DIST_MAX) { // Swipe (kurz)
        doIR(CONTROL_CH, value);
      } else { // Hold → Volume
        int d = 500;
        while (inches2 < DIST_MAX) {
          value = handleDist(inches2);
          doIR(CONTROL_VOL, value);
          delay(d);
          inches2 = microsecondsToInches(doPing());
          d = 100;
        }
        delay(500); // Verhindert Channel-Wechsel nach Volume
      }
    }
  }
  delay(50);
}

int handleDist(int inches) {
  if (inches > DIST_DOWN) {
    digitalWrite(led, HIGH);
    return CONTROL_UP;
  } else {
    digitalWrite(led, LOW);
    return CONTROL_DOWN;
  }
}

void doIR(int control, int val) {
  switch (control) {
    case CONTROL_POW:
      Serial.println("power on/off 0xA90");
      for (int i = 0; i < 3; i++) {
        setColor(255, 0, 0);
        irsend.sendSony(0xA90, 12);
        delay(40);
      }
      break;
    case CONTROL_CH:
      setColor(0, 255, 0);
      if (val == CONTROL_UP) {
        digitalWrite(led, HIGH);
        for (int i = 0; i < 3; i++) { irsend.sendSony(0x090, 12); delay(40); }
        Serial.println("channel up 0x090");
      } else {
        for (int i = 0; i < 3; i++) { irsend.sendSony(0x890, 12); delay(40); }
        Serial.println("channel down 0x890");
      }
      break;
    case CONTROL_VOL:
      setColor(0, 0, 255);
      if (val == CONTROL_UP) {
        digitalWrite(led, HIGH);
        for (int i = 0; i < 3; i++) { irsend.sendSony(0x490, 12); delay(40); }
        Serial.println("volume up 0x490");
      } else {
        for (int i = 0; i < 3; i++) { irsend.sendSony(0xC90, 12); delay(40); }
        Serial.println("volume down 0xC90");
      }
      break;
  }
}

void setColor(int r, int g, int b) {
  analogWrite(ledR, r);
  analogWrite(ledG, g);
  analogWrite(ledB, b);
}

long doPing() {
  digitalWrite(pingPin, LOW);
  delayMicroseconds(2);
  digitalWrite(pingPin, HIGH);
  delayMicroseconds(5);
  digitalWrite(pingPin, LOW);
  return pulseIn(echoPin, HIGH);
}

long microsecondsToInches(long us) { return us / 74 / 2; }
long microsecondsToCentimeters(long us) { return us / 29 / 2; }

Vorteile & Ausblick

Schaltplan & Fritzing

Breadboard-Schaltbild & Fritzing-Datei (flickmote_9Gx3XNFHEp.fzz) im Projekt enthalten.

Herstellungsprozess

  1. Ultraschall-Schwebegerät mit Arduino bauen – Akustische Levitation Schritt für Schritt
  2. Bluetooth-gesteuerter Arduino-Spybot bauen – Überwachungsroboter mit IP-Kamera
  3. DIY Arduino TV-B-Gone: Universelle TV-Aus-Fernbedienung
  4. Einen eigenen LED-Master-Clock mit Alarm bauen – aus 12 Metern Entfernung ablesbar
  5. Find Me: Smarter Gegenstands-Finder mit Arduino und Bluetooth
  6. Optimierte Stromversorgungslösungen für Arduino-Projekte
  7. Arduino Tic Tac Toe mit MAX7219 LED-Matrix und Karton-Gehäuse
  8. Intelligenten Arduino-Vierbeiner-Roboter bauen: Schritt-für-Schritt-Anleitung
  9. DIY Arduino Lenkrad / Joystick für Rennspiele – USB-HID-Umbau
  10. Kompaktes Arduino-Radar mit HC-SR04 Ultraschallsensor & 1,8″ Display