0

I have made a application which can make communication between Arduino and phone. But I have a problem that is, it can be only send several letters in a one characteristic.

 public boolean writeData(BluetoothGattCharacteristic characteristic, byte[] data){
        if(btAdapter == null || btGatt == null){
            logAdapter.add("BluetoothAdapter not initialized.");
            return false;
        }
        characteristic.setValue(data);
        return btGatt.writeCharacteristic(characteristic);
    }

if the data is over 1MB, Do I have to make more BluetoothGattcharacteristic and add on BluetoothGattService? or is there are another better way to make it work??

tonykrjhc
  • 129
  • 6
  • 1
    Your data is clipped by MTU barrier of the BLE module that you use along with your Arduino. I don't think that the module supports a large amount of MTU in one transfer frame. That's you must implement an algorithm that it divides the data by MTU size on the Android side and reunites it on the Arduino side. – Kozmotronik Jun 08 '22 at 09:14
  • 1
    This [so question](https://stackoverflow.com/q/30130162/12749998) may help you to figure it out. – Kozmotronik Jun 08 '22 at 09:17
  • 1
    Use for example https://developer.android.com/reference/android/bluetooth/BluetoothDevice#createL2capChannel(int) to get a better way of sending huge amounts of data. – Emil Jun 08 '22 at 19:12

1 Answers1

2

You will have to create some wrapper logic if you want to do something like this. Characteristics follow the basic rule of attributes which have a max length of 512 bytes, but you can only transfer 20 bytes at a time.

What you can do is set up a pair of characteristics

  • One "transfer" for you to write the bytes into
  • One "signal" for the receiver who can signal if it is ready to process more bytes.

Having read the signal, if it is "Ready" (signaling that the reader is ready), you can set the signal to "Not Ready" and write your bytes into the transfer one, so that the receiver can process them.

After processing your receiver can set the signal to "Ready" again and rinse and repeat.

For distinguishing your data frames from each other you can use the first byte as a "counter"/"id" which is incremented on each transfer so the reader can know when new data was actually written.

But following the basic idea you can do any number of variations on the implementation.

(Note that BLE and Characteristics were not really designed for this kind of bulk data transfer in mind so while you can certainly create an implementation, it may have a drastic effect on your battery life. If you use a battery in the first place ofcourse :))

vnagy
  • 790
  • 6
  • 8
  • 1
    The max MTU supports 512 byte of ATT data, but the MTU could be smaller, so don't rely on a hardcoded 512. Also, the statement "you can only transfer 20 bytes at a time" is ambiguous and not typically correct. The 20 bytes applies to data in a Link Layer packet, and 20 only applies if running BT 4.0 or 4.1. Data length extensions support up to 255 bytes of data in a packet. But an Android app likely need not worry about this...the MTU is what matters. – BHass Jun 17 '22 at 15:06