Zur Messung von Entfernungen im nahen Bereich (~2cm bis ~5m) gibt es Sensormodule für den Arduino, die
diese Arbeit mit Ultraschall erledigen.
Ein Ultraschall-Puls wird von einem Lautsprecher abgegeben und (fall sich ein Objekt im Bereich des
Schallkegels befindet) wieder reflektiert wie ein Echo. Anhand der verstrichenen Zeit kann die Entfernung
zum Objekt berechnet werden.
Die Schallgeschwindigkeit in trockener Luft von 20°C beträgt 343,5 m/s.
Die Ausbreitungsgeschwindigkeit ist aber auch abhängig von der Luft-Temperatur.
Ausbreitungsgeschwindigkeit (in Luft) = 331,5 + (0,6 * T)
Aus der Zeit td von Versenden des Ultraschall-Pulses bis zum Eintreffen beim Empfänger und
der Ultraschallgeschwindigkeit cU ergibt sich Distanz:
d = 0,5 * (cU / td)
Der Faktor 0,5 berücksichtigt, dass die gemessene Zeit sowohl den Hinweg als auch den Rückweg des Schalls umfasst.
Das Ultraschallmodul HC-SR04 eignet sich zur Entfernungsmessung im Bereich zwischen 2cm bis ca. 3m mit
einer Auflösung von 3mm. Es benötigt eine Versorgungsspannung von 5V bei einer Stromaufnahme von <2mA.
Nach Triggerung mit einer fallenden Flanke (TTL - Pegel) misst das Modul selbstständig die Entfernung und
wandelt diese in ein PWM Signal welches am Ausgang zur Verfügung steht.
Ein Messintervall hat eine Dauer von 20ms. Es können also 50 Messungen pro Sekunde durchgeführt werden.
Spannungsversorgung | 5V (±10%) |
---|---|
TTL Pegel | L < 1,0V |
messbare Distanz | ~ 2cm bis 300cm |
Messintervall | 0,3cm |
Messungen pro Sekunde | maximal 50 |
Strombedarf | ca. 2mA pro Messung |
Vcc | Spannungsversorgung 5V |
---|---|
Trig | Triggereingang, TTL-Pegel |
Echo | Ausgang Messergebnis, TTL-Pegel |
Gnd | Masseanschluss |
Das Auslösen eines Messzyklus geschieht durch eine fallende Flanke am Eingang (Trig) für mindestens 10μs.
Das Modul sendet darauf nach ca. 250μs ein 40 kHz Burst-Signal für die Dauer von 200μs. Danach geht der
Ausgang (Echo) sofort auf H-Pegel und das Modul wartet auf den Empfang des Echos. Wird dieses
detektiert fällt der Ausgang auf L-Pegel. 20ms nach Triggerung kann eine weitere Messung stattfinden. Wird kein
Echo detektiert verweilt der Ausgang für insgesamt 200ms auf H-Pegel und zeigt so die erfolglose Messung an.
Danach wartet das Modul auf die nächste fallende Flanke am Triggereingang und die Messung beginnt neu.
Die besten Messergebnisse ergeben sich bei Reflektion an glatten, ebenen Flächen. Bei Distanzen bis 1m ist das
Material der Fläche recht unkritisch. Der Winkel zum Objekt kann bei kurzen Distanzen von unter 1m bis etwa 45°
betragen. Auch recht dünne Objekte werden zuverlässig erkannt. Ein normaler Kugelschreiber z.B. lässt sich bis
auf eine Distanz von ca. 30cm sicher erfassen. Bei der maximalen Distanz von 3m muss schon genau gezielt
werden und es sollten keine anderen Gegenstände in ähnlicher Entfernung im Sendekegel von 15° vorhanden
sein.
Der folgende Code errechnet die Entfernung zu einem vor dem Ultraschall befindlichen Objekt.
Der Wert "58" in der Berechnung von distance
errechnet sich
dadurch, dass durch die Schallgeschwindigkeit der Puls 29µs für 1cm in der Luft benötigt. Und da der Puls
sowohl hin, als auch wieder zurückkehrt, müssen wir den Wert auf 58µs verdoppeln.
Die Funktion pulseIn(pin, value)
misst die Dauer zwischen einem Puls und dem
Empfang des Echos.
Ist value = HIGH, wartet die Funktion am spezifizierten Pin bis das Signal auf HIGH wechselt, um dann die
Zeit zu messen bis das Signal wieder auf LOW zurückfällt.
Ist value = LOW, startet die Messung, sobald
der Pin aus LOW geht, und misst die Zeit bis zum nächsten Signalwechsel nach HIGH.
#define PIN_TRIGGER 12
#define PIN_ECHO 13
const int SENSOR_MAX_RANGE = 300; // in cm
unsigned long duration;
unsigned int distance;
void setup()
{
Serial.begin(9600);
pinMode(PIN_TRIGGER, OUTPUT);
pinMode(PIN_ECHO, INPUT);
}
void loop()
{
digitalWrite(PIN_TRIGGER, LOW);
delayMicroseconds(2);
digitalWrite(PIN_TRIGGER, HIGH);
delayMicroseconds(10);
duration = pulseIn(PIN_ECHO, HIGH);
distance = duration/58;
if (distance > SENSOR_MAX_RANGE || distance <= 0){
Serial.println("Out of sensor range!");
} else {
Serial.println("Distance to object: " + String(distance) + " cm");
}
delay(1000);
}
#define PIN_TRIGGER 12
#define PIN_ECHO 13
#define PIN_PIEZO 11
const int SENSOR_MIN_RANGE = 2; // in cm
const int SENSOR_MAX_RANGE = 20; // in cm
unsigned long duration;
unsigned int distance, toneFrequency = 0;
void setup()
{
Serial.begin(9600);
pinMode(PIN_TRIGGER, OUTPUT);
pinMode(PIN_ECHO, INPUT);
for (byte pin=2; pin<=10; pin++) {
pinMode(pin, OUTPUT);
}
}
void loop()
{
digitalWrite(PIN_TRIGGER, LOW);
delayMicroseconds(2);
digitalWrite(PIN_TRIGGER, HIGH);
delayMicroseconds(10);
duration = pulseIn(PIN_ECHO, HIGH);
distance = duration/58;
for (byte pin=2; pin<=10; pin++) {
digitalWrite(pin, LOW);
}
noTone(PIN_PIEZO);
if (distance <= SENSOR_MAX_RANGE && distance >= SENSOR_MIN_RANGE){
toneFrequency = map(distance, SENSOR_MIN_RANGE, SENSOR_MAX_RANGE, 700, 200);
digitalWrite(map(distance, SENSOR_MIN_RANGE, SENSOR_MAX_RANGE, 2, 10), HIGH);
tone(PIN_PIEZO, toneFrequency);
}
delay(150);
}
zurück