|     Inicio    |   |         |  |   FOROS      |  |      |      
   Elastix - VoIP B4A (Basic4Android) App inventor 2 PHP - MySQL
  Estación meteorológica B4J (Basic4Java) ADB Shell - Android Arduino
  Raspberry Pi Visual Basic Script (VBS) FireBase (BD autoactualizable) NodeMCU como Arduino
  AutoIt (Programación) Visual Basic Cosas de Windows Webs interesantes
Translate:
Búsqueda en este sitio:


.

Tutorial del Internet de las Cosas y Bluetooth con el ESP32
Juan Antonio Villalpando

Volver al índice del tutorial

____________________________

160.- Bluetooth Low Energy. BLE. Librería. De AI2 a ESP32. De ESP32 a AI2.

_________________________________
- BLE. Librería.

- El módulo Wemos D1 R32 con el chip ESP32, tiene Bluetooth: v4.2 BR/EDR y Bluetooth Low Energy (BLE), así que lo podemos utilizar con el Bluetooth clásico 4.0 y con el BLE.

- En esta página podemos encontrar una extensión para que App Inventor pueda trabajar con BLE:

- http://iot.appinventor.mit.edu/#/bluetoothle/bluetoothleintro

- Aquí muestro distintas versiones de esta extensión, en estos tutoriales vamos a utilizar la 2018-11-24

BLE-with-new-ConnectDevice.aix (2019-06-27) (Version beta) (mirror)

edu.mit.appinventor.ble-20181124.aix (20181124) (Version estable)

edu.mit.appinventor.ble.aix (20171109)

edu.mit.appinventor.BluetoothLE.aix (version 2)

- http://ai2.appinventor.mit.edu/reference/other/IoT.html (Ejemplo. 2016)

 

- Por otra parte me voy a basar en los ejemplos que podemos consultar en esta dirección:

https://github.com/nkolban/ESP32_BLE_Arduino/tree/7951347ed68313d75c367e1f2cce763cb56d1eb2

 

- Lo primero que tendría que hacer es bajar y descomprimir este archivo: ESP32_BLE.zip

- (Otra versión: ESP32_BLE_2.zip)

- Obtendremos la carpeta ESP32_BLE, copiamos esa carpeta en la carpeta ../Arduino/libraries/

- Puedes encontrar ejemplos en su carpeta examples.

________________________________________________________________

- NOTA: en estos ejemplos que vamos a realizar debemos tener en cuenta que a veces el MIT COMPANION no actualiza el Bluetooth cuando hacemos cambios en el código, así que si no obtienes en el listado el BLE de la tarjeta Wemos, desconecta la app del MIT COMPANION y vuélvela a conectar.

- Otra cosa importante es que cada vez que hagamos cambios en los códigos Deshabilitemos y Habilitemos el Bluetooth del móvil, para eso he puesto la extensión com.KIO4_Bluetooth.aix en estos ejemplos.

com.KIO4_Bluetooth.aix

- Si sigue sin funcionarte estos ejemplos, instala la aplicación en vez de utilizar el emulador de MIT Companion.

- En los ejemplos de Notificaciones he puesto:

- El bloque de solicitud de permisos.

- En Android 5 me ha funcionado mejor que en Android 9. A veces para que funcionara en Android 9 lo ejecutaba antes en Android 5 y después en Android 9.

- Para que funcione BLE, el móvil debe tener activado el permiso de Ubicación (Location)
https://stackoverflow.com/questions/33045581/location-needs-to-be-enabled-for-bluetooth-low-energy-scanning-on-android-6-0

https://stackoverflow.com/questions/33043582/bluetooth-low-energy-startscan-on-android-6-0-does-not-find-devices/33045489#33045489

_________________________________
1.- Listado de BLE cercanos.

https://github.com/nkolban/ESP32_BLE_Arduino/tree/master/examples/BLE_scan

scan_ble.ino

/*
   Based on Neil Kolban example for IDF: 
https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleScan.cpp
   Ported to Arduino ESP32 by Evandro Copercini
*/

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEScan.h>
#include <BLEAdvertisedDevice.h>

int scanTime = 30; //In seconds

