I have downloaded the android sample of Bluetooth chat app to send text between two android devices using Bluetooth.
I have installed and run this app in two android devices.
I faced many problems in that code
1. Cleared the Service discovery failed exception:
For service discovery failed exception, In Bluetooth Chat Service, I have checked sdk version and for the sdk version which is greater than Ginger Bread,
I have used Method class to invoke RfCOMM socket connection and my first exception is solved in this approach.
Exception Code
tmp = device.createRfcommSocketToServiceRecord(MY_UUID);
Fixed Exception code
try {
if (Build.VERSION.SDK_INT < 9) {
try {
tmp = device.createRfcommSocketToServiceRecord(MY_UUID);
} catch (IOException e1) {
e1.printStackTrace();
}
} else {
Method m = null;
try {
m = device.getClass().getMethod("createRfcommSocket",
new Class[] { int.class });
} catch (NoSuchMethodException e) {
e.printStackTrace();
}
try {
tmp = (BluetoothSocket) m.invoke(device, 1);
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
} catch (Exception e) {
Log.e(TAG, "create() failed", e);
}
2. Cleared java.io.IOException: Software caused connection abort
I have made check whether the InputStream is available
Exception Code
bytes = mmInStream.read(buffer);
Fixed Exception code
if (mmInStream.available() > 0) {
// Read from the InputStream
bytes = mmInStream.read(buffer);
Now my problem is when I try to send data between connected devices, it throws the following error message "Connection Reset By Peer" while writing to output stream
Exception code:
public void write(byte[] buffer, int start, int end) {
mHandler.obtainMessage(BluetoothChat.MESSAGE_WRITE, -1, -1, buffer).sendToTarget();
if (mmOutStream !=null) {
try {
mmOutStream.write(buffer);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
else{
Log.e("OutputStream Null","");
}
}
== Update ==
Even though it shows that both devices are connected, the accept method returns fail
**06-19 10:30:23.625: D/BluetoothChatService(2630): connected
06-19 10:30:23.625: D/BluetoothChatService(2630): cancel Thread[AcceptThread,5,main]
06-19 10:30:23.625: V/BluetoothSocket.cpp(2630): abortNative
06-19 10:30:23.625: V/BluetoothSocket.cpp(2630): ...asocket_abort(50) complete
06-19 10:30:23.625: V/BluetoothSocket.cpp(2630): ...accept(50, RFCOMM) = -1 (errno 125)
06-19 10:30:23.632: E/BluetoothChatService(2630): accept() failed
06-19 10:30:23.632: E/BluetoothChatService(2630): java.io.IOException: Operation Canceled
06-19 10:30:23.632: E/BluetoothChatService(2630): at android.bluetooth.BluetoothSocket.acceptNative(Native Method)
I had alot of problems with the chat example myself, so i tried another approach.
First you have to make one device host and the other the client, this works with the example pretty well. if you dont have this running, i can provide you with that code aswell.
Using the classes above, you get the socket for the connection. Use that to pass it to this class and then you can send using the write method. and the incoming messages are automatically parsed in the run-method (i added a message id and length to the front, thats why there is so much things going on in there)
private class ConnectedThread extends Thread {
/** the connection socket */
private final BluetoothSocket mmSocket;
/** input stream for incoming messages */
private final InputStream mmInStream;
/** output stream for outgoing messages */
private final OutputStream mmOutStream;
/**
* save the socket and get the streams
*
* @param socket
*/
public ConnectedThread(BluetoothSocket socket) {
mmSocket = 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) {
e.printStackTrace();
}
mmInStream = tmpIn;
mmOutStream = tmpOut;
}
/**
* reads incoming data and splits it into single messages
*/
public void run() {
/** buffer for a single byte message */
byte[] buffer = new byte[1024];
/** number of bytes returned from read() */
int bytes;
// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// read overhead from the InputStream
bytes = mmInStream.read(buffer, 0, LEN_SIZE + LEN_TYPE);
// if no bytes are read, wait for a new message
if (bytes == 0)
continue;
// get the size bytes and convert them to int
byte[] size_arr = new byte[LEN_SIZE];
for (int i = 0; i < LEN_SIZE; i++)
size_arr[i] = buffer[i];
int size = convertByteArrayToInt(size_arr, LEN_SIZE);
// the type is 1 byte after the size
byte type = buffer[LEN_SIZE];
// array for the output data
byte[] output = new byte[size + LEN_TYPE];
output[0] = type;
// current position, read until cPos == size
int cPos = 0;
while (cPos < size) {
// either read the buffer lenght or the remaining bytes
int read_len = Math.min(buffer.length, size - cPos);
bytes = mmInStream.read(buffer, 0, read_len);
// write the bytes to the output
for (int i = 0; i < bytes; i++)
output[cPos + i + LEN_TYPE] = buffer[i];
// increase the current position
cPos += bytes;
}
// add the message to the queue
mMessageData.add(output);
// tell the service about the new message
mHandler.obtainMessage(BluetoothService.CONNECTION_RECV_MSG, mConnectionAddress).sendToTarget();
} catch (IOException e) {
// tell the service about the disconnect
mHandler.obtainMessage(BluetoothService.CONNECTION_LOST, mConnectionAddress).sendToTarget();
e.printStackTrace();
break;
} catch (Exception e) {
e.printStackTrace();
}
}
}
/**
* writes a byte stream to the connection
*
* @param bytes
* the byte stream
*/
public void write(byte[] bytes) {
try {
mmOutStream.write(bytes, 0, bytes.length);
mmOutStream.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
/**
* close the socket
*/
public void cancel() {
try {
mmSocket.close();
} catch (IOException e) {
}
}
}
This worked for me, i hope it also does for you. If you have any question, feel free to ask :-)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With