From: liangzhenying <867174124@qq.com> Date: Fri, 7 Jun 2024 06:40:56 +0000 (+0800) Subject: 新增文件传输接口 X-Git-Url: http://git.snicker.com.cn/?a=commitdiff_plain;h=38abc819b5b80ee3c6a6e1ddeff8d398f6140de1;p=mirrors%2FIOTBluetooth-iOS.git 新增文件传输接口 --- diff --git a/Doc/galaxy.lzma b/Doc/galaxy.lzma new file mode 100644 index 0000000..fb481b9 Binary files /dev/null and b/Doc/galaxy.lzma differ diff --git a/IOTBluetooth/IOTBluetooth/Example/AbilityViewController.swift b/IOTBluetooth/IOTBluetooth/Example/AbilityViewController.swift index f390f9d..86a693c 100644 --- a/IOTBluetooth/IOTBluetooth/Example/AbilityViewController.swift +++ b/IOTBluetooth/IOTBluetooth/Example/AbilityViewController.swift @@ -9,9 +9,9 @@ import UIKit import IOTBluetooth class AbilityViewController: BaseViewController { - + @IBOutlet weak var listView: UITableView! - + override func viewDidLoad() { super.viewDidLoad() title = "已连接" + IBManager.currentConnected!.name @@ -37,21 +37,28 @@ extension AbilityViewController: UITableViewDelegate, UITableViewDataSource { } func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { - activityIndicatorView.startAnimating() + let data = datas[indexPath.row] - IBSender() - .ability(data.ability) - .parameters(data.parameters) - .response {[weak self] result in - guard let self = self else {return} - if result.isSuccess{ - //请求成功 + if data.label.isEqual("mp3"){ +// IBFileSender().sendMp3(URL(fileURLWithPath: "")) + } + else{ + activityIndicatorView.startAnimating() + IBSender() + .ability(data.ability) + .parameters(data.parameters) + .response {[weak self] result in + guard let self = self else {return} + if result.isSuccess{ + //请求成功 + } + else{ + //请求失败 + } + print(result) + activityIndicatorView.stopAnimating() } - else{ - //请求失败 - } - print(result) - activityIndicatorView.stopAnimating() - } + } } + } diff --git a/IOTBluetooth/IOTBluetooth/Example/Datas.swift b/IOTBluetooth/IOTBluetooth/Example/Datas.swift index 566d552..429ff48 100644 --- a/IOTBluetooth/IOTBluetooth/Example/Datas.swift +++ b/IOTBluetooth/IOTBluetooth/Example/Datas.swift @@ -41,7 +41,7 @@ let datas: [(ability: IBAbility, label: String, parameters: [IBParameter])] = [ (.auxiliary, "设置手表辅助功能参数", [.auxiliary(.bloodOxygen)]), (.unit, "设置手表公英制单位", [.value(1)]), - (.sendWeather, "发送天气数据", [.weather(IBWeather())]), + (.disk, "获取SD卡剩余空间", []), (.unpair, "发送解除配对消息", []), (.sendUnpair, "发送取消解除配对消息", []), @@ -86,8 +86,19 @@ let datas: [(ability: IBAbility, label: String, parameters: [IBParameter])] = [ (.syncGPS, "同步路径坐标集历史数据", [.value(1654012800)]), (.sendSyncEnd, "发送同步数据结束消息", []), (.addressBook, "发送通讯录", [.addressBook([IBAddressBook()])]), - -// (.revokeFileSend, "撤销当前文件传输", [.file(.mp3)]), -// (.fetchFiles, "获取指定类型所有文件", [.file(.mp3)]), -// (.deleteFiles, "删除指定类型所有文件", [.file(.mp3)]), + + (.epo, "发送EPO文件信息", [.epo(IBEpo())]), + (.ota, "发送OTA文件信息", [.ota(IBOta())]), + (.mp3, "发送MP3文件信息", [.MP3(IBMp3())]), + (.customDial, "发送自定义表盘文件汇总信息", [.customDial(IBCustomDial())]), + (.marketDial, "发送市场表盘文件汇总信息", [.marketDial(IBMarketDial())]), + (.dialInfo, "发送单个表盘文件信息", [.dialInfo(IBDialInfo())]), + (.fileCheckCode, "发送文件校验码", [.value(10)]), + + (.revokeFileSend, "撤销当前文件传输", [.file(.mp3)]), + (.deleteFile, "删除指定文件", [.deleteFile(IBDeleteFile())]), + (.deleteFiles, "删除指定类型所有文件", [.file(.mp3)]), + + + (.sendWeather, "发送天气数据", [.weather(IBWeather())]), ] diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.pbxproj b/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.pbxproj index 5ffed27..76bc46c 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.pbxproj +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.pbxproj @@ -10,11 +10,17 @@ 180B01982BFC831300524729 /* IBHistoryHeartRate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 180B01972BFC831300524729 /* IBHistoryHeartRate.swift */; }; 180B019E2BFC9CF400524729 /* IBHistoryBaseTraining.swift in Sources */ = {isa = PBXBuildFile; fileRef = 180B019D2BFC9CF400524729 /* IBHistoryBaseTraining.swift */; }; 180CE2652C0D728F00A7006E /* IBAddressBook.swift in Sources */ = {isa = PBXBuildFile; fileRef = 180CE2642C0D728F00A7006E /* IBAddressBook.swift */; }; + 181441CF2C11571400CCDD46 /* IBMp3.swift in Sources */ = {isa = PBXBuildFile; fileRef = 181441CE2C11571400CCDD46 /* IBMp3.swift */; }; + 181441D12C11575D00CCDD46 /* IBOta.swift in Sources */ = {isa = PBXBuildFile; fileRef = 181441D02C11575D00CCDD46 /* IBOta.swift */; }; + 181441D32C115AC500CCDD46 /* IBFileSender.swift in Sources */ = {isa = PBXBuildFile; fileRef = 181441D22C115AC500CCDD46 /* IBFileSender.swift */; }; + 181441D52C116AE500CCDD46 /* IBDial.swift in Sources */ = {isa = PBXBuildFile; fileRef = 181441D42C116AE500CCDD46 /* IBDial.swift */; }; 184431322BF3720E00546E4E /* IBOtherTarget.swift in Sources */ = {isa = PBXBuildFile; fileRef = 184431312BF3720E00546E4E /* IBOtherTarget.swift */; }; 1849DC8F2BEC8007002C2D2D /* IBVibrateSound.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1849DC8E2BEC8007002C2D2D /* IBVibrateSound.swift */; }; 1849DC912BECD131002C2D2D /* IBCode.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1849DC902BECD131002C2D2D /* IBCode.swift */; }; 184B94CB2BF606CC0042BEB3 /* IBTrainTarget.swift in Sources */ = {isa = PBXBuildFile; fileRef = 184B94CA2BF606CC0042BEB3 /* IBTrainTarget.swift */; }; 1859DFA02BFF5A2700112E8C /* IBSendTime.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1859DF9F2BFF5A2700112E8C /* IBSendTime.swift */; }; + 18884C442C11DBA300E01458 /* IBDeleteFile.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18884C432C11DBA300E01458 /* IBDeleteFile.swift */; }; + 18884C462C12A4EA00E01458 /* IBEpo.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18884C452C12A4EA00E01458 /* IBEpo.swift */; }; 18993AA22C073FED006742D2 /* IBBloodOxygen.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18993AA12C073FED006742D2 /* IBBloodOxygen.swift */; }; 189C15892C05E0CD00676A80 /* IBTarinState.swift in Sources */ = {isa = PBXBuildFile; fileRef = 189C15882C05E0CD00676A80 /* IBTarinState.swift */; }; 189C158B2C05F27C00676A80 /* IBAbout.swift in Sources */ = {isa = PBXBuildFile; fileRef = 189C158A2C05F27C00676A80 /* IBAbout.swift */; }; @@ -103,11 +109,17 @@ 180B01972BFC831300524729 /* IBHistoryHeartRate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBHistoryHeartRate.swift; sourceTree = ""; }; 180B019D2BFC9CF400524729 /* IBHistoryBaseTraining.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBHistoryBaseTraining.swift; sourceTree = ""; }; 180CE2642C0D728F00A7006E /* IBAddressBook.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBAddressBook.swift; sourceTree = ""; }; + 181441CE2C11571400CCDD46 /* IBMp3.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBMp3.swift; sourceTree = ""; }; + 181441D02C11575D00CCDD46 /* IBOta.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBOta.swift; sourceTree = ""; }; + 181441D22C115AC500CCDD46 /* IBFileSender.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBFileSender.swift; sourceTree = ""; }; + 181441D42C116AE500CCDD46 /* IBDial.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBDial.swift; sourceTree = ""; }; 184431312BF3720E00546E4E /* IBOtherTarget.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBOtherTarget.swift; sourceTree = ""; }; 1849DC8E2BEC8007002C2D2D /* IBVibrateSound.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBVibrateSound.swift; sourceTree = ""; }; 1849DC902BECD131002C2D2D /* IBCode.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBCode.swift; sourceTree = ""; }; 184B94CA2BF606CC0042BEB3 /* IBTrainTarget.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBTrainTarget.swift; sourceTree = ""; }; 1859DF9F2BFF5A2700112E8C /* IBSendTime.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBSendTime.swift; sourceTree = ""; }; + 18884C432C11DBA300E01458 /* IBDeleteFile.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBDeleteFile.swift; sourceTree = ""; }; + 18884C452C12A4EA00E01458 /* IBEpo.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBEpo.swift; sourceTree = ""; }; 18993AA12C073FED006742D2 /* IBBloodOxygen.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBBloodOxygen.swift; sourceTree = ""; }; 189C15882C05E0CD00676A80 /* IBTarinState.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBTarinState.swift; sourceTree = ""; }; 189C158A2C05F27C00676A80 /* IBAbout.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBAbout.swift; sourceTree = ""; }; @@ -220,6 +232,7 @@ 8A65F9602BAC0810005C1EA4 /* IBSimulateParser.swift */, 8A878FE12BA9444C008C7F26 /* IBParameter.swift */, 8A79D2242BA4278E0096A98C /* IBSender.swift */, + 181441D22C115AC500CCDD46 /* IBFileSender.swift */, 8A79D2262BA433330096A98C /* IBNotify.swift */, 8A9F6AC02BA04BE100DA520F /* IBManager.swift */, 8A0A39BE2B980BEF006A3B18 /* IOTBluetooth.h */, @@ -304,6 +317,11 @@ 18EFF59A2C080F14001B1E0E /* IBUserInfo.swift */, 18C9589A2C082FA7006A5DE8 /* IBWeather.swift */, 180CE2642C0D728F00A7006E /* IBAddressBook.swift */, + 181441CE2C11571400CCDD46 /* IBMp3.swift */, + 181441D02C11575D00CCDD46 /* IBOta.swift */, + 181441D42C116AE500CCDD46 /* IBDial.swift */, + 18884C452C12A4EA00E01458 /* IBEpo.swift */, + 18884C432C11DBA300E01458 /* IBDeleteFile.swift */, 1849DC902BECD131002C2D2D /* IBCode.swift */, ); path = Models; @@ -434,6 +452,7 @@ 180B019E2BFC9CF400524729 /* IBHistoryBaseTraining.swift in Sources */, 8A87FBB52BAA85FB00096761 /* IBTrainingData.swift in Sources */, 8A878FE42BA94D09008C7F26 /* IBChecker.swift in Sources */, + 18884C442C11DBA300E01458 /* IBDeleteFile.swift in Sources */, 189C15892C05E0CD00676A80 /* IBTarinState.swift in Sources */, 8A76B60B2BA851730016F2AB /* IBParser.swift in Sources */, 18EFF59B2C080F14001B1E0E /* IBUserInfo.swift in Sources */, @@ -454,9 +473,11 @@ 8A65F9652BAC271B005C1EA4 /* IBScreen.swift in Sources */, 1859DFA02BFF5A2700112E8C /* IBSendTime.swift in Sources */, 8A65F9632BAC1018005C1EA4 /* IBTargetStep.swift in Sources */, + 181441D32C115AC500CCDD46 /* IBFileSender.swift in Sources */, 8A34B9252BA2A069000F66BD /* IBWatchInfo.swift in Sources */, 8A0A39D62B980EC9006A3B18 /* IBPeripheralUUID.swift in Sources */, 189C15952C05FFC700676A80 /* IBHistoryCalorie.swift in Sources */, + 181441CF2C11571400CCDD46 /* IBMp3.swift in Sources */, 8A9F6AC12BA04BE100DA520F /* IBManager.swift in Sources */, 18EC6E282BFF4C6D00757CA8 /* IBPhoneInfo.swift in Sources */, 18C9589F2C086A9D006A5DE8 /* IBHistorySleep.swift in Sources */, @@ -465,14 +486,17 @@ 18E7AC962BF5E39900CB9393 /* IBHeartRate.swift in Sources */, 18C9589B2C082FA7006A5DE8 /* IBWeather.swift in Sources */, 8A0A39D82B980F58006A3B18 /* UTF8.swift in Sources */, + 181441D12C11575D00CCDD46 /* IBOta.swift in Sources */, 18E7AC922BF44C6800CB9393 /* IBSleep.swift in Sources */, 8A0A39C62B980C88006A3B18 /* IBluetooth.swift in Sources */, 8A0A39CB2B980CFC006A3B18 /* Logger.swift in Sources */, 189C158F2C05F85200676A80 /* IBHistoryStep.swift in Sources */, 8A5822D12BA1C80700590AB6 /* LRC.swift in Sources */, 8A0A39DA2B981037006A3B18 /* Date.swift in Sources */, + 181441D52C116AE500CCDD46 /* IBDial.swift in Sources */, 18993AA22C073FED006742D2 /* IBBloodOxygen.swift in Sources */, 8A0A39CD2B980D53006A3B18 /* IBPeripheral.swift in Sources */, + 18884C462C12A4EA00E01458 /* IBEpo.swift in Sources */, 8A87FBB32BAA7F3900096761 /* IBLanguage.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate b/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate index 69bbb2d..d9462a7 100644 Binary files a/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate and b/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate differ diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAbility.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAbility.swift index a7565fc..cb5c81d 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAbility.swift +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAbility.swift @@ -9,7 +9,7 @@ import Foundation /// 功能指令 public class IBAbility { - + /// 命令类型 let type: `Type` @@ -168,7 +168,7 @@ public extension IBAbility { /// 最高不超过 250 ,如果需要关闭最高心率提醒,可将最高心率设为255,开启则设正常值即可。 static let heartRateHigh = IBAbility.short.id(0x15).parser(IBGeneralParser.self).checker(IBHeartRateHighChecker.self) - /// 手势拍照 + /// 手势拍照 /// - Parameter action: /// 0 = 退出手势拍照 \ /// 1 = 进入手势拍照 @@ -204,7 +204,7 @@ public extension IBAbility { /// APP获取某表盘ID是否已安装 /// - Parameter value:Int - /// - Returns: Int + /// - Returns: Int /// 1 = 已安装 \ /// 2 = 未安装 \ /// Read from ``IBResponse``.value @@ -338,7 +338,7 @@ public extension IBAbility { /// - Returns: [IBHistoryBurningItem] \ /// Read from ``IBResponse``.items static let syncFatBurning = IBAbility.short.id(0x44).parser(IBSyncBurningParser.self).checker(IBValueChecker.self) - + /// 同步站立历史数据 /// - Parameter value: /// 0 = 今天 \ @@ -393,7 +393,7 @@ public extension IBAbility { /// - Returns: [IBHistorySleepItem] \ /// Read from ``IBResponse``.items static let syncSleep = IBAbility.short.id(0x4B).parser(IBSyncSleepParser.self).checker(IBValueChecker.self) - + /// 同步路径坐标集历史数据 /// - Parameter value:开始训练时间戳 /// - Returns: [IBHistoryGpsItem] \ @@ -431,75 +431,87 @@ public extension IBAbility { /// - Parameter weather: see ``IBWeather`` static let sendWeather = IBAbility.long.id(0x20).parser(IBGeneralParser.self).checker(IBWeatherChecker.self) - /// APP发送通讯录 + /// 发送通讯录 /// - Parameter addressBook: see ``IBAddressBook`` - /// 0~20 + /// 联系人个数0~20 static let addressBook = IBAbility.long.id(0x0B).parser(IBGeneralParser.self).checker(IBAddressBookChecker.self) -// /// 撤销当前文件传输 -// static let revokeFileSend = IBAbility.short.id(0x20).parser(IBGeneralParser.self).checker(IBFileChecker.self) -// /// 获取指定类型所有文件(当前只支持 MP3 和 表盘) -// static let fetchFiles = IBAbility.short.id(0x21).parser(IBGeneralParser.self).checker(IBFileChecker.self) -// /// 删除指定类型所有文件(当前只支持 MP3 和 表盘) -// static let deleteFiles = IBAbility.short.id(0x22).parser(IBGeneralParser.self).checker(IBFileChecker.self) -// -// + // MARK: - 文件 + + /// 发送MP3文件信息 + /// - Parameter mp3: see ``IBMp3`` + static let mp3 = IBAbility.file.id(0x21).parser(IBGeneralParser.self).checker(IBMp3Checker.self) + + /// 发送自定义表盘文件汇总信息 + /// - Parameter customDial: see ``IBCustomDail`` + static let customDial = IBAbility.file.id(0x22).parser(IBGeneralParser.self).checker(IBCustomDialChecker.self) + + /// 发送市场表盘文件汇总信息 + /// - Parameter marketDial: see ``IBMarketDail`` + static let marketDial = IBAbility.file.id(0x22).parser(IBGeneralParser.self).checker(IBMarketDialChecker.self) + + /// 发送单个表盘文件信息 + /// - Parameter dialInfo: see ``IBDailInfo`` + static let dialInfo = IBAbility.file.id(0x24).parser(IBGeneralParser.self).checker(IBDialInfoChecker.self) + + /// 发送文件校验码 + /// - Parameter value:Int + static let fileCheckCode = IBAbility.file.id(0x23).parser(IBGeneralParser.self).checker(IBValueChecker.self) + + /// 删除指定文件 + /// - Parameter deleteFile: see ``IBDeleteFile`` + static let deleteFile = IBAbility.long.id(0x22).parser(IBGeneralParser.self).checker(IBDeleteFileChecker.self) + + /// 删除指定类型所有文件(当前只支持 MP3 和 表盘) + /// - Parameter file: see ``IBFile`` + static let deleteFiles = IBAbility.short.id(0x22).parser(IBGeneralParser.self).checker(IBFileChecker.self) + + /// 发送OTA文件信息 + /// - Parameter ota: see ``IBOta`` + static let ota = IBAbility.file.id(0x20).parser(IBGeneralParser.self).checker(IBOtaChecker.self) + + + /// 发送EPO文件信息 + /// - Parameter epo: see ``IBEpo`` + static let epo = IBAbility.file.id(0x28).parser(IBGeneralParser.self).checker(IBEpoChecker.self) + + /// 撤销当前文件传输 + /// - Parameter file: see ``IBFile`` + static let revokeFileSend = IBAbility.short.id(0x20).parser(IBGeneralParser.self).checker(IBFileChecker.self) + + // /// 获取指定类型所有文件(当前只支持 MP3 和 表盘) + // static let fetchFiles = IBAbility.short.id(0x21).parser(IBGeneralParser.self).checker(IBFileChecker.self) } extension IBAbility { - - -// -// // MARK: - Fetch 获取数据 - -// /// 撤销当前文件传输 -// static let revokeFileTransfer = IBAbility.short.id(0x20) - -// /// 删除指定文件(数据包为文件索引号) -// static let deleteFile = IBAbility.long.id(0x22) - - -// -// -// /// 发送OTA文件信息 -// static let ota = IBAbility.file.id(0x20) -// /// 发送MP3文件信息 -// static let mp3 = IBAbility.file.id(0x21) -// /// 发送表盘文件信息 -// static let dial = IBAbility.file.id(0x22) -// /// APP发送文件校验码 -// static let fileCheckCode = IBAbility.file.id(0x23) -// ///  发送单个表盘文件信息 -// static let dialInfo = IBAbility.file.id(0x24) -// /// 发送EPO文件信息(04,25) -// static let epo = IBAbility.file.id(0x28) -// -// -// // MARK: - 私有 - -// -// /// 获取当前数据(jSON格式)【不使用】 -// static let var681B9E92 = IBAbility.short.id(0x06) -// /// 开关多媒体功能(播放手机音乐、通话等)【不使用】 -// static let var681254AC = IBAbility.short.id(0x09) -// /// 进入工厂测试模式【不使用】 -// static let varD3D21DC8 = IBAbility.short.id(0x30) -// /// 同步压力历史数据【不使用】 -// static let varA2A25CD8 = IBAbility.short.id(0x42) -// -// /// 修改手表蓝牙名称【未使用】 -// static let var8FA46D73 = IBAbility.long.id(0x03) -// /// 同步基础训练实时心率记录【不使用】 -// static let var6CFBF636 = IBAbility.long.id(0x4B) -// /// 同步当天任意时间之后的基础训练记录【不使用】 -// static let var4D0264A9 = IBAbility.long.id(0x4D) -// /// APP发送靶心率区间值给手表(暂不用) -// static let var7EE39B21 = IBAbility.long.id(0x0C) -// -// /// 发送模块升级信息(04,26)【不使用】 -// static let var1FFA68BC = IBAbility.file.id(0x26) -// ///  发送模块单个文件升级信息(04,27)【不使用】 -// static let var9AD723C3 = IBAbility.file.id(0x27) -// /// 发送EPO文件信息(04,25)(旧版,不用) -// static let var4F791698 = IBAbility.file.id(0x25) + + // + // + // // MARK: - 私有 + + // + // /// 获取当前数据(jSON格式)【不使用】 + // static let var681B9E92 = IBAbility.short.id(0x06) + // /// 开关多媒体功能(播放手机音乐、通话等)【不使用】 + // static let var681254AC = IBAbility.short.id(0x09) + // /// 进入工厂测试模式【不使用】 + // static let varD3D21DC8 = IBAbility.short.id(0x30) + // /// 同步压力历史数据【不使用】 + // static let varA2A25CD8 = IBAbility.short.id(0x42) + // + // /// 修改手表蓝牙名称【未使用】 + // static let var8FA46D73 = IBAbility.long.id(0x03) + // /// 同步基础训练实时心率记录【不使用】 + // static let var6CFBF636 = IBAbility.long.id(0x4B) + // /// 同步当天任意时间之后的基础训练记录【不使用】 + // static let var4D0264A9 = IBAbility.long.id(0x4D) + // /// APP发送靶心率区间值给手表(暂不用) + // static let var7EE39B21 = IBAbility.long.id(0x0C) + // + // /// 发送模块升级信息(04,26)【不使用】 + // static let var1FFA68BC = IBAbility.file.id(0x26) + // ///  发送模块单个文件升级信息(04,27)【不使用】 + // static let var9AD723C3 = IBAbility.file.id(0x27) + // /// 发送EPO文件信息(04,25)(旧版,不用) + // static let var4F791698 = IBAbility.file.id(0x25) } diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBChecker.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBChecker.swift index 43f0f55..b30715a 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBChecker.swift +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBChecker.swift @@ -95,6 +95,22 @@ struct IBFileChecker: IBChecker { return [value.rawValue.byte] } } +struct IBOtaChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .ota(value) = parameters[.ota] else { fatalError("缺少参数: ota") } + guard let data = value.encode else { fatalError("json解析异常: ota") } + Logger.log(value.jsonString ?? "") + return data.bytes + } +} +struct IBEpoChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .epo(value) = parameters[.epo] else { fatalError("缺少参数: epo") } + guard let data = value.encode else { fatalError("json解析异常: epo") } + Logger.log(value.jsonString ?? "") + return data.bytes + } +} struct IBTargetStepChecker: IBChecker { static func check(_ parameters: [IBParameter]) -> [UInt8] { @@ -289,3 +305,64 @@ struct IBAddressBookChecker: IBChecker { } } +// MARK: - 文件传输 +struct IBMp3Checker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .MP3(value) = parameters[.mp3] else { fatalError("缺少参数: MP3") } + guard let data = value.encode else { fatalError("json解析异常: MP3") } + Logger.log(value.jsonString ?? "") + return data.bytes + } +} +struct IBCustomDialChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .customDial(value) = parameters[.customDial] else { fatalError("缺少参数: customDial") } + Logger.log(value.description) + let data = value.UID.byte2 + [value.batteryStyle.byte] + [value.timeStyle.byte] + [value.timeColor.byte] + [value.numberOfFiles.byte] + return data + } +} +struct IBMarketDialChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .marketDial(value) = parameters[.marketDial] else { fatalError("缺少参数: marketDial") } + Logger.log(value.description) + var data = value.UID.byte2 + if let name = value.theme?.data(using: .utf8),!name.isEmpty { + data += [name.count.byte] + data += name + } + else{ + data += [0.byte] + } + data += [value.numberOfFiles.byte] + return data + } +} +struct IBDialInfoChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .dialInfo(value) = parameters[.dialInfo] else { fatalError("缺少参数: marketDial") } + Logger.log(value.description) + var data = value.UID.byte2 + [value.number.byte] + [value.fileType.byte] + if let name = value.fileName.data(using: .utf8),!name.isEmpty { + data += [name.count.byte] + data += name + } + else{ + data += [0.byte] + } + data += value.fizeSize.byte4 + return data + } +} + +struct IBDeleteFileChecker: IBChecker { + static func check(_ parameters: [IBParameter]) -> [UInt8] { + guard case let .deleteFile(value) = parameters[.deleteFile] else { fatalError("缺少参数: deleteFile") } + Logger.log(value.description) + var data = [value.uids.count.byte] + [value.fileType.byte] + for uid in value.uids { + data += uid.byte2 + } + return data + } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBFileSender.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBFileSender.swift new file mode 100644 index 0000000..bb776e8 --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBFileSender.swift @@ -0,0 +1,37 @@ +// +// IBFileSender.swift +// IOTBluetooth +// +// Created by incar on 2024/6/6. +// + +import Foundation + + +public class IBFileSender { + + + public init() { + + } + +// public func sendMp3(_ filePath:URL){ +//// let data = Data(filePath) +// let model = IBMp3() +// +// IBSender() +// .ability(.mp3) +// .parameters([.MP3(model)]) +// .response {[weak self] result in +// guard let self = self else {return} +// if result.isSuccess{ +// //请求成功 +// } +// else{ +// //请求失败 +// } +// print(result) +// +// } +// } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBManager.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBManager.swift index bf98a16..3d8f214 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBManager.swift +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBManager.swift @@ -31,7 +31,7 @@ public class IBManager { public extension IBManager { /// SDK 版本号 - static let version: String = "1.0.7" + static let version: String = "1.0.8" /// 默认为 false static var isDebug: Bool = false { didSet { Logger.isDebug = isDebug } diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBParameter.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBParameter.swift index 23dfa2e..b10eb73 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBParameter.swift +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBParameter.swift @@ -30,6 +30,13 @@ enum IBKey: String { case userInfo = "userInfo" case weather = "weather" case addressBook = "addressBook" + case epo = "epo" + case ota = "ota" + case mp3 = "mp3" + case customDial = "customDial" + case marketDial = "marketDial" + case dialInfo = "dialInfo" + case deleteFile = "deleteFile" } /// 参数 @@ -78,6 +85,20 @@ public enum IBParameter { case weather(IBWeather) /// 发送通讯录 case addressBook([IBAddressBook]) + /// 发送EPO文件信息 + case epo(IBEpo) + /// 发送OTA文件信息 + case ota(IBOta) + /// 发送mp3文件信息 + case MP3(IBMp3) + /// 发送自定义表盘信息汇总 + case customDial(IBCustomDial) + /// 发送表盘市场信息汇总 + case marketDial(IBMarketDial) + /// 发送单个表盘文件信息 + case dialInfo(IBDialInfo) + /// 删除指定文件 + case deleteFile(IBDeleteFile) var key: IBKey { switch self { @@ -103,6 +124,14 @@ public enum IBParameter { case .userInfo(_): return .userInfo case .weather(_): return .weather case .addressBook(_): return .addressBook + case .epo(_): return .epo + case .ota(_): return .ota + case .MP3(_): return .mp3 + case .customDial(_): return .customDial + case .marketDial(_): return .marketDial + case .dialInfo(_): return .dialInfo + case .deleteFile(_): return .deleteFile + } } } @@ -123,10 +152,10 @@ public enum IBFile: Int { case mp3 /// 表盘信息 case dial - /// 天气 - case weather - /// 闹钟 - case clock + /// OTA(W4) + case ota_w4 + ///EPO + case epo } //0:运动 //1:心率 diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBClock.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBClock.swift index 7b12f33..600d82b 100644 --- a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBClock.swift +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBClock.swift @@ -12,7 +12,17 @@ public class IBClock: Codable { /// 闹钟列表 public var alarms: [IBClockInfo] = [] - public init() { } + public init() { +// for i in 0...4{ +// let model = IBClockInfo() +// model.id = i +// model.hour = i*3 +// model.minute = i*10 +// model.enable = i%2 +// model.repeat = [1,2,3,4,5,6,7] +// alarms.append(model) +// } + } } /// 闹钟信息模型 diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDeleteFile.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDeleteFile.swift new file mode 100644 index 0000000..eeac194 --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDeleteFile.swift @@ -0,0 +1,22 @@ +// +// IBDeleteFile.swift +// IOTBluetooth +// +// Created by incar on 2024/6/6. +// + +import Foundation + +/// 删除文件模型 +public class IBDeleteFile:Codable { + /// 文件类型,2:MP3 3:表盘 + public var fileType: Int = 2 + /// 文件UID,文件唯一编号。一次最多5个 + public var uids: [Int] = [] + + public init() { } + + public var description: String { + return "IBDeleteFile(fileType: \(fileType), uids:\(uids))" + } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDial.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDial.swift new file mode 100644 index 0000000..cb5dea1 --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBDial.swift @@ -0,0 +1,67 @@ +// +// IBDail.swift +// IOTBluetooth +// +// Created by incar on 2024/6/6. +// + +import Foundation +/// 表盘文件汇总信息模型(自定义) +public class IBCustomDial { + /// UID,0~4:自定义表盘UID(不可变更) + public var UID: Int = 0 + /// 电池图标样式, 0:无图标 1:黑色图标 2:白色图标 + public var batteryStyle: Int = 0 + /// 时间样式 0:时间在下方 1:时间在上方 + public var timeStyle: Int = 0 + /// 时间字体颜色 0:亮白 1:黑 2:暗白 3:绿 4:橙 5:蓝 + public var timeColor: Int = 0 + /// 文件数目,0~255,为0则后面无需发送各个文件。(仅有一种情况为0,即自定义表盘背景图跟之前一样,仅改变了电池和时间样式) + public var numberOfFiles: Int = 0 + + public init() { } + + public var description: String { + return "IBCustomDail(UID: \(UID), batteryStyle:\(batteryStyle), timeStyle:\(timeStyle), timeColor:\(timeColor), numberOfFiles:\(numberOfFiles))" + } +} + +/// 表盘文件汇总信息模型(表盘市场) +public class IBMarketDial { + /// UID,0x05~0xffff:表盘市场UID + public var UID: Int = 0 + /// 主题名称长度。0~255,为0则后面名称不用传,且SD卡中该表盘文件夹名字为“unknown_xxxx”(xxxx为UID)。(仅表盘市场有该项) + public var themeLength: Int = 0 + /// 主题名称,名字字节数为前面名称长度指定,UTF-8编码,仅表盘市场有该项,自定义表盘名称统一为"custom" + public var theme: String? + /// 文件数目,0~255,为0则后面无需发送各个文件。(仅有一种情况为0,即自定义表盘背景图跟之前一样,仅改变了电池和时间样式) + public var numberOfFiles: Int = 0 + + public init() { } + + public var description: String { + return "IBMarketDail(UID: \(UID), themeLength:\(themeLength), theme:\(theme ?? ""), numberOfFiles:\(numberOfFiles))" + } +} + +/// 单个表盘文件信息模型 +public class IBDialInfo { + /// UID,0x05~0xffff:表盘市场UID + public var UID: Int = 0 + /// 文件编号,1~255,即该主题表盘中的第几个文件,最大为表盘文件汇总信息中的文件数目 + public var number: Int = 0 + /// 文件类型,0:表盘jSON文件(压缩后统一命名为local_page.lzma)1:图片文件(除缩略图外的其他图片)(背景图压缩后统一命名为main_bg.lzma)2:缩略图:(压缩后统一命名为thumbnail.lzma) + public var fileType: Int = 0 + /// 文件名称长度,6~255,不能为0,文件后缀统一为.lzma + public var nameLength: Int = 0 + /// 文件名称,名称字节数为前面名称长度指定,UTF-8编码 + public var fileName: String = "" + /// 文件大小,0x01~0xffffffff + public var fizeSize: Int = 0 + + public init() { } + + public var description: String { + return "IBDailInfo(UID: \(UID), number:\(number),fileType: \(fileType), nameLength:\(nameLength), fileName:\(fileName), fizeSize:\(fizeSize))" + } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBEpo.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBEpo.swift new file mode 100644 index 0000000..03e29c3 --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBEpo.swift @@ -0,0 +1,25 @@ +// +// IBEpo.swift +// IOTBluetooth +// +// Created by incar on 2024/6/7. +// + +import Foundation +/// IBEpo信息模型 +public class IBEpo:Codable { + /// 文件类型,7 + internal var type: Int = 7 + /// 固定字段为1 + internal var valid: Int = 1 + /// 文件名 + public var fileName: String = "" + /// 纬度值 + public var lat: String = "" + /// 经度值 + public var lon: String = "" + /// 文件大小,单位byte + public var size: Int = 1000 + + public init() { } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBMp3.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBMp3.swift new file mode 100644 index 0000000..d30879c --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBMp3.swift @@ -0,0 +1,25 @@ +// +// IBMp3.swift +// IOTBluetooth +// +// Created by incar on 2024/6/6. +// + +import Foundation +/// mp3文件信息模型 +public class IBMp3:Codable { + /// 歌曲名字 + public var name: String = "" + /// 文件类型,2:MP3 + internal var type: Int = 2 + /// 文件大小,单位byte + public var size: Int = 0 + +// enum CodingKeys: String, CodingKey { +// case name = "pn" +// case type = "tp" +// case mac = "mac" +// } + + public init() { } +} diff --git a/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBOta.swift b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBOta.swift new file mode 100644 index 0000000..6e6bdf6 --- /dev/null +++ b/IOTBluetooth/IOTBluetooth/IOTBluetooth/Models/IBOta.swift @@ -0,0 +1,25 @@ +// +// IBOta.swift +// IOTBluetooth +// +// Created by incar on 2024/6/6. +// + +import Foundation +/// OTA文件信息模型 +public class IBOta:Codable { + /// 文件类型,1:OTA + internal var type: Int = 1 + /// 文件大小,单位byte + public var size: Int = 0 + /// major是主版本号,mid是中间版本号,minor是次版本号,用于与手表当前版本比较,新于当前版本才可升级 + public var major: Int = 0 + /// mid是中间版本号 + public var mid: Int = 0 + /// minor是次版本号 + public var minor: Int = 0 + /// 是否强制升级,0为非强制,1为强制 + public var isForced: Int = 0 + + public init() { } +}