我正在開發一個Android應用程序,它以每秒8000字節的速度從BLE傳感器接收數據。Android - BLE連接參數和在SQLite數據庫中存儲BLE傳感器數據
我的應用中的連接邏輯基於Google的BluetoothLeGatt示例。有用。我沒有改變任何東西,也沒有明確設置任何連接參數,如連接事件之間的間隔(我不認爲Android 4.4 API支持)。
我正在測試兩款Android手機,均使用Android版本4.4.2,並使用TI BLE嗅探器來監控BLE流量。
一個電話協商一個7.5ms的間隔,並且每個連接事件交換三個20字節的數據包。另一部電話在連接事件之間協商48.75ms,並且每個事件交換19個20字節的數據包(每秒的有效數據傳輸速率大致相同)。
我的問題是,我試圖從BLE服務活動中記錄數據,因爲它涉及到SQLite數據庫。日誌記錄以7.5ms爲間隔工作。但是,該應用會以48.75ms的間隔鎖定手機。 (一般來說,該手機的連接性不太穩定)。我認爲這是因爲它正在處理19個數據包在彼此之上。
我的問題:
1.是否有無論如何,我可以使兩個手機(和任何未來的設備)使用7.5毫秒的間隔,因爲這似乎更好?有沒有辦法控制參數Minimum/Maximum_CE_Length?
- 有沒有比直接從BLE服務活動記錄數據更好的方法? These SQLite Android Developer pages建議使用ASync任務,但由於數據不會進入UI線程,因此看起來並不合適。
我的代碼片段: 這是我的連接代碼directly from the BluetoothLeGatt sample
/**
* Connects to the GATT server hosted on the Bluetooth LE device.
*
* @param address The device address of the destination device.
*
* @return Return true if the connection is initiated successfully. The connection result
* is reported asynchronously through the
* {@code BluetoothGattCallback#onConnectionStateChange(android.bluetooth.BluetoothGatt, int, int)}
* callback.
*/
public boolean connect(final String address) {
if (mBluetoothAdapter == null || address == null) {
Log.w(TAG, "BluetoothAdapter not initialized or unspecified address.");
return false;
}
// Previously connected device. Try to reconnect.
if (mBluetoothDeviceAddress != null && address.equals(mBluetoothDeviceAddress)
&& mBluetoothGatt != null) {
Log.d(TAG, "Trying to use an existing mBluetoothGatt for connection.");
if (mBluetoothGatt.connect()) {
mConnectionState = STATE_CONNECTING;
return true;
} else {
return false;
}
}
final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(address);
if (device == null) {
Log.w(TAG, "Device not found. Unable to connect.");
return false;
}
// We want to directly connect to the device, so we are setting the autoConnect
// parameter to false.
mBluetoothGatt = device.connectGatt(this, false, mGattCallback);
Log.d(TAG, "Trying to create a new connection.");
mBluetoothDeviceAddress = address;
mConnectionState = STATE_CONNECTING;
return true;
}`
我的日誌代碼是在broadcastUpdate功能:
private void broadcastUpdate(final String action,
final BluetoothGattCharacteristic characteristic) {
final Intent intent = new Intent(action);
StringBuilder stringBuilder = new StringBuilder();
StringBuilder descStringBuilder = new StringBuilder();
byte[] newData = characteristic.getValue();
String dataString;
if (newData != null && newData.length > 0) {
if (UUID_SENSOR_FFF4.equals(characteristic.getUuid())) {
totalDataBytes += newData.length;
// https://stackoverflow.com/questions/8150155/java-gethours-getminutes-and-getseconds
estimatedTime = System.currentTimeMillis();
Date timeDiff = new Date(estimatedTime - startTime - 19 * 3600000);
SimpleDateFormat timeFormat = new SimpleDateFormat("HH:mm:ss.SSS");
descStringBuilder.append("CHAR_FFF4\n");
descStringBuilder.append("Total Data: " + totalDataBytes + " Bytes\n");
descStringBuilder.append("Elapsed Time: " + timeFormat.format(timeDiff) + "\n");
for (int i = 0; i < newData.length; i++){
byte[] tempArray = { newData[i+1], newData[i] };
ByteBuffer wrapper = ByteBuffer.wrap(tempArray);
short tempShort = wrapper.getShort();
i++;
stringBuilder.append(tempShort);
stringBuilder.append(", ");
}
dataString = stringBuilder.toString();
values.put(NbmcContract.NmbcDeviceData.COLUMN_TIMESTAMP, estimatedTime);
values.put(NbmcContract.NmbcDeviceData.COLUMN_DATA_STRING, dataString);
long newRowId = db.insert(NbmcContract.NmbcDeviceData.TABLE_NAME, null, values);
descStringBuilder.append("Row ID: " + newRowId + "\n");
} else {
descStringBuilder.append(getCharacteristicString(characteristic) + "\nDATA: ");
// We expect these characteristics to return ASCII strings
if ( DEVICE_NAME_CHAR.equals(characteristic.getUuid()) ||
MODEL_NUM_CHAR.equals(characteristic.getUuid()) ||
SERIAL_NUM_CHAR.equals(characteristic.getUuid()) ||
FIRMWARE_REV_CHAR.equals(characteristic.getUuid()) ||
HARDWARE_REV_CHAR.equals(characteristic.getUuid()) ||
FIRMWARE_REV_CHAR.equals(characteristic.getUuid()) ||
SOFTWARE_REV_CHAR.equals(characteristic.getUuid()) ||
MANUF_NAME_STRING_CHAR.equals(characteristic.getUuid()))
{
for (byte byteChar : newData) {
stringBuilder.append(String.format("%c", byteChar));
}
}
else {
for (byte byteChar : newData) {
stringBuilder.append(String.format("%02X", byteChar));
}
}
dataString = stringBuilder.toString();
}
String descString = descStringBuilder.toString();
intent.putExtra("DESC_STRING", descString);
UUID uuid = characteristic.getUuid();
String uuidString = uuid.toString();
intent.putExtra("CHAR_UUID", uuidString);
intent.putExtra("EXTRA_DATA", dataString);
}
sendBroadcast(intent);
}
這是[FAQ](http://www.sqlite.org/faq.html#q19);在一次交易中寫入多個條目。 –