How to use nrf24 for BLE in esp32
Posted: Mon Sep 13, 2021 1:20 pm
I want to use the nrf24 for BLE, I have tried googling but can't find any meaningful result. If anyone have implemented this before or know of any library please share. I have tried the BTLE library but it is only for the AVR architecture.
Few of the sketches I've tried:
After uploading the code nothing shows up in the nrf24's android/ios application
This code halt after "Initial communicate with radio fail", so guessing can't initialize the nrf24 module.
I've tested the module with other devices (arduinos) and it works, I'm using an esp32 pico mini 02 board and the arduino IDE.
Few of the sketches I've tried:
Code: Select all
#include <SPI.h>
#include <RF24.h>
#include <BTLE.h>
#define MOSI 34
#define MISO 38
#define SS 32
#define SCK 35
#define CE 37
RF24 radio(SS, 37);
BTLE btle(&radio);
void setup() {
Serial.begin(115200);
SPI.begin(SCK, MISO, MOSI, SS);//SCLK, MISO, MOSI, SS
// pinMode(37, OUTPUT);
// digitalWrite(37, LOW);
while (!Serial) { }
Serial.println("BTLE advertisement sender");
btle.begin("foobar");
}
void loop() {
btle.advertise(0, 0);
btle.hopChannel();
Serial.print(".");
}
Code: Select all
#include "BLEDevice.h"
#include "BLEServer.h"-
#include "BLEUtils.h"
#include "BLE2902.h"
BLEServer *pServer = NULL;
BLECharacteristic * pTxCharacteristic;
#include <SPI.h>
#include <NRFLite.h> // Using NRFLite library
#define RADIO_TX_ID 13 // Transmitter Radio ID. Not use in this program
#define DESTINATION_RADIO_ID 18 // Our Receiving Radio ID.
#define RF_CHAN 108 //Using Radio Channel
#define PIN_RADIO_CE 37
#define PIN_RADIO_CSN 32
#define PIN_RADIO_MOSI 34
#define PIN_RADIO_MISO 38
#define PIN_RADIO_SCK 35
NRFLite _radio;
char strf1[10];
char strf2[10];
char strf3[10];
char strout1[40];
char strout2[40];
char strout3[40];
char strout4[40];
char strout5[40];
char strout6[40];
char strout7[40];
uint8_t BCdata[40];
//*********************************************************************
#define ainm 2.9298/4096.0 //Arduino ADC multiple factor from Vin
#define aoutm 2.6636/4096.0 //Arduino ADC multiple factor from Vout
#define at1m 1.0086/2048.0
#define at2m 1.0082/2048.0
#define v12M 3.246 // ADC multiple factor from v12
#define v8M 2.149 // ADC multiple factor from v8
#define v4M 1.08865 // ADC multiple factor from v4
#define PwmBaseFreq 20000 // base PWM frequency 31.25KHz
#define ILM 2.5686// ADC multiplication factor for average inductor current
//#define IinM 2.5339// ADC multiplication factor for average inductor current
#define IinM 2.614// ADC multiplication factor for average inductor current
#define IoutM 2.4578 // ADC multiplication factor for output current
#define VintrM 4.8441 // ADC multiplication factor for internal input voltage
#define V5M 1.9989 // ADC multiplication factor Vcc, 5V
float ADC1b = 0.000125F; // ADS1115 resolution at range of 4.096V.
// measured by Arduino ADC
float faout; // output voltages
float fat1; // temperature 1
float fat2; // temperature 2
float pwr_in; // input power
float pwr_out; // output power
float sum_pwr_in; // sum of 100 input power
float avg_pwr_in,avg_prv_pwr; // average input power and prv_pwr
float pwr_bat; // battery power pos= charging neg= discharging
float i_bat; // current flows into battery, pos= charging neg= discharging
// Measured by ADS1115A
float fVin; // solar input voltage
float fLi12; // v12
float fLi8; // v8
float fLi4; // v4
// Measured by ADS1115B
float fIL; // inductor current
float fIin; // input current
float fIout; // output current
float fVintr; // internal input voltage
float fV5; // Vcc
float vb12,vb8,vb4; // voltage across battery
float vbmis; //voltage difference between battery
// int16_t junk=0; // temperatory storage
long freq = PwmBaseFreq;
float pwr_on_t; // Total power on time in sec.
struct __attribute__((packed)) RadioPacket // Note the packed attribute.
{
// measured by Arduino ADC
uint8_t RadioId;
int16_t ain; // sum of 4 output voltages
int16_t aout; // sum of 4 output voltages
int16_t at1; // sum of 2 temperature 1
int16_t at2; // sum of 2 temperature 2
// Measured by ADS1115A
int16_t Iin; // input current
int16_t Li12; // v12
int16_t Li8; // v8
int16_t Li4; // v4
// Measured by ADS1115B
int16_t IL; // Input current
int16_t Iout; // Output current
int16_t Vintr; // Internal input voltage
int16_t V5; // Vcc
// PWM
int16_t PulseWidth;
uint8_t err; // error code 0= no error.
uint8_t portb;//PORTB
uint8_t portd; //PORTD value
uint16_t SendCounts; // number packages sent
};
//*********************************************************************
bool deviceConnected = false;
bool oldDeviceConnected = false;
// See the following for generating UUIDs:
// https://www.uuidgenerator.net/
#define SERVICE_UUID "b20e2d8f-6ae0-4655-ad8d-4ad5a4d5e32e" // UART service UUID
#define CHARACTERISTIC_UUID_TX "c85392bc-558f-4f58-8942-ee4051a8a13c"
#define CHARACTERISTIC_UUID_RX "e1b6fed9-1ea4-4057-8311-46a52da9346a"
class MyServerCallbacks: public BLEServerCallbacks {
void onConnect(BLEServer* pServer) {
deviceConnected = true;
};
void onDisconnect(BLEServer* pServer) {
deviceConnected = false;
}
};
class MyCallbacks: public BLECharacteristicCallbacks {
void onWrite(BLECharacteristic *pCharacteristic) {
std::string rxValue = pCharacteristic->getValue();
if (rxValue.length() > 0) {
Serial.println("*********");
Serial.print("Received Value: ");
for (int i = 0; i < rxValue.length(); i++)
Serial.print(rxValue[i]);
Serial.println();
Serial.println("*********");
}
}
};
//******************************************************************
RadioPacket vm;
//******************************************************************
void setup() {
Serial.begin(115200);
Serial.println("Begin");
// Configure SPI pins.
SPI.begin(PIN_RADIO_SCK, PIN_RADIO_MISO, PIN_RADIO_MOSI, PIN_RADIO_CSN);
// Indicate to NRFLite that it should not call SPI.begin() during initialization since it has already been done.
uint8_t callSpiBegin = 0;
if (!_radio.init(DESTINATION_RADIO_ID, PIN_RADIO_CE, PIN_RADIO_CSN, NRFLite::BITRATE250KBPS, RF_CHAN, callSpiBegin)) {
Serial.println(" Initial communicate with radio fail");
while (1); // Wait here forever.
}
else Serial.println(" NRF24L01 Connected");
// Create the BLE Device
BLEDevice::init("Solar Charger");
// 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
pTxCharacteristic = pService->createCharacteristic(
CHARACTERISTIC_UUID_TX,
BLECharacteristic::PROPERTY_NOTIFY
);
pTxCharacteristic->addDescriptor(new BLE2902());
BLECharacteristic * pRxCharacteristic = pService->createCharacteristic(
CHARACTERISTIC_UUID_RX,
BLECharacteristic::PROPERTY_WRITE
);
pRxCharacteristic->setCallbacks(new MyCallbacks());
// Start the service
pService->start();
// Start advertising
pServer->getAdvertising()->start();
Serial.println("Waiting a client connection to notify...");
}
void loop() {
while (_radio.hasData()) {
_radio.readData(&vm); // Reading RF data.
conv_float(); // converted to floating point measurements
prn_results(); //print vm data
if (deviceConnected) {
for(int i=0;i<32;i++) BCdata[i] = strout1[i];
pTxCharacteristic->setValue(BCdata, strlen(strout1));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout2[i];
pTxCharacteristic->setValue(BCdata, strlen(strout2));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout3[i];
pTxCharacteristic->setValue(BCdata, strlen(strout3));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout4[i];
pTxCharacteristic->setValue(BCdata, strlen(strout4));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout5[i];
pTxCharacteristic->setValue(BCdata, strlen(strout5));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout6[i];
pTxCharacteristic->setValue(BCdata, strlen(strout6));
pTxCharacteristic->notify();
for(int i=0;i<32;i++) BCdata[i] = strout7[i];
pTxCharacteristic->setValue(BCdata, strlen(strout7));
pTxCharacteristic->notify();
BCdata[0] = 10; BCdata[1] = 0;
pTxCharacteristic->setValue(BCdata, 1);
pTxCharacteristic->notify();
}
// 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;
}
}
}
//******************************************************************
void conv_float(){
// convert all measurement to floating point
fLi12 =v12M *ADC1b * vm.Li12; // voltage at v12 reference to GND
fLi8 = v8M *ADC1b * vm.Li8; // voltage at v8 reference to GND
fLi4 = v4M *ADC1b * vm.Li4; // voltage at v4 reference to GND
fIL = ILM *ADC1b * vm.IL; // Inductor current
fIin = IinM *ADC1b * vm.Iin; // Input current
if (fIL < 0.0) fIL = 0.0;
fIout = IoutM *ADC1b * vm.Iout; // output current
if (fIout < 0.0) fIout = 0.0;
fVintr = VintrM *ADC1b * vm.Vintr; // Input voltage internal
fV5 = V5M *ADC1b * vm.V5; // Vcc=5V
// fV5 = 4.9958; // V5 fix due to fail in ADS1115, measured by DVM
faout = aoutm*fV5*vm.aout; // Output voltage
fVin = ainm*fV5*vm.ain; // Input voltage
fat1 = at1m*fV5*vm.at1; // temperature voltage at probe 1
//convert voltage to temperature, equation is base on measurement.+/- 5C between 20C to 80C
if (fat1 < 3.455) fat1 = 25.5*fat1 -17.5;
else if (fat1 < 4.095) fat1 = 39.2*fat1 -64.1;
else fat1 = 75.8*fat1 -215.2;
fat2 = at2m*fV5*vm.at2; // temperature voltage at probe 2
//convert voltage to temperature, equation is base on measurement.+/- 5C between 20C to 80C
if (fat2 < 3.483) fat2 = 25.2*fat2 -17.2;
else if (fat2 < 4.143) fat2 = 37.9*fat2 -60.9;
else fat2 = 921*fat2 -286.3;
vb12 = fLi12 - fLi8; // v12 Li battery voltage
vb8 = fLi8 - fLi4; // v8 Li battery voltage
vb4 = fLi4; // v4 Li battery voltage
vbmis = max(vb12, max(vb8,vb4)) - min(vb12, min(vb8,vb4)); //max difference in Li battery voltages
// ind_dv = fIL-fLi12; // voltage across inductor
i_bat = fIL -fIout;
// pwr_in = fVin*fIin;
// pwr_out = fLi12 * fIL;
// sum_pwr_in+=pwr_in;*/
}
//***********************************************************************
// print measurements
void prn_results() {
sprintf(strout1, "RdID %i S# %i Err %i\n", vm.RadioId,vm.SendCounts, vm.err);
dtostrf(fLi12,1,3,strf1);
dtostrf(fLi8,1,3,strf2);
dtostrf(fLi4,1,3,strf3);
sprintf(strout2, "V12 %s V8 %s V4 %s\n", strf1,strf2,strf3);
dtostrf(fVin,1,3,strf1);
dtostrf(fVintr,1,2,strf2);
dtostrf(faout,1,2,strf3);
sprintf(strout3, "Vin %s Vx %s Vo %s\n", strf1,strf2,strf3);
dtostrf(vb12,1,3,strf1);
dtostrf(vb8,1,3,strf2);
dtostrf(vb4,1,3,strf3);
sprintf(strout4, "B12 %s B8 %s B4 %s\n", strf1,strf2,strf3);
dtostrf(fV5,1,3,strf2);
dtostrf(vbmis,1,3,strf3);
sprintf(strout5, "freq %i V5 %s Vm %s\n", freq,strf2,strf3);
dtostrf(fIin,1,2,strf1);
dtostrf(fIout,1,2,strf2);
dtostrf(i_bat,1,2,strf3);
sprintf(strout6, "Iin %sA Io %sA Ib %sA\n", strf1,strf2,strf3);
dtostrf(fat1,1,1,strf1);
dtostrf(fat2,1,1,strf2);
sprintf(strout7, "T1 %sC T2 %sC PW %i\n", strf1,strf2,vm.PulseWidth);
Serial.print(strout1);
Serial.print(strout2);
Serial.print(strout3);
Serial.print(strout4);
Serial.print(strout5);
Serial.print(strout6);
Serial.print(strout7);// Serial.println(strlen(strout7));
Serial.println();
}
//*****************************************
I've tested the module with other devices (arduinos) and it works, I'm using an esp32 pico mini 02 board and the arduino IDE.