Я ищу для решения, как обнаружить присутствие моего телефона на близком расстоянии от ESP32 без установки чего-то вроде приложения iBeacon, которое может разряжать мою батарею.
- Я начал на примере сниффера BLE, который работает хорошо, но с рандомизацией MAC на Android он бесполезен.
- Затем я перешел к решению, использующему эмуляцию HID-клавиатуры. После сопряжения он легко подключается, когда телефон попадает в зону действия. Как только он подключен, я могу вызвать необходимое действие, а затем отключить ESP32 Bluetooth, чтобы он не был подключен все время. Когда мне нужно снова проверить телефон, я просто могу снова включить сервер. Это было бы отличное решение, но... Мне нужно проверить еще (хотя бы два) телефона. Я пытался дублировать серверы BLE для переключения между двумя симутинами или запускать их одновременно, но безуспешно - либо это невозможно, либо это превышает мои знания об этой магии рекламы/сопряжения/соединения BLE.
- Третьим решением было бы иметь отдельный ESP для каждого телефона - возможно, но только в крайнем случае.
Для решения с клавиатурой я использую этот код, найденный в Интернете:
#include
#include
#include
#include
#include "BLE2902.h"
#include "BLEHIDDevice.h"
#include "HIDTypes.h"
#include "HIDKeyboardTypes.h"
#include
BLEHIDDevice* hid;
BLECharacteristic* input;
BLECharacteristic* output;
BLEAdvertising *pAdvertising;
BLEServer *pServer;
bool connected = false;
bool restart = false;
class MyCallbacks : public BLEServerCallbacks {
void onConnect(BLEServer* pServer){
connected = true;
Serial.println("Connected");
BLE2902* desc = (BLE2902*)input->getDescriptorByUUID(BLEUUID((uint16_t)0x2902));
desc->setNotifications(true);
// NEEDED ACTIONS
}
void onDisconnect(BLEServer* pServer){
connected = false;
Serial.println("DisConnected");
BLE2902* desc = (BLE2902*)input->getDescriptorByUUID(BLEUUID((uint16_t)0x2902));
desc->setNotifications(false);
restart = true;
}
};
void setup() {
Serial.begin(115200);
Serial.println("Starting BLE work!");
BLEDevice::init("Backpack-MeowMeow");
pServer = BLEDevice::createServer();
pServer->setCallbacks(new MyCallbacks());
pServer->getPeerDevices(true);
hid = new BLEHIDDevice(pServer);
input = hid->inputReport(1); // outputReport(1); // manufacturer()->setValue(name);
hid->pnp(0x02, 0xe502, 0xa111, 0x0210);
hid->hidInfo(0x00,0x02);
BLESecurity *pSecurity = new BLESecurity();
// pSecurity->setKeySize();
pSecurity->setAuthenticationMode(ESP_LE_AUTH_BOND);
hid->startServices();
pAdvertising = pServer->getAdvertising();
pAdvertising->setAppearance(HID_BARCODE);
pAdvertising->addServiceUUID(hid->hidService()->getUUID());
pAdvertising->start();
hid->setBatteryLevel(7);
//ESP_LOGD(LOG_TAG, "Advertising started!");
//delay(portMAX_DELAY);
}
void loop() {
if(connected){
delay(10);
}
if (restart) {
restart = false;
pAdvertising->start();
}
delay(50);
}
Подробнее здесь: https://stackoverflow.com/questions/676 ... -detection