嵌入式开发大作业

2017-4-17

设计一个实验,要求新意与复杂度,先后顺序(10分钟/组),在规定时间内做好 presentation和演示。

###文档

###1.实验目标
在实验–利用Profiles的特征值进行无线点灯的基础上,simpleBLEPeripheral作为从机,手机(Nexus 5x)作为主机。
实现二者的连接(连接上音乐响起,断开音乐停止),并且从机可以发送数据到手机。

###2.实验工具
CC2540 底板 + IAR 软件
Nexus 5x + Android Studio

###3.实验过程(代码–修改的部分)

####[3.1] 从机模块(CC2540 底板 + IAR 软件)
一、配置文件的修改
[1.0] 从机模块(CC2540 底板 + IAR 软件)
[1.1] 增加char6的宏定义(simpleGATTprofile.h)
截图1
[1.2] 增加char6的UUID(simpleGATTprofile.c的GLOBAL VARIABLES段中)
截图2
[1.3] 增加char6的配置属性(eGATTprofile.c的Profile Attributes - variables段中)
截图3
[1.4] 修改属性表(simpleGATTprofile.c)
截图
[1.5] 修改特征值的参数函数(simpleGATTprofile.c)
截图
[1.6] 修改特征值的读写函数(simpleGATTprofile.c)
截图
截图
[1.7] 增加 char6 的通知开关初始化(simpleGATTprofile.c)
截图
[1.8] 增加通知开关初始化的实时更新(simpleGATTprofile.c)
截图
二、应用层的修改
[2.1]设置连接密码
截图.png
[2.2] 修改特征值初始化的数值(simpleBLEPeripheral.c的SimpleBLEPeripheral_Init函数中)
截图
[2.3] 修改应用层的回掉函数(simpleBLEPeripheral.c的simpleProfileChangeCB函数中)
截图

#####[3.2] 主机模块(Nexus 5x + Android Studio)
一、新建工程
Android 官方文档说明 Android 4.3 为 BLE 的核心功能提供平台支持和 API,所以新建工程最小SDK为4.3(即API 18).
截图

二、声明权限

1
2
3
4
<uses-permissionandroid:name="android.permission.BLUETOOTH"/>
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN"/>
<uses-feature android:name="android.hardware.bluetooth_le"
android:required="true"/>

三、检查手机设备是否支持蓝牙(启用蓝牙功能)、获取蓝牙适配器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// 检查当前手机是否支持ble 蓝牙,如果不支持退出程序
if (!getPackageManager().hasSystemFeature(PackageManager.FEATURE_BLUETOOTH_LE)) {
Toast.makeText(this, R.string.ble_not_supported, Toast.LENGTH_SHORT).show();
finish();
}

// 初始化 Bluetooth adapter, 通过蓝牙管理器得到一个参考蓝牙适配器(API必须在以上android4.3或以上和版本)
final BluetoothManager bluetoothManager = (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE);
mBluetoothAdapter = bluetoothManager.getAdapter();

// 检查设备上是否支持蓝牙
if (mBluetoothAdapter == null) {
Toast.makeText(this, R.string.error_bluetooth_not_supported, Toast.LENGTH_SHORT).show();
finish();
return;
}

四、开启蓝牙

1
2
3
4
5
6
7
//确保蓝夜在设备上可以开启
if (!mBluetoothAdapter.isEnabled()) {
if (!mBluetoothAdapter.isEnabled()) {
Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
startActivityForResult(enableBtIntent, REQUEST_ENABLE_BT);
}
}

五、扫描并显示蓝牙设备

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
 // 10秒后停止查找搜索.
private static final long SCAN_PERIOD = 10000;

