How to connect Android app to Arduino using HTTP and Arduino Webserver

This tutorial describes how to connect an Android app to Arduino using a Webserver that runs on Arduino. The Android app uses the HTTP protocol to connect to Arduino. Therefore we need an Arduino Webserver that manages the HTTP connections.

To connect Android to Arduino, we need:

Android app side:

  • Color picker View
  • Http client that sends data to Arduin

Arduino side:

  • HTTP server to get data
  • Simple JSON parser
  • RGB led controller

What will you learn in this Arduino tutorial? You will learn how to:

  • develop an Arduino Webserver
  • manage incoming HTTP connection in Arduino
  • control an RGB LEDs strip using Android app
  • develop an Android app that sends data to Arduino

Introduction

This is an interesting topic because it mixes two ecosystems together and you can apply this Arduino IoT project in different scenarios.  This project is an evolution of a project described in the previous posts called Internet of Things with Arduino and Android. First of all, this project covers how to integrate Arduino and Android so that they exchange data.

This project covers a common scenario where there is a need to send data to Arduino from an Android app. The easiest way is using the HTTP protocol and developing an Arduino Webserver that handles the incoming HTTP connections from the Android app. Through the HTTP, Arduino receives commands from the Android app.

To make things more interesting, this Arduino tutorial will describe how to control an RGB LEDs strips from an Android app. This example is interesting because of two different aspects:

  • first, we can use this Arduino project as a prototyping project when we want to control RGB LEDs
  • Second, the integration between Android and Arduino is a common use case, especially when it happens through HTTP.

First of all, if you are new to the Internet of things project, you should read Internet of things project with Arduino and Android, so that you get introduced to IoT projects.

The final result is shown in the video below:

Connecting Arduino and Android using HTTP

Before digging into the project details, it is useful to have an overview of this Arduino IoT project and how we will use the Android app to send data to Arduino through the HTTP:

Integrating Arduino and Android using HTTP through Arduino Web server

The picture above summarizes the concepts covered until now.

Now we know what to do let’s start.

Developing the Android app to control RGB LED color

To control RGB LED from an Android app, the first step is creating an Android color picker UI so that the user can pick the color he wants to see on the Arduino led (RGB). Let us start with the final Android UI result:

android color picker to select color for RGB strips connected to Arduino

To create this interface we use an interesting open source project called Color Picker. This component is very easy to use.

At the first step, we create the main layout based on Android Floating Action Button:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
		xmlns:app="http://schemas.android.com/apk/res-auto"
		xmlns:tools="http://schemas.android.com/tools"
		android:layout_width="match_parent"
		android:layout_height="match_parent"
		android:paddingBottom="@dimen/activity_vertical_margin"
		android:paddingLeft="@dimen/activity_horizontal_margin"
		android:paddingRight="@dimen/activity_horizontal_margin"
		android:paddingTop="@dimen/activity_vertical_margin"
		app:layout_behavior="@string/appbar_scrolling_view_behavior"
		tools:context="com.survivingwithandroid.rgbcontroller.MainActivity"
		tools:showIn="@layout/activity_main">
	<TextView android:layout_width="wrap_content"
			android:layout_height="wrap_content"
			android:text="Control Arduino RGB Led"
			android:layout_centerInParent="true"
			android:textSize="25sp"/>
	<TextView android:layout_width="wrap_content"
			android:layout_height="wrap_content"
			android:layout_alignParentBottom="true"
			android:layout_alignParentLeft="true"
			android:layout_marginLeft="5dp"
			android:id="@+id/msg"/>
</RelativeLayout>Code language: HTML, XML (xml)

As a result, when the user presses the FAB the app has to show the Color picker dialog:

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);
    ......
    FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
          // Handle FAB click event
        }
      }
    }Code language: Java (java)

It is time to show the Color picker dialog that will control RGB led in the onClick method:

ColorPickerDialogBuilder
  .with(MainActivity.this)
  .setTitle("Choose RGB color")
  .initialColor(Color.WHITE)
  .wheelType(ColorPickerView.WHEEL_TYPE.FLOWER)
  .lightnessSliderOnly()
  .density(12)
  .setOnColorSelectedListener(new OnColorSelectedListener() {
    @Override
    public void onColorSelected(int selectedColor) {
      // Nothing to do...
    }
  })
  .setPositiveButton("ok", new ColorPickerClickListener() {
    @Override
    public void onClick(DialogInterface dialog,
      int selectedColor, Integer[] allColors) {
      int r = (selectedColor << 16) && 0xFF;
      int g = (selectedColor << 8) && 0xFF;
      int b = (selectedColor << 0) &&  0xFF;
      Log.d("RGB", "R [" + r + "] - G [" + g + "] - B [" + b + "]");
      sendColor(r, g, b);
    }
  })
  .setNegativeButton("cancel", new DialogInterface.OnClickListener() {
    @Override
    public void onClick(DialogInterface dialog, int which) {}
  })
  .build()
  .show();Code language: Java (java)

As you can see this component is very simple to use, when the user clicks OK button the app extracts the Red, Green and Blue component and sends it to Arduino using a simple JSON through HTTP.

How to build an Android HTTP client to send data to Arduino

To send data to Arduino from the Android app, it is necessary to create a simple HTTP client that sends Red, Green and Blue component as JSON string.

Arduino will use this information to control the RGB LED. The Android HTTP client is very simple and it is based on OkHttp.

private void sendColor(int r, int g, int b) {
    Log.d("RGB", "Sending data to Arduino....");
    Request req = new Request.Builder().url(URL)
      .post(RequestBody.create(JSON, createJSON(r, g, b)))
      .build();
    tv.setText("Sending data to Arduino...");
    client.newCall(req).enqueue(new Callback() {
          @Override
          public void onFailure(Call call, IOException e) { // Handle call failure }
            @Override
            public void onResponse(Call call, Response response) throws IOException {
              // OK Response...inform the user }
            });
        }Code language: Java (java)

where createJSON method is very simple:

private String createJSON(int r, int g, int b) {
  return "{\"color\": [" + r + "," + g + "," + b + "]}";
}Code language: Java (java)

it returns the three colors values. The Android app is completed, as you can see with a few lines of code we created a nice Android app that will control RGB LED connected to Arduino.

How to connect and control RGB LEDs connected to Arduino: schematic

Now the Android client side is ready, therefore it is time to build the Arduino sketch so that it is possible to control LEDs connected to Arduino. This tutorial uses common anode RGB LED, that means the Vcc is connected to the anode. If you use a common cathode led the cathode must be connected to the ground. The Arduino sketch is shown below:

arduino led: control RGB led using android app

The three led pins are connected to Arduino PWM using a 300-ohm resistance.

That’s all, the “hardware” part is ready to be used. If you want to test the Arduino LED to know if everything works correctly you can write a simple sketch to check if the Arduino RGB is working properly. In the diagram above, the ethernet shield is not shown to simplify the diagram. Of course, to connect Arduino to Internet is necessary to have an ethernet shield or a WI-FI shield. This tutorial uses the ethernet shield.

Arduino HTTP WebServer

In addition to the “hardware” part, Arduino has to accept HTTP connection because the Android client sends data (the RGB values) using HTTP. Therefore, it is necessary to build a simple HTTP server that parses the incoming requests and extracts the values. In the setup method of the sketch, we initialize the Arduino PINs to control the RGB LED and the ethernet IP.

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  // Pin mode
  pinMode(redPin, OUTPUT);
  pinMode(bluePin, OUTPUT);
  pinMode(greenPin, OUTPUT);
  Serial.print("Ready...");
  // Ethernet.begin(mac, ip);
  server.begin();
  Serial.println("Begin...");
}Code language: C++ (cpp)

Finally, it is time to accept incoming requests and parse them.

Accept HTTP request and Parse the JSON message using Arduino

To parse the HTTP request and extract data, we can use this piece of code:

void loop() {
  // Is there a client (Our Android smartphone)
  EthernetClient client = server.available();
  if (client) {
    // Let's start reading
    boolean isLastLine = true;
    boolean isBody = false;
    header = "";
    reqData = "";
    int contentLen = 0;
    Serial.print("Client connected!");
    while (client.connected()) {
      if (client.available()) {
        // Read data
        char c = client.read();
        if (contentSize == contentLen) {
          Serial.println("Body [" + reqData + "]");
          // Extract the JSON string like [r,g,b]
          int pos1 = reqData.indexOf("[");
          int pos2 = reqData.lastIndexOf("]");
          // Parse the string looking for ,
          String colors = reqData.substring(pos1 + 1, pos2);
          Serial.println("Colors [" + colors + "]");
          int idx1 = colors.indexOf(',');
          int idx2 = colors.indexOf(',', idx1 + 1);
          int idx3 = colors.indexOf(',', idx2 + 1);
          String sRed = colors.substring(0, idx1);
          String sGreen = colors.substring(idx1 + 1, idx2);
          String sBlue = colors.substring(idx2 + 1, idx3);
          // Convert the Red, Green and Blue string values to int
          int red = sRed.toInt();
          int green = sGreen.toInt();
          int blue = sBlue.toInt();
          // Set the RGB led color according to the values sent by the Android client
          setColor(red, green, blue);
          // Create the response to client
          client.println("HTTP/1.1 200 OK");
          client.println("Content-Type: text/html");
          client.println("Connection: close");
          client.println();
          // send web page
          client.println("");
          client.println("");
          delay(1);
          break;
        }
        if (c == '\n' & amp; & amp; isLastLine) {
          isBody = true;
          int pos = header.indexOf(CONTENT_LENGTH_TXT);
          String tmp = header.substring(pos, header.length());
          //Serial.println("Tmp ["+tmp+"]");
          int pos1 = tmp.indexOf("\r\n");
          String size = tmp.substring(CONTENT_LENGTH_TXT.length(), pos1);
          Serial.println("Size [" + size + "]");
          contentSize = size.toInt();
        }
        if (isBody) {
          reqData += c;
          contentLen++;
        } else {
          header += c;
        }
        if (c == '\n') {
          isLastLine = true;
        } else if (c != '\r') {
          isLastLine = false;
        }
      }
    }
    // Close connection
    Serial.println("Stop..");
    client.stop();
  }
}Code language: C++ (cpp)

The source code seems to be complex but it is very simple if you look at it carefully. It is simply an HTTP Arduino server.
The last part is setting the Arduino led color:

void setColor(int red, int green, int blue) {
  #ifdef COMMON_ANODE
   red = 255 - red;
   green = 255 - green;
   blue = 255 - blue;
  #endif
  analogWrite(redPin, red);
  analogWrite(bluePin, green);
  analogWrite(greenPin, blue);
}Code language: C++ (cpp)

Notice that if we use a common anode, we have to invert the values.

Recommended:
Arduino MKR1000 Tutorial
How to use Ubidots with Arduino to build IoT project

Conclusion

At the end of this post, you know how to send data from an Android app to Arduino through the HTTP using an Arduino Web server that accepts incoming connections. In other words, Android app remotely controls the Arduino board that in turn is the Arduino led controller.  There are other ways to exchange data with Arduino: one method is based on Arduino Rest API. This project is useful because it teaches how to exchange data between Arduino and the Android app. In this scenario, the Android app controls an RGB Led connected to Arduino, anyway this project can be further extended and it is possible to control other kinds of peripherals. Once you know how to control a simple RGB LED from Android you can further extend the project implementing a DIY cloud lamp that can be controlled using your smartphone.

    1. JJ April 15, 2016
      • Francesco Azzola April 15, 2016
    2. meccip May 3, 2016
      • Francesco Azzola May 4, 2016
        • meccip May 4, 2016
          • Francesco Azzola May 6, 2016
    3. aryo August 13, 2016
    4. Pingback: Arduino Data logger: Xively IoT platform August 25, 2016
    5. Vicos August 30, 2016
    6. redim October 6, 2016

    Add Your Comment