Я строю приложение, похожее на Meshtastic, используя Kotlin. До сих пор я успешно реализовал BLE сканирующего/обнаружения, спаривания и подключения через GATT - плюс я могу читать информацию о устройстве, например, уровень батареи и прочность сигнала.
Моя текущая проблема заключается в отправке. Сообщения Я использую Protobuf для сериализации и написания в характеристике GATT без ошибок, но устройство LORA не отображает и не обрабатывает отправленное сообщение. Мне интересно, связана ли проблема с каналом BLE, используемым UUID или форматом сообщений. >
private val gattcallback = object: bluetoothgattcallback () {< /p>
override fun onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int) {
try {
val device = gatt.device
if (newState == BluetoothProfile.STATE_CONNECTED) {
Log.d("BLEManager", "Connected to GATT server: ${device.address}")
connectionStates[device] = true
deviceConnectionStates[device] = bluetoothGatt
gatt.discoverServices()
} else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
Log.d("BLEManager", "Disconnected from GATT server: ${device.address}")
connectionStates[device] = false
deviceConnectionStates[device] = null
//Toast.makeText(context, "Device disconnected", Toast.LENGTH_SHORT).show()
}
} catch (e: SecurityException) {
Log.d("BLEManager", "Error in connection state change: $e")
}
}
override fun onServicesDiscovered(gatt: BluetoothGatt, status: Int) {
try {
if (status == BluetoothGatt.GATT_SUCCESS) {
val btmService = gatt.getService(BTM_SERVICE_UUID)
if (btmService != null) {
Log.d("BLEManager", "BTM Service discovered.")
val myNodeInfoCharacteristic = btmService.getCharacteristic(BTM_FROM_RADIO_CHARACTER)
if (myNodeInfoCharacteristic != null) {
gatt.readCharacteristic(myNodeInfoCharacteristic)
Log.d("BLEManager", "BTM_MY_NODE_INFO_CHARACTER is found: $myNodeInfoCharacteristic")
} else {
Log.e("BLEManager", "BTM_MY_NODE_INFO_CHARACTER not found.")
}
// Read signal strength
readSignalStrength(gatt)
// Read battery level
readBatteryLevel(gatt)
// Request configuration (frequency)
requestConfiguration(gatt)
val fromRadioCharacteristic = btmService.getCharacteristic(BTM_FROM_RADIO_CHARACTER)
if (fromRadioCharacteristic != null) {
gatt.setCharacteristicNotification(fromRadioCharacteristic, true)
fromRadioCharacteristic.value = BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE
gatt.writeCharacteristic(fromRadioCharacteristic)
Log.e("BLEManager", "Notification enabled: ${fromRadioCharacteristic}")
} else {
Log.e("BLEManager", "Characteristic not found.")
}
// Store the BTM_TO_RADIO_CHARACTER for writing later
val toRadioCharacteristic = btmService.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
this@BLEManager.toRadioCharacteristic = toRadioCharacteristic
Log.d("BLEManager", "BTM_TO_RADIO_CHARACTER ready for writing: $toRadioCharacteristic")
}
// Read the BTM_FROM_NUM_CHARACTER
val fromNumCharacteristic = btmService.getCharacteristic(BTM_FROM_NUM_CHARACTER)
if (fromNumCharacteristic != null) {
gatt.readCharacteristic(fromNumCharacteristic)
Log.d("BLEManager", "Reading BTM_FROM_NUM_CHARACTER: $fromNumCharacteristic")
}
} else {
Log.d("BLEManager", "Everything failed cos BTM_SERVICE_UUID is null")
}
}
}catch (e:SecurityException){
Log.d("BLEManager", "Service discovery failed: $e")
}
}
@Deprecated("Deprecated in Java")
override fun onCharacteristicChanged(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic) {
if (characteristic.uuid == BTM_FROM_RADIO_CHARACTER) {
try {
val messageBytes = characteristic.value
val fromRadioMessage = MeshProtos.FromRadio.parseFrom(messageBytes)
if (fromRadioMessage.hasPacket()) {
val packet = fromRadioMessage.packet
val fromNodeId = packet.from
val toNodeId = packet.to
val payload = packet.decoded.payload.toStringUtf8()
Log.d("BLE", "Received message from node $fromNodeId: $payload ")
Log.d("BLEManager", "Received message: $toNodeId")
}else{
Log.d("BLEManager", "The radio has no packet")
}
if (fromRadioMessage.hasConfig()) {
val config = fromRadioMessage.config
val frequency = config.lora.frequencyOffset
Log.d("BLEManager", "Frequency: $frequency Hz")
}else{
Log.d("BLEManager", "The radio no packet")
}
if (fromRadioMessage.hasMyInfo()) {
val localNodeId = fromRadioMessage.myInfo.myNodeNum
Log.d("BLE", "Local Node ID: $localNodeId")
// Store the local node ID for future use
}else{
Log.d("BLEManager", "The radio packet")
}
} catch (e: Exception) {
Log.e("BLEManager", "Failed to parse ACK message: ${e.message}")
}
}
}
@Deprecated("Deprecated in Java")
override fun onCharacteristicRead(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
try {
val myNodeInfo = MyNodeInfo.parseFrom(characteristic.value)
val nodeId = myNodeInfo.myNodeNum
Log.d("BLEManager", "Retrieved node ID: $nodeId")
when (characteristic.uuid) {
UUID.fromString("00002a19-0000-1000-8000-00805f9b34fb") -> {
val batteryLevel = characteristic.value[0].toInt()
Log.d("BLEManager", "Battery level: $batteryLevel%")
// Update UI or store the battery level
}
}
} catch (e: Exception) {
Log.e("BLEManager", "Failed to parse MyNodeInfo: ${e.message}")
}
}
}
override fun onCharacteristicWrite(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
Log.d("BLEManager", "Message sent successfully")
} else {
Log.e("BLEManager", "Failed to send message with status: $status")
}
}
override fun onReadRemoteRssi(gatt: BluetoothGatt, rssi: Int, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
Log.d("BLEManager", "Signal strength (RSSI): $rssi dBm")
}
}
}
private fun readSignalStrength(gatt: BluetoothGatt) {
try {
gatt.readRemoteRssi()
}catch (e: SecurityException){
Log.d("BLEManager", "rss: $e")
}
}
private fun readBatteryLevel(gatt: BluetoothGatt) {
val batteryService = gatt.getService(UUID.fromString("0000180f-0000-1000-8000-00805f9b34fb"))
val batteryLevelCharacteristic = batteryService?.getCharacteristic(UUID.fromString("00002a19-0000-1000-8000-00805f9b34fb"))
if (batteryLevelCharacteristic != null) {
try {
gatt.readCharacteristic(batteryLevelCharacteristic)
}catch (e: SecurityException){
Log.d("BLEManager", "Battery level: $e")
}
} else {
Log.e("BLEManager", "Battery Level characteristic not found.")
}
}
private fun requestConfiguration(gatt: BluetoothGatt) {
val toRadioCharacteristic = gatt.getService(BTM_SERVICE_UUID)
?.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
val configRequest = MeshProtos.ToRadio.newBuilder()
.setWantConfigId(1) // Request configuration
.build()
val messageBytes = configRequest.toByteArray()
toRadioCharacteristic.value = messageBytes
try {
gatt.writeCharacteristic(toRadioCharacteristic)
Log.d("BLEManager", "$toRadioCharacteristic: $messageBytes")
}catch (e: SecurityException){
Log.d("BLEManager", "request configuration: e")
}
}
}
fun sendMessage(device: BluetoothDevice, message: String) {
connectionStates[device] = true
deviceConnectionStates[device] = bluetoothGatt
//selectDevice(device)
try {
val toRadioCharacteristic = bluetoothGatt?.getService(BTM_SERVICE_UUID)
?.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
val meshPacket = MeshProtos.Data.newBuilder()
.setPortnum(Portnums.PortNum.TEXT_MESSAGE_APP)
.setPayload(message.toByteStringUtf8())
.build()
val protobufMessage = MeshProtos.MeshPacket.newBuilder()
.setFrom(0x00000001)
.setTo(0x00000002)
.setChannel(3)
.setDecoded(meshPacket)
.build()
val toRadioMessage = MeshProtos.ToRadio.newBuilder()
.setPacket(protobufMessage)
.build()
val messageBytes = toRadioMessage.toByteArray()
toRadioCharacteristic.writeType = BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT
toRadioCharacteristic.value = messageBytes
val success = bluetoothGatt?.writeCharacteristic(toRadioCharacteristic)
if (success != null) {
Log.d("BLEManager", "Message sent to BTM_TO_RADIO_CHARACTER: $message")
saveMessageToDatabase(
message = message,
incoming = false
)
//publish(mqttTopic, message, 1, true)
} else {
Log.e("BLEManager", "Failed to send message to BTM_TO_RADIO_CHARACTER.")
}
} else {
Log.e("BLEManager", "BTM_TO_RADIO_CHARACTER not found.")
}
} catch (e: SecurityException) {
Log.e("BLEManager", "Error writing to BTM_TO_RADIO_CHARACTER: ${e.message}")
}
}
< /code>
Я хочу отправить сообщение в Decces Lora (устройства ESP32), и, кроме того, я хочу, чтобы сообщение отображалось на OLED -экране устройства. Я включил Protobuf, но устройство не может обработать сообщение, и, кроме того, я не могу получить идентификатор узла устройства Lora. Это всегда говорит мне, что идентификатор извлечения узла - 0. Я хочу иметь возможность отправлять сообщение на устройство LORA, которое будет отображаться на экране. Снова у меня нет ошибки
Подробнее здесь: https://stackoverflow.com/questions/794 ... g-protobuf
Проблема при отправке сообщения на устройство LORA с помощью ProToBuf ⇐ Android
Форум для тех, кто программирует под Android
1738848965
Anonymous
Я строю приложение, похожее на Meshtastic, используя Kotlin. До сих пор я успешно реализовал BLE сканирующего/обнаружения, спаривания и подключения через GATT - плюс я могу читать информацию о устройстве, например, уровень батареи и прочность сигнала.
Моя текущая проблема заключается в отправке. Сообщения Я использую Protobuf для сериализации и написания в характеристике GATT без ошибок, но устройство LORA не отображает и не обрабатывает отправленное сообщение. Мне интересно, связана ли проблема с каналом BLE, используемым UUID или форматом сообщений. >
private val gattcallback = object: bluetoothgattcallback () {< /p>
override fun onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int) {
try {
val device = gatt.device
if (newState == BluetoothProfile.STATE_CONNECTED) {
Log.d("BLEManager", "Connected to GATT server: ${device.address}")
connectionStates[device] = true
deviceConnectionStates[device] = bluetoothGatt
gatt.discoverServices()
} else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
Log.d("BLEManager", "Disconnected from GATT server: ${device.address}")
connectionStates[device] = false
deviceConnectionStates[device] = null
//Toast.makeText(context, "Device disconnected", Toast.LENGTH_SHORT).show()
}
} catch (e: SecurityException) {
Log.d("BLEManager", "Error in connection state change: $e")
}
}
override fun onServicesDiscovered(gatt: BluetoothGatt, status: Int) {
try {
if (status == BluetoothGatt.GATT_SUCCESS) {
val btmService = gatt.getService(BTM_SERVICE_UUID)
if (btmService != null) {
Log.d("BLEManager", "BTM Service discovered.")
val myNodeInfoCharacteristic = btmService.getCharacteristic(BTM_FROM_RADIO_CHARACTER)
if (myNodeInfoCharacteristic != null) {
gatt.readCharacteristic(myNodeInfoCharacteristic)
Log.d("BLEManager", "BTM_MY_NODE_INFO_CHARACTER is found: $myNodeInfoCharacteristic")
} else {
Log.e("BLEManager", "BTM_MY_NODE_INFO_CHARACTER not found.")
}
// Read signal strength
readSignalStrength(gatt)
// Read battery level
readBatteryLevel(gatt)
// Request configuration (frequency)
requestConfiguration(gatt)
val fromRadioCharacteristic = btmService.getCharacteristic(BTM_FROM_RADIO_CHARACTER)
if (fromRadioCharacteristic != null) {
gatt.setCharacteristicNotification(fromRadioCharacteristic, true)
fromRadioCharacteristic.value = BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE
gatt.writeCharacteristic(fromRadioCharacteristic)
Log.e("BLEManager", "Notification enabled: ${fromRadioCharacteristic}")
} else {
Log.e("BLEManager", "Characteristic not found.")
}
// Store the BTM_TO_RADIO_CHARACTER for writing later
val toRadioCharacteristic = btmService.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
this@BLEManager.toRadioCharacteristic = toRadioCharacteristic
Log.d("BLEManager", "BTM_TO_RADIO_CHARACTER ready for writing: $toRadioCharacteristic")
}
// Read the BTM_FROM_NUM_CHARACTER
val fromNumCharacteristic = btmService.getCharacteristic(BTM_FROM_NUM_CHARACTER)
if (fromNumCharacteristic != null) {
gatt.readCharacteristic(fromNumCharacteristic)
Log.d("BLEManager", "Reading BTM_FROM_NUM_CHARACTER: $fromNumCharacteristic")
}
} else {
Log.d("BLEManager", "Everything failed cos BTM_SERVICE_UUID is null")
}
}
}catch (e:SecurityException){
Log.d("BLEManager", "Service discovery failed: $e")
}
}
@Deprecated("Deprecated in Java")
override fun onCharacteristicChanged(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic) {
if (characteristic.uuid == BTM_FROM_RADIO_CHARACTER) {
try {
val messageBytes = characteristic.value
val fromRadioMessage = MeshProtos.FromRadio.parseFrom(messageBytes)
if (fromRadioMessage.hasPacket()) {
val packet = fromRadioMessage.packet
val fromNodeId = packet.from
val toNodeId = packet.to
val payload = packet.decoded.payload.toStringUtf8()
Log.d("BLE", "Received message from node $fromNodeId: $payload ")
Log.d("BLEManager", "Received message: $toNodeId")
}else{
Log.d("BLEManager", "The radio has no packet")
}
if (fromRadioMessage.hasConfig()) {
val config = fromRadioMessage.config
val frequency = config.lora.frequencyOffset
Log.d("BLEManager", "Frequency: $frequency Hz")
}else{
Log.d("BLEManager", "The radio no packet")
}
if (fromRadioMessage.hasMyInfo()) {
val localNodeId = fromRadioMessage.myInfo.myNodeNum
Log.d("BLE", "Local Node ID: $localNodeId")
// Store the local node ID for future use
}else{
Log.d("BLEManager", "The radio packet")
}
} catch (e: Exception) {
Log.e("BLEManager", "Failed to parse ACK message: ${e.message}")
}
}
}
@Deprecated("Deprecated in Java")
override fun onCharacteristicRead(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
try {
val myNodeInfo = MyNodeInfo.parseFrom(characteristic.value)
val nodeId = myNodeInfo.myNodeNum
Log.d("BLEManager", "Retrieved node ID: $nodeId")
when (characteristic.uuid) {
UUID.fromString("00002a19-0000-1000-8000-00805f9b34fb") -> {
val batteryLevel = characteristic.value[0].toInt()
Log.d("BLEManager", "Battery level: $batteryLevel%")
// Update UI or store the battery level
}
}
} catch (e: Exception) {
Log.e("BLEManager", "Failed to parse MyNodeInfo: ${e.message}")
}
}
}
override fun onCharacteristicWrite(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
Log.d("BLEManager", "Message sent successfully")
} else {
Log.e("BLEManager", "Failed to send message with status: $status")
}
}
override fun onReadRemoteRssi(gatt: BluetoothGatt, rssi: Int, status: Int) {
if (status == BluetoothGatt.GATT_SUCCESS) {
Log.d("BLEManager", "Signal strength (RSSI): $rssi dBm")
}
}
}
private fun readSignalStrength(gatt: BluetoothGatt) {
try {
gatt.readRemoteRssi()
}catch (e: SecurityException){
Log.d("BLEManager", "rss: $e")
}
}
private fun readBatteryLevel(gatt: BluetoothGatt) {
val batteryService = gatt.getService(UUID.fromString("0000180f-0000-1000-8000-00805f9b34fb"))
val batteryLevelCharacteristic = batteryService?.getCharacteristic(UUID.fromString("00002a19-0000-1000-8000-00805f9b34fb"))
if (batteryLevelCharacteristic != null) {
try {
gatt.readCharacteristic(batteryLevelCharacteristic)
}catch (e: SecurityException){
Log.d("BLEManager", "Battery level: $e")
}
} else {
Log.e("BLEManager", "Battery Level characteristic not found.")
}
}
private fun requestConfiguration(gatt: BluetoothGatt) {
val toRadioCharacteristic = gatt.getService(BTM_SERVICE_UUID)
?.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
val configRequest = MeshProtos.ToRadio.newBuilder()
.setWantConfigId(1) // Request configuration
.build()
val messageBytes = configRequest.toByteArray()
toRadioCharacteristic.value = messageBytes
try {
gatt.writeCharacteristic(toRadioCharacteristic)
Log.d("BLEManager", "$toRadioCharacteristic: $messageBytes")
}catch (e: SecurityException){
Log.d("BLEManager", "request configuration: e")
}
}
}
fun sendMessage(device: BluetoothDevice, message: String) {
connectionStates[device] = true
deviceConnectionStates[device] = bluetoothGatt
//selectDevice(device)
try {
val toRadioCharacteristic = bluetoothGatt?.getService(BTM_SERVICE_UUID)
?.getCharacteristic(BTM_TO_RADIO_CHARACTER)
if (toRadioCharacteristic != null) {
val meshPacket = MeshProtos.Data.newBuilder()
.setPortnum(Portnums.PortNum.TEXT_MESSAGE_APP)
.setPayload(message.toByteStringUtf8())
.build()
val protobufMessage = MeshProtos.MeshPacket.newBuilder()
.setFrom(0x00000001)
.setTo(0x00000002)
.setChannel(3)
.setDecoded(meshPacket)
.build()
val toRadioMessage = MeshProtos.ToRadio.newBuilder()
.setPacket(protobufMessage)
.build()
val messageBytes = toRadioMessage.toByteArray()
toRadioCharacteristic.writeType = BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT
toRadioCharacteristic.value = messageBytes
val success = bluetoothGatt?.writeCharacteristic(toRadioCharacteristic)
if (success != null) {
Log.d("BLEManager", "Message sent to BTM_TO_RADIO_CHARACTER: $message")
saveMessageToDatabase(
message = message,
incoming = false
)
//publish(mqttTopic, message, 1, true)
} else {
Log.e("BLEManager", "Failed to send message to BTM_TO_RADIO_CHARACTER.")
}
} else {
Log.e("BLEManager", "BTM_TO_RADIO_CHARACTER not found.")
}
} catch (e: SecurityException) {
Log.e("BLEManager", "Error writing to BTM_TO_RADIO_CHARACTER: ${e.message}")
}
}
< /code>
Я хочу отправить сообщение в Decces Lora (устройства ESP32), и, кроме того, я хочу, чтобы сообщение отображалось на OLED -экране устройства. Я включил Protobuf, но устройство не может обработать сообщение, и, кроме того, я не могу получить идентификатор узла устройства Lora. Это всегда говорит мне, что идентификатор извлечения узла - 0. Я хочу иметь возможность отправлять сообщение на устройство LORA, которое будет отображаться на экране. Снова у меня нет ошибки
Подробнее здесь: [url]https://stackoverflow.com/questions/79418132/problem-in-sending-message-to-the-lora-device-using-protobuf[/url]
Ответить
1 сообщение
• Страница 1 из 1
Перейти
- Кемерово-IT
- ↳ Javascript
- ↳ C#
- ↳ JAVA
- ↳ Elasticsearch aggregation
- ↳ Python
- ↳ Php
- ↳ Android
- ↳ Html
- ↳ Jquery
- ↳ C++
- ↳ IOS
- ↳ CSS
- ↳ Excel
- ↳ Linux
- ↳ Apache
- ↳ MySql
- Детский мир
- Для души
- ↳ Музыкальные инструменты даром
- ↳ Печатная продукция даром
- Внешняя красота и здоровье
- ↳ Одежда и обувь для взрослых даром
- ↳ Товары для здоровья
- ↳ Физкультура и спорт
- Техника - даром!
- ↳ Автомобилистам
- ↳ Компьютерная техника
- ↳ Плиты: газовые и электрические
- ↳ Холодильники
- ↳ Стиральные машины
- ↳ Телевизоры
- ↳ Телефоны, смартфоны, плашеты
- ↳ Швейные машинки
- ↳ Прочая электроника и техника
- ↳ Фототехника
- Ремонт и интерьер
- ↳ Стройматериалы, инструмент
- ↳ Мебель и предметы интерьера даром
- ↳ Cантехника
- Другие темы
- ↳ Разное даром
- ↳ Давай меняться!
- ↳ Отдам\возьму за копеечку
- ↳ Работа и подработка в Кемерове
- ↳ Давай с тобой поговорим...
Мобильная версия