class MyAdvertisedDeviceCallbacks: public BLEAdvertisedDeviceCallbacks {
    void onResult(BLEAdvertisedDevice advertisedDevice) {
      Serial.printf("Advertised Device: %s \n", advertisedDevice.toString().c_str());
    }
};

void setup() {
  Serial.begin(115200);
  Serial.println("Scanning...");

  BLEDevice::init("");
  BLEScan* pBLEScan = BLEDevice::getScan(); //create new scan
  pBLEScan->setAdvertisedDeviceCallbacks(new MyAdvertisedDeviceCallbacks());
  pBLEScan->setActiveScan(true); //active scan uses more power, but get results faster
  BLEScanResults foundDevices = pBLEScan->start(scanTime);
  Serial.print("Devices found: ");
  Serial.println(foundDevices.getCount());
  Serial.println("Scan done!");
}

void loop() {
  // put your main code here, to run repeatedly:
  delay(2000);
}

- BLE Scanner.

- Podemos ver los UUID con esta aplicación:

https://play.google.com/store/apps/details?id=com.macdom.ble.blescanner&hl=es

_________________________________
2.- App Inventor envía información a la tarjeta mediante BLE. Monitor Serie.

p110i_esp32_ble_enviar.aia

- App Inventor (Android) conecta por BLE con la tarjeta. Escribimos un mensaje y lo enviamos. La tarjeta tomará ese mensaje y lo presentará en el Monitor Serie.

- Este mensaje estará en las variables value y valor.

- Se presentará de varias forma, una mediante value y otra mediante el String valor en la parte del código de BLE.

- Además la variable valor se presentará cada 2 segundos mediante el bloque loop {}

- IMPORTANTE: aunque pongamos un texto largo, solo se enviará un paquete de 20 caracteres.

- El siguiente mensaje: "El Ñandú corrió por Cádiz" se mostrará en el Monitor Serie: "El Ñandú corrió p", observa 17 caracteres, eso es porque los caracteres especiales Ñ, ó, ú, se envían en dos bytes.

_________________________________
- Diseño.

_________________________________
- Bloques.

- Observa los números de serviceUuid y characteristicUuid, están tomados del código que cargará en la tarjeta del ESP32.

_________________________________
- Código.

https://github.com/nkolban/ESP32_BLE_Arduino/tree/7951347ed68313d75c367e1f2cce763cb56d1eb2/examples/BLE_write

- Consulta el Monitor Serie.

ble_enviar.ino

/*
    Based on Neil Kolban example for IDF: 
https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleWrite.cpp
    Ported to Arduino ESP32 by Evandro Copercini
*/
// Modificado por Juan Antonio Villalpando.
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>

String valor;

#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();

      if (value.length() > 0) {
        valor = "";
        for (int i = 0; i < value.length(); i++){
          // Serial.print(value[i]); // Presenta value.
          valor = valor + value[i];
        }

        Serial.println("*********");
        Serial.print("valor = ");
        Serial.println(valor); // Presenta valor.
      }
    }
};

void setup() {
  Serial.begin(115200);

  BLEDevice::init("MyESP32");
  BLEServer *pServer = BLEDevice::createServer();
  BLEService *pService = pServer->createService(SERVICE_UUID);
  BLECharacteristic *pCharacteristic = pService->createCharacteristic(
                                         CHARACTERISTIC_UUID,
                                         BLECharacteristic::PROPERTY_READ |
                                         BLECharacteristic::PROPERTY_WRITE
                                       );

  pCharacteristic->setCallbacks(new MyCallbacks());
  pCharacteristic->setValue("Hello World");
  pService->start();

  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();
}

void loop() {
  // put your main code here, to run repeatedly:
  delay(2000);
   // Serial.println("valor en el loop = ");
   // Serial.println(valor); // Presenta valor.
}

_________________________________
3.- Reloj. La tarjeta ESP32 envía mediante BLE números aleatorios a App. Monitor Serie.

p110i_esp32_ble_recibir.aia

- El código de la tarjeta crea un número aleatorio del 0 al 100. Lo convierte en String.

- Cuando pulsamos el Botón de "Recibir" en App Inventor, recibimos un número aleatorio y se muestra en una Etiqueta.

