Reputation: 37
I am unable read data from ble device to android app. If I do continous and simultaneous data communication, either of the way discommunicate though bluetooth is connected.
I am trying to receive 30 bytes of data from ble device continuously. I tried with mtu size change but no use. If I start sending 30 bytes of data from app, data receiving from ble device to app, will be stopped. I am unable to do simultaneous data communication. Can someone please help me to do simultaneous data communication continuously. I am sending30 bytes of data to ble device in the rate of 300ms and I have to receive 30 bytes of data from ble device at the rate of 1 sec.I am successfully able to read or write at a time. But not both at a time.
If I fix mtu size for 20, then I can read 20 bytes from ble device simultaneously. But I have to read 30 bytes of data from ble device.
I also wanted to know, Is there any possibility to read and write simultaneously over ble continuously without data loss?
I am doing gatt.requestMtu(512) at the time successful gatt connection.
public void onConnectionStateChange(BluetoothGatt gatt, int status, int newState) {
String intentAction;
if (newState == BluetoothProfile.STATE_CONNECTED) {
intentAction = ACTION_GATT_CONNECTED;
mConnectionState = STATE_CONNECTED;
broadcastUpdate(intentAction);
gatt.requestMtu(512);
Intent i = new Intent("status").putExtra("status",staticConnectionStatus);
sendBroadcast(i);
} else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
intentAction = ACTION_GATT_DISCONNECTED;
mConnectionState = STATE_DISCONNECTED;
Intent intent = new Intent("status");
intent.putExtra("status", staticConnectionStatus);
sendBroadcast(intent);
Log.d(TAG, "Disconnected from GATT server.");
broadcastUpdate(intentAction);
}
}
@Override
public void onCharacteristicRead(BluetoothGatt gatt,
BluetoothGattCharacteristic characteristic,
int status) {
if (status == BluetoothGatt.GATT_SUCCESS) {
Log.d(TAG, "ACTION_DATA_AVAILABLE" + ACTION_DATA_AVAILABLE);
broadcastUpdate(ACTION_DATA_AVAILABLE, characteristic);
byte[] charValue = characteristic.getValue();
byte flag = charValue[0];
} else if (status == BluetoothGatt.GATT_FAILURE) {
Log.d(TAG, "failed");
}
byte[] charValue = characteristic.getValue();
byte flag = charValue[0];
}
@Override
public void onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
//gatt.requestMtu(185);
broadcastUpdate(ACTION_DATA_AVAILABLE, characteristic);
byte[] charValue = characteristic.getValue();
byte flag = charValue[0];
}
};
public void writeRXCharacteristic(byte[] value) {
if (mBluetoothGatt != null) {
// try {
// Thread.sleep(200);
// } catch (InterruptedException e) {
// e.printStackTrace();
// }
BluetoothGattService RxService = mBluetoothGatt.getService(UUID.fromString("0000FEFB-0000-1000-8000-00805F9B34FB"));
if (RxService == null) {
// showMessage("Rx service not found!");
broadcastUpdate(DEVICE_DOES_NOT_SUPPORT_UART);
return;
}
BluetoothGattCharacteristic RxChar = RxService.getCharacteristic(UUID.fromString("00000001-0000-1000-8000-008025000000"));
if (RxChar == null) {
// showMessage("Rx charateristic not found!");
broadcastUpdate(DEVICE_DOES_NOT_SUPPORT_UART);
return;
}
RxChar.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT);
RxChar.setValue(value);
if (mBluetoothGatt != null) {
boolean status = mBluetoothGatt.writeCharacteristic(RxChar);
} else {
broadcastUpdate(DEVICE_DOES_NOT_SUPPORT_UART);
}
} else {
broadcastUpdate(DEVICE_DOES_NOT_SUPPORT_UART);
}
}
//Im notifying the service UUID on services discovered
BluetoothGattCharacteristic TxChar = RxService.getCharacteristic(UUID.fromString("00000002-0000-1000-8000-008025000000"));
mBluetoothGatt.setCharacteristicNotification(TxChar, true);
Upvotes: 2
Views: 1923
Reputation: 78975
Here's some comparable Kotlin code that works with a serial connection and increased MTU size. I've removed error handling, logging and some application specific code.
It uses two characteristics: - The command characteristic is used to send data from the phone to the device. - The feedback characteristic is used to receive data sent by the device.
Note the way it works:
import android.bluetooth.BluetoothGatt
import android.bluetooth.BluetoothGattCallback
import android.bluetooth.BluetoothGattCharacteristic
import android.bluetooth.BluetoothProfile
class BleConnection(private val device: BluetoothDevice) : Connection {
private var deviceGatt: BluetoothGatt? = null
private var commandCharacteristic: BluetoothGattCharacteristic? = null
private var feedbackCharacteristic: BluetoothGattCharacteristic? = null
private val gattCallback = object: BluetoothGattCallback() {
override fun onConnectionStateChange(gatt: BluetoothGatt?, status: Int, newState: Int) {
[email protected](gatt, newState)
}
override fun onServicesDiscovered(gatt: BluetoothGatt?, status: Int) {
[email protected](gatt)
}
override fun onCharacteristicChanged(gatt: BluetoothGatt?, characteristic: BluetoothGattCharacteristic?) {
[email protected](characteristic)
}
override fun onMtuChanged(gatt: BluetoothGatt?, mtu: Int, status: Int) {
[email protected](gatt)
}
}
// Start to connect
override fun connect() {
deviceGatt = device.connectGatt(null, false, gattCallback)
}
// The connection state has changed
private fun onConnectionStateChange(gatt: BluetoothGatt?, newState: Int) {
when (newState) {
BluetoothProfile.STATE_CONNECTED -> {
gatt!!.discoverServices()
}
BluetoothProfile.STATE_DISCONNECTED -> {
...
}
}
}
// GATT services have been discovered
fun onServicesDiscovered(gatt: BluetoothGatt?) {
for (service in gatt!!.services) {
if (service.uuid == Constants.SERVICE_UUID) {
feedbackCharacteristic = service.getCharacteristic(Constants.FEEDBACK_CHAR_UUID)
commandCharacteristic = service.getCharacteristic(Constants.COMMAND_CHAR_UUID)
// Increase the MTU
gatt.requestMtu(256)
}
}
}
// The MTU has successfully been changed
fun onMtuChange(gatt: BluetoothGatt?) {
gatt!!.setCharacteristicNotification(feedbackCharacteristic, true)
// ... notify that connection is fully established and ready
}
// Characteristic has been changed (i.e. new data has been received)
fun onCharacteristicChanged(characteristic: BluetoothGattCharacteristic?) {
val data = characteristic!!.value
// ... process the received data
}
// may only be called after the connection has been fully established
// (see onMtuChange() )
override fun sendData(command: ByteArray) {
commandCharacteristic!!.value = command
deviceGatt!!.writeCharacteristic(commandCharacteristic!!)
}
}
Upvotes: 0