ESP32 Bluetooth SPP with bidirectional communication (send and receive)
-
- Posts: 2
- Joined: Mon Mar 11, 2019 2:07 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
Hi,
Can someone please tell me if Bluetooth SPP supports multiple clients in case of bi-directional communication? If yes, implementation code, please.
Can someone please tell me if Bluetooth SPP supports multiple clients in case of bi-directional communication? If yes, implementation code, please.
- gunar.kroeger
- Posts: 143
- Joined: Fri Jul 27, 2018 6:48 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
It does. You will have to save the connection handle from incoming clients and direct the messages with esp_spp_write to the correct handlesuriyaelango wrote: Hi,
Can someone please tell me if Bluetooth SPP supports multiple clients in case of bi-directional communication? If yes, implementation code, please.
"Running was invented in 1612 by Thomas Running when he tried to walk twice at the same time."
-
- Posts: 2
- Joined: Mon Mar 11, 2019 2:07 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
The esp_spp_write function is an IDF function. Any chance it works with the Arduino framework for ESP32?
- ESP_Me-no-dev
- Posts: 80
- Joined: Mon Jan 04, 2016 6:30 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
We already have a library and example in Arduino for SPP use: https://github.com/espressif/arduino-es ... rialBT.ino
-
- Posts: 3
- Joined: Wed Mar 20, 2019 7:20 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
The BluetoothSerial library does not allow to connect directly to other devices (when a UUID is given) using SPP. Is this correct? If not, is there an example to do this in Arduino?ESP_Me-no-dev wrote: ↑Tue Mar 19, 2019 4:01 pmWe already have a library and example in Arduino for SPP use: https://github.com/espressif/arduino-es ... rialBT.ino
(I want to connect the ESP32 to the Neurosky Mindwave Mobile which uses Serial Port Profile (classic bluetooth). I have looked into the SPP_initiator example and it allows me to connect to the device but couldn't receive any data from it.)
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
I'm trying to do the same thing, to connect to an existing bluetooth serial device. Have you figured out a way to do with with Arduino?SpartaYigit wrote: ↑Wed Mar 20, 2019 7:29 pmThe BluetoothSerial library does not allow to connect directly to other devices (when a UUID is given) using SPP. Is this correct? If not, is there an example to do this in Arduino?
(I want to connect the ESP32 to the Neurosky Mindwave Mobile which uses Serial Port Profile (classic bluetooth). I have looked into the SPP_initiator example and it allows me to connect to the device but couldn't receive any data from it.)
Thanks.
-
- Posts: 3
- Joined: Wed Mar 20, 2019 7:20 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
Yeah, currently it is working with arduino. I have changed the bluetooth serial library to allow connecting to the Mindwave headset. The only problem left is the data that i am receiving. I can only see the raw data that the headset sends over (every 2 ms). I cannot seem to get the eSense values out of it which is sent every 1 second. Maybe we can help eachother out.JWardell wrote: ↑Wed Apr 24, 2019 3:33 amI'm trying to do the same thing, to connect to an existing bluetooth serial device. Have you figured out a way to do with with Arduino?SpartaYigit wrote: ↑Wed Mar 20, 2019 7:29 pmThe BluetoothSerial library does not allow to connect directly to other devices (when a UUID is given) using SPP. Is this correct? If not, is there an example to do this in Arduino?
(I want to connect the ESP32 to the Neurosky Mindwave Mobile which uses Serial Port Profile (classic bluetooth). I have looked into the SPP_initiator example and it allows me to connect to the device but couldn't receive any data from it.)
Thanks.
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
So you had to modify the bluetooth serial library to allow pairing etc, or did you change to a different library? How difficult is it? Is there a way to get a list of discoverable devices?SpartaYigit wrote: ↑Wed Apr 24, 2019 12:37 pmYeah, currently it is working with arduino. I have changed the bluetooth serial library to allow connecting to the Mindwave headset. The only problem left is the data that i am receiving. I can only see the raw data that the headset sends over (every 2 ms). I cannot seem to get the eSense values out of it which is sent every 1 second. Maybe we can help eachother out.
Trying to find what you are trying to interface with, some kind of EEG?
-
- Posts: 3
- Joined: Wed Mar 20, 2019 7:20 pm
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
Correct, I was trying to get the brainwave values from a Neurosky MindWave headset through the bluetooth conection.JWardell wrote: ↑Thu Apr 25, 2019 2:39 amSo you had to modify the bluetooth serial library to allow pairing etc, or did you change to a different library? How difficult is it? Is there a way to get a list of discoverable devices?SpartaYigit wrote: ↑Wed Apr 24, 2019 12:37 pmYeah, currently it is working with arduino. I have changed the bluetooth serial library to allow connecting to the Mindwave headset. The only problem left is the data that i am receiving. I can only see the raw data that the headset sends over (every 2 ms). I cannot seem to get the eSense values out of it which is sent every 1 second. Maybe we can help eachother out.
Trying to find what you are trying to interface with, some kind of EEG?
I modified the Bluetooth Serial library with the SPP_initiator example from ESP32-IDF to have the buffer functionality of the library when data is being received. It was a lot of work in the beginning to understand the code but now it finally works. There is code available on Qita https://qiita.com/ajtajta_j/items/297c6191635b47c945cb from which i started to directly connect to a device when the UUID is known (but has no buffer). There is a bt_discovery example on GitHub to see a list of discoverable devices.
Feel free to ask if something is not clear.
Re: ESP32 Bluetooth SPP with bidirectional communication (send and receive)
loboris wrote: ↑Fri Apr 06, 2018 1:11 pmYou just have to combine receiving and sending, like in this simple example based on example_spp_acceptor_demo.c
Tested with Bluetooth terminal Android application.Code: Select all
/* This example code is in the Public Domain (or CC0 licensed, at your option.) Unless required by applicable law or agreed to in writing, this software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */ #include <stdint.h> #include <string.h> #include <stdbool.h> #include <stdio.h> #include "nvs.h" #include "nvs_flash.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "esp_log.h" #include "esp_bt.h" #include "esp_bt_main.h" #include "esp_gap_bt_api.h" #include "esp_bt_device.h" #include "esp_spp_api.h" #include "time.h" #include "sys/time.h" #define SPP_TAG "SPP_ACCEPTOR_DEMO" #define SPP_SERVER_NAME "SPP_SERVER" #define EXCAMPLE_DEVICE_NAME "ESP_SPP_ACCEPTOR" #define SPP_SHOW_DATA 0 #define SPP_SHOW_SPEED 1 #define SPP_SHOW_MODE SPP_SHOW_DATA /*Choose show mode: show data or speed*/ static const esp_spp_mode_t esp_spp_mode = ESP_SPP_MODE_CB; static struct timeval time_new, time_old; static long data_num = 0; static const esp_spp_sec_t sec_mask = ESP_SPP_SEC_NONE; static const esp_spp_role_t role_slave = ESP_SPP_ROLE_SLAVE; static void print_speed(void) { float time_old_s = time_old.tv_sec + time_old.tv_usec / 1000000.0; float time_new_s = time_new.tv_sec + time_new.tv_usec / 1000000.0; float time_interval = time_new_s - time_old_s; float speed = data_num * 8 / time_interval / 1000.0; ESP_LOGI(SPP_TAG, "speed(%fs ~ %fs): %f kbit/s" , time_old_s, time_new_s, speed); data_num = 0; time_old.tv_sec = time_new.tv_sec; time_old.tv_usec = time_new.tv_usec; } static void esp_spp_cb(esp_spp_cb_event_t event, esp_spp_cb_param_t *param) { char buf[1024]; char spp_data[256]; switch (event) { case ESP_SPP_INIT_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_INIT_EVT"); esp_bt_dev_set_device_name(EXCAMPLE_DEVICE_NAME); esp_bt_gap_set_scan_mode(ESP_BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE); esp_spp_start_srv(sec_mask,role_slave, 0, SPP_SERVER_NAME); break; case ESP_SPP_DISCOVERY_COMP_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_DISCOVERY_COMP_EVT"); break; case ESP_SPP_OPEN_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_OPEN_EVT"); break; case ESP_SPP_CLOSE_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_CLOSE_EVT"); break; case ESP_SPP_START_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_START_EVT"); break; case ESP_SPP_CL_INIT_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_CL_INIT_EVT"); break; case ESP_SPP_DATA_IND_EVT: #if (SPP_SHOW_MODE == SPP_SHOW_DATA) ESP_LOGI(SPP_TAG, "ESP_SPP_DATA_IND_EVT len=%d handle=%d", param->data_ind.len, param->data_ind.handle); if (param->data_ind.len < 1023) { snprintf(buf, (size_t)param->data_ind.len, (char *)param->data_ind.data); printf("%s\n", buf); sprintf(spp_data, "Receined characters: %d\n", param->data_ind.len); esp_spp_write(param->write.handle, strlen(spp_data), (uint8_t *)spp_data); } else { esp_log_buffer_hex("",param->data_ind.data,param->data_ind.len); } #else gettimeofday(&time_new, NULL); data_num += param->data_ind.len; if (time_new.tv_sec - time_old.tv_sec >= 3) { print_speed(); } #endif break; case ESP_SPP_CONG_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_CONG_EVT"); break; case ESP_SPP_WRITE_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_WRITE_EVT"); break; case ESP_SPP_SRV_OPEN_EVT: ESP_LOGI(SPP_TAG, "ESP_SPP_SRV_OPEN_EVT"); gettimeofday(&time_old, NULL); break; default: break; } } void app_main() { esp_err_t ret = nvs_flash_init(); if (ret == ESP_ERR_NVS_NO_FREE_PAGES) { ESP_ERROR_CHECK(nvs_flash_erase()); ret = nvs_flash_init(); } ESP_ERROR_CHECK( ret ); esp_bt_controller_config_t bt_cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT(); if (esp_bt_controller_init(&bt_cfg) != ESP_OK) { ESP_LOGE(SPP_TAG, "%s initialize controller failed\n", __func__); return; } if (esp_bt_controller_enable(ESP_BT_MODE_CLASSIC_BT) != ESP_OK) { ESP_LOGE(SPP_TAG, "%s enable controller failed\n", __func__); return; } if (esp_bluedroid_init() != ESP_OK) { ESP_LOGE(SPP_TAG, "%s initialize bluedroid failed\n", __func__); return; } if (esp_bluedroid_enable() != ESP_OK) { ESP_LOGE(SPP_TAG, "%s enable bluedroid failed\n", __func__); return; } if (esp_spp_register_callback(esp_spp_cb) != ESP_OK) { ESP_LOGE(SPP_TAG, "%s spp register failed\n", __func__); return; } if (esp_spp_init(esp_spp_mode) != ESP_OK) { ESP_LOGE(SPP_TAG, "%s spp init failed\n", __func__); return; } }
I have this working, but what I wonder is, why does sending data with "esp_epp_write()" causing to receive the same data on the client as well? Only on a per-char basis like so when sending the string "Hello!":
Code: Select all
I (230963) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
H
I (230973) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
e
I (230973) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
l
I (230983) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
l
I (230993) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
o
I (230993) SPP_ACCEPTOR_DEMO: ESP_SPP_DATA_IND_EVT len=1 handle=129
!
Who is online
Users browsing this forum: No registered users and 73 guests