我已经制作了一款通过HC-05蓝牙模块连接到Arduino Mega 2560的应用程序。 我成功通过蓝牙向Arduino发出命令,但相反的通信显然不起作用。我不知道问题是在Arduino还是Android方面。
Arduino使用以下简单说明发送消息: #包括 ... SoftwareSerial蓝牙(12,11);
void setup(){
Serial.begin(9600);
bluetooth.begin(9600);
...
}
void loop(){
...
bluetooth.listen();
while (bluetooth.available() > 0) {
char inByte = bluetooth.read();
if(inByte == '0') {
bluetooth.print('a');
delay(500);
}
}
...
}
相反Android代码如下:
package com.example.arduo;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.UUID;
import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.ToggleButton;
public class MainActivity extends Activity implements OnClickListener {
Button Connect;
ToggleButton OnOff;
TextView Result;
private String dataToSend;
private static final String TAG = "Jon";
private BluetoothAdapter mBluetoothAdapter = null;
private BluetoothSocket btSocket = null;
private OutputStream outStream = null;
private static String address = "00:14:02:13:00:10";
private static final UUID MY_UUID = UUID
.fromString("00001101-0000-1000-8000-00805F9B34FB");
private InputStream inStream = null;
Handler handler = new Handler();
byte delimiter = 10;
boolean stopWorker = false;
int readBufferPosition = 0;
byte[] readBuffer = new byte[1024];
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Connect = (Button) findViewById(R.id.connect);
OnOff = (ToggleButton) findViewById(R.id.tgOnOff);
Result = (TextView) findViewById(R.id.msgJonduino);
Connect.setOnClickListener(this);
OnOff.setOnClickListener(this);
CheckBt();
BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(address);
Log.e("Jon", device.toString());
}
@Override
public void onClick(View control) {
switch (control.getId()) {
case R.id.connect:
Connect();
break;
case R.id.tgOnOff:
if (OnOff.isChecked()) {
dataToSend = "1";
writeData(dataToSend);
} else if (!OnOff.isChecked()) {
dataToSend = "0";
writeData(dataToSend);
}
break;
}
}
private void CheckBt() {
mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
if (!mBluetoothAdapter.isEnabled()) {
Toast.makeText(getApplicationContext(), "Bluetooth Disabled !",
Toast.LENGTH_SHORT).show();
}
if (mBluetoothAdapter == null) {
Toast.makeText(getApplicationContext(),
"Bluetooth null !", Toast.LENGTH_SHORT)
.show();
}
}
public void Connect() {
Log.d(TAG, address);
BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(address);
Log.d(TAG, "Connecting to ... " + device);
mBluetoothAdapter.cancelDiscovery();
try {
btSocket = device.createRfcommSocketToServiceRecord(MY_UUID);
btSocket.connect();
Log.d(TAG, "Connection made.");
Toast.makeText(getApplicationContext(), "Connessione effettuata",
Toast.LENGTH_SHORT).show();
} catch (IOException e) {
try {
btSocket.close();
} catch (IOException e2) {
Log.d(TAG, "Unable to end the connection");
Toast.makeText(getApplicationContext(), "Impossibile terminare la connessione",
Toast.LENGTH_SHORT).show();
}
Log.d(TAG, "Socket creation failed");
Toast.makeText(getApplicationContext(), "Creazione socket fallita.",
Toast.LENGTH_SHORT).show();
}
beginListenForData();
}
private void writeData(String data) {
try {
outStream = btSocket.getOutputStream();
} catch (IOException e) {
Log.d(TAG, "Bug BEFORE Sending stuff", e);
Toast.makeText(getApplicationContext(), "Bug prima di mandare i dati",
Toast.LENGTH_SHORT).show();
}
String message = data;
byte[] msgBuffer = message.getBytes();
try {
outStream.write(msgBuffer);
Toast.makeText(getApplicationContext(), "Dati inviati correttamente",
Toast.LENGTH_SHORT).show();
} catch (IOException e) {
Log.d(TAG, "Bug while sending stuff", e);
Toast.makeText(getApplicationContext(), "Bug mandando i dati",
Toast.LENGTH_SHORT).show();
}
}
@Override
protected void onDestroy() {
super.onDestroy();
try {
btSocket.close();
} catch (IOException e) {
}
}
public void beginListenForData() {
try {
inStream = btSocket.getInputStream();
} catch (IOException e) {
}
Thread workerThread = new Thread(new Runnable()
{
public void run()
{
while(!Thread.currentThread().isInterrupted() && !stopWorker)
{
try
{
int bytesAvailable = inStream.available();
if(bytesAvailable > 0)
{
byte[] packetBytes = new byte[bytesAvailable];
inStream.read(packetBytes);
for(int i=0;i<bytesAvailable;i++)
{
byte b = packetBytes[i];
if(b == delimiter)
{
byte[] encodedBytes = new byte[readBufferPosition];
System.arraycopy(readBuffer, 0, encodedBytes, 0, encodedBytes.length);
final String data = new String(encodedBytes, "US-ASCII");
readBufferPosition = 0;
handler.post(new Runnable()
{
public void run()
{
// if(Result.getText().toString().equals("..")) {
Result.setText(data);
// } else {
// Result.append("\n"+data);
//}
/* You also can use Result.setText(data); it won't display multilines
*/
}
});
}
else
{
readBuffer[readBufferPosition++] = b;
}
}
}
}
catch (IOException ex)
{
stopWorker = true;
}
}
}
});
workerThread.start();
}
}
有人知道为什么Android没有收到或只是显示Arduino发送的角色? 谢谢大家!!
答案 0 :(得分:3)
我找到了一种有效的方式。我刚刚使用此代码更改了Android代码,对于遇到同样问题的人来说这很有用!
package bt.andard.btandard;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.lang.reflect.Method;
import java.util.UUID;
import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.Intent;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends Activity {
private static final String TAG = "bluetooth2";
Button btnOn, btnOff;
TextView txtArduino;
Handler h;
final int RECEIVE_MESSAGE = 1; //1 // Status for Handler
private BluetoothAdapter btAdapter = null;
private BluetoothSocket btSocket = null;
private StringBuilder sb = new StringBuilder();
private ConnectedThread mConnectedThread;
// SPP UUID service
private static final UUID MY_UUID = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");
// MAC-address of Bluetooth module (you must edit this line)
private static String address = "00:14:02:13:00:10";
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
btnOn = (Button) findViewById(R.id.btnOn); // button LED ON
btnOff = (Button) findViewById(R.id.btnOff); // button LED OFF
txtArduino = (TextView) findViewById(R.id.txtArduino); // for display the received data from the Arduino
h = new Handler() {
public void handleMessage(android.os.Message msg) {
switch (msg.what) {
case RECEIVE_MESSAGE: // if receive massage
byte[] readBuf = (byte[]) msg.obj;
String strIncom = new String(readBuf, 0, msg.arg1); // create string from bytes array
Toast.makeText(getBaseContext(), strIncom, Toast.LENGTH_LONG).show();
sb.append(strIncom); // append string
int endOfLineIndex = sb.indexOf("\r\n"); // determine the end-of-line
if (endOfLineIndex > 0) { // if end-of-line,
String sbprint = sb.substring(0, endOfLineIndex); // extract string
sb.delete(0, sb.length()); // and clear
txtArduino.setText("Data from Arduino: " + strIncom); // update TextView
// btnOff.setEnabled(true);
// btnOn.setEnabled(true);
}
//Log.d(TAG, "...String:"+ sb.toString() + "Byte:" + msg.arg1 + "...");
break;
}
};
};
btAdapter = BluetoothAdapter.getDefaultAdapter(); // get Bluetooth adapter
checkBTState();
btnOn.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
// btnOn.setEnabled(false);
mConnectedThread.write("1"); // Send "1" via Bluetooth
//Toast.makeText(getBaseContext(), "Turn on LED", Toast.LENGTH_SHORT).show();
}
});
btnOff.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
// btnOff.setEnabled(false);
mConnectedThread.write("0"); // Send "0" via Bluetooth
//Toast.makeText(getBaseContext(), "Turn off LED", Toast.LENGTH_SHORT).show();
}
});
}
private BluetoothSocket createBluetoothSocket(BluetoothDevice device) throws IOException {
if(Build.VERSION.SDK_INT >= 10){
try {
final Method m = device.getClass().getMethod("createInsecureRfcommSocketToServiceRecord", new Class[] { UUID.class });
return (BluetoothSocket) m.invoke(device, MY_UUID);
} catch (Exception e) {
Log.e(TAG, "Could not create Insecure RFComm Connection",e);
}
}
return device.createRfcommSocketToServiceRecord(MY_UUID);
}
@Override
public void onResume() {
super.onResume();
Log.d(TAG, "...onResume - try connect...");
// Set up a pointer to the remote node using it's address.
BluetoothDevice device = btAdapter.getRemoteDevice(address);
// Two things are needed to make a connection:
// A MAC address, which we got above.
// A Service ID or UUID. In this case we are using the
// UUID for SPP.
try {
btSocket = createBluetoothSocket(device);
} catch (IOException e) {
errorExit("Fatal Error", "In onResume() and socket create failed: " + e.getMessage() + ".");
}
// Discovery is resource intensive. Make sure it isn't going on
// when you attempt to connect and pass your message.
btAdapter.cancelDiscovery();
// Establish the connection. This will block until it connects.
Log.d(TAG, "...Connecting...");
try {
btSocket.connect();
Log.d(TAG, "....Connection ok...");
} catch (IOException e) {
try {
btSocket.close();
} catch (IOException e2) {
errorExit("Fatal Error", "In onResume() and unable to close socket during connection failure" + e2.getMessage() + ".");
}
}
// Create a data stream so we can talk to server.
Log.d(TAG, "...Create Socket...");
mConnectedThread = new ConnectedThread(btSocket);
mConnectedThread.start();
}
@Override
public void onPause() {
super.onPause();
Log.d(TAG, "...In onPause()...");
try {
btSocket.close();
} catch (IOException e2) {
errorExit("Fatal Error", "In onPause() and failed to close socket." + e2.getMessage() + ".");
}
}
private void checkBTState() {
// Check for Bluetooth support and then check to make sure it is turned on
// Emulator doesn't support Bluetooth and will return null
if(btAdapter==null) {
errorExit("Fatal Error", "Bluetooth not support");
} else {
if (btAdapter.isEnabled()) {
Log.d(TAG, "...Bluetooth ON...");
} else {
//Prompt user to turn on Bluetooth
Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
startActivityForResult(enableBtIntent, 1);
}
}
}
private void errorExit(String title, String message){
Toast.makeText(getBaseContext(), title + " - " + message, Toast.LENGTH_LONG).show();
finish();
}
private class ConnectedThread extends Thread {
private final InputStream mmInStream;
private final OutputStream mmOutStream;
public ConnectedThread(BluetoothSocket socket) {
InputStream tmpIn = null;
OutputStream tmpOut = null;
// Get the input and output streams, using temp objects because
// member streams are final
try {
tmpIn = socket.getInputStream();
tmpOut = socket.getOutputStream();
} catch (IOException e) { }
mmInStream = tmpIn;
mmOutStream = tmpOut;
}
public void run() {
byte[] buffer = new byte[256]; // buffer store for the stream
int bytes; // bytes returned from read()
// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// Read from the InputStream
bytes = mmInStream.read(buffer); // Get number of bytes and message in "buffer"
h.obtainMessage(RECEIVE_MESSAGE, bytes, -1, buffer).sendToTarget(); // Send to message queue Handler
} catch (IOException e) {
break;
}
}
}
/* Call this from the main activity to send data to the remote device */
public void write(String message) {
Log.d(TAG, "...Data to send: " + message + "...");
byte[] msgBuffer = message.getBytes();
try {
mmOutStream.write(msgBuffer);
} catch (IOException e) {
Log.d(TAG, "...Error data send: " + e.getMessage() + "...");
}
}
}
}