I²C: Der Zweidraht-Bus für Sensoren & Module (SDA/SCL)

SCL)

I²C – Der Zweidraht-Bus für Sensoren & Module

I²C (auch I2C oder TWI) ist ein serielles Busprotokoll mit nur zwei Leitungen: SDA (Daten) und SCL (Takt). Es eignet sich hervorragend, um mehrere Sensoren und Peripherie auf kurzer Distanz an einen Mikrocontroller wie Arduino oder ESP32 anzuschließen.

Was ist I²C?

I²C arbeitet mit einem Master (z. B. Mikrocontroller) und einem oder mehreren Slaves (Sensoren/Aktoren). Jedes Gerät hat eine 7-Bit-Adresse (gelegentlich 10-Bit), über die es angesprochen wird. Daten laufen synchron zum Takt auf der SCL-Leitung.

Warum I²C?

  • Wenige Leitungen: Nur SDA und SCL für viele Geräte – ideal bei wenig Pins.
  • Einfache Verdrahtung: Geräte werden parallel an denselben Bus gehängt.
  • Großes Ökosystem: Sehr viele Sensor-Breakouts (BME280, MPU-6050, OLEDs, RTC …).
  • Geschwindigkeiten: Standard-Mode 100 kHz, Fast-Mode 400 kHz, teils bis 1 MHz.

Worauf achten?

  • Pull-Ups: SDA/SCL brauchen Pull-Up-Widerstände (oft auf Breakouts vorhanden).
  • Gemeinsame Masse: GND aller Teilnehmer verbinden.
  • Pegel: Viele Controller arbeiten mit 3,3 V; bei 5-V-Systemen Level-Shifter nutzen.
  • Adressen: Konflikte vermeiden (z. B. 0x76/0x77 beim BME280 wählbar).
  • Leitungslänge: Kurz halten; Bus-Kapazität begrenzt.

Pin-Beispiele

  • Arduino Uno: A4 = SDA, A5 = SCL
  • ESP32-DevKit: häufig GPIO21 = SDA, GPIO22 = SCL (je nach Board konfigurierbar)

Beispiel 1: I²C-Scanner (Arduino)

Findet alle am Bus angeschlossenen Adressen. Verkable vorher SDA/SCL und GND.


#include <Wire.h>

void setup() {
  Serial.begin(115200);
  Wire.begin();                         // Uno: A4/A5, ESP32: Pins in Wire.begin(SDA,SCL)
  Serial.println("\nI2C-Scanner");
}

void loop() {
  byte count = 0;
  for (byte address = 1; address < 127; address++) {
    Wire.beginTransmission(address);
    byte error = Wire.endTransmission();
    if (error == 0) {
      Serial.print("Gefunden: 0x");
      Serial.println(address, HEX);
      count++;
    }
    delay(5);
  }
  if (count == 0) {
    Serial.println("Keine I2C-Geräte gefunden");
  } else {
    Serial.print("Summe: "); Serial.println(count);
  }
  delay(2000);
}

Beispiel 2: I²C-Scan (MicroPython, z. B. ESP32)

Passe die Pins SCL/SDA an dein Board an.


from machine import I2C, Pin
i2c = I2C(0, scl=Pin(22), sda=Pin(21), freq=400000)  # ESP32-Beispiel
addrs = i2c.scan()
print("Gefunden:", [hex(a) for a in addrs])

Beispiel 3: BME280 lesen (Arduino, I²C)

Minimalbeispiel mit der Adafruit-Bibliothek (Adresse je nach Modul 0x76/0x77).


#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>

Adafruit_BME280 bme;

void setup() {
  Serial.begin(115200);
  Wire.begin();                                 // ggf. Pins setzen: Wire.begin(SDA,SCL)
  if (!bme.begin(0x76)) {
    Serial.println("BME280 nicht gefunden!");
    while (1) delay(10);
  }
}

void loop() {
  Serial.print("T: "); Serial.print(bme.readTemperature());
  Serial.print(" °C  RH: "); Serial.print(bme.readHumidity());
  Serial.print(" %  p: "); Serial.print(bme.readPressure() / 100.0);
  Serial.println(" hPa");
  delay(2000);
}

Troubleshooting (Kurz)

  • Gerät wird nicht gefunden: Adresse prüfen, Scanner nutzen, Pull-Ups vorhanden?
  • Unstabile Werte: Versorgung & Masseführung checken, Kabellänge reduzieren.
  • Pegelproblem: 3,3-V-Controller nicht direkt mit 5-V-I²C betreiben – Level-Shifter!
  • Mehrere Geräte gleiche Adresse: Jumper/Adresse umstellen oder Multiplexer (z. B. TCA9548A) verwenden.

Weiterführend: SPI, UART, ESP32, Arduino, BME280, Pull-Ups, Level-Shifter.

0 Kommentare

Kommentieren

Bitte beachten Sie, dass Kommentare vor ihrer Veröffentlichung genehmigt werden müssen.