Skip to content

Technik Blog

Programmieren | Arduino | ESP32 | MicroPython | Python | Raspberry Pi | Raspberry Pi Pico

Menu
  • Smarthome
  • Arduino
  • ESP32 & Co.
  • Raspberry Pi & Pico
  • Solo Mining
  • Über mich
  • Deutsch
  • English
Menu

Android App Entwicklung: ESP Controller ansprechen #2

Posted on 29. Januar 201920. Mai 2025 by Stefan Draeger

Im letzten Tutorial habe ich erläutert wie man eine Verbindung zu einem ESP Controller aufbaut und Daten sendet & empfängt.

Ausführen der App - Absenden eines Request an den WittyCloud
Ausführen der App – Absenden eines Request an den WittyCloud

Nun möchte ich gerne erläutern wie man den Fotowiderstand ausliest und an die Android App sendet.

Auslesen eines Fotowiderstandes und anzeigen des Wertes in einer AndroidApp
Dieses Video auf YouTube ansehen.

Als Mikrocontroller habe ich den WittyCloud verwendet, dieser bietet sich an da der Controller neben einem ESP12 Chip auch über einen Fotowiderstand und einem NeoPixel verfügt.

Als Grundlage möchte ich die Android-App aus dem letzten Tutorial Android App Entwicklung: ESP Controller ansprechen #1 verwenden.

Android App Entwicklung: ESP Controller ansprechen, Ausbaustufe 1Herunterladen

Wie auch im letzten Tutorial möchte ich den Aufbau Schritt für Schritt erläutern und zum Schluss haben wir eine lauffähige Android-App.

Solltest du im nachfolgenden Tutorial Fehler finden, oder Fragen haben, so kannst du dich gerne per E-Mail an mich wenden.

Schaltung

Für dieses Tutorial benötigst du einen ESPx mit einem Fotowiderstand, wie bereits erwähnt verwende, ich den WittyCloud dieser hat bereits einen Fotowiderstand verbaut.

Witty Cloud
Witty Cloud

Wenn du diesen nicht besitzt ist das nicht schlimm, es kann jeder beliebige ESPx Controller verwendet werden welcher über min. einen analogen Pin verfügt.

Aufbau der Schaltung für einen NodeMCU

In diesem Abschnitt möchte ich nun beschreiben, wie du eine Schaltung mit einem NodeMCU und einem Fotowiderstand aufbaust.

Du benötigst für diese Schaltung folgende Bauteile:

  • 1x NodeMCU,
  • 1x Fotowiderstand,
  • 1x 10kOhm Widerstand,
  • 4x Breadboardkabel,
  • 1x Breadboard mit 400 Pins

Anschluß & Schaltung

Der Fotowiderstand verfügt über 2 Beinchen, eines von diesen wird mit dem 10kOhm Widerstand und das andere mit 3,3V verbunden. Des Weiteren wird zwischen dem Fotowiderstand und dem Widerstand ein Breadboardkabel mit dem analogen Pin A0 verbunden.

Schaltung - NodeMCU mit Fotowiderstand
Schaltung – NodeMCU mit Fotowiderstand
NodeMCU mit Fotowiderstand
NodeMCU mit Fotowiderstand

Quellcode

Hier nun ein einfacher Sketch um die Funktionalität der Schaltung zu testen.

#define FOTORESISTOR A0
void setup() {
   Serial.begin(9600);
}   

void loop() {
   int value = analogRead(FOTORESISTOR);    //Ließt den Wert des Sensors vom analogen PIN A0
   Serial.println(value);
   delay(750);
}

Schritt 1 – Auslesen der Werte des Fotowiderstandes

Als Erstes wollen wir nun die Werte des Fotowiderstandes auslesen. Dazu erzeugen wir uns eine neue Funktion in unserem bestehenden Sketch aus dem ersten Tutorial.

Android App – ESP Sketch – 01_simpleTextHerunterladen
void callFotoresistor(){
  //Ließt den Wert des Fotowiderstandes vom analogen PIN A0
  int value = analogRead(FOTORESISTOR);
  //absenden des Wertes an den verbundenen Client
  sendResult("{\"msg\": \""+String(value)+"\"}");
}

Zusätzlich müssen wir diese Methode dem Server bekannt geben,
damit wir aus der Android App die Adresse „http://<<IP-Adresse>>/fotoresistor“ aufrufen können.

Dazu erweitern wir die Setup Funktion um folgenden Eintrag:

...
server.on("/greeting", callGreeting);
server.on("/fotoresistor", callFotoresistor);
     
server.begin(); // Starten des Servers.
...

Schritt 2 – Auswerten der JSON Daten

Nachdem wir nun die Werte senden können, müssen wir diese noch auswerten. Die Daten empfangen wir im JSON Format, um aus diesem Datenformat die Schlüssel/Wertepaare auszulesen, verwende ich die Bibliothek Google Gson.

Ein einfacher JUnitTest

Wie diese Bibliothek funktioniert möchte ich in einem kurzen und knackigen JUnit Testcase erläutern.

Es wird ein JSON String mit {„msg“:“Hello from ESP8266!“} der Gson Bibliothek übergeben und in die Klasse „SimpleData“ transformiert.

package de.draegerit.simpleGsonProject;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;

import org.junit.Test;

import com.google.gson.Gson;

public class ReadJsonData {

   //Beispiel JSON mit einem Schlüssel "msg" und dem Wert "Hello from ESP8266!"
   private static final String JSON_DATA = "{\"msg\":\"Hello from ESP8266!\"}";

   @Test
   public void readSimpleData() {
      //erzeugen einer Gson Instanz
      Gson gson = new Gson();
      //Mit der Methode "fromJson" wird das JSON Datenformat in die übergebene Klasse umgewandelt.
      //Es ist wichtig das für jeden Schlüssel im JSON ein Feld in der Klasse existiert und das der Datentyp stimmt.
      SimpleData data = gson.fromJson(JSON_DATA, SimpleData.class);
		
      //Testen ob die Daten erfolgreich umgewandelt wurden.
      assertNotNull(data);
      //Der Wert in unserer Klasse "SimpleData" sollte "Hello from ESP8266!" sein.
      assertEquals("Hello from ESP8266!", data.getMsg());
   }

   //Eine einfache Klasse zum testen des JSON Formates.
   class SimpleData {
	
      //Feld zum speichern der Nachricht.
      private String msg;

      public String getMsg() { return msg; }
      public void setMsg(String msg) { this.msg = msg; }
  }
}

Einbinden der Bibliothek in das Android Projekt

Bevor wir diese Bibliothek verwenden können, müssen wir diese in unser BuildScript einbauen. Dazu öffnen wir die Datei „build.gradle (Module: app)“. Im unteren Abschnitt der Datei finden wir die „dependencies“ dieses sind die Abhängigkeiten für unser Projekt.

Dort fügen wir die nachfolgende Zeile hinzu und klicken danach auf den Link „Sync Now“ (gelber Balken, oben links).

implementation group: 'com.google.code.gson', name: 'gson', version: '2.8.5'

Es wird nun die Bibliothek aus dem Internet geladen und das Projekt gebaut.

Wenn dieser Schritt erfolgreich ausgeführt wurde, kann mit der Implementation begonnen werden.

Umwandeln des JSON Formates

Wir erhalten vom ESP ein JSON mit eine Schlüssel / Wertepaar, der Schlüssel lautet in unserem Beispiel „msg“. D.h. wir erzeugen uns zunächst eine Klasse, welche später unser JSON repräsentieren soll.

package de.draegerit.esptutorialapp;

public class EspMessage {
    
   private String msg;

   public String getMsg() { return msg; }

   public void setMsg(String msg) { this.msg = msg; }
}

Da wir bereits eine Funktion haben um unsere Daten an den ESP zu senden wollen wir diese nutzen und auch auf das Empfangen reagieren. Wir ja nun zwei Anwendungsfälle einmal das eine Willkommensnachricht abgesendet wird und einmal nun unseren Fotowiderstand (und später wollen wir noch unseren NeoPixel steuern).

Hier bietet es sich an ein ENUM zu erzeugen welcher Werte für unsere „Actions“ enthält. Wir bauen hier nun noch mit ein das die Adresse enthalten ist und ob die Aktionen Parameter übergeben kann.

package de.draegerit.esptutorialapp;

public enum EAction {
   GREETING("greeting?text=", true), FOTORESISTOR("/fotoresistor", false);

   private String adress;
   private boolean hasParameter;

   EAction(String adress, boolean hasParameter) {
       this.adress = adress;
       this.hasParameter = hasParameter;
   }

   public String getAdress() { return adress; }

   public boolean isHasParameter() { return hasParameter; }
}

Und dieses ENUM übergeben wir unserem Konstruktor der Klasse „RequestAsyncTask“. Da wir vom ESP Controller einen Wert erwarten und keinen senden wollen schreiben wir uns einen neuen Konstruktor welcher keinen zusätzlichen Text erwartet. (Wir könnten auch ein „null“ anstelle des Textes setzen.)

private EAction action;
public RequestAsyncTask(String ipAdresse, String text, EAction action) {
   this.ipAdresse = ipAdresse;
   this.text = text;
   this.action = action;
}

public RequestAsyncTask(String ipAdresse, EAction action) {
   this(ipAdresse,null,action);
}

Zusätzlich müssen wir unsere bestehende Funktion für den Aufruf der Willkommensnachricht anpassen. In diesem Zuge benennen wir diese um von „sendRequest“ in „sendWellcomeGreetingRequest“.

private void sendWellcomeGreetingRequest(String ipAdresse, String text) {
   RequestAsyncTask connectionAsyncTask = new RequestAsyncTask(ipAdresse, text, EAction.GREETING);
   connectionAsyncTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
}

Nun passen wir unseren Aufruf in der Funktion „doInBackground“ an, damit wir unterscheiden können, ob wir eine Willkommensnachricht absenden oder aber einen Wert des Fotowiderstandes erhalten wollen.

StringBuffer urlBuffer = new StringBuffer();
urlBuffer.append("http://");
urlBuffer.append(ipAdresse);
urlBuffer.append("/");
urlBuffer.append(action.getAdress());
if(action.isHasParameter()){
  switch(action){
     case GREETING:
        urlBuffer.append(text);
     break;
  }
}

Layout anpassen

Nun wollen wir einen zweiten Button erzeugen und diesem in der Funktion „onClick“ die Aktion zuweisen einen Request an den ESP Controller zu senden, einen Wert des Fotowiderstandes auszulesen und zurückzuliefern.

Unser Layout „activity_main.xml“ erweitern wir wiefolgt:

<TableRow
   android:layout_width="match_parent"
   android:layout_height="match_parent"
   android:layout_marginTop="15dp">
   <Button
      android:id="@+id/wellcomeBtn"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_span="2"
      android:text="@string/btnWellcomeMsg" />
</TableRow>

<TableRow
   android:layout_width="match_parent"
   android:layout_height="match_parent"
   android:layout_marginTop="15dp">
   <Button
      android:id="@+id/fotoresistorBtn"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_span="2"
      android:text="@string/btnFotoresistorMsg" />
</TableRow>

Die Texte für die Schaltflächen werden in der Datei „strings.xml“ verwaltet, hier müssen wir nun die beiden Texte hinzufügen.

<resources>
...
  <string name="btnWellcomeMsg">Willkommensnachricht absenden</string>
  <string name="btnFotoresistorMsg">Fotowiderstand auslesen</string>
...
</resources>

Des Weiteren müssen wir (natürlich) unserem neuen Button eine Aktion zuweisen.

private Button fotoresistorBtn;
@Override
protected void onCreate(Bundle savedInstanceState) {
   ...
   fotoresistorBtn = findViewById(R.id.fotoresistorBtn);
   fotoresistorBtn.setOnClickListener(new View.OnClickListener() {
      @Override
      public void onClick(View v) {
         if (isNetworkAvailable()) {
          sendFotoresistorRequest(ipAdressEditText.getText().toString());
         }
      }
   });
   ...
}

Da wir unsere Funktion „doInBackground“ bereits multifunktional umgeschrieben haben brauchen wir nichts weiter tun. 

Ergebnis vom ESP Controller transformieren

Im nächsten Schritt wollen wir nun das Ergebnis (der Respond) vom ESP Controller in unser „EspMessage“ Objekt transformieren / umwandeln. Dazu nutzen wir wie eingangs erwähnt die Bibliothek Google Gson.

@Override
protected void onPostExecute(String result) {
   super.onPostExecute(result);
   Log.i("ESPTutorialApp", result);
   if (errorMsg == null && result.trim().length() > 0) {
      Gson gson = new Gson();
      EspMessage message = gson.fromJson(result, EspMessage.class);
      if (message != null) {
         textView.setText(message.getMsg());
      }
   } else if (errorMsg != null) {
      showErrorMessage(errorMsg);
   }
}

Nun wird uns der Wert des Fotowiderstandes in der App angezeigt, wenn wir den Button „FOTOWIDERSTAND AUSLESEN“ betätigen.

aktueller Wert des Fotowiderstandes vom WittyCloud
aktueller Wert des Fotowiderstandes vom WittyCloud

Download

Android App Entwicklung: ESP Controller ansprechen, Ausbaustufe 2Herunterladen
Android App – ESP Sketch – 02_fotoresistorHerunterladen

Ausblick

Nun nachdem wir den Wert lesen können, wollen wir uns diesen in einem Liniendiagramm anzeigen lassen. Dazu müssen wir jedoch unser Layout (fast) komplett umstellen. Im nächsten Tutorial werden wir also eine Navigationsleiste hinzufügen und für jede bestehende Funktion eine Extraseite einrichten. 

Schreibe einen Kommentar Antworten abbrechen

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

Fragen oder Feedback?

Du hast eine Idee, brauchst Hilfe oder möchtest Feedback loswerden?
Support-Ticket erstellen

Newsletter abonnieren

Bleib auf dem Laufenden: Erhalte regelmäßig Updates zu neuen Projekten, Tutorials und Tipps rund um Arduino, ESP32 und mehr – direkt in dein Postfach.

Jetzt Newsletter abonnieren

Unterstütze meinen Blog

Wenn dir meine Inhalte gefallen, freue ich mich über deine Unterstützung auf Tipeee.
So hilfst du mit, den Blog am Leben zu halten und neue Beiträge zu ermöglichen.

draeger-it.blog auf Tipeee unterstützen

Vielen Dank für deinen Support!
– Stefan Draeger

Kategorien

Tools

  • Unix-Zeitstempel-Rechner
  • ASCII Tabelle
  • Spannung, Strom, Widerstand und Leistung berechnen
  • Widerstandsrechner
  • 8×8 LED Matrix Tool
  • 8×16 LED Matrix Modul von Keyestudio
  • 16×16 LED Matrix – Generator

Links

Blogverzeichnis Bloggerei.de TopBlogs.de das Original - Blogverzeichnis | Blog Top Liste Blogverzeichnis trusted-blogs.com

Stefan Draeger
Königsberger Str. 13
38364 Schöningen

Tel.: 01778501273
E-Mail: info@draeger-it.blog

Folge mir auf

  • Impressum
  • Datenschutzerklärung
  • Disclaimer
  • Cookie-Richtlinie (EU)
©2025 Technik Blog | Built using WordPress and Responsive Blogily theme by Superb
Cookie-Zustimmung verwalten
Wir verwenden Technologien wie Cookies, um Geräteinformationen zu speichern und/oder darauf zuzugreifen. Wir tun dies, um das Surferlebnis zu verbessern und um personalisierte Werbung anzuzeigen. Wenn Sie diesen Technologien zustimmen, können wir Daten wie das Surfverhalten oder eindeutige IDs auf dieser Website verarbeiten. Wenn Sie Ihre Zustimmung nicht erteilen oder zurückziehen, können bestimmte Funktionen beeinträchtigt werden.
Funktional Immer aktiv
Die technische Speicherung oder der Zugang ist unbedingt erforderlich für den rechtmäßigen Zweck, die Nutzung eines bestimmten Dienstes zu ermöglichen, der vom Teilnehmer oder Nutzer ausdrücklich gewünscht wird, oder für den alleinigen Zweck, die Übertragung einer Nachricht über ein elektronisches Kommunikationsnetz durchzuführen.
Vorlieben
Die technische Speicherung oder der Zugriff ist für den rechtmäßigen Zweck der Speicherung von Präferenzen erforderlich, die nicht vom Abonnenten oder Benutzer angefordert wurden.
Statistiken
Die technische Speicherung oder der Zugriff, der ausschließlich zu statistischen Zwecken erfolgt. Die technische Speicherung oder der Zugriff, der ausschließlich zu anonymen statistischen Zwecken verwendet wird. Ohne eine Vorladung, die freiwillige Zustimmung deines Internetdienstanbieters oder zusätzliche Aufzeichnungen von Dritten können die zu diesem Zweck gespeicherten oder abgerufenen Informationen allein in der Regel nicht dazu verwendet werden, dich zu identifizieren.
Marketing
Die technische Speicherung oder der Zugriff ist erforderlich, um Nutzerprofile zu erstellen, um Werbung zu versenden oder um den Nutzer auf einer Website oder über mehrere Websites hinweg zu ähnlichen Marketingzwecken zu verfolgen.
Optionen verwalten Dienste verwalten Verwalten von {vendor_count}-Lieferanten Lese mehr über diese Zwecke
Einstellungen anzeigen
{title} {title} {title}