- Los números aleatorios son creados cada 2 segundos.

- He querido mantener tanto el código de App Inventor como el de la tarjeta Wemos del ejemplo anterior, así que simplemente he modificado esos dos códigos, algunas líneas no son necesarias. El bloque de lectura es ReadStrings.

- En este ejemplo he puesto un Reloj.

- Consulta el Monitor Serie.

_________________________________
- Diseño.

_________________________________
- Bloques.

- Observa los números de serviceUuid y characteristicUuid, están tomados del código que cargará en la tarjeta.

_________________________________
- Código.

https://github.com/nkolban/ESP32_BLE_Arduino/tree/7951347ed68313d75c367e1f2cce763cb56d1eb2/examples/BLE_write

- Observa cómo toma el dato: pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio

ble_recibir.ino

/*
    Based on Neil Kolban example for IDF: 
https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleWrite.cpp
    Ported to Arduino ESP32 by Evandro Copercini
*/
// Modificado por Juan Antonio Villalpando.
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>

String valor;
int aleatorio;
String alea = "2";


#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();
      pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio

      if (value.length() > 0) {
        valor = "";
        for (int i = 0; i < value.length(); i++){
          // Serial.print(value[i]); // Presenta value.
          valor = valor + value[i];
        }

        Serial.println("*********");
        Serial.print("valor = ");
        Serial.println(valor); // Presenta valor.
      }
    }
};

void setup() {
  Serial.begin(115200);

  BLEDevice::init("MyESP32");
  BLEServer *pServer = BLEDevice::createServer();
  BLEService *pService = pServer->createService(SERVICE_UUID);
  BLECharacteristic *pCharacteristic = pService->createCharacteristic(
                                         CHARACTERISTIC_UUID,
                                         BLECharacteristic::PROPERTY_READ |
                                         BLECharacteristic::PROPERTY_WRITE
                                       );

  pCharacteristic->setCallbacks(new MyCallbacks());
  pCharacteristic->setValue("Iniciado.");
  pService->start();

  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();
}

void loop() {
  // put your main code here, to run repeatedly:
  delay(2000);
  //Serial.println("valor en el loop = ");
  //Serial.println(valor); // Presenta valor.
  aleatorio = random(1,100); // Crea el numero aleatorio.
  alea = (String) aleatorio; // Lo convierte en String.
}

_________________________________
4.- BLE Server envía número aleatorio a App. Monitor Serie.

https://github.com/nkolban/ESP32_BLE_Arduino/tree/master/examples/BLE_server

p110_esp32_ble_server.aia

- Es un código similar al anterior, crea un número aleatorio del 0 al 100. Lo convierte en String.

- El Reloj de App Inventor chequea el valor de aleatorio cada 2 segundos.

- Observa el Monitor Serie.

_________________________________
- Diseño.

_________________________________
- Bloques.

_________________________________
- Código.

ble_server.ino

/*
    Based on Neil Kolban example for IDF: 
https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleServer.cpp
    Ported to Arduino ESP32 by Evandro Copercini
*/
// Modificado por Juan Antonio Villalpando.
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>


#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"

String valor;
int aleatorio;
String alea = "2";

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();
      pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio
      Serial.println(alea);
    }
};

void setup() {
  Serial.begin(115200);
  Serial.println("Starting BLE work!");

  BLEDevice::init("MyESP32");
  BLEServer *pServer = BLEDevice::createServer();
  BLEService *pService = pServer->createService(SERVICE_UUID);
  BLECharacteristic *pCharacteristic = pService->createCharacteristic(
                                         CHARACTERISTIC_UUID,
                                         BLECharacteristic::PROPERTY_READ |
                                         BLECharacteristic::PROPERTY_WRITE
                                       );
  pCharacteristic->setCallbacks(new MyCallbacks());
  pCharacteristic->setValue("Inicio.");
  pService->start();
  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();
  Serial.println("Characteristic defined! Now you can read it in your phone!");
}

void loop() {
  // put your main code here, to run repeatedly:
  delay(2000);
  aleatorio = random(1,100); // Crea el numero aleatorio.
  alea = (String) aleatorio; // Lo convierte en String.
}

