# 小屏幕WiFi+蓝牙配网功能设计
## 1. 概述
本设计针对504×410分辨率的小屏幕设备,实现蓝牙配网功能。用户通过长按屏幕左上角进入配网模式,使用蓝牙与移动端配网APP建立连接,完成WiFi网络配置。
### 核心特性
- **小屏幕优化**: 专为504×410分辨率设计的触摸友好界面
- **蓝牙配网**: 通过蓝牙连接进行网络配置
- **手势触发**: 长按左上角触发配网模式
- **状态反馈**: 实时显示配网进度和连接状态
- **自动重试**: 配网失败时自动重试连接
## 2. 技术架构
### 2.1 系统架构图
``mermaid
graph TD
A[用户长按触发] --> B[配网模式检测器]
B --> C[蓝牙配网管理器]
C --> D[蓝牙配网服务]
D --> F[蓝牙广播服务]
D --> G[配网数据接收器]
F --> J[移动端配网APP]
G --> L[网络连接器]
L --> M[连接状态管理器]
M --> N[配网结果反馈]
```
### 2.2 核心组件
#### BluetoothConfigManager (蓝牙配网管理器)
``mermaid
classDiagram
class BluetoothConfigManager {
-BluetoothConfigService bluetoothService
-ConnectionStatusManager statusManager
+startConfigMode()
+stopConfigMode()
+switchConfigMode()
+onConfigResult()
}
class BluetoothConfigService {
-BluetoothAdapter adapter
-ConfigDataReceiver receiver
+startAdvertising()
+stopAdvertising()
+onDataReceived()
}
class WiFiHotspotConfigService {
-WifiManager wifiManager
-HTTPConfigServer server
+createHotspot()
+startConfigServer()
+onConfigReceived()
}
```
## 3. 功能模块设计
### 3.1 触发机制
#### 长按检测器 (LongPressDetector)
``mermaid
sequenceDiagram
participant U as 用户
participant D as LongPressDetector
participant M as ConfigNetworkManager
participant UI as ConfigModeUI
U->>D: 长按左上角区域
D->>D: 检测按压时长(3秒)
D->>M: triggerConfigMode()
M->>UI: showConfigModeDialog()
UI->>U: 显示配网选择界面
```
#### 触摸区域定义
- **触发区域**: 左上角50×50dp区域
- **长按时长**: 3秒钟
- **视觉反馈**: 渐进式圆形进度指示器
### 3.2 BLE配网模式
#### BLE服务端架构
```mermaid
flowchart TD
A[小程序客户端] --> B[连接设备iB86]
B --> C[BLE GATT服务器]
C --> D[Service 0xFA00]
D --> E[Characteristic 0xEA01
状态通知]
D --> F[Characteristic 0xEA03
扫描指令]
D --> G[Characteristic 0xEA05
SSID配置]
D --> H[Characteristic 0xEA06
密码配置]
F --> I[WiFi扫描器]
I --> J[扫描结果]
J --> E
G --> K[配网管理器]
H --> K
K --> L[WiFi连接器]
L --> M[连接状态]
M --> E
```
#### BLE协议规范
**设备信息**
- **设备名称**: iB86
- **Service UUID**: 0xFA00
- **角色**: BLE服务端(GATT Server)
**Characteristic定义**
| UUID | 权限 | 功能描述 |
|------|------|----------|
| 0xEA01 | Notify | 状态通知和扫描结果回传 |
| 0xEA03 | Write | 接收扫描指令 |
| 0xEA05 | Write | 接收WiFi SSID |
| 0xEA06 | Write | 接收WiFi密码 |
#### AT命令协议
**状态码定义**
```
AT+STATE=0 # 当前无操作
AT+STATE=1 # 收到扫描指令,开始扫描网络
AT+STATE=2 # 收到SSID和密码,开始连接网络
AT+STATE=3 # 已连接WiFi并获取IP
AT+STATE=6 # 密码错误
AT+STATE=7 # 没有找到该WiFi
```
**指令格式**
```
# 扫描指令
AT+SSID # 或 AT+SCAN
# 扫描结果回传格式
AT+SSID=<数量>,,,...,
# 示例: AT+SSID=1603,iLock,TP-LINK15DA,HUAWEI-AB8D
```
#### 配网流程
```mermaid
sequenceDiagram
participant MP as 小程序
participant BLE as BLE服务器
participant WIFI as WiFi扫描器
participant NET as 网络连接器
MP->>BLE: 连接设备iB86
MP->>BLE: 写入0xEA03 "AT+SSID"
BLE->>BLE: 更新状态AT+STATE=1
BLE->>WIFI: 开始WiFi扫描
WIFI->>BLE: 返回扫描结果
BLE->>MP: 通过0xEA01回传扫描结果
MP->>BLE: 写入0xEA05 目标SSID
MP->>BLE: 写入0xEA06 WiFi密码
BLE->>BLE: 更新状态AT+STATE=2
BLE->>NET: 尝试连接WiFi
alt 连接成功
NET->>BLE: 连接成功并获取IP
BLE->>BLE: 更新状态AT+STATE=3
BLE->>MP: 通过0xEA01通知成功
else 密码错误
NET->>BLE: 认证失败
BLE->>BLE: 更新状态AT+STATE=6
BLE->>MP: 通过0xEA01通知密码错误
else 网络未找到
NET->>BLE: 网络不存在
BLE->>BLE: 更新状态AT+STATE=7
BLE->>MP: 通过0xEA01通知网络未找到
end
```
## 4. 用户界面设计
### 4.1 小屏幕适配规范
#### 布局约束
``xml
504x410dp
48dp
16sp
16dp
12dp
```
#### 界面层级结构
```mermaid
graph TD
A[长按触发] --> B[BLE配网页面]
B --> C[BLE服务器启动]
B --> D[等待小程序连接]
B --> E[WiFi扫描状态]
B --> F[配网进度显示]
B --> G[连接结果页面]
G --> H[返回主界面]
```
### 4.2 状态指示器设计
#### 配网状态机
```mermaid
stateDiagram-v2
[*] --> 待机模式
待机模式 --> 配网触发检测 : 长按左上角
配网触发检测 --> BLE服务启动 : 触发成功
BLE服务启动 --> 等待连接 : AT+STATE=0
等待连接 --> WiFi扫描 : 收到AT+SSID指令
WiFi扫描 --> 扫描中 : AT+STATE=1
扫描中 --> 等待配置 : 回传扫描结果
等待配置 --> 连接WiFi : 收到SSID和密码
连接WiFi --> 连接中 : AT+STATE=2
连接中 --> 连接成功 : AT+STATE=3
连接中 --> 密码错误 : AT+STATE=6
连接中 --> 网络未找到 : AT+STATE=7
连接成功 --> [*]
密码错误 --> 等待配置 : 重新配置
网络未找到 --> 等待配置 : 重新配置
```
## 5. 数据模型
### 5.1 配网配置模型
#### WiFiConfigData
```java
public class WiFiConfigData {
private String ssid; // WiFi名称
private String password; // WiFi密码
private SecurityType security; // 加密类型
private boolean isHidden; // 是否隐藏网络
private String ipConfig; // IP配置类型
private String proxyConfig; // 代理配置
}
```
#### BluetoothConfigStatus
```java
public class BluetoothConfigStatus {
private ConfigState state; // 配网状态
private String message; // 状态消息
private int progress; // 进度百分比
private long timestamp; // 时间戳
}
}
```
### 5.2 枚举定义
```java
public enum ConfigState {
IDLE("待机"), // AT+STATE=0
DETECTING("检测触发"),
BLE_SERVER_STARTING("BLE服务启动"),
WAITING_CONNECTION("等待连接"),
WIFI_SCANNING("WiFi扫描中"), // AT+STATE=1
WAITING_CONFIG("等待配置"),
CONNECTING_WIFI("连接WiFi中"), // AT+STATE=2
SUCCESS("连接成功"), // AT+STATE=3
PASSWORD_ERROR("密码错误"), // AT+STATE=6
NETWORK_NOT_FOUND("网络未找到"); // AT+STATE=7
}
```
## 6. 核心服务实现
### 6.1 配网触发服务
#### LongPressGestureDetector
```java
public class LongPressGestureDetector {
private static final long LONG_PRESS_DURATION = 3000; // 3秒
private static final int TRIGGER_AREA_SIZE = 50; // 50dp
public boolean isInTriggerArea(float x, float y) {
return x <= dpToPx(TRIGGER_AREA_SIZE) &&
y <= dpToPx(TRIGGER_AREA_SIZE);
}
public void handleTouchEvent(MotionEvent event) {
// 处理触摸事件逻辑
}
}
```
### 6.2 BLE配网服务
#### BleConfigGattServer
```java
public class BleConfigGattServer {
// UUID定义
private static final UUID SERVICE_UUID = UUID.fromString("0000fa00-0000-1000-8000-00805f9b34fb");
private static final UUID STATUS_CHAR_UUID = UUID.fromString("0000ea01-0000-1000-8000-00805f9b34fb");
private static final UUID SCAN_CHAR_UUID = UUID.fromString("0000ea03-0000-1000-8000-00805f9b34fb");
private static final UUID SSID_CHAR_UUID = UUID.fromString("0000ea05-0000-1000-8000-00805f9b34fb");
private static final UUID PASSWORD_CHAR_UUID = UUID.fromString("0000ea06-0000-1000-8000-00805f9b34fb");
private BluetoothGattServer gattServer;
private ATCommandProcessor atProcessor;
public void startGattServer() {
BluetoothGattService service = new BluetoothGattService(
SERVICE_UUID, BluetoothGattService.SERVICE_TYPE_PRIMARY);
// 0xEA01 - 状态通知Characteristic
BluetoothGattCharacteristic statusChar = new BluetoothGattCharacteristic(
STATUS_CHAR_UUID,
BluetoothGattCharacteristic.PROPERTY_NOTIFY,
BluetoothGattCharacteristic.PERMISSION_READ);
// 0xEA03 - 扫描指令Characteristic
BluetoothGattCharacteristic scanChar = new BluetoothGattCharacteristic(
SCAN_CHAR_UUID,
BluetoothGattCharacteristic.PROPERTY_WRITE,
BluetoothGattCharacteristic.PERMISSION_WRITE);
// 0xEA05 - SSID配置Characteristic
BluetoothGattCharacteristic ssidChar = new BluetoothGattCharacteristic(
SSID_CHAR_UUID,
BluetoothGattCharacteristic.PROPERTY_WRITE,
BluetoothGattCharacteristic.PERMISSION_WRITE);
// 0xEA06 - 密码配置Characteristic
BluetoothGattCharacteristic passwordChar = new BluetoothGattCharacteristic(
PASSWORD_CHAR_UUID,
BluetoothGattCharacteristic.PROPERTY_WRITE,
BluetoothGattCharacteristic.PERMISSION_WRITE);
service.addCharacteristic(statusChar);
service.addCharacteristic(scanChar);
service.addCharacteristic(ssidChar);
service.addCharacteristic(passwordChar);
gattServer.addService(service);
}
}
```
#### ATCommandProcessor
```java
public class ATCommandProcessor {
private WiFiScanManager wifiScanner;
private WiFiConnectionManager wifiConnector;
private BleConfigGattServer gattServer;
public void processCommand(String command, UUID characteristicUuid) {
if (SCAN_CHAR_UUID.equals(characteristicUuid)) {
if ("AT+SSID".equals(command) || "AT+SCAN".equals(command)) {
handleWiFiScan();
}
} else if (SSID_CHAR_UUID.equals(characteristicUuid)) {
handleSSIDConfig(command);
} else if (PASSWORD_CHAR_UUID.equals(characteristicUuid)) {
handlePasswordConfig(command);
}
}
private void handleWiFiScan() {
notifyState(1); // AT+STATE=1
wifiScanner.startScan(new WiFiScanCallback() {
@Override
public void onScanCompleted(List ssidList) {
String result = formatScanResult(ssidList);
gattServer.notifyCharacteristic(STATUS_CHAR_UUID, result.getBytes());
}
});
}
private String formatScanResult(List ssidList) {
StringBuilder sb = new StringBuilder();
sb.append("AT+SSID=").append(ssidList.size());
for (String ssid : ssidList) {
sb.append(",").append(ssid);
}
return sb.toString();
}
private void handleSSIDConfig(String ssid) {
this.targetSSID = ssid;
checkAndConnect();
}
private void handlePasswordConfig(String password) {
this.targetPassword = password;
checkAndConnect();
}
private void checkAndConnect() {
if (targetSSID != null && targetPassword != null) {
notifyState(2); // AT+STATE=2
wifiConnector.connect(targetSSID, targetPassword, new WiFiConnectionCallback() {
@Override
public void onConnected(String ipAddress) {
notifyState(3); // AT+STATE=3
}
@Override
public void onPasswordError() {
notifyState(6); // AT+STATE=6
}
@Override
public void onNetworkNotFound() {
notifyState(7); // AT+STATE=7
}
});
}
}
private void notifyState(int state) {
String stateMsg = "AT+STATE=" + state;
gattServer.notifyCharacteristic(STATUS_CHAR_UUID, stateMsg.getBytes());
}
}
```
## 7. 安全性设计
### 7.1 数据传输安全
#### 蓝牙配网安全
- **配对验证**: 使用PIN码配对验证
- **数据加密**: AES-128加密WiFi凭证
- **超时机制**: 配网会话5分钟超时
- **设备认证**: 验证设备MAC地址白名单
### 7.2 权限管理
#### 必需权限清单
``xml
```
## 8. 测试策略
### 8.1 功能测试
#### 测试用例矩阵
| 测试场景 | 蓝牙配网 | 预期结果 |
|---------|---------|----------|
| 正常配网流程 | ✓ | 配网成功 |
| 错误WiFi凭证 | ✓ | 显示错误信息 |
| 网络连接超时 | ✓ | 自动重试 |
| 长按触发 | - | 正确进入配网 |
| 小屏幕适配 | ✓ | 界面正常显示 |
### 8.2 性能测试
#### 关键指标
- **触发响应时间**: < 500ms
- **蓝牙广播启动**: < 2s
- **配网完成时间**: < 30s
- **内存占用**: < 50MB
- **CPU占用**: < 20%
### 8.3 兼容性测试
#### 测试环境
- **Android版本**: API 26-34
- **蓝牙版本**: 4.0+
- **WiFi标准**: 802.11 b/g/n
- **屏幕分辨率**: 504×410dp
- **设备类型**: 嵌入式Android设备