private void scanLeDevice(final boolean enable) {
if (enable) {
// 经过预定扫描期后停止扫描
mHandler.postDelayed(new Runnable() {
@Override
public void run() {
mScanning = false;
mBluetoothAdapter.stopLeScan(mLeScanCallback);
invalidateOptionsMenu();
}
}, SCAN_PERIOD);

mScanning = true;
mBluetoothAdapter.startLeScan(mLeScanCallback);
} else {
mScanning = false;
mBluetoothAdapter.stopLeScan(mLeScanCallback);
}
invalidateOptionsMenu();
}
// 扫描结果返回.
private BluetoothAdapter.LeScanCallback mLeScanCallback = new BluetoothAdapter.LeScanCallback() {

@Override
public void onLeScan(final BluetoothDevice device, int rssi, byte[] scanRecord) {
runOnUiThread(new Runnable() {
@Override
public void run() {
mLeDeviceListAdapter.addDevice(device);
mLeDeviceListAdapter.notifyDataSetChanged();
}
});
}
};
//仅显示设备的名字和地址
static class ViewHolder {
TextView deviceName;
TextView deviceAddress;
}

六、连接到 GATT 服务端

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
private BluetoothManager mBluetoothManager;   //蓝牙设备管理器
private BluetoothAdapter mBluetoothAdapter; //蓝牙适配器
private String mBluetoothDeviceAddress; //蓝牙设备地址
private BluetoothGatt mBluetoothGatt;
private int mConnectionState = STATE_DISCONNECTED;

private static final int STATE_DISCONNECTED = 0; //设备无法连接
private static final int STATE_CONNECTING = 1; //设备正在连接
private static final int STATE_CONNECTED = 2; //设备连接完毕

public final static String ACTION_GATT_CONNECTED = "com.example.bluetooth.le.ACTION_GATT_CONNECTED";
public final static String ACTION_GATT_DISCONNECTED = "com.example.bluetooth.le.ACTION_GATT_DISCONNECTED";
public final static String ACTION_GATT_SERVICES_DISCOVERED = "com.example.bluetooth.le.ACTION_GATT_SERVICES_DISCOVERED";
public final static String ACTION_DATA_AVAILABLE = "com.example.bluetooth.le.ACTION_DATA_AVAILABLE";
public final static String EXTRA_DATA = "com.example.bluetooth.le.EXTRA_DATA";

public final static UUID UUID_HEART_RATE_MEASUREMENT = UUID.fromString(SampleGattAttributes.HEART_RATE_MEASUREMENT);

// I通过BLE API的不同类型的回掉方法
// connection change and services discovered.
private final BluetoothGattCallback mGattCallback = new BluetoothGattCallback() {
@Override
public void onConnectionStateChange(BluetoothGatt gatt, int status, int newState) {
String intentAction;
if (newState == BluetoothProfile.STATE_CONNECTED) {
//设备已连接
intentAction = ACTION_GATT_CONNECTED;
mConnectionState = STATE_CONNECTED;
broadcastUpdate(intentAction);
Log.i(TAG, "Connected to GATT server.");
// Attempts to discover services after successful connection.
Log.i(TAG, "Attempting to start service discovery:" +
mBluetoothGatt.discoverServices());

} else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
//设备无法连接
intentAction = ACTION_GATT_DISCONNECTED;
mConnectionState = STATE_DISCONNECTED;
Log.i(TAG, "Disconnected from GATT server.");
broadcastUpdate(intentAction);
}
}

//发现新服务端
@Override
public void onServicesDiscovered(BluetoothGatt gatt, int status) {
if (status == BluetoothGatt.GATT_SUCCESS) {
broadcastUpdate(ACTION_GATT_SERVICES_DISCOVERED);
} else {
Log.w(TAG, "onServicesDiscovered received: " + status);
}
}
//读写特性
public void readCharacteristic(BluetoothGattCharacteristic characteristic) {
if (mBluetoothAdapter == null || mBluetoothGatt == null) {
Log.w(TAG, "BluetoothAdapter not initialized");
return;
}
mBluetoothGatt.readCharacteristic(characteristic);
}

七、读取 BLE 信息

1
2
3
4
5
final StringBuilder stringBuilder = new StringBuilder(data.length);
for(byte byteChar : data)
stringBuilder.append(String.format("%02X ", byteChar));
intent.putExtra(EXTRA_DATA, new String(data) + "\n" + stringBuilder.toString());
}

###4.实验结果

手机截图
输入key后的连接
运行首页
结果

###5.感谢
1.老师,您辛苦了,谢谢您。让我上了一门很棒的课(以后周一周二上午没课啦)
2.感谢我给力的队友,合作很愉快
3.感谢博主的分享
CC2540
Android