_________________________________
5.- Sin Reloj. App Inventor envía un dato cualquiera. BLE reenvía un número aleatorio.

p110i_esp32_ble_enviar_recibir.aia

- Observa que recibiremos una respuesta del módulo BLE y la tendremos en App Inventor sin utilizar el Reloj.

- Enviamos cualquier texto escrito en el CampoDeTexto al módulo BLE mediante "Envía información".

- Observaremos el texto enviado en el Monitor Serie.

- El módulo BLE genera un número aleatorio del 0 al 100, y nos lo devuelve. Se presenta en una Etiqueta.

_________________________________
- Diseño.

_________________________________
- Bloques.

_________________________________
- Código.

ble_envia_recibe.ino

// Modificado por Juan Antonio Villalpando.
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>

String valor;
int aleatorio;
String alea;

#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();
      pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio
      
	  if (value.length() > 0) {
        valor = "";
        for (int i = 0; i < value.length(); i++){
          // Serial.print(value[i]); // Presenta value.
          valor = valor + value[i];
        }

        Serial.println("*********");
        Serial.print("valor = ");
        Serial.println(valor); // Presenta valor.
      }
    }
};

void setup() {
  Serial.begin(115200);

  BLEDevice::init("MyESP32");
  BLEServer *pServer = BLEDevice::createServer();
  BLEService *pService = pServer->createService(SERVICE_UUID);
  BLECharacteristic *pCharacteristic = pService->createCharacteristic(
                                         CHARACTERISTIC_UUID,
                                         BLECharacteristic::PROPERTY_READ |
                                         BLECharacteristic::PROPERTY_WRITE
                                       );

  pCharacteristic->setCallbacks(new MyCallbacks());
  pCharacteristic->setValue("Iniciado.");
  pService->start();

  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();
}

void loop() {
  delay(1000);
  aleatorio = random(1,100); // Crea el numero aleatorio.
  alea = (String) aleatorio; // Lo convierte en String.aleatorio
}

_________________________________
6.- Sin Reloj. App Inventor envía un dato. BLE reenvía un número aleatorio según el dato.

p110i_esp32_ble_enviar_recibir.aia (es el mismo código que el anterior)

- Si escribimos "uno" en el CampoDeTexto, nos devolverá un número aleatorio del 1 al 50.
- Si escribimos "dos" en el CampoDeTexto, nos devolverá un número aleatorio del 100 al 200.
- Si escribimos "tres" en el CampoDeTexto, nos devolverá dos números aleatorios, ejemplo (34,148)

- Si escribimos otra palabra, nos devolverá esa palabra.

- Observa el Monitor Serie.

ble_envia_recibe_2.ino

// Modificado por Juan Antonio Villalpando.
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>

String valor;
int aleatorio1;
int aleatorio2;
String alea1;
String alea2;
String alea3;

#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"

class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();
     
	  if (value.length() > 0) {
        valor = "";
        for (int i = 0; i < value.length(); i++){
          // Serial.print(value[i]); // Presenta value.
          valor = valor + value[i];
        }

        Serial.println("*********");
        Serial.print("valor = ");
        Serial.println(valor); // Presenta valor.
		
        if(valor == "uno") {
        pCharacteristic->setValue(alea1.c_str()); // Pone el numero aleatorio
          }
        if(valor == "dos") {
        pCharacteristic->setValue(alea2.c_str()); // Pone el numero aleatorio
          }
        if(valor == "tres") {
        pCharacteristic->setValue(alea3.c_str()); // Pone el numero aleatorio
          }
      }
    }
};

void setup() {
  Serial.begin(115200);

  BLEDevice::init("MyESP32");
  BLEServer *pServer = BLEDevice::createServer();
  BLEService *pService = pServer->createService(SERVICE_UUID);
  BLECharacteristic *pCharacteristic = pService->createCharacteristic(
                                         CHARACTERISTIC_UUID,
                                         BLECharacteristic::PROPERTY_READ |
                                         BLECharacteristic::PROPERTY_WRITE
                                       );

  pCharacteristic->setCallbacks(new MyCallbacks());
  pCharacteristic->setValue("Iniciado.");
  pService->start();

  BLEAdvertising *pAdvertising = pServer->getAdvertising();
  pAdvertising->start();
}

void loop() {
  delay(1000);
  aleatorio1 = random(1,50); // Crea el numero aleatorio.
  alea1 = (String) aleatorio1; // Lo convierte en String.aleatorio
  aleatorio2 = random(100,200); // Crea el numero aleatorio.
  alea2 = (String) aleatorio2; // Lo convierte en String.aleatorio
  alea3 = alea1 + "," + alea2;
       }

_________________________________
_________________________________

- Ejemplos con Notificación.
__________________________________________________________________
7.- Mediante Registry y Notificación. El ESP32 envía números aleatorios.

p110i_esp32_ble_notifica.aia

- En el ejemplo 4, vimos cómo el ESP32 generaba números aleatorios y App Inventor los recibía mediante el bloque ReadStrings y un Reloj. También debíamos utilizar el bloque WriteStrings para solicitarle la información.

- Ahora también el ESP32 va a generar números aleatorios, pero App Inventor los va a recibir de otra manera.

- Se utilizará el bloque RegisterForStrings, esta acción configurará a la extensión para que esté comprobando si hay un cambio de información recibida, sin utilizar el Reloj.

- El Bloque StringReceived, recibirá el valor enviado por el ESP32.

- El Reloj no es necesario en este código.

_________________________________
- Diseño.

_________________________________
- Bloques.

_________________________________
- Código.

- Basado en este código:

https://github.com/nkolban/ESP32_BLE_Arduino/blob/master/examples/BLE_notify/BLE_notify.ino

ble_notificacion.ino

/*
    Based on Neil Kolban example for IDF:
   https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleNotify.cpp
   Ported to Arduino ESP32 by Evandro Copercini updated by chegewara
   Create a BLE server that, once we receive a connection, will send periodic notifications.
   A connect hander associated with the server starts a background task that performs notification
   every couple of seconds.
*/

// Modificado por Juan A. Villalpando
// http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm

#include <BLEDevice.h>
#include <BLEServer.h>
#include <BLEUtils.h>
#include <BLE2902.h>

BLEServer* pServer = NULL;
BLECharacteristic* pCharacteristic = NULL;
bool deviceConnected = false;
bool oldDeviceConnected = false;
uint32_t value = 0;

// See the following for generating UUIDs:
// https://www.uuidgenerator.net/

#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"


class MyServerCallbacks: public BLEServerCallbacks {
    void onConnect(BLEServer* pServer) {
      deviceConnected = true;
    };

    void onDisconnect(BLEServer* pServer) {
      deviceConnected = false;
    }
};

void setup() {
  Serial.begin(115200);

  // Create the BLE Device
  BLEDevice::init("MyESP32");

  // Create the BLE Server
  pServer = BLEDevice::createServer();
  pServer->setCallbacks(new MyServerCallbacks());

  // Create the BLE Service
  BLEService *pService = pServer->createService(SERVICE_UUID);

  // Create a BLE Characteristic
  pCharacteristic = pService->createCharacteristic(
                      CHARACTERISTIC_UUID,
                      BLECharacteristic::PROPERTY_READ   |
                      BLECharacteristic::PROPERTY_WRITE  |
                      BLECharacteristic::PROPERTY_NOTIFY |
                      BLECharacteristic::PROPERTY_INDICATE
                    );

  // https://www.bluetooth.com/specifications/gatt/viewer?
  // attributeXmlFile=org.bluetooth.descriptor.gatt.client_characteristic_configuration.xml
  // Create a BLE Descriptor
  pCharacteristic->addDescriptor(new BLE2902());

  // Start the service
  pService->start();

  // Start advertising
  BLEAdvertising *pAdvertising = BLEDevice::getAdvertising();
  pAdvertising->addServiceUUID(SERVICE_UUID);
  pAdvertising->setScanResponse(false);
  pAdvertising->setMinPreferred(0x0);  // set value to 0x00 to not advertise this parameter
  BLEDevice::startAdvertising();
  Serial.println("Waiting a client connection to notify...");
}

void loop() {
    // notify changed value
    if (deviceConnected) {
       // pCharacteristic->setValue((uint8_t*)&value, 4);
        int aleatorio = random(1,100); // Crea el numero aleatorio.
        String alea = (String) aleatorio; // Lo convierte en String.
        pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio
        delay(500); // bluetooth stack will go into congestion, if too many packets are sent.
    }
    // disconnecting
    if (!deviceConnected && oldDeviceConnected) {
        delay(500); // give the bluetooth stack the chance to get things ready
        pServer->startAdvertising(); // restart advertising
        Serial.println("start advertising");
        oldDeviceConnected = deviceConnected;
    }
    // connecting
    if (deviceConnected && !oldDeviceConnected) {
        // do stuff here on connecting
        oldDeviceConnected = deviceConnected;
    }
}

_________________________________ no actualizado
8.- Mediante Registry y Notificación. El ESP32 envía números aleatorios. App Inventor envía números con un Deslizador.

p110_esp32_ble_notifica_Deslizador.aia

- Este ejemplo es la unión del ejemplo anterior, el 7 y el 2.

- En el ejemplo 7 acabamos de ver que el ESP32 envía un número aleatorio y App Inventor lo recibe como Notificación (sin utilizar reloj)

- El ejemplo 2 trataba de enviar una información desde App Inventor al ESP32

- En este ejemplo la información enviada desde App Inventor al ESP32 será un número creado por un Deslizador.

- El envío del número de App Inventor al ESP32 por una parte, y el envío de aleatorio desde ESP32 a App Inventor son independientes.

- En este ejemplo el bloque RegisterForStrings lo he puesto dentro del evento Connected.

- Ese número se verá en forma de caracter en el Monitor Serie.

- He probado los códigos en Android 5 y Android 9, fue mejor en el Android 5.

_________________________________
- Diseño.

 

_________________________________
- Bloques.

- Observa que he puesto solicitud de permiso.

- También he utilizado mi extensión para Habilitar y Deshabilitar el Bluetooth del móvil.

_________________________________
- Código.

ble_notificacion.ino

/*
    Video: https://www.youtube.com/watch?v=oCMOYS71NIU
    Based on Neil Kolban example for IDF: 
	https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleNotify.cpp
    Ported to Arduino ESP32 by Evandro Copercini
    updated by chegewara
   Create a BLE server that, once we receive a connection, will send periodic notifications.
   The service advertises itself as: 4fafc201-1fb5-459e-8fcc-c5c9c331914b
   And has a characteristic of: beb5483e-36e1-4688-b7f5-ea07361b26a8
   The design of creating the BLE server is:
   1. Create a BLE Server
   2. Create a BLE Service
   3. Create a BLE Characteristic on the Service
   4. Create a BLE Descriptor on the characteristic
   5. Start the service.
   6. Start advertising.
   A connect hander associated with the server starts a background task that performs notification
   every couple of seconds.
*/

// Modificado por Juan A. Villalpando
// KIO4.COM

#include <BLEDevice.h>
#include <BLEServer.h>
#include <BLEUtils.h>
#include <BLE2902.h>

String valor;

BLEServer* pServer = NULL;
BLECharacteristic* pCharacteristic = NULL;
bool deviceConnected = false;
bool oldDeviceConnected = false;
//uint32_t value = 0;

// See the following for generating UUIDs:
// https://www.uuidgenerator.net/

#define SERVICE_UUID        "4fafc201-1fb5-459e-8fcc-c5c9c331914b"
#define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8"


class MyServerCallbacks: public BLEServerCallbacks {
    void onConnect(BLEServer* pServer) {
      deviceConnected = true;
    };

    void onDisconnect(BLEServer* pServer) {
      deviceConnected = false;
    }
};

////////////////////// WriteStrings /////////////////////////////
class MyCallbacks: public BLECharacteristicCallbacks {
    void onWrite(BLECharacteristic *pCharacteristic) {
      std::string value = pCharacteristic->getValue();

      if (value.length() > 0) {
        Serial.println("*********");
        Serial.print("New value: ");
        valor = "";
        for (int i = 0; i < value.length(); i++){
          Serial.print(value[i]); // Presenta value.
          valor = valor + value[i];
        }

        Serial.println();
        Serial.print("valor = ");
        Serial.println(valor); // Presenta valor.
        Serial.println("*********");
      }
    }
};
///////////////////////////////////////////////////

void setup() {
  Serial.begin(115200);

  // Create the BLE Device
  BLEDevice::init("ESP32");

  // Create the BLE Server
  pServer = BLEDevice::createServer();
  pServer->setCallbacks(new MyServerCallbacks());

  // Create the BLE Service
  BLEService *pService = pServer->createService(SERVICE_UUID);

  // Create a BLE Characteristic
  pCharacteristic = pService->createCharacteristic(
                      CHARACTERISTIC_UUID,
                      BLECharacteristic::PROPERTY_READ   |
                      BLECharacteristic::PROPERTY_WRITE  |
                      BLECharacteristic::PROPERTY_NOTIFY |
                      BLECharacteristic::PROPERTY_INDICATE
                    );

  // https://www.bluetooth.com/specifications/gatt/viewer?
// attributeXmlFile=org.bluetooth.descriptor.gatt.client_characteristic_configuration.xml // Create a BLE Descriptor pCharacteristic->addDescriptor(new BLE2902()); // Esta línea es para el WriteStrings: pCharacteristic->setCallbacks(new MyCallbacks()); // Start the service pService->start(); // Start advertising BLEAdvertising *pAdvertising = BLEDevice::getAdvertising(); pAdvertising->addServiceUUID(SERVICE_UUID); pAdvertising->setScanResponse(false); pAdvertising->setMinPreferred(0x0); // set value to 0x00 to not advertise this parameter BLEDevice::startAdvertising(); Serial.println("Waiting a client connection to notify..."); } void loop() { // notify changed value if (deviceConnected) { std::string value = pCharacteristic->getValue(); // pCharacteristic->setValue((uint8_t*)&value, 4); int aleatorio = random(1,100); // Crea el numero aleatorio. String alea = (String) aleatorio; // Lo convierte en String. pCharacteristic->setValue(alea.c_str()); // Pone el numero aleatorio pCharacteristic->notify(); // value++; delay(500); // bluetooth stack will go into congestion, if too many packets are sent. } // disconnecting if (!deviceConnected && oldDeviceConnected) { delay(500); // give the bluetooth stack the chance to get things ready pServer->startAdvertising(); // restart advertising Serial.println("start advertising"); oldDeviceConnected = deviceConnected; } // connecting if (deviceConnected && !oldDeviceConnected) { // do stuff here on connecting oldDeviceConnected = deviceConnected; } }

_________________________________
9.- Mediante Registry y Notificación. App Inventor envía números mediante un Deslizador y ESP32 le devuelve el doble de ese número.

p110i_esp32_ble_notifica_Deslizador.aia (es la misma aplicación que la del ejemplo anterior)

- Mediante un Deslizador y el bloque WriteStrings, App Inventor envía un número del 1 al 100.

- Utilizamos el bloque RegisterForStrings, gracias a este bloque la aplicación está preparada para recibir un String por Bluetooth BLE sin necesidad de utilizar el Reloj.

- El código del ESP32 recibe el número y devuelve el doble del número recibido.

- Observarás que hay un pequeño retraso en el recibo del número.

- He probado los códigos en Android 5 y Android 9, fue mejor en el Android 5.

_________________________________
- Diseño.

_________________________________
- Bloques.

_________________________________
- Código.

ble_notificacion_envia_recibe_doble.ino

/*
    Video: https://www.youtube.com/watch?v=oCMOYS71NIU
    Based on Neil Kolban example for IDF: 
https://github.com/nkolban/esp32-snippets/blob/master/cpp_utils/tests/BLE%20Tests/SampleNotify.cpp Ported to Arduino ESP32 by Evandro Copercini updated by chegewara Create a BLE server that, once we receive a connection, will send periodic notifications. A connect hander associated with the server starts a background task that performs notification every couple of seconds. */ // Modificado por Juan A. Villalpando // http://kio4.com/arduino/160i_Wemos_ESP32_BLE.htm #include <BLEDevice.h> #include <BLEServer.h> #include <BLEUtils.h> #include <BLE2902.h> String valor; BLEServer* pServer = NULL; BLECharacteristic* pCharacteristic = NULL; bool deviceConnected = false; bool oldDeviceConnected = false; //uint32_t value = 0; #define SERVICE_UUID "4fafc201-1fb5-459e-8fcc-c5c9c331914b" #define CHARACTERISTIC_UUID "beb5483e-36e1-4688-b7f5-ea07361b26a8" class MyServerCallbacks: public BLEServerCallbacks { void onConnect(BLEServer* pServer) { deviceConnected = true; }; void onDisconnect(BLEServer* pServer) { deviceConnected = false; } }; ////////////////////// WriteStrings ///////////////////////////// class MyCallbacks: public BLECharacteristicCallbacks { void onWrite(BLECharacteristic *pCharacteristic) { std::string value = pCharacteristic->getValue(); if (value.length() > 0) { valor = ""; for (int i = 0; i < value.length(); i++){ // Serial.print(value[i]); // Presenta value. valor = valor + value[i]; } Serial.println("*********"); Serial.print("valor = "); Serial.println(valor); // Presenta valor. } } }; /////////////////////////////////////////////////// void setup() { Serial.begin(115200); // Create the BLE Device BLEDevice::init("MyESP32"); // Create the BLE Server pServer = BLEDevice::createServer(); pServer->setCallbacks(new MyServerCallbacks()); // Create the BLE Service BLEService *pService = pServer->createService(SERVICE_UUID); // Create a BLE Characteristic pCharacteristic = pService->createCharacteristic( CHARACTERISTIC_UUID, BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_WRITE | BLECharacteristic::PROPERTY_NOTIFY | BLECharacteristic::PROPERTY_INDICATE ); // https://www.bluetooth.com/specifications/gatt/viewer? // attributeXmlFile=org.bluetooth.descriptor.gatt.client_characteristic_configuration.xml // Create a BLE Descriptor pCharacteristic->addDescriptor(new BLE2902()); // Esta línea es para el WriteStrings: pCharacteristic->setCallbacks(new MyCallbacks()); // Start the service pService->start(); // Start advertising BLEAdvertising *pAdvertising = BLEDevice::getAdvertising(); pAdvertising->addServiceUUID(SERVICE_UUID); pAdvertising->setScanResponse(false); pAdvertising->setMinPreferred(0x0); // set value to 0x00 to not advertise this parameter BLEDevice::startAdvertising(); Serial.println("Waiting a client connection to notify..."); } void loop() { // notify changed value if (deviceConnected) { std::string value = pCharacteristic->getValue(); // pCharacteristic->setValue((uint8_t*)&value, 4); int doble = valor.toInt() * 2 ; String doblado = (String) doble; // Lo convierte en String. pCharacteristic->setValue(doblado.c_str()); // Pone el numero doble pCharacteristic->notify(); // value++; delay(5); // bluetooth stack will go into congestion, if too many packets are sent. } // disconnecting if (!deviceConnected && oldDeviceConnected) { delay(500); // give the bluetooth stack the chance to get things ready pServer->startAdvertising(); // restart advertising Serial.println("start advertising"); oldDeviceConnected = deviceConnected; } // connecting if (deviceConnected && !oldDeviceConnected) { // do stuff here on connecting oldDeviceConnected = deviceConnected; } }

______________________________________________
- Generador de UUID para BLE.

- Cada servicio, característica y descriptor tiene un UUID (Universally Unique Identifier). Un UUID es un número único de 16 bytes.

- Hay algunos UUID normalizados: SIG (Bluetooth Special Interest Group).

- Pero podemos crearnos unos UUID personales para nuestra aplicación: UUID generator.

_______________________________

- Mi correo:
juana1991@yahoo.com
- KIO4.COM - Política de cookies. Textos e imágenes propiedad del autor:
© Juan A. Villalpando
No se permite la copia de información ni imágenes.
Usamos cookies propias y de terceros que entre otras cosas recogen datos sobre sus hábitos de navegación y realizan análisis de uso de nuestro sitio.
Si continúa navegando consideramos que acepta su uso. Acepto    Más información