# ECellBluetooth >ECellBluetooth applies to all bluetooth devices, provides the connection management, quick and convenient and OTA upgrade instructions sent. ## Project configuration * Reference header file ``` #import ``` * Project demo directory Scan 扫描连接外设demo | Scan the connected peripherals demo Function 所有指令发送demo | All instructions sent the demo Firmware 固件升级指引 | Firmware upgrade guide DialPush 表盘推送demo | Dial push demo * Project configuration **Targets -> Info->Privacy -> Bluetooth Peripheral Usage Description** **Targets -> Capabilities -> Background Modes -> Uses Bluetooth LE accessories ✔️** **Targets -> Embedded Binaries -> add IOSDFULibrary.framework and Zip.framework** ``` - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { #ifdef DEBUG [[ECellBluetoothManager shareInstance] registrationServices:YES IsReconnect:YES]; #else [[ECellBluetoothManager shareInstance] registrationServices:NO IsReconnect:YES]; #endif return YES; } ``` ## Architecture ``` #import #import #import #import #import #import ``` ### ``` ======= Get Command ======= /// 获取固件版本信息 | Get firmware information + (void)getFirmwareInfoCommand:(void(^_Nullable)(ECell_BLE_COMMAND_ERROR_TYPE errorType, NSDictionary *_Nullable json))callback; { adapterNumber = 1001; deviceName = "ZW12"; firmwareVersion = "1.0.5"; macAddress = "EE:DB:22:17:61:A2"; platform = 0; protocolVersion = "1.0"; } /// 获取电量 | Get attery + (void)getBatteryCommand:(void(^_Nullable)(ECell_BLE_COMMAND_ERROR_TYPE errorType, NSDictionary *_Nullable json))callback; status: (0: 未充电 1: 充电完成 2: 正在充电 | 0: not charged 1: charging completed 2: charging in progress) { power = 100; status = 0; } /// 获取配置信息 | Get configuration information + (void)getProfileCommand:(void(^_Nullable)(ECell_BLE_COMMAND_ERROR_TYPE errorType, NSDictionary *_Nullable json))callback; cycle: 重复 0:表示仅一次 1:表示每天重复(bit0 - bit6分别表示周一到周日的重复设置,所有位都为0时,表示只提醒一次) | Repeat 0: only once 1: every day (bit0-bit6 is the repeat setting from Monday to Sunday, and when all bits are 0, it is only reminded once) label: 0:闹钟 1:会议 | 0: Alarm clock 1: Meeting hand 0:左手 1:右手 | 0: left hand 1: right hand raise 0:抬手亮屏关闭 1:抬手亮屏开启 | 0: turn off the bright screen 1: turn on the bright screen flip 0:翻腕亮屏关闭 1:翻腕亮屏开启 | 0: turn wrist bright screen off 1: turn wrist bright screen on drinkRemind(interval): 间隔(分钟)| interval(min) heartRateCheck(interval): 间隔(分钟)10的倍数 | interval(min) remindType: 提醒方式 1:亮屏 2:震动 3:亮屏+震动 | Reminder 1: bright screen 2: vibration 3: bright screen + vibration genger: 性别 0:女 1:男 | 0: female 1: male sittingTime: 久坐时间(分钟)超过这个时间提醒 | Sitting time (min) Over this time reminder sittingThreshold: 久坐阈值(步数)以小时为单位久坐时间内,步数低于这个阈值才提醒 | Sedentary threshold(Step) sportMode: 0: 日常计步 1:走路 2: 跑步 3: 骑行 4: 爬山 | 0: daily step counting 1: walking 2: running 3: cycling 4: climbing { alarmClock = ( { cycle = 0; hour = 0; isOpen = 0; label = 0; min = 0; }, { cycle = 0; hour = 0; isOpen = 0; label = 0; min = 0; }, { cycle = 0; hour = 0; isOpen = 0; label = 0; min = 0; }, { cycle = 0; hour = 0; isOpen = 0; label = 0; min = 0; }, { cycle = 0; hour = 0; isOpen = 0; label = 0; min = 0; } ); drinkRemind = { cycle = 0; endHour = 21; interval = 120; isOpen = 0; startHour = 7; }; handUp = { flip = 0; hand = 0; raise = 0; }; heartRateCheck = { endHour = 13; interval = 30; isOpen = 0; startHour = 11; }; notDisturb = { endHour = 0; isOpen = 1; startHour = 0; }; remindMode = { remindType = 0; }; sedentary = { cycle = 1; endHour = 18; isOpen = 0; sittingThreshold = 200; sittingTime = 60; startHour = 8; }; setPush = { isOpen = 61; }; target = { sportMode = 0; targetSteps = 8917760; }; userInfo = { age = 30; gender = 0; goalStep = 8917760; height = 170; sportMode = 0; weight = 65; }; } /// 获取当前实时数据 | Get the current real-time data /// @param type 1:睡眠 2:心率 3:计步 4:运动模式 | 1: sleep 2: heart rate 3: count steps 4: exercise mode + (void)getRealTimeDataCommandType:(NSInteger)type callback:(void(^_Nullable)(ECell_BLE_COMMAND_ERROR_TYPE errorType, NSDictionary *_Nullable json))callback; type: 3 { stepCalorie = 0; stepDistance = 0; stepNumber = 0; timestamp = 1591637040; } type: 2 { heartRate = 80; timestamp = 1591637160; } /// 获取指定日期健康数据 | Gets health data for the specified date /// @param type 1:睡眠,2:心率,3:计步,4:运动 5:血压 6:血氧 | 1: sleep, 2: heart rate, 3: step counting, 4: exercise 5: blood pressure 6: blood oxygen /// @param year 年 /// @param month 月 /// @param day 日 /// 设备最多保存七天数据 | The device holds data for up to seven days + (void)getHealthDataCommandType:(NSInteger)type year:(NSInteger)year month:(NSInteger)month day:(NSInteger)day callback:(void(^_Nullable)(ECell_BLE_COMMAND_ERROR_TYPE errorType, NSDictionary *_Nullable json))callback; class StepModel { // mac地址 var macID: String = "" /// 计步日期(2017-01-16) var dataDate: String = "" /// 步数 var stepNumber: Int = 0 /// 计步距离(米) var stepDistance: Int = 0 /// 计步卡路里(千卡) var stepCalorie: Float = 0 /// 计步时长(分钟) var stepDuration: Int = 0 /// 计步详情(step|cal|m|时段,...) var stepDetails: String = "0|0.0|0.0|0,0|0.0|0.0|1,0|0.0|0.0|2,0|0.0|0.0|3,0|0.0|0.0|4,0|0.0|0.0|5,0|0.0|0.0|6,0|0.0|0.0|7,0|0.0|0.0|8,0|0.0|0.0|9,0|0.0|0.0|10,0|0.0|0.0|11,0|0.0|0.0|12,0|0.0|0.0|13,0|0.0|0.0|14,0|0.0|0.0|15,0|0.0|0.0|16,0|0.0|0.0|17,0|0.0|0.0|18,0|0.0|0.0|19,0|0.0|0.0|20,0|0.0|0.0|21,0|0.0|0.0|22,0|0.0|0.0|23" } class SleepModel { // mac地址 var macID: String = "" /// 睡眠日期(2018-06-20) var dataDate: String = "" /// 深睡时长 var deepSleepDuration: Int = 0 /// 浅睡时长 var lightSleepDuration: Int = 0 /// 清醒时长 var awakeDuration: Int = 0 /// 总睡眠时长 var totalSleepDuration: Int = 0 /// 入睡时间(2020-04-16 21:04) var fallingSleepTimes: String = "" /// 醒来时间 var awakeTimes: String = "" /// 醒来次数 var awakeNumber: Int = 0 /// 睡眠详情数据(睡眠类型|开始时间戳|持续时长|结束时间戳,..) 睡眠类型:0: 未进入睡眠 1:轻度睡眠 2:深度睡眠 var sleepDetails: String = "" func getToatlSleepTimeStr() -> String { return "\(totalSleepDuration / 60)h \(totalSleepDuration % 60)m" } } class HeartRateModel { // mac地址 var macID: String = "" /// 心率日期(2018-06-20) var dataDate: String = "" /// 最大心率 var heartMax: Int = 0 /// 最小心率 var heartMin: Int = 0 /// 平均心率 var heartAvg: Int = 0 /// 心率详情(心率值|时间戳,...) var heartDetails: String = "" } class SportModel { /// mac地址 var macID: String = "" /// 运动时间(2017-12-17 10:20:20) var dataDate: String = "" /// 版本号 var verison: Int = 0 /// 运动类型 1.健走 2.户外跑 3.室内跑 4.登山 5.越野跑 6.半马 7.全马 8.跳绳 9.羽毛球 10.篮球 11.骑行 12.滑冰 13.健身房 14.瑜伽 15.网球 16.兵乓球 17.足球 18.游泳 19.性爱 20.室内骑行 21.室内健走22.自由训练 var sportType: Int = 0 /// 运动时长(秒) var duration: Int = 0 /// 距离(米) var distance: Int = 0 /// 卡路里(千卡) var calorie: Float = 0 /// 运动步数(划水次数,仅游泳模式使用) var stepNumber: Int = 0 /// 最大心率 var heartMax: Int = 0 /// 平均心率 var heartAvg: Int = 0 /// 最小心率 var heartMin: Int = 0 /// 最大步频(泳池长度) var stepFrequencyMax: Int = 0 /// 平均步频(游泳效率SWOLF) var stepFrequencyAvg: Int = 0 /// 最小步频(泳姿) var stepFrequencyMin: Int = 0 /// 最大配速(s) var paceMax: Int = 0 /// 平均配速(s) var paceAvg: Int = 0 /// 最小配速(s) var paceMin: Int = 0 /// 开始绝对海拔 var startAltitude: Int = 0 /// 结束绝对海拔 var endAltitude: Int = 0 /// GPS个数 var gpsCount: Int = 0 /// 公里牌个数 var kmCount: Int = 0 /// 步数个数 var stepCount: Int = 0 /// 心率个数 var heartCount: Int = 0 /// 趟数详情个数 var trainDetailCount: Int = 0 /// GPS时间 var gpsTimestamp: Int = 0 /// GPS数组(时间差|纬度|经度|海拔,...) var gpsDeatail: String = "" /// 公里牌数组(时间戳|纬度|经度|步数,...) var kmDetail: String = "" /// 步数时间 var stepTimestamp: Int = 0 /// 步数数组(时间差|步数|距离(m),...) var stepDetail: String = "" /// HRS时间戳 var hrsTimestamp: Int = 0 /// HRS数组(时间差(默认为5S)|心率(未采样到为0)) var hrsDetail: String = "" /// 游泳详细数组(时间戳|仰泳划水次数|蛙泳划水次数|蝶泳划水次数|自由泳划水次数|混合泳划水次数) var swimmingDetail: String = "" // MARK:- 计算属性 /// 全程步频(步/分钟) var stepFrequency: Int { if stepNumber <= 0 { return 0 } let temp = Float(stepNumber) / (Float(duration) / 60.0) return lroundf(temp + 0.5) } /// 全程步幅(厘米) var stride: Int { if stepNumber <= 0 { return 0 } return (distance * 100) / stepNumber } } ======= Listen Command ======= ECell_BLE_REPORT_COMMAND_realStep { stepCalorie = 0; stepDistance = 10; stepNumber = 18; timestamp = 1591637580; } ECell_BLE_REPORT_COMMAND_realHeartRate { heartRate = 65; timestamp = 1591637580; } ECell_BLE_REPORT_COMMAND_realBloodPressure ECell_BLE_REPORT_COMMAND_realBloodOxyge ECell_BLE_REPORT_COMMAND_cameraControl state: 0:退出 1:打开相机 2:拍照(只设备发手机) | 0: exit 1: open camera 2: Take photos (send mobile phone only) { state = 0; } ECell_BLE_REPORT_COMMAND_findPhone ```