Android и Arduino. Привет Android из Arduino

В 3-ей части статьи нами был рассмотрен проект для передачи данных от Android-устройства в ADK-плату. Сейчас мы рассмотрим обратную задачу.

Но для того, чтобы немного усложнить наш пример, мы немного усложним нашу задачу. Передавать в Android Нужно будет 2 переменные: первая будет содержать случайное число, а вторая — состояние нажатия кнопки. На Android устройстве первая переменная будет отображаться простым текстом, а вторая будет влиять на переключатель. Т.е. если кнопка, подключенная к плате Arduino ADK нажата, то и переключатель на Android устройстве будет включен.

Программа для Arduino

Скетч для Arduino будет следующий:

#include
#include

// Adb connection.
Connection * connection;
long lastTime;
byte rndNum; // Случайное число
int buttonState = 0; // Состояние кнопки
uint16_t tosend; // Данные для передачи в Android
const int buttonPin = 2; // PIN-подключенной кнопки

void setup()
{
pinMode(buttonPin, INPUT);

// Инициализация подсистемы ADB.
ADB::init();

// Open an ADB stream to the phone’s shell. Auto-reconnect. Use any unused port number eg:4568
connection = ADB::addConnection(«tcp:4568», true, NULL);

//Serial.begin(115200);
randomSeed(analogRead(0)); // Для генератора случайных чисел (чтобы не повторялись значения)
}

void loop()
{
if ((millis() — lastTime) > 100) // Условие выполняется каждые 100 мс
{
rndNum = random(1, 99); // Генерируем случайное число от 1 до 99
buttonState = digitalRead(buttonPin); // Считываем состояние цифр. входа

tosend = (rndNum << 8) | buttonState; // Формируем слово из 2-х байт

Serial.println(tosend,BIN);
connection->write(2,(uint8_t*)&tosend); // Отсылаем 2 байта

lastTime = millis();
}

// Poll the ADB subsystem.
ADB::poll();
}

Код я постарался хорошо прокомментировать, поэтому расписывать подробно его не буду. Здесь используется основная функция connection->write(), которая отсылает данные по USB кабелю через TCP на Android устройство. В функции передается 2 параметра, первый — кол-во байт для пересылки, второй — сами данные. Обратите, внимание, что предварительно, мы упаковали 2 байта данных в 2-х байтовое слово.

Компилируем скетч и загружаем его в нашу плату.

Программа для Android

Создание проекта, настройку манифест файла вы можете посмотреть в предыдущей статье.

Немного про активити. В прошлый раз я говорил, что activity можно создавать при помощи графического интерфейса и при помощи XML файла. В этот раз я приведу XML-файл нашего активити (см. в файлах)

Ключевыми элементами здесь являются switch1 (переключатель) и textView2 (текстовое поле). Вот что должно получиться:

Теперь открываем файл /src/com/example/arduino53/MainActivity.java, все в нем удаляем и копируем следующие строки:

package com.example.arduino53;

import java.io.IOException;

import org.microbridge.server.Server;
import org.microbridge.server.AbstractServerListener;

import android.os.AsyncTask;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.widget.Switch;
import android.widget.TextView;

public class MainActivity extends Activity {

private int Ard_data1 = 0;
private int Ard_data2 = 0;
public final String APP_NAME = «arduino53»;

Server server = null;

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Создаем TCP сервер (на основе сервера MicroBridge LightWeight)
try
{
server = new Server(4568); //Этот же порт необходимо использовать и на ADK-плате
server.start();
} catch (IOException e)
{
Log.e(APP_NAME, «Unable to start TCP server», e);
System.exit(-1);
}

server.addListener(new AbstractServerListener() {

@Override
public void onReceive(org.microbridge.server.Client client, byte[] data)
{
Log.d(APP_NAME, «data0:»+data[0]+»; data1:»+data[1]);
if (data.length<2) Log.e(APP_NAME, «Размер данных менее 2-х байт:»+data.length);

Ard_data1 = data[0];
Ard_data2 = data[1];

//Any update to UI can not be carried out in a non UI thread like the one used
//for Server. Hence runOnUIThread is used.
runOnUiThread(new Runnable() {
//@Override
public void run() {
new UpdateData().execute(Ard_data1,Ard_data2);
}
});
}
});
}

@Override
protected void onDestroy (){
super.onDestroy();
server.stop();
}

class UpdateData extends AsyncTask {
// Called to initiate the background activity
@Override
protected Integer[] doInBackground(Integer… ArdState) {
return (ArdState); //Возвращаем в onPostExecute()
}

@Override
protected void onProgressUpdate(Integer… values) {
super.onProgressUpdate(values);
// Not used in this case
}

@Override
protected void onPostExecute(Integer… result) {
//Log.d(APP_NAME, «onPostExecute0:»+result[0]);
//Log.d(APP_NAME, «onPostExecute1:»+result[1]);

TextView txt_btn_Arduino = (TextView) findViewById(R.id.textView2);
txt_btn_Arduino.setText(String.valueOf(result[1])); // Выводим на activity RND число полученное от ADK

Switch switch1 = (Switch) findViewById(R.id.switch1);

if(result[0] == 1){
switch1.setChecked(true);
}
else switch1.setChecked(false);
}
}
}

Здесь мы для класса server определяем метод server.addListener(new AbstractServerListener() {}), а также onReceive() который вызывается каждый раз, при получении данных от сервера MicroBridge.

Затем мы создаем новый поток. Для этого используется класс AsyncTask с тремя методами (всего их 4, но мы один из них не используем):
doInBackground() — выполняется в фоновом потоке. Здесь необходимо производить сложные вычисления, но мы здесь ничего не делаем, а просто возвращаем объект в метод onPostExecute()
onProgressUpdate() — используется для ввода промежуточных результатов (в нашей программе не задействован)
onPostExecute() — выполняется после метода doInBackground(). В нем мы принимаем данные в массив result и отображаем данные на экране устройства в элементе TextView, а также двигаем переключатель Switch в зависимости от положения нажатой внешней кнопки.

Обращаю ваше внимание, что создание UI элементов в классе AsyncTask возможно лишь в методе onPostExecute().

Ниже вы можете скачать проекты для Arduino и Android, а также все необходимые библиотеки


Прикрепленные файлы:

Добавить комментарий

Ваш адрес email не будет опубликован.