Kapazitiver Bodenfeuchte-Sensor mit Arduino auslesen & richtig kalibrieren

Die klassischen Bodenfeuchte-Sensoren mit den zwei Metallzinken haben ein Problem: Sie rosten. Nach ein paar Wochen im feuchten Erdreich sind die Elektroden zerfressen und die Messwerte driften weg. Der kapazitive Bodenfeuchte-Sensor löst genau das – er hat keine freiliegenden Kontakte, korrodiert nicht und hält jahrelang. Der Haken: Er liefert dir keine fertigen Prozentwerte, sondern eine rohe Analogzahl, die du erst kalibrieren musst. In diesem Tutorial lernst du, wie du den Sensor korrekt ausliest, sauber auf deine Erde kalibrierst, die Werte in Prozent umrechnest, auf einem OLED anzeigst und am Ende sogar eine automatische Bewässerung daraus baust.

Warum kapazitiv statt resistiv?

Es gibt zwei Bauarten von Bodenfeuchte-Sensoren, und der Unterschied ist entscheidend für die Lebensdauer:

Merkmal Resistiv (2 Zinken) Kapazitiv (Platine)
Messprinzip Widerstand durch Erde Kapazität durch Erde
Korrosion stark, Elektroden rosten keine, alles beschichtet
Lebensdauer Wochen bis Monate Jahre
Ausgang analog + digital analog (0–3,3 V typ.)
Stromfluss durch Erde ja (Elektrolyse!) nein
Fazit billig, aber Verschleiß Standard für Dauerbetrieb

Der kapazitive Sensor misst nicht den Widerstand zwischen zwei Metallstäben, sondern die Änderung der elektrischen Kapazität rund um die (vollständig lackierte) Sensorfläche. Feuchte Erde hat eine völlig andere Dielektrizität als trockene – und genau das erfasst der Sensor, ohne dass jemals Strom durch die Erde fließt. Dadurch gibt es keine Elektrolyse, keine Korrosion und keine driftenden Werte. Genau deshalb steckt er in jeder ernsthaften automatischen Pflanzenbewässerung.

ℹ️ Wichtig: nicht ganz eintauchen! Nur der untere, sensorische Teil gehört in die Erde – die obere Kante mit den Lötstellen und dem Stecker muss trocken bleiben. Fast alle Module haben eine aufgedruckte Maximallinie. Steckst du das Modul zu tief, kann Feuchtigkeit an die Elektronik kriechen und den Sensor auf Dauer zerstören.

Das brauchst du

Kapazitiver Bodenfeuchte-Sensor – der Star dieses Tutorials
Arduino UNO R3 (USB-C) oder ESP32 – je nach Projekt
OLED-Display 0,96 Zoll – für die Anzeige ohne PC
KY-019 Relais-Modul – optional, für die Pumpensteuerung
Breadboard & Jumper-Kabel – für den Aufbau

1Verkabelung: nur drei Leitungen

Der Sensor hat drei Pins: VCC, GND und AOUT (Analog-Ausgang). Er wird an einen Analogeingang deines Boards angeschlossen. Am Arduino UNO ist das z. B. A0, am ESP32 ein ADC1-Pin wie GPIO 34.

Sensor Arduino UNO ESP32
VCC 5V 3V3
GND GND GND
AOUT A0 GPIO 34 (ADC1)

⚠️ ESP32: nur ADC1-Pins nutzen! Der ESP32 hat zwei Analog-Einheiten. ADC2 (u. a. GPIO 0, 2, 4, 12–15, 25–27) ist gesperrt, sobald WLAN läuft – dann bekommst du dort nur Unsinn. Nutze für Analogmessungen mit aktivem WLAN immer ADC1-Pins: GPIO 32, 33, 34, 35, 36, 39. GPIO 34–39 sind reine Eingänge und dafür ideal.

⚠️ 3,3 V am ESP32: Betreibe den Sensor am ESP32 mit 3,3 V, nicht mit 5 V. So bleibt der Analogausgang im erlaubten Bereich des ESP32-ADC (max. 3,3 V). Am 5-V-Arduino UNO schließt du ihn dagegen an 5 V an.

2Rohwerte auslesen – der erste Test

Bevor du irgendetwas umrechnest, musst du sehen, was der Sensor überhaupt liefert. Der folgende Sketch gibt einfach den rohen Analogwert im seriellen Monitor aus. Am Arduino UNO liegt der ADC bei 10 Bit (0–1023), am ESP32 bei 12 Bit (0–4095).

// Fuer Arduino UNO (10 Bit, 0-1023)
#define SENSOR_PIN A0

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

void loop() {
  int roh = analogRead(SENSOR_PIN);
  Serial.print("Rohwert: ");
  Serial.println(roh);
  delay(500);
}

Für den ESP32 ist der Code fast identisch – nur der Pin und die Baudrate ändern sich:

// Fuer ESP32 (12 Bit, 0-4095)
#define SENSOR_PIN 34

void setup() {
  Serial.begin(115200);
}

void loop() {
  int roh = analogRead(SENSOR_PIN);
  Serial.print("Rohwert: ");
  Serial.println(roh);
  delay(500);
}

Lade den Sketch hoch und beobachte den seriellen Monitor. Du wirst eine wichtige Eigenheit bemerken: Bei diesem Sensor bedeutet ein hoher Rohwert trockene Erde und ein niedriger Wert feuchte Erde. Das ist umgekehrt, als man intuitiv denkt – und der Grund, warum wir gleich sauber kalibrieren.

3Die Kalibrierung: der wichtigste Schritt

Jeder Sensor, jede Erde und jede Versorgungsspannung ist ein bisschen anders. Deshalb gibt es keine allgemeingültige Formel – du musst deine beiden Extremwerte selbst ermitteln: den Wert bei komplett trockener Luft und den Wert in ganz nasser Erde. Genau zwischen diesen beiden Punkten liegt dein Messbereich.

So gehst du vor:

  1. Lade den Rohwert-Sketch aus Schritt 2 hoch und öffne den seriellen Monitor.
  2. Trockenwert messen: Halte den Sensor einfach in die Luft (oder in staubtrockene Erde). Notiere den stabilen Rohwert – das ist dein TROCKEN-Wert (der höchste).
  3. Nasswert messen: Stecke den Sensor bis zur Maximallinie in ein Glas Wasser oder in klatschnasse Erde. Notiere den Rohwert – das ist dein NASS-Wert (der niedrigste).
  4. Trage beide Werte in den nächsten Sketch ein.

ℹ️ Typische Werte (nur als Anhaltspunkt!): Am Arduino UNO liegt der Trockenwert oft um 620, der Nasswert um 310. Am ESP32 mit 12 Bit eher bei 3200 (trocken) und 1400 (nass). Deine Werte werden abweichen – verlasse dich auf deine eigene Messung, nicht auf diese Zahlen.

⚠️ In Wasser tauchen, aber nur bis zur Linie: Für den Nasswert darf wirklich nur der sensorische Bereich ins Wasser. Tauchst du das Modul komplett unter, riskierst du einen Kurzschluss an den Lötstellen. Die aufgedruckte weiße Linie ist die Grenze.

4Von Rohwert zu Prozent: die map()-Funktion

Jetzt rechnen wir die Rohwerte in einen schönen Prozentwert um: 0 % = staubtrocken, 100 % = klatschnass. Das Werkzeug dafür ist Arduinos map()-Funktion. Weil hoher Rohwert = trocken ist, drehen wir die Zuordnung um, sodass am Ende hohe Prozente feuchte Erde bedeuten.

// Fuer Arduino UNO – DEINE kalibrierten Werte eintragen!
#define SENSOR_PIN A0

const int TROCKEN = 620;   // dein Luftwert (hoch)
const int NASS    = 310;   // dein Wasserwert (niedrig)

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

void loop() {
  int roh = analogRead(SENSOR_PIN);

  // roh von [NASS..TROCKEN] auf [100..0] abbilden
  int prozent = map(roh, NASS, TROCKEN, 100, 0);
  prozent = constrain(prozent, 0, 100);   // sauber begrenzen

  Serial.print("Roh: ");     Serial.print(roh);
  Serial.print("   Feuchte: "); Serial.print(prozent);
  Serial.println(" %");
  delay(1000);
}

Die Zeile constrain(prozent, 0, 100) ist wichtig: Sollte der Sensor mal kurz einen Wert außerhalb deines kalibrierten Bereichs liefern (z. B. noch trockener als beim Kalibrieren), verhindert sie hässliche Werte wie -5 % oder 108 %. So bleibt die Anzeige immer sauber zwischen 0 und 100.

💡 Messwerte zappeln? Mittelwert bilden! Analoge Sensoren rauschen leicht. Statt eines einzelnen analogRead() mittelst du besser über mehrere Messungen – das glättet die Anzeige spürbar:

int leseMittelwert(int pin) {
  long summe = 0;
  for (int i = 0; i < 20; i++) {
    summe += analogRead(pin);
    delay(5);
  }
  return summe / 20;   // Durchschnitt aus 20 Messungen
}

5Anzeige auf dem OLED – ohne PC ablesbar

Ein Sensor, der seine Werte nur im seriellen Monitor zeigt, ist im Blumentopf nutzlos. Mit einem 0,96-Zoll-OLED baust du eine kleine, autarke Anzeige. Das OLED hängt am I2C-Bus (SDA/SCL) und braucht die Bibliotheken Adafruit_GFX und Adafruit_SSD1306.

#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SENSOR_PIN A0
#define TROCKEN 620
#define NASS    310

Adafruit_SSD1306 oled(128, 64, &Wire, -1);

void setup() {
  oled.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  oled.clearDisplay();
  oled.setTextColor(SSD1306_WHITE);
}

void loop() {
  int roh = analogRead(SENSOR_PIN);
  int prozent = constrain(map(roh, NASS, TROCKEN, 100, 0), 0, 100);

  oled.clearDisplay();
  oled.setTextSize(1);
  oled.setCursor(0, 0);
  oled.println("Bodenfeuchte");

  oled.setTextSize(3);
  oled.setCursor(0, 20);
  oled.print(prozent);
  oled.println(" %");

  // kleiner Fortschrittsbalken
  oled.drawRect(0, 55, 128, 8, SSD1306_WHITE);
  oled.fillRect(0, 55, map(prozent, 0, 100, 0, 128), 8, SSD1306_WHITE);

  oled.display();
  delay(1000);
}

Jetzt zeigt das Display groß den Feuchte-Prozentwert und darunter einen Balken, der sich mit der Feuchte füllt. Steck den Sensor in deine Zimmerpflanze, häng das Display daneben – fertig ist der Feuchte-Monitor. Wie du das OLED noch mit Grafiken und Icons aufwertest, steht im Artikel OLED Display SSD1306 mit Arduino.

6Die Königsdisziplin: automatisch gießen

Der logische nächste Schritt: Unterschreitet die Feuchte eine Schwelle, schaltet der Arduino über ein Relais eine kleine Pumpe ein und gießt, bis die Erde wieder feucht genug ist. Damit die Pumpe nicht dauernd an- und ausflattert, arbeiten wir mit einer Hysterese: Einschalten bei z. B. 30 %, Ausschalten erst wieder bei 60 %.

#define SENSOR_PIN A0
#define RELAIS_PIN 7
#define TROCKEN 620
#define NASS    310

const int GIESSEN_UNTER = 30;   // unter 30 % -> Pumpe an
const int STOPP_UEBER   = 60;   // ueber 60 % -> Pumpe aus
bool pumpeLaeuft = false;

void setup() {
  Serial.begin(9600);
  pinMode(RELAIS_PIN, OUTPUT);
  digitalWrite(RELAIS_PIN, LOW);   // Pumpe aus
}

void loop() {
  int roh = analogRead(SENSOR_PIN);
  int feuchte = constrain(map(roh, NASS, TROCKEN, 100, 0), 0, 100);

  if (!pumpeLaeuft && feuchte < GIESSEN_UNTER) {
    pumpeLaeuft = true;
    digitalWrite(RELAIS_PIN, HIGH);
    Serial.println("Zu trocken -> Pumpe AN");
  }
  else if (pumpeLaeuft && feuchte > STOPP_UEBER) {
    pumpeLaeuft = false;
    digitalWrite(RELAIS_PIN, LOW);
    Serial.println("Feucht genug -> Pumpe AUS");
  }

  Serial.print("Feuchte: "); Serial.print(feuchte); Serial.println(" %");
  delay(2000);
}

⚠️ Pumpe niemals direkt am Arduino-Pin: Eine Wasserpumpe zieht viel zu viel Strom für einen GPIO. Sie gehört über das Relais und ein eigenes Netzteil geschaltet. Der Arduino steuert nur das Relais-Signal, die Pumpe bekommt ihren Strom separat. Eine ausführliche, ESP32-basierte Variante mit WLAN-Überwachung findest du im Artikel Automatische Pflanzenbewässerung mit ESP32.

ℹ️ Sicherheits-Timeout einbauen: Für den Dauerbetrieb solltest du die maximale Pumpenlaufzeit begrenzen (z. B. "nie länger als 20 Sekunden am Stück"). Fällt der Sensor mal aus oder rutscht aus der Erde, verhindert das eine Überschwemmung. Miss dazu mit millis() die Laufzeit und schalte notfalls hart ab.

Praxistipps für zuverlässige Messungen

🌱 So misst du richtig

  • Immer gleich tief einstecken – die Einstecktiefe beeinflusst den Wert
  • Nicht direkt am Topfrand – dort trocknet die Erde schneller aus als in der Mitte
  • Nach dem Gießen kurz warten – das Wasser braucht Zeit, sich zu verteilen
  • Bei großen Beeten mehrere Sensoren nutzen und den Mittelwert bilden

Ergebnis: stabile, wiederholbare Werte statt Zufallszahlen

💡 Sensor länger haltbar machen: Auch der kapazitive Sensor lebt länger, wenn du seine Kante mit etwas Heißkleber oder Schrumpfschlauch zusätzlich gegen aufsteigende Feuchtigkeit abdichtest – genau an der Stelle, wo Platine und Erde aufeinandertreffen. Das ist die einzige echte Schwachstelle dieser Sensoren.

Troubleshooting

⚠️ Wert ändert sich kaum zwischen trocken und nass: Meist eine Spannungsfrage. Manche günstigen Module liefern bei 3,3 V nur einen kleinen Hub. Teste am 5-V-Arduino, ob der Bereich größer wird, oder mittle über mehr Messungen.

⚠️ Am ESP32 nur Zufallswerte: Fast immer ein ADC2-Pin mit aktivem WLAN. Wechsle auf einen ADC1-Pin (GPIO 32–39).

⚠️ Prozentwert hängt bei 0 oder 100 fest: Deine Kalibrierwerte TROCKEN/NASS passen nicht. Miss sie neu und trage die echten Rohwerte ein – sie müssen zu deinem Board (10 vs. 12 Bit) passen.

⚠️ Werte driften über Tage weg: Feuchtigkeit ist an die Lötstellen gekrochen. Sensor trocknen, Kante abdichten, nicht zu tief einstecken.

🚀 Alles für dein Bodenfeuchte-Projekt

Damit legst du direkt los:

Fazit

Der kapazitive Bodenfeuchte-Sensor ist die klar bessere Wahl für jedes Projekt, das länger als ein paar Wochen laufen soll – weil er schlicht nicht korrodiert. Der einzige Preis dafür ist die Kalibrierung: Du musst deinen Trocken- und deinen Nasswert einmal selbst ermitteln. Danach liefert dir map() saubere Prozentwerte, die du auf dem OLED anzeigst oder zur automatischen Bewässerung nutzt.

Merke dir die drei wichtigsten Punkte: hoher Rohwert bedeutet trocken (nicht umgekehrt), am ESP32 nur ADC1-Pins verwenden, und den Sensor nie über die Maximallinie eintauchen. Wenn du diese drei Dinge beachtest, hast du einen Feuchtesensor, der jahrelang zuverlässig misst – und die Grundlage für deinen automatisch bewässerten, immer grünen Garten.

Zurück zum Blog