去掉发送等待
authorliangzhenying <867174124@qq.com>
Thu, 13 Feb 2025 07:41:24 +0000 (15:41 +0800)
committerliangzhenying <867174124@qq.com>
Thu, 13 Feb 2025 07:41:24 +0000 (15:41 +0800)
IOTBluetooth/IOTBluetooth/Example/ChatViewController.swift
IOTBluetooth/IOTBluetooth/Example/IBSpeaker.swift [new file with mode: 0644]
IOTBluetooth/IOTBluetooth/Example/ViewController.swift
IOTBluetooth/IOTBluetooth/IOTBluetooth.xcodeproj/project.pbxproj
IOTBluetooth/IOTBluetooth/IOTBluetooth.xcworkspace/xcuserdata/yaozuopan.xcuserdatad/UserInterfaceState.xcuserstate
IOTBluetooth/IOTBluetooth/IOTBluetooth.xcworkspace/xcuserdata/yaozuopan.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist
IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAiManager.swift
IOTBluetooth/IOTBluetooth/IOTBluetooth/IBReceiveManager.swift
IOTBluetooth/IOTBluetooth/IOTBluetooth/IBSender.swift
IOTBluetooth/IOTBluetooth/IOTBluetooth/IBluetooth.swift

index a367ff1..40ccefe 100644 (file)
@@ -26,12 +26,12 @@ class ChatViewController: UIViewController{
         
         setupViews()
         setupChatCallBack()
-        //设置默认平台
-        self.title = MSPlatform.doubao.title
+
     }
     
     func setupViews(){
-        self.title = "大模型对话"
+        //设置默认平台
+        self.title = MSPlatform.doubao.title
         self.view.backgroundColor = .white
         self.navigationItem.rightBarButtonItems = [UIBarButtonItem(title: "切换平台", style: .done, target: self, action: #selector(changePlatform))]
 
@@ -50,6 +50,10 @@ class ChatViewController: UIViewController{
     }
     
     func setupChatCallBack(){
+        IBAiManager.shared.useMode = { [weak self] mode in
+            guard let self = self else {return}
+            self.title = mode.title
+        }
         IBAiManager.shared.aiResponse = {[weak self] response in
             print(response.description)
             guard let self = self else {return}
@@ -57,6 +61,7 @@ class ChatViewController: UIViewController{
                 if let model = list.last,model.reponseId == response.reponseId {
                     list.removeLast()
                     list.append(response)
+//                    IBSpeaker.shared.appendText(response.totalContent)
                 }
                 else{
                     list.append(response)
@@ -66,6 +71,9 @@ class ChatViewController: UIViewController{
                     tableView.scrollToRow(at: IndexPath(row: list.count - 1, section: 0), at: .none, animated: true)
                 }
             }
+            if  response.type == 4{
+                IBSpeaker.shared.appendText(response.totalContent)
+            }
         }
     }
     
diff --git a/IOTBluetooth/IOTBluetooth/Example/IBSpeaker.swift b/IOTBluetooth/IOTBluetooth/Example/IBSpeaker.swift
new file mode 100644 (file)
index 0000000..a34681b
--- /dev/null
@@ -0,0 +1,85 @@
+//
+//  IBSpeaker.swift
+//  IOTBluetooth
+//
+//  Created by liangshi on 2025/2/13.
+//
+
+import AVFoundation
+
+class IBSpeaker: NSObject, AVSpeechSynthesizerDelegate {
+    static let shared = IBSpeaker()
+    // MARK: - Properties
+    private let synthesizer = AVSpeechSynthesizer()
+    private var textBuffer: String = "" // 用于存储待播放的文字
+    private var isPlaying: Bool = false // 是否正在播放
+    
+    // MARK: - Initializer
+    override init() {
+        super.init()
+        synthesizer.delegate = self
+    }
+    
+    // MARK: - Public Methods
+    
+    /// 添加文字并开始播放
+    func appendText(_ text: String) {
+        textBuffer += text
+        
+        // 如果没有正在播放,则开始播放
+        if !isPlaying {
+            playNextChunk()
+        }
+    }
+    
+    /// 停止播放并清空缓冲区
+    func stop() {
+        synthesizer.stopSpeaking(at: .immediate)
+        textBuffer = ""
+        isPlaying = false
+    }
+    
+    // MARK: - Private Methods
+    
+    /// 播放缓冲区中的下一段文字
+    private func playNextChunk() {
+        guard !textBuffer.isEmpty else {
+            isPlaying = false
+            return
+        }
+        
+        // 每次播放一段文字(可以根据需要调整)
+        let chunkSize = textBuffer.count // 每次播放的字符数
+        let endIndex = textBuffer.index(textBuffer.startIndex, offsetBy: min(chunkSize, textBuffer.count))
+        let chunk = String(textBuffer[..<endIndex])
+        
+        // 移除已播放的文字
+        textBuffer.removeSubrange(..<endIndex)
+        
+        // 创建语音并播放
+        let utterance = AVSpeechUtterance(string: chunk)
+        utterance.voice = AVSpeechSynthesisVoice(language: "zh-CN") // 设置语言为中文
+        utterance.rate = 0.5 // 设置语速
+        utterance.pitchMultiplier = 1.0 // 设置音调
+        
+        synthesizer.speak(utterance)
+        isPlaying = true
+    }
+    
+    // MARK: - AVSpeechSynthesizerDelegate
+    
+    func speechSynthesizer(_ synthesizer: AVSpeechSynthesizer, didFinish utterance: AVSpeechUtterance) {
+        print("语音播放完成")
+        // 当前段落播放完成后,继续播放下一段
+        playNextChunk()
+    }
+
+    func speechSynthesizer(_ synthesizer: AVSpeechSynthesizer, didCancel utterance: AVSpeechUtterance) {
+        print("语音播放取消")
+        isPlaying = false
+    }
+    
+    func speechSynthesizer(_ synthesizer: AVSpeechSynthesizer, willSpeakRangeOfSpeechString characterRange: NSRange, utterance: AVSpeechUtterance) {
+        print("正在播放: \(characterRange)")
+    }
+}
index cbe421e..9aabe25 100644 (file)
@@ -7,7 +7,7 @@
 
 import UIKit
 import IOTBluetooth
-
+import AVFAudio
 class ViewController: BaseViewController {
 
     @IBOutlet weak var listView: UITableView!
index fe243d4..40db681 100644 (file)
@@ -72,6 +72,7 @@
                3F2AF82F2D57125D00635545 /* ChatViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3F2AF7F92D57118D00635545 /* ChatViewController.swift */; };
                3F2AF8352D573B6200635545 /* ChatCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3F2AF8342D573B5D00635545 /* ChatCell.swift */; };
                3F6A07CC2D2D2C3F00F4122A /* IBPassword.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3F6A07CB2D2D2C3F00F4122A /* IBPassword.swift */; };
+               3F8167202D5DC65B002936D5 /* IBSpeaker.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3F81671F2D5DC64B002936D5 /* IBSpeaker.swift */; };
                3F9355B72D38FF2100C54DAB /* IBPush.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3F9355B62D38FF1900C54DAB /* IBPush.swift */; };
                3FCFBFDE2D548D70003FC090 /* pumpkin.lzma in Resources */ = {isa = PBXBuildFile; fileRef = 3FCFBFDD2D548D70003FC090 /* pumpkin.lzma */; };
                3FFAE0552D3A042900325873 /* IBContact.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3FFAE0542D3A03EF00325873 /* IBContact.swift */; };
                3F2AF7F92D57118D00635545 /* ChatViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ChatViewController.swift; sourceTree = "<group>"; };
                3F2AF8342D573B5D00635545 /* ChatCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ChatCell.swift; sourceTree = "<group>"; };
                3F6A07CB2D2D2C3F00F4122A /* IBPassword.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBPassword.swift; sourceTree = "<group>"; };
+               3F81671F2D5DC64B002936D5 /* IBSpeaker.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBSpeaker.swift; sourceTree = "<group>"; };
                3F9355B62D38FF1900C54DAB /* IBPush.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBPush.swift; sourceTree = "<group>"; };
                3FCFBFDD2D548D70003FC090 /* pumpkin.lzma */ = {isa = PBXFileReference; lastKnownFileType = file; path = pumpkin.lzma; sourceTree = "<group>"; };
                3FFAE0542D3A03EF00325873 /* IBContact.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IBContact.swift; sourceTree = "<group>"; };
                                8A1DFF512B9EB4F800B735FF /* AppDelegate.swift */,
                                8A1DFF552B9EB4F800B735FF /* ViewController.swift */,
                                8A34B9262BA2AB66000F66BD /* ConnectViewController.swift */,
+                               3F81671F2D5DC64B002936D5 /* IBSpeaker.swift */,
                                8A76B6082BA84C2B0016F2AB /* AbilityViewController.swift */,
                                3F2AF7F92D57118D00635545 /* ChatViewController.swift */,
                                3F2AF8342D573B5D00635545 /* ChatCell.swift */,
                                8A76B6092BA84C2B0016F2AB /* AbilityViewController.swift in Sources */,
                                3F2AF8352D573B6200635545 /* ChatCell.swift in Sources */,
                                3F2AF82F2D57125D00635545 /* ChatViewController.swift in Sources */,
+                               3F8167202D5DC65B002936D5 /* IBSpeaker.swift in Sources */,
                                8A34B9272BA2AB66000F66BD /* ConnectViewController.swift in Sources */,
                                18EF697A2C47A86D00AA0A36 /* IBTools.swift in Sources */,
                                8A1DFF562B9EB4F800B735FF /* ViewController.swift in Sources */,
index a7a12e0..a6580cf 100644 (file)
Binary files a/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcworkspace/xcuserdata/yaozuopan.xcuserdatad/UserInterfaceState.xcuserstate and b/IOTBluetooth/IOTBluetooth/IOTBluetooth.xcworkspace/xcuserdata/yaozuopan.xcuserdatad/UserInterfaceState.xcuserstate differ
index 7b40878..3670467 100644 (file)
@@ -7,47 +7,17 @@
       <BreakpointProxy
          BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
          <BreakpointContent
-            uuid = "614B2AEC-7047-4DF3-9E22-65096DA81F63"
+            uuid = "E8730F99-9BCA-41EE-90B8-54A71862AC30"
             shouldBeEnabled = "Yes"
             ignoreCount = "0"
             continueAfterRunningActions = "No"
-            filePath = "IOTBluetooth/IBAiManager.swift"
+            filePath = "Example/IBSpeaker.swift"
             startingColumnNumber = "9223372036854775807"
             endingColumnNumber = "9223372036854775807"
-            startingLineNumber = "128"
-            endingLineNumber = "128"
-            landmarkName = "receiveAiData(sbcData:)"
+            startingLineNumber = "45"
+            endingLineNumber = "45"
+            landmarkName = "playNextChunk()"
             landmarkType = "7">
-            <Locations>
-               <Location
-                  uuid = "614B2AEC-7047-4DF3-9E22-65096DA81F63 - 3e429f5031b96ab5"
-                  shouldBeEnabled = "Yes"
-                  ignoreCount = "0"
-                  continueAfterRunningActions = "No"
-                  symbolName = "closure #1 (Swift.Optional&lt;Swift.String&gt;, Swift.Optional&lt;MixSdk.MSError&gt;) -&gt; () in IOTBluetooth.IBAiManager.receiveAiData(sbcData: Foundation.Data) -&gt; ()"
-                  moduleName = "Example.debug.dylib"
-                  usesParentBreakpointCondition = "Yes"
-                  urlString = "file:///Users/yaozuopan/Documents/code/IOTBluetooth-iOS/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAiManager.swift"
-                  startingColumnNumber = "9223372036854775807"
-                  endingColumnNumber = "9223372036854775807"
-                  startingLineNumber = "128"
-                  endingLineNumber = "128">
-               </Location>
-               <Location
-                  uuid = "614B2AEC-7047-4DF3-9E22-65096DA81F63 - 3e429f5031b96ab5"
-                  shouldBeEnabled = "Yes"
-                  ignoreCount = "0"
-                  continueAfterRunningActions = "No"
-                  symbolName = "closure #1 (Swift.Optional&lt;Swift.String&gt;, Swift.Optional&lt;MixSdk.MSError&gt;) -&gt; () in IOTBluetooth.IBAiManager.receiveAiData(sbcData: Foundation.Data) -&gt; ()"
-                  moduleName = "Example.debug.dylib"
-                  usesParentBreakpointCondition = "Yes"
-                  urlString = "file:///Users/yaozuopan/Documents/code/IOTBluetooth-iOS/IOTBluetooth/IOTBluetooth/IOTBluetooth/IBAiManager.swift"
-                  startingColumnNumber = "9223372036854775807"
-                  endingColumnNumber = "9223372036854775807"
-                  startingLineNumber = "128"
-                  endingLineNumber = "128">
-               </Location>
-            </Locations>
          </BreakpointContent>
       </BreakpointProxy>
    </Breakpoints>
index 9f0e16b..2c3417a 100644 (file)
@@ -18,12 +18,26 @@ public class IBAiManager{
     public var productKey:String = ""
     /// chatGptKey
     public var chatGptKey:String = ""
+    /// 使用大模型
+    public var useMode:((_ result:MSPlatform) -> Void)?
+    /// 使用大模型
+    public var aiResponse:((_ result:IBAiResponse) -> Void)?
     
-    public var aiResponse:((_ response:IBAiResponse) -> Void)?
+    var chatModeMap:[Int:MSPlatform] = [0:.yiyan,
+                                        1:.chatGPT,
+                                        2:.kimi,
+                                        3:.doubao,
+                                        4:.aliyun,
+                                        5:.xunfei,
+    ]
         
     var responseId = ""
     var reply = ""
     
+    var isLogin:Bool{
+        return MixSdk.shared.auth.authorized
+    }
+    
     
     init(){
         MixSdk.shared.isDebug = true
@@ -31,12 +45,17 @@ public class IBAiManager{
     }
     
     func aiValid(_ data:Data){
+        if !isLogin{
+            Logger.log("ai未登录!!!")
+            login()
+        }
+        
         let result = IBGeneralParser.dataPacket(data)
         let code = result.int
-        let desc = ["文心一言","ChatGPT","KIMI","豆包","通义千问","讯飞星火"]
-        Logger.log("询问模型是否可用:",code >= desc.count ? "未知": desc[code])
+        let platform = chatModeMap[code] ?? .doubao
+        useMode?(platform)
         let model = IBAiValid()
-        model.isValid = true
+        model.isValid = isLogin
         if code == 1 {
             model.key = chatGptKey
         }
@@ -46,13 +65,10 @@ public class IBAiManager{
             .response { result in
                 
             }
-
     }
     func aiRequest(_ data:Data){
         let result = IBGeneralParser.dataPacket(data)
         let code = result.int
-        let desc =  ["文心一言","ChatGPT","KIMI","豆包","通义千问","讯飞星火"]
-        Logger.log("使用模型:",code >= desc.count ? "未知": desc[code])
         IBSender()
             .ability(IBAbility.aiReady)
             .parameters([.value(1)])
@@ -61,13 +77,9 @@ public class IBAiManager{
             }
         
 
-        var platform = MSPlatform.doubao
+        let platform = chatModeMap[code] ?? .doubao
         var key = ""
-        if code == 0 {
-            platform = .yiyan
-        }
-        else if code == 1 {
-            platform = .chatGPT
+        if code == 1 {
             key = chatGptKey
             if chatGptKey.isEmpty {
                 Logger.log("请先设置chatGpt Key!")
@@ -75,19 +87,9 @@ public class IBAiManager{
 //            let gptModel = "gpt-4-turbo"
 //            MixSdk.shared.chatGpt.changeModel(model:gptModel )
         }
-        else if code == 2 {
-            platform = .kimi
-        }
-        else if code == 3 {
-            platform = .doubao
-        }
-        else if code == 4 {
-            platform = .aliyun
-        }
-        else if code == 5 {
-            platform = .xunfei
-        }
+        Logger.log("使用模型:",platform.title)
         MixSdk.shared.setPlatform(platform,key: key)
+        useMode?(platform)
     }
     func fectchAiAudio(){
         IBSender()
@@ -187,9 +189,13 @@ extension IBAiManager{
     }
 }
 
-
-
 extension IBAiManager{
+    func login(){
+        let mac = IBBluetooth.shared.currentConnected.macAddress.split(separator: ":").joined().uppercased()
+        login(deviceId:mac ) { token, error in
+            
+        }
+    }
     /// 登录
     /// - Parameters:
     ///   - deviceId: 设备ID
index a326f2a..0e6ef0a 100644 (file)
@@ -5,74 +5,65 @@
 //  Created by incar on 2024/7/15.
 //
 
-import Foundation
 import CoreBluetooth
-
+import Foundation
 
 @objc protocol IBReceiveManagerDelegate {
-    func receiveManagerDidReceiveFullData(characteristic: CBCharacteristic,_ data:Data)
+    func receiveManagerDidReceiveFullData(
+        characteristic: CBCharacteristic, _ data: Data)
 }
 
-class IBReceiveManager{
-    var delegate:IBReceiveManagerDelegate?
+class IBReceiveManager {
+    var delegate: IBReceiveManagerDelegate?
     static let shared = IBReceiveManager()
-    
+
     var headData = Data()
     var lastData = Data()
     var totalData = Data()
-    
-    
-    func receice(characteristic: CBCharacteristic){
-        
-        
+
+    func receice(characteristic: CBCharacteristic) {
+
         guard let data = characteristic.value else { return }
-        if(data.count == 2 && data.int == 0){
-//            Logger.log("收到0000指令异常")
+        if data.count == 2 && data.int == 0 {
+            //            Logger.log("收到0000指令异常")
             return
         }
-        
-        if data.count >= 18,data[0] == 0x72{
+
+        if data.count >= 18, data[0] == 0x72 {
             let mark = characteristic.isNotifying ? "Notify Read" : "Read"
             let uuid = characteristic.uuid.uuidString
             let pkgTotal = data[3...6].int
             let dataTotal = data[7...10].int
             let pkgIndex = data[11...14].int
             let pkgLen = data[15...16].int
-            
-            Logger.log(mark, uuid, "->", "pkgTotal = \(pkgTotal),dataTotal = \(dataTotal),pkgIndex = \(pkgIndex),pkgLen = \(pkgLen)",data.joined(" "))
-            
-//            if data[1] == 0x01,data[2] == 0x34{
-//                //ai语音
-                if pkgIndex == 1{
-                    headData = data.prefix(17)
-                    lastData = data.suffix(1)
-                }
-                IBBluetooth.shared.deinitTimer()
-                IBBluetooth.shared.startTimer()
-                totalData = totalData + data.suffix(from: 17).prefix(pkgLen)
-                if pkgTotal == pkgIndex{
-                    Logger.log("total = \(dataTotal),receive = \(totalData.count)")
-                    let fullData = headData + totalData + lastData
-                    didGetFullData(characteristic: characteristic, data: fullData)
-                }
-//            }
-//            else{
-//                didGetFullData(characteristic: characteristic, data: data)
-//            }
-        }
-        else{
-            Logger.log( data.joined(" "))
+
+            Logger.log(
+                mark, uuid, "->",
+                "pkgTotal = \(pkgTotal),dataTotal = \(dataTotal),pkgIndex = \(pkgIndex),pkgLen = \(pkgLen)",
+                data.joined(" "))
+            if pkgIndex == 1 {
+                headData = data.prefix(17)
+                lastData = data.suffix(1)
+            }
+            totalData = totalData + data.suffix(from: 17).prefix(pkgLen)
+            if pkgTotal == pkgIndex {
+                Logger.log("total = \(dataTotal),receive = \(totalData.count)")
+                let fullData = headData + totalData + lastData
+                didGetFullData(characteristic: characteristic, data: fullData)
+            }
+        } else {
+            Logger.log(data.joined(" "))
             didGetFullData(characteristic: characteristic, data: data)
         }
     }
-    
-    func didGetFullData(characteristic: CBCharacteristic,data:Data){
-//        Logger.log( data.joined(" "))
-        
-        delegate?.receiveManagerDidReceiveFullData(characteristic: characteristic, data)
+
+    func didGetFullData(characteristic: CBCharacteristic, data: Data) {
+        //        Logger.log( data.joined(" "))
+        delegate?.receiveManagerDidReceiveFullData(
+            characteristic: characteristic, data)
         totalData = Data()
-        
-        if characteristic.uuid.uuidString == readCharacteristicUUID  {
+
+        if characteristic.uuid.uuidString == readCharacteristicUUID {
             let info = IBWatchInfo(data)
             IBBluetooth.shared.currentConnected.battery = info.battery
             IBBluetooth.shared.currentConnected.macAddress = info.macAddress
@@ -80,15 +71,17 @@ class IBReceiveManager{
             IBBluetooth.shared.currentConnected.customerID = info.customerID
             sendDeviceInfo()
         }
-        
+
         if IBNotify.handle(data) {
-//            Logger.log("通知消息")
+            Logger.log("通知消息")
             return
         }
     }
-    
-    func sendDeviceInfo(){
-        let mac = UserDefaults.standard.object(forKey: "IOTBletooth.mac") as? [Int] ?? []
+
+    func sendDeviceInfo() {
+        let mac =
+            UserDefaults.standard.object(forKey: "IOTBletooth.mac") as? [Int]
+            ?? []
         let model = IBPhoneInfo()
         model.mac = mac
         IBSender()
@@ -96,23 +89,21 @@ class IBReceiveManager{
             .parameters([.sendPhone(model)])
             .response { result in
                 Logger.log(result)
-                if result.code != .success{
+                if result.code != .success {
                     //通知连接失败
                     IBManager.completeHandler?(false)
                     IBManager.completeHandler = nil
                     return
                 }
-                guard let value = result.value as? Int else {return}
+                guard let value = result.value as? Int else { return }
                 if value == 2 {
                     //通知连接成功
                     IBManager.completeHandler?(true)
                     IBManager.completeHandler = nil
-                }
-                else if value == 1{
+                } else if value == 1 {
                     //等待手表同意连接
                     Logger.log("等待手表同意连接")
-                }
-                else if value == 3{
+                } else if value == 3 {
                     //手表已与其他手机绑定
                     IBManager.completeHandler?(false)
                     IBManager.completeHandler = nil
@@ -120,4 +111,3 @@ class IBReceiveManager{
             }
     }
 }
-
index d498e98..dd7ec95 100644 (file)
@@ -14,12 +14,31 @@ public typealias IBCompletionHandler = (_ result: IBResponse) -> Void
 public class IBSender {
     public init() {
         Self.all.append(self)
+        startTimer()
     }
     
     var ability: IBAbility!
     var parameters: [IBParameter] = []
     var completion: IBCompletionHandler!
     
+    var timer: Timer?
+    func startTimer() {
+        deinitTimer()
+        
+        self.timer = Timer.scheduledTimer(withTimeInterval: 10.0, repeats: false, block: { [unowned self] _ in
+            deinitTimer()
+            self.completion?(.response.code(.timeout))
+            self.remove()
+        })
+    }
+    
+    func deinitTimer() {
+        guard let _ = self.timer else { return }
+        self.timer?.invalidate()
+        self.timer = nil
+        Logger.log("销毁定时器")
+    }
+    
     var dataPacket: [[UInt8]] {
         var totalData: [UInt8] = []
         if isValue(ability.checker) {
@@ -101,7 +120,7 @@ public class IBSender {
     }
     
     deinit {
-//        Logger.log("deinit IBSender")
+        Logger.log("deinit IBSender")
     }
 }
 
@@ -135,6 +154,16 @@ extension IBSender {
     
     /// 从缓存实例集合中移除该实例
     func remove() {
+        deinitTimer()
         Self.all.removeAll { $0 === self }
     }
+    
+    static func answer(_ data: Data) -> IBSender? {
+        for item in Self.all {
+            if item.isAnswer(data) {
+                return item
+            }
+        }
+        return nil
+    }
 }
index 0fcd66f..de72d12 100644 (file)
@@ -78,8 +78,8 @@ class IBBluetooth: NSObject {
     
     /// 当前连接设备
     var currentConnected: IBPeripheral!
-    /// 最后消息发送实例
-    private weak var lastSender: IBSender?
+//    /// 最后消息发送实例
+//    private weak var lastSender: IBSender?
     
     /// 文件发送实例
     internal weak var fileSender: IBFileSender?
@@ -137,20 +137,6 @@ class IBBluetooth: NSObject {
 //            Logger.log("手机未连上蓝牙设备!")
 //            return
 //        }
-        
-        if let _ = lastSender {
-            sender.completion(.response.code(.failure).message("有命令正在执行中..."))
-            sender.remove()
-            Logger.log("有命令正在执行中...")
-            if Self.timer == nil{
-                startTimer()
-            }
-            return
-        }
-        
-        startTimer()
-        lastSender = sender
-        
         for dataPacket in sender.dataPacket {
 //            Thread.sleep(forTimeInterval:0.02)
             
@@ -226,13 +212,8 @@ extension IBBluetooth: CBCentralManagerDelegate {
 //        IBNotify.post(.connectedDeviceDidChange)
         Logger.log("已连接", currentConnected.name)
         IBNotify.post(.connectStateDidChange, object: 1)
-        
-        IBAiManager.shared.login(deviceId: "28110687C456") { token, error in
-            
-        }
-//        IBAiManager.shared.login(deviceId: currentConnected.macAddress) { token, error in
-//            
-//        }
+
+        IBAiManager.shared.login()
     }
     
     func centralManager(_ central: CBCentralManager, didFailToConnect peripheral: CBPeripheral, error: Error?) {
@@ -246,12 +227,6 @@ extension IBBluetooth: CBCentralManagerDelegate {
         Logger.log("断开连接")
         
         deinitTimer()
-        if let sender = lastSender{
-            lastSender = nil
-            sender.completion?(.response.code(.failure))
-            sender.remove()
-        }
-        
         self.fileSender?.lastData?.fileWriteHander?(.response.code(.failure).message("蓝牙设备断开连接"))
         
         IBManager.completeHandler?(false)
@@ -328,12 +303,12 @@ extension IBBluetooth: CBPeripheralDelegate {
         else{
             Logger.log(characteristic.uuid.uuidString, "write success")
         }
-        if let sender = lastSender,sender.ability.type == .ai{
-            lastSender = nil
-            sender.completion?(.response.code(.success))
-            sender.remove()
-            return
-        }
+//        if let sender = lastSender,sender.ability.type == .ai{
+//            lastSender = nil
+//            sender.completion?(.response.code(.success))
+//            sender.remove()
+//            return
+//        }
         if let hander = self.fileSender?.lastData?.fileWriteHander{
             hander(error == nil ? .response.code(.success):.response.code(.failure))
         }
@@ -342,9 +317,7 @@ extension IBBluetooth: CBPeripheralDelegate {
 
 extension IBBluetooth:IBReceiveManagerDelegate {
     func receiveManagerDidReceiveFullData(characteristic: CBCharacteristic,_ data: Data) {
-        if let sender = lastSender,sender.isAnswer(data) == true {
-            deinitTimer()
-            lastSender = nil
+        if let sender = IBSender.answer(data) {
             sender.completion?(sender.parse(data))
             sender.remove()
             return
@@ -360,23 +333,17 @@ extension IBBluetooth:IBReceiveManagerDelegate {
 
 extension IBBluetooth {
     static var timer: Timer?
-    func startTimer() {
+    private func startTimer() {
         deinitTimer()
         
         Self.timer = Timer.scheduledTimer(withTimeInterval: 10.0, repeats: false, block: { [unowned self] _ in
             deinitTimer()
-            if let sender = lastSender{
-                lastSender = nil
-                sender.completion?(.response.code(.timeout))
-                sender.remove()
-            }
-
             self.fileSender?.lastData?.fileWriteHander?(.response.code(.timeout))
         })
 //        Logger.log("创建定时器")
     }
     
-    func deinitTimer() {
+    private func deinitTimer() {
         guard let _ = Self.timer else { return }
         Self.timer?.invalidate()
         Self.timer = nil