Author Topic: Mehrere Ultraschallsensoren über I2C anschliessen  (Read 21894 times)

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Mehrere Ultraschallsensoren über I2C anschliessen
« on: April 17, 2014, 10:40:30 AM »
Hallo zusammen,

Ich versuche zwei Ultraschallsensoren vom Typ srf02 über ein Grove - Base Shield v1.3 per I2C an ein Arduino anzuschliessen. Inzwischen habe ich herausgefunden, dass man die Adressen ändern muss, damit nicht beide als einer berechnet wird. Wie, dass ich diese Adresse jedoch ändern kann, habe ich nicht herausgefunden. Könnt ihr mir bei diesem Problem weiterhelfen?
Wie kann ich die Adresse des Ultraschallsensors ändern?
Muss ich noch eine Masteradresse machen, wie kann ich das bewerkstelligen?

Vielen, vielen Dank schon mal im voraus.
Juli

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #1 on: April 17, 2014, 10:41:07 AM »
Ich benutze ein Arduino Uno.

MathiasW

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 614
  • Karma: +13/-0
    • my Arduino page
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #2 on: April 17, 2014, 03:14:41 PM »
Salut,

die Prozedur zum Wechsel der I2C Adresse ist in diesem Artikel beschrieben:
http://www.robot-electronics.co.uk/htm/srf02techI2C.htm#Address
Ich habe einen SFR02, so dass ich das testen kann, wenn Du Probleme mit der Sequenz hast. Ich habe auch ein kleines Sketch, das alle I2C Adressen scannt und auflistet, ob sich an einer Adresse eine Device befindet (siehe Anhang)

Ciao, Mathias

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #3 on: April 25, 2014, 10:28:17 AM »
hallo zusammen,
danke mathias für den sketch, allerding gibt der bei mir nur unverständliches kauderwelsch wieder.
ich habe ausserdem einen anderen code, bei dem die srfadresse 0x70 ist und nicht 0xE0.

Der code:

#include <Wire.h>
#define srfAddress 0x70                           // Address of the SRF08
#define cmdByte 0x00                              // Command byte
#define rangeByte 0x02                            // Byte for start of ranging data
byte highByte = 0x00;                             // Stores high byte from ranging
byte lowByte = 0x00;                              // Stored low byte from ranging
int range = 0;
int rangeData;

void setup(){
    Serial.begin(9600);
    Wire.begin();                               
    }

void loop(){
 
  rangeData=getRange(); 
  Serial.print("Entfernung: ");
  Serial.println(rangeData, DEC);   
  delay(100);                                      // Wait before looping
}

int getRange(){                                   // This function gets a ranging from the SRF08
  Wire.beginTransmission(srfAddress);             // Start communticating with SRF08
  Wire.write(cmdByte);                             // Send Command Byte
  Wire.write(0x51);                                // Send 0x51 to start a ranging
  Wire.endTransmission(); 
  delay(100);                                     // Wait for ranging to be complete
  Wire.beginTransmission(srfAddress);             // start communicating with SRFmodule
  Wire.write(rangeByte);                           // Call the register for start of ranging data
  Wire.endTransmission();
  Wire.requestFrom(srfAddress, 2);                // Request 2 bytes from SRF module
  while(Wire.available() < 2);                    // Wait for data to arrive
  highByte = Wire.read();                      // Get high byte
  lowByte = Wire.read();                       // Get low byte
  range = (highByte << 8) + lowByte;              // Put them together
  return(range);                                  // Returns Range
}

den habe ich von hier -> http://forum.arduino.cc/index.php?topic=86368.0

wenn ich hier jetzt aber in der srfadresse 0xE0 reinschreibe anstatt 0x70(nachdem ich die adresse geändert habe), klappt es nicht.

danke zusammen, juli

pylon

  • freakyfriday
  • Full Member
  • *
  • Posts: 158
  • Karma: +16/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #4 on: April 25, 2014, 02:23:31 PM »
Code: [Select]
  Wire.requestFrom(srfAddress, 2);                // Request 2 bytes from SRF module
  while(Wire.available() < 2);                    // Wait for data to arrive

Die while-Zeile ist ein ganz schlechte Idee. Wenn der vorangegangene Wire.requestFrom() geklappt hat, ist er unnütz, wenn nicht, ist es eine Endlos-Schleife.

Besser sieht das so aus:

Code: [Select]
int getRange(){                                   // This function gets a ranging from the SRF08
  Wire.beginTransmission(srfAddress);             // Start communticating with SRF08
  Wire.write(cmdByte);                             // Send Command Byte
  Wire.write(0x51);                                // Send 0x51 to start a ranging
  if (Wire.endTransmission()) return -1;
  delay(100);                                     // Wait for ranging to be complete
  Wire.beginTransmission(srfAddress);             // start communicating with SRFmodule
  Wire.write(rangeByte);                           // Call the register for start of ranging data
  if (Wire.endTransmission()) return -1;
  if (Wire.requestFrom(srfAddress, 2) == 2) {        // Request 2 bytes from SRF module
    highByte = Wire.read();                      // Get high byte
    lowByte = Wire.read();                       // Get low byte
    range = (highByte << 8) + lowByte;              // Put them together
    return(range);                                  // Returns Range
  }
  return -1;
}

Du müsstest allerdings in loop() auch auf den Rückgabewert -1 reagieren.

MathiasW

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 614
  • Karma: +13/-0
    • my Arduino page
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #5 on: April 26, 2014, 05:47:17 PM »
Salut,

der i2cscanner läuft mit 115200 baud - ist das auch im SerialMonitor eingestellt? Das würde den Zeichensalat erklären. Dieser Code läuft bei mir Problemlos:
Code: [Select]
/***************************************************

Ultraschall-Entfernungsmesser SRF02 über
I2C-BUS am Arduino angeschlossen.
Ausgabe über LC-Dislay.
Der Code wurde erstellt unter teilweiser Verwendung
von Code aus dem Buch "Arduino" von Ulli Sommer
Franzis-Verlag

****************************************************/


#include <Wire.h> // Wire-Bibliothek einbinden
#include <LiquidCrystal.h> // LCD-Library einbinden

#define srfAddress ( 0xE0 >> 1) // I2C-BUS-Adresse des SRF02. Da der Arduino eine 7-Bit Adresse erwartet, muss ein Bit nach rechts geschoben werden.
#define cmdByte 0x00
#define rangeByte 0x02

byte MSB = 0x00; // Höherwertiges Byte ( Most Significant Byte )
byte LSB = 0x00; // Niederwertiges Byte ( Lower Significant Byte )

LiquidCrystal lcd(12, 11, 5, 4, 3, 2); // LCD-Anschlüsse festlegen

void setup()
{
  Wire.begin();
  Serial.begin(9600);
  Serial.println("SRF02 Ultrasonic Ranger");
}

void loop ()
{
  int rangeData = getRange();
  Serial.print("Entf.: "); // Daten ausgeben
  Serial.print(rangeData);
  Serial.println(" cm");
  delay(250);
}

int getRange()
{
  int range = 0;
//  return (range);

  Wire.beginTransmission(srfAddress);
  Wire.write(cmdByte);
  Wire.write(0x51);
  Wire.endTransmission();

  delay(100);

  Wire.beginTransmission(srfAddress);
  Wire.write(rangeByte);
  Wire.endTransmission();

  Wire.requestFrom(srfAddress, 2 );
  while (Wire.available() < 2);
  MSB = Wire.read();
  LSB = Wire.read();

  range = (MSB << 8) + LSB;

  return (range);

}
Bitte beachte, dass die Addresse 0xE0 des SRF02 um ein Byte nach Rechts geschoben werden muss, was dann dem Wert 0x70 entspricht. (Keine Ahnung, warum man eine Addresse um ein Byte verschoben angibt)

Ciao, Mathias

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #6 on: April 28, 2014, 08:11:23 AM »
hallo,

super, danke. Es war wirklich das mit den 115200 baud. Jetzt kann ich es auch verstehen, was der da brabbelt.
Und danke für den Hinweis mit den Byts. Dass schau ich mir sofort mal etwas genauer an.

Vielen Dank nochmal, langsam komme ich rein.

Freundliche Grüsse,
Juli

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #7 on: April 29, 2014, 08:12:49 AM »
Hallo zusammen, vielen Dank nochmal.
Ich habe allerdings immer noch ein kleines Problem. Die Adresse wird nicht geändert wenn ich den Befehl dazu gebe. Es bleibt immer die 0x70, wenn ich sie im Nachhinei scanne.

Code: [Select]
#include <Wire.h>


#define srfAddress (0xE0 >> 1,0xA0,0xAA,0xA5,0xF2 >> 1)                           // Address of the SRF08
                            // Stored low byte from ranging

void setup()
{
 
}

void loop()
{
 
}

Ist mein Befehl völlig falsch oder habe ich etwas übersehen?

Freundliche Grüsse,

Juli

pylon

  • freakyfriday
  • Full Member
  • *
  • Posts: 158
  • Karma: +16/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #8 on: April 29, 2014, 08:56:55 PM »
Quote
Ist mein Befehl völlig falsch oder habe ich etwas übersehen?

Welcher Befehl? Dieser Sketch enthält keinen einzigen Befehl. Der #define bewirkt nichts, gar nichts. Was willst Du genau machen?

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #9 on: April 30, 2014, 07:27:14 AM »
Wie kann ich die Adresse von meinem zweiten Srf02 Ultraschallsensor verändern, damit ich zwei Ultraschallsensoren gleichzeitig laufen lassen kann?

julan

pylon

  • freakyfriday
  • Full Member
  • *
  • Posts: 158
  • Karma: +16/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #10 on: April 30, 2014, 02:27:28 PM »
Mit diesem Code wechselst Du auf die Adresse 0x78 (= 0xF0 in der 8-bit-Version).

Code: [Select]
#include "Wire.h"

#define currentAddress 0x70
#define newAddress 0x78

void setup() {
  Serial.begin(9600);
  Wire.begin();
  Wire.beginTransaction(currentAddress);
  Wire.write(0x00);
  Wire.write(0xA0);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 1. command byte");
    return;
  }
  Wire.beginTransaction(currentAddress);
  Wire.write(0x00);
  Wire.write(0xA5);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 2. command byte");
    return;
  }  Wire.beginTransaction(currentAddress);
  Wire.write(0x00);
  Wire.write(0xAA);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 3. command byte");
    return;
  }  Wire.beginTransaction(currentAddress);
  Wire.write(0x00);
  Wire.write(newAddress << 1);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 1. command byte");
    return;
  }
  Serial.print("Successfully configured new Address: ");
  Serial.println(newAddress);
}

void loop() {
}

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #11 on: May 01, 2014, 10:56:48 AM »
Ach super danke.
Das sieht so aus als ob ich mich mal mit den wire. befehlen etwas mehr beschäftigen.
Hast du da vielleicht gerade noch ein Beispiel oder eine Aufgabe wo ich das etwas besser lernen kann?

gruss Juli

Julianbr

  • Newbie
  • *
  • Posts: 10
  • Karma: +0/-0
Re: Mehrere Ultraschallsensoren über I2C anschliessen
« Reply #12 on: May 02, 2014, 11:27:32 AM »
Hallo Pylon,

Vielen Dank nochmal für den Sketch,

Leider hat er am Anfang nicht funktioniert, aber mit ein paar kleinen Änderungen hat es geklappt:

Code: [Select]
#include "Wire.h"

#define currentAddress 0x70                                    //aktuelle Adresse reinschreiben  /  type in current address
#define newAddress 0x74                                        //neue Adresse reinschreiben  /  type in new adress

void setup() {
 
  delay (10000);                                                //Delay for Serial Monitor
 
  Serial.begin(115200);
  Wire.begin();
  Wire.beginTransmission(currentAddress);
  Wire.write(0x00);
  Wire.write(0xA0);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 1. command byte (maybe adress already changed)");
    return;
  }
    Wire.beginTransmission(currentAddress);
  Wire.write(0x00);
  Wire.write(0xAA);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 2. command byte");
    return;
  }
    Wire.beginTransmission(currentAddress);
  Wire.write(0x00);
  Wire.write(0xA5);
  if (Wire.endTransmission()) {
    Serial.println("Error writing 3. command byte");
    return;
 
  }  Wire.beginTransmission(currentAddress);
  Wire.write(0x00);
  Wire.write(newAddress << 1);
  if (Wire.endTransmission()) {
    Serial.println("Error writing new adress byte");
    return;
  }
  Serial.print("Successfully configured new Address: ");
  Serial.println(newAddress);
}

void loop() {
}

Man muss darauf achten, dass auf dem Datenblatthttp://www.robot-electronics.co.uk/htm/srf02techI2C.htm die Befehle um die Adresse zu ändern nicht in der richtigen Reihenfolge sind. In diesem Sketch stimmt die Reihenfolge und so funktioniert es.
Am Anfang des Sketches habe ich einen Delay eingebaut, damit man Zeit hat den Serial Monitor zu öffnen und die Erfolgreiche Änderung auch zu sehen. Denn ansonsten führt das Programm den Befehl aus und wenn man den Serial öffnet will es ihn nochmal ausführen, hat aber bereits eine andere Adresse und gibt daher eine Error Warnung an.

Freundliche Grüsse,

Julian