14
14
15
15
/*
16
16
* This sketch demonstrate how to run both Central and Peripheral roles
17
- * at the same tiem
17
+ * at the same time. It will act as a relay between an central (mobile)
18
+ * to another peripheral using bleuart service.
18
19
*/
19
20
#include < bluefruit.h>
20
21
@@ -35,149 +36,178 @@ void setup()
35
36
Bluefruit.begin (true , true );
36
37
// Set max power. Accepted values are: -40, -30, -20, -16, -12, -8, -4, 0, 4
37
38
Bluefruit.setTxPower (4 );
38
- Bluefruit.setName (" Bluefruit52" );
39
+ Bluefruit.setName (" Bluefruit52 duo" );
40
+
41
+ // Callbacks for Peripheral
42
+ Bluefruit.setConnectCallback (prph_connect_callback);
43
+ Bluefruit.setDisconnectCallback (prph_disconnect_callback);
39
44
40
45
// Callbacks for Central
41
46
Bluefruit.Central .setConnectCallback (cent_connect_callback);
42
47
Bluefruit.Central .setDisconnectCallback (cent_disconnect_callback);
43
48
44
-
49
+ // Configure and Start BLE Uart Service
50
+ bleuart.begin ();
51
+ bleuart.setRxCallback (prph_bleuart_rx_callback);
45
52
46
53
// Init BLE Central Uart Serivce
47
54
clientUart.begin ();
48
- clientUart.setRxCallback (bleuart_rx_callback );
55
+ clientUart.setRxCallback (cent_bleuart_rx_callback );
49
56
50
57
51
58
/* Start Central Scanning
52
59
* - Enable auto scan if disconnected
53
60
* - Interval = 100 ms, window = 80 ms
61
+ * - Filter only accept bleuart service
54
62
* - Don't use active scan
55
63
* - Start(timeout) with timeout = 0 will scan forever (until connected)
56
64
*/
57
65
Bluefruit.Scanner .setRxCallback (scan_callback);
58
66
Bluefruit.Scanner .restartOnDisconnect (true );
59
67
Bluefruit.Scanner .setInterval (160 , 80 ); // in unit of 0.625 ms
68
+ Bluefruit.Scanner .filterUuid (bleuart.uuid );
60
69
Bluefruit.Scanner .useActiveScan (false );
61
- Bluefruit.Scanner .start (0 ); // // 0 = Don't stop scanning after n seconds
70
+ Bluefruit.Scanner .start (0 ); // 0 = Don't stop scanning after n seconds
71
+
72
+ // Set up and start advertising
73
+ startAdv ();
62
74
}
63
75
64
- /* *
65
- * Callback invoked when scanner pick up an advertising data
66
- * @param report Structural advertising data
67
- */
76
+ void startAdv (void )
77
+ {
78
+ // Advertising packet
79
+ Bluefruit.Advertising .addFlags (BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE);
80
+ Bluefruit.Advertising .addTxPower ();
81
+
82
+ // Include bleuart 128-bit uuid
83
+ Bluefruit.Advertising .addService (bleuart);
84
+
85
+ // Secondary Scan Response packet (optional)
86
+ // Since there is no room for 'Name' in Advertising packet
87
+ Bluefruit.ScanResponse .addName ();
88
+
89
+ /* Start Advertising
90
+ * - Enable auto advertising if disconnected
91
+ * - Interval: fast mode = 20 ms, slow mode = 152.5 ms
92
+ * - Timeout for fast mode is 30 seconds
93
+ * - Start(timeout) with timeout = 0 will advertise forever (until connected)
94
+ *
95
+ * For recommended advertising interval
96
+ * https://developer.apple.com/library/content/qa/qa1931/_index.html
97
+ */
98
+ Bluefruit.Advertising .restartOnDisconnect (true );
99
+ Bluefruit.Advertising .setInterval (32 , 244 ); // in unit of 0.625 ms
100
+ Bluefruit.Advertising .setFastTimeout (30 ); // number of seconds in fast mode
101
+ Bluefruit.Advertising .start (0 ); // 0 = Don't stop advertising after n seconds
102
+ }
103
+
104
+ void loop ()
105
+ {
106
+ // do nothing, all the work is done in callback
107
+ }
108
+
109
+ /* ------------------------------------------------------------------*/
110
+ /* Peripheral
111
+ *------------------------------------------------------------------*/
112
+ void prph_connect_callback (uint16_t conn_handle)
113
+ {
114
+ char peer_name[32 ] = { 0 };
115
+ Bluefruit.Gap .getPeerName (conn_handle, peer_name, sizeof (peer_name));
116
+
117
+ Serial.print (" [Prph] Connected to " );
118
+ Serial.println (peer_name);
119
+ }
120
+
121
+ void prph_disconnect_callback (uint16_t conn_handle, uint8_t reason)
122
+ {
123
+ (void ) conn_handle;
124
+ (void ) reason;
125
+
126
+ Serial.println ();
127
+ Serial.println (" [Prph] Disconnected" );
128
+ }
129
+
130
+ void prph_bleuart_rx_callback (void )
131
+ {
132
+ // Forward data from Mobile to our peripheral
133
+ char str[20 +1 ] = { 0 };
134
+ bleuart.read (str, 20 );
135
+
136
+ Serial.print (" [Prph] RX: " );
137
+ Serial.println (str);
138
+
139
+ if ( clientUart.discovered () )
140
+ {
141
+ clientUart.print (str);
142
+ }else
143
+ {
144
+ bleuart.println (" [Prph] Central role not connected" );
145
+ }
146
+ }
147
+
148
+ /* ------------------------------------------------------------------*/
149
+ /* Central
150
+ *------------------------------------------------------------------*/
68
151
void scan_callback (ble_gap_evt_adv_report_t * report)
69
152
{
70
153
// Check if advertising contain BleUart service
71
154
if ( Bluefruit.Scanner .checkReportForService (report, clientUart) )
72
155
{
73
- Serial.print (" BLE UART service detected. Connecting ... " );
156
+ Serial.println (" BLE UART service detected. Connecting ... " );
74
157
75
158
// Connect to device with bleuart service in advertising
76
159
Bluefruit.Central .connect (report);
77
160
}
78
161
}
79
162
80
- /* *
81
- * Callback invoked when an connection is established
82
- * @param conn_handle
83
- */
84
163
void cent_connect_callback (uint16_t conn_handle)
85
164
{
86
- Serial.println (" Connected" );
87
-
88
- Serial.print (" Dicovering DIS ... " );
89
- if ( clientDis.discover (conn_handle) )
90
- {
91
- Serial.println (" Found it" );
92
- char buffer[32 +1 ];
93
-
94
- // read and print out Manufacturer
95
- memset (buffer, 0 , sizeof (buffer));
96
- if ( clientDis.getManufacturer (buffer, sizeof (buffer)) )
97
- {
98
- Serial.print (" Manufacturer: " );
99
- Serial.println (buffer);
100
- }
101
-
102
- // read and print out Model Number
103
- memset (buffer, 0 , sizeof (buffer));
104
- if ( clientDis.getModel (buffer, sizeof (buffer)) )
105
- {
106
- Serial.print (" Model: " );
107
- Serial.println (buffer);
108
- }
109
-
110
- Serial.println ();
111
- }
165
+ char peer_name[32 ] = { 0 };
166
+ Bluefruit.Gap .getPeerName (conn_handle, peer_name, sizeof (peer_name));
112
167
113
- Serial.print (" Discovering BLE Uart Service ... " );
168
+ Serial.print (" [Cent] Connected to " );
169
+ Serial.println (peer_name);;
114
170
115
171
if ( clientUart.discover (conn_handle) )
116
172
{
117
- Serial.println (" Found it" );
118
-
119
- Serial.println (" Enable TXD's notify" );
173
+ // Enable TXD's notify
120
174
clientUart.enableTXD ();
121
-
122
- Serial.println (" Ready to receive from peripheral" );
123
175
}else
124
176
{
125
- Serial.println (" Found NONE" );
126
-
127
177
// disconect since we couldn't find bleuart service
128
178
Bluefruit.Central .disconnect (conn_handle);
129
179
}
130
180
}
131
181
132
- /* *
133
- * Callback invoked when a connection is dropped
134
- * @param conn_handle
135
- * @param reason
136
- */
137
182
void cent_disconnect_callback (uint16_t conn_handle, uint8_t reason)
138
183
{
139
184
(void ) conn_handle;
140
185
(void ) reason;
141
186
142
- Serial.println (" Disconnected" );
187
+ Serial.println (" [Cent] Disconnected" );
143
188
}
144
189
145
190
/* *
146
191
* Callback invoked when uart received data
147
- * @param uart_svc Reference object to the service where the data
192
+ * @param cent_uart Reference object to the service where the data
148
193
* arrived. In this example it is clientUart
149
194
*/
150
- void bleuart_rx_callback (BLEClientUart& uart_svc )
195
+ void cent_bleuart_rx_callback (BLEClientUart& cent_uart )
151
196
{
152
- Serial.print (" [RX]: " );
153
-
154
- while ( uart_svc.available () )
155
- {
156
- Serial.print ( (char ) uart_svc.read () );
157
- }
158
-
159
- Serial.println ();
160
- }
197
+ char str[20 +1 ] = { 0 };
198
+ cent_uart.read (str, 20 );
199
+
200
+ Serial.print (" [Cent] RX: " );
201
+ Serial.println (str);
161
202
162
- void loop ()
163
- {
164
- if ( Bluefruit.Central .connected () )
203
+ if ( bleuart.notifyEnabled () )
165
204
{
166
- // Not discovered yet
167
- if ( clientUart.discovered () )
168
- {
169
- // Discovered means in working state
170
- // Get Serial input and send to Peripheral
171
- if ( Serial.available () )
172
- {
173
- delay (2 ); // delay a bit for all characters to arrive
174
-
175
- char str[20 +1 ] = { 0 };
176
- Serial.readBytes (str, 20 );
177
-
178
- clientUart.print ( str );
179
- }
180
- }
181
- }
205
+ // Forward data from our peripheral to Mobile
206
+ bleuart.print ( str );
207
+ }else
208
+ {
209
+ // response with no prph message
210
+ clientUart.println (" [Cent] Peripheral role not connected" );
211
+ }
182
212
}
183
213
0 commit comments