-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathBluetooth.java
220 lines (192 loc) · 8.56 KB
/
Bluetooth.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
package blah.com.minipcr;
import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.Context;
import android.content.Intent;
import android.os.Handler;
import android.os.ParcelUuid;
import android.widget.Toast;
import android.os.SystemClock;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Set;
import java.util.UUID;
public class Bluetooth {
private String DEVICE_NAME = "HC-05"; // Change this to match your bluetooth device name.
private String DEVICE_UUID;
private Context context;
private MainActivity mainActivity;
private BluetoothAdapter mBluetoothAdapter;
private BluetoothSocket mmSocket;
private BluetoothDevice mmDevice;
private OutputStream mmOutputStream;
private InputStream mmInputStream;
private Thread workerThread;
private byte[] readBuffer;
private int readBufferPosition;
private volatile boolean stopWorker;
public Bluetooth(Context context, MainActivity mainActivity){
// When this object is created, it needs the context of it's instantiating class, as well as
// reference to the class itself
this.context = context;
this.mainActivity = mainActivity;
stopWorker = false; // A flag to start/stop the background thread checking for incoming data
}
// Function that searches for the Bluetooth with DEVICE_NAME
public int findBT()
{
// Retrieve a BluetoothAdapter object
mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
if(mBluetoothAdapter == null)
{
Toast toast = Toast.makeText(context, "No Bluetooth adapter available", Toast.LENGTH_LONG);
toast.show();
return -1;
}
// Make sure Bluetooth is enabled
if(!mBluetoothAdapter.isEnabled())
{
Intent enableBluetooth = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
((Activity) context).startActivityForResult(enableBluetooth, 0);
}
// Loop through paired devices looking for DEVICE_NAME
Set<BluetoothDevice> pairedDevices = mBluetoothAdapter.getBondedDevices();
if(pairedDevices.size() > 0)
{
for(BluetoothDevice device : pairedDevices) {
if (device.getName().equals(DEVICE_NAME)) {
mmDevice = device;
Method method = null;
try {
// If and when device is found, retrieved it's UUID
method = mmDevice.getClass().getMethod("getUuids", null);
ParcelUuid[] deviceUuids = (ParcelUuid[]) method.invoke(mmDevice, null);
DEVICE_UUID = deviceUuids[0].getUuid().toString(); // Will only be one UUID.
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
break;
}
}
}
// If device was not found
if(DEVICE_UUID == null){
// Did not find device, user must pair with it, so open Bluetooth settings
Intent intentBluetooth = new Intent();
intentBluetooth.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intentBluetooth.setAction(android.provider.Settings.ACTION_BLUETOOTH_SETTINGS);
context.startActivity(intentBluetooth);
final Handler handler = new Handler();
handler.postDelayed(new Runnable() {
@Override
public void run() {
Toast toast = Toast.makeText(context, "Pair with " + DEVICE_NAME + " in Bluetooth Settings with key 1234. Then return to app and try again.", Toast.LENGTH_LONG);
toast.show();
}
}, 1000);
return -1;
}
else { // Else device was found
Toast toast = Toast.makeText(context, "Bluetooth device found", Toast.LENGTH_LONG);
toast.show();
}
return 0;
}
// Method that opens Bluetooth connection with DEVICE_NAME
public void openBT() throws IOException
{
// Create socket, connect to device, grab input and output data streams
UUID uuid = UUID.fromString(DEVICE_UUID); //Standard SerialPortService ID
mmSocket = mmDevice.createRfcommSocketToServiceRecord(uuid);
mmSocket.connect();
mmOutputStream = mmSocket.getOutputStream();
mmInputStream = mmSocket.getInputStream();
Toast toast = Toast.makeText(context, "Bluetooth connection opened", Toast.LENGTH_LONG);
toast.show();
}
public void beginListenForData()
{
Toast toast = Toast.makeText(context, "Listening for incoming Bluetooth data in background", Toast.LENGTH_LONG);
toast.show();
final Handler handler = new Handler();
final byte delimiter = 10; //This is the ASCII code for a newline character '\n'
stopWorker = false;
readBufferPosition = 0;
readBuffer = new byte[1024];
workerThread = new Thread(new Runnable()
{
public void run()
{
while(!Thread.currentThread().isInterrupted() && !stopWorker) // While stopWorker is false
{
try
{
// If there is no input data stream then bail
if(mmInputStream == null) {
stopWorker = true;
break;
}
int bytesAvailable = mmInputStream.available();
if(bytesAvailable > 0) // If there is data available to be read in
{
// Read in the data and loop through each byte
byte[] packetBytes = new byte[bytesAvailable];
mmInputStream.read(packetBytes);
for(int i=0;i<bytesAvailable;i++)
{
byte b = packetBytes[i];
if(b == delimiter) // If the new line character is found
{
// Grab the read data and pass it to the MainActivity
final byte[] encodedBytes = new byte[readBufferPosition];
System.arraycopy(readBuffer, 0, encodedBytes, 0, encodedBytes.length);
readBufferPosition = 0;
handler.post(new Runnable()
{
public void run()
{
mainActivity.receiveData(encodedBytes); // MAKE SURE MAINACTIVITY IMPLEMENTS THIS METHOD
}
});
}
else // While the delimeter (new line char) is not found, keep looping through bytes
{
readBuffer[readBufferPosition++] = b;
}
}
}
}
catch (IOException ex)
{
stopWorker = true;
}
}
}
});
workerThread.start(); // Start the background thread
}
// Send a byte of data over Bluetooth
public void sendData(byte data) throws IOException
{
mmOutputStream.write(data);
}
// Close the Bluetooth connection and clean up
public void closeBT() throws IOException
{
stopWorker = true;
mmOutputStream.close();
mmInputStream.close();
mmSocket.close();
Toast toast = Toast.makeText(context, "Bluetooth closed", Toast.LENGTH_LONG);
toast.show();
}
}