hid数据异常代理回调,需要重新关闭开启usb监听
authorliangzhenying <867174124@qq.com>
Thu, 6 Jun 2024 09:58:50 +0000 (17:58 +0800)
committerliangzhenying <867174124@qq.com>
Thu, 6 Jun 2024 09:58:50 +0000 (17:58 +0800)
Document/AiMouseSdk接口文档.md
MouseSdk/AiMouseSdk/AiMouseSdk/AiMouseSdk.h
MouseSdk/AiMouseSdk/AiMouseSdk/AiMouseSdk.m
MouseSdk/AiMouseSdk/AiMouseSdk/AiRecordManager.h
MouseSdk/AiMouseSdk/AiMouseSdk/AiRecordManager.m
MouseSdk/MouseSdk.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate
MouseSdk/MouseSdk/HidManager.m

index 23359c8..dd7784f 100644 (file)
@@ -17,6 +17,7 @@
 | 1.0.17 | 增加命令控制录音功能                                | 梁振营 | 2024-05-28 |\r
 | 1.0.19 | 新增连接状态回调                                    | 梁振营 | 2024-05-29 |\r
 | 1.0.21 | 鉴权逻辑优化,隐藏鉴权接口                          | 梁振营 | 2024-05-31 |\r
+| 1.0.21 | 新增设置品牌接口、USB数据异常接口回调               | 梁振营 | 2024-06-06 |\r
 \r
 \r
 \r
@@ -55,6 +56,7 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 ## SDK相关接口\r
 \r
 ```objective-c\r
+\r
 /// 单利\r
 +(AiMouse *)shared;\r
 \r
@@ -62,10 +64,18 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 /// - Parameter level: 等级\r
 - (void)setLogLevel:(AiMouseLogLevel)level;\r
 \r
+\r
+/// 断开连接\r
+- (void)didDisconnect;\r
+\r
 /// 切换连接类型\r
 /// - Parameter type: 连接类型\r
 - (void)switchConnect:(AiMouseConnectType)type;\r
 \r
+///// 开始鉴权\r
+///// - Parameter finished: 鉴权结果回调\r
+//- (void)startAuthentication:(void (^)(AiMouseAuthState state))complete;\r
+\r
 /// 传输业务数据给sdk\r
 /// - Parameter data:ai特征传过来的数据\r
 - (void)sendAiDataToSdk:(NSData *)data;\r
@@ -82,6 +92,12 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 /// - Parameter completation: 信号强度回调,如果获取成功,则value有值,否则为nil\r
 - (void)getRSSI:(void (^)(NSString *value,NSError *error))complete;\r
 \r
+/// 设置品牌名称\r
+/// - Parameters:\r
+///   - value: 品牌名称\r
+///   - finished: 设置结果回调\r
+- (void)setBrand:(NSString *)brand completation:(void (^)(BOOL isSuccess,NSError *error))finished;\r
+\r
 /// 设置CPI\r
 /// - Parameters:\r
 ///   - value: AiMouseDeviceInfo 中可以设置的值CPI_list\r
@@ -112,7 +128,6 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 ///   - finished: 设置结果回调\r
 - (void)setMouseMode:(int)mode completation:(void (^)(BOOL isSuccess,NSError *error))finished;\r
 \r
-\r
 /// 获取录音模式\r
 /// - Parameter complete: mode  0:常规模式,按按键打开关闭录音  1:命令模式,发命令打开关闭录音 。error为nil才代表获取成功\r
 - (void)getRecordMode:(void (^)(int mode,NSError *error))complete;\r
@@ -129,7 +144,6 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 /// - Parameter complete: mode 0:2.4G模式,1:蓝牙1模式,2:蓝牙2模式  。error为nil才代表获取成功\r
 - (void)getMouseModel:(void (^)(int mode,NSError *error))complete;\r
 \r
-\r
 /// 打开录音\r
 /// - finished: 执行结果回调\r
 - (void)openRecord:(void (^)(BOOL isSuccess,NSError *error))finished;\r
@@ -146,12 +160,11 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 ```objective-c\r
 @protocol AiMouseDelegate <NSObject>\r
 \r
-\r
 /// 设备连接状态\r
 /// - Parameter connected: 是否连接\r
 - (void)aiMouseConnectStateDidChange:(BOOL)connected;\r
 \r
-/// 设备鉴权结果返回\r
+/// 鉴权结果返回\r
 /// - Parameter authState: 鉴权状态\r
 - (void)aiMouseAuthenticationResult:(AiMouseAuthState)authState;\r
 \r
@@ -175,7 +188,11 @@ libz.tbd、libbz2.tbd、libiconv.tbd、liblzma5.tbd、CoreAudio.framework、Vide
 /// 输出sdk日志\r
 /// - Parameter log: 日志\r
 - (void)aiMouseAddLog:(NSString *)log;\r
+\r
+/// hid数据异常,需要重新开启监听usb设备\r
+- (void)hidDataError;\r
 @end\r
+\r
 ```\r
 \r
 \r
@@ -695,7 +712,5 @@ static uint32_t IOHIDDevGetUInt32Property(IOHIDDeviceRef inIOHIDDeviceRef, CFStr
 ## 注意事项\r
 \r
 - 设备信息数据使用的是设备信息通道,走设备信息接口;AI数据使用的是AI通道,走AI接口。\r
-- 只有鉴权成功了以后,AI相关功能才可用。authState鉴权状态,默认是Unknow。所以必须在连上蓝牙设备找到鉴权特征后,需要主动调用startAuthentication方法去鉴权。(只有鉴权成功,AI功能才可用)\r
-- SDK只封装了蓝牙相关数据处理,APP自己维护蓝牙设备的扫描连接。蓝牙设备一段时间没有任何操作的话,会自动断开连接。APP可以在检测到断开后重连。\r
-- 当切换蓝牙或者USB,需要调用switchConnect切换连接类型。\r
+- 只有鉴权成功了以后,AI相关功能才可用。\r
 \r
index f2d528b..022cf89 100644 (file)
@@ -43,7 +43,6 @@ typedef NS_ENUM(NSInteger,AiMouseAuthState) {
 
 @protocol AiMouseDelegate <NSObject>
 
-
 /// 设备连接状态
 /// - Parameter connected: 是否连接
 - (void)aiMouseConnectStateDidChange:(BOOL)connected;
@@ -72,6 +71,9 @@ typedef NS_ENUM(NSInteger,AiMouseAuthState) {
 /// 输出sdk日志
 /// - Parameter log: 日志
 - (void)aiMouseAddLog:(NSString *)log;
+
+/// hid数据异常,需要重新开启监听usb设备
+- (void)hidDataError;
 @end
 
 @interface AiMouse : NSObject
index e60f767..66decb0 100644 (file)
@@ -64,7 +64,7 @@
 }
 
 -(NSString *)version{
-    return @"1.0.27";
+    return @"1.0.29";
 }
 
 -(AiDeviceInfoManager *)deviceInfoManager{
 }
 - (void)didDisconnect{
     [self showLog:@"系统断开连接"];
+    [self stopRecord:true];
     [self.connectManager disConnected];
+    
 }
 - (void)switchConnect:(AiMouseConnectType)type{
     if(type != _connectType && self.connected){
             [subData getBytes:&cmd length:1];
 //            [self showLog:[NSString stringWithFormat:@"cmd = %X",cmdInt]];
             if(cmd == 0x31 || cmd == 0x21 || cmd == 0x25 ||cmd == 0x27){
+                self.recordManager.startCmd = subData;
                 [self startRecord];
             }
             else if(cmd == 0x32 || cmd == 0x22 || cmd == 0x26 ||cmd == 0x28){
-                [self stopRecord];
+                [self stopRecord:false];
             }
         }
         else{
 
 #pragma mark - deviceInfoManager
 -(void)sendDeviceDataToSdk:(NSData *)data{
-    [self.connectManager resetTimeOut];
     [self showLog:[NSString stringWithFormat:@"[receive][device] %@",data]];
+    if (self.connected == false) {
+        if([AiMouseTools dataToHexString:data].length < 10){
+            if (self.delegate) [self.delegate hidDataError];
+            return;
+        }
+    }
+    
+    [self.connectManager resetTimeOut];
     [self.deviceInfoManager receiveData:data];
     [self checkAuthState];
 }
             [ws sendCmdData:cmd];
             
             if(self.connectType == AiMouseConnectType_hid){
-                [ws stopRecord];
+                [ws stopRecord:false];
             }
         }
     }];
     [self.recordManager start];
 }
 
-- (void)stopRecord{
-    [self.recordManager stop];
+- (void)stopRecord:(BOOL)sendCmd{
+    if (self.recordManager.recording ) {
+        [self.recordManager stop];
+    }
+    if (sendCmd) {
+        [self sendCmdData:self.recordManager.stopCmd];
+    }
 //    [self showLog:@"结束录音"];
 }
 
index 846505f..55c44b5 100644 (file)
@@ -10,6 +10,9 @@
 NS_ASSUME_NONNULL_BEGIN
 
 @interface AiRecordManager : NSObject
+@property (nonatomic,assign)BOOL recording;
+@property (nonatomic,strong)NSData *startCmd;
+@property (nonatomic,readonly)NSData *stopCmd;
 @property (nonatomic,strong)void (^didRecordData)(NSData *data);
 
 - (void)checkPermissions;
index 03a51b3..bf8d05b 100644 (file)
 //    return manager;
 //}
 
+/// 前  第一次单击31(开始录音), 第二次单击32(结束录音) , 按下21(开始录音)抬起22(结束录音)
+/// 中  单击42, 按下25(开始录音)抬起26(结束录音)
+/// 后  单击43,按下27(开始录音)抬起28(结束录音)
+-(NSData *)stopCmd{
+
+    uint8 startCmd;
+    [self.startCmd getBytes:&startCmd length:1];
+    
+    uint8 cmd = 0x00;
+    if (startCmd== 0x31) {
+        cmd = 0x32;
+    }
+    else if (startCmd == 0x21) {
+        cmd = 0x22;
+    }
+    else if (startCmd == 0x25) {
+        cmd = 0x26;
+    }
+    else if (startCmd == 0x27) {
+        cmd = 0x28;
+    }
+    
+    NSData *data = [NSData dataWithBytes:&cmd length:1];
+    return data;
+}
+
 -(instancetype)init{
     if (self = [super init ]) {
         self.isAllowRecord = false;
@@ -44,7 +70,7 @@
     //    catch let error as NSError {
     //      print("ERROR:", error)
     //    }
-    
+    self.recording = true;
     
     self.audioEngine = [[AVAudioEngine alloc] init];
     AVAudioInputNode *input = self.audioEngine.inputNode;
 
 - (void)stop{
     [self.audioEngine stop];
+    self.recording = false;
     //    [self finishRecored:self.recordData];
 }
 
index f49d6f3..4c03716 100644 (file)
Binary files a/MouseSdk/MouseSdk.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate and b/MouseSdk/MouseSdk.xcworkspace/xcuserdata/apple.xcuserdatad/UserInterfaceState.xcuserstate differ
index 7bc3f5e..17e3f98 100644 (file)
@@ -48,7 +48,7 @@ const long productID = 0x8601;
 
 - (void)open{
     self.hidManager = IOHIDManagerCreate(kCFAllocatorDefault, kIOHIDOptionsTypeNone);
-    IOHIDManagerScheduleWithRunLoop(self.hidManager, CFRunLoopGetMain(), kCFRunLoopDefaultMode);
+    IOHIDManagerScheduleWithRunLoop(self.hidManager, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode);
     IOReturn ret = IOHIDManagerOpen(self.hidManager, 0L);
     if (ret != kIOReturnSuccess) {
         NSLog(@"打开设备失败!");
@@ -78,15 +78,9 @@ const long productID = 0x8601;
 #pragma mark - Hid CallBack
 /// 匹配到设备回调
 static void hidAppearDevice(void *inContext,IOReturn inResult,void *inSender,IOHIDDeviceRef inIOHIDDeviceRef) {
-    uint32_t vid = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDVendorIDKey));
-    uint32_t pid = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDProductIDKey));
+    [[HidManager shared] showLog:[NSString stringWithFormat:@"发现设备 %@\n ",inIOHIDDeviceRef]];
     uint32_t PrimaryUsagePage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsagePageKey));
     uint32_t PrimaryUsage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsageKey));
-    [[HidManager shared] showLog:[NSString stringWithFormat:@"vid = %u, pid = %u, PrimaryUsagePage = %u, PrimaryUsage = %u,",vid,pid,PrimaryUsagePage,PrimaryUsage]];
-    [[HidManager shared] showLog:[NSString stringWithFormat:@"发现设备 %@\n ",inIOHIDDeviceRef]];
-    
-    //    PrimaryUsagePage=1 PrimaryUsage=0,设备信息
-    //    PrimaryUsagePage=65283 PrimaryUsage=0,ai
     if(PrimaryUsagePage == 1 && PrimaryUsage == 0){
         //设备信息
         [HidManager shared].deviceInfoCha = inIOHIDDeviceRef;
@@ -100,6 +94,8 @@ static void hidAppearDevice(void *inContext,IOReturn inResult,void *inSender,IOH
         }else{
             NSLog(@"打开设备信息成功!");
         }
+        CFRetain(inIOHIDDeviceRef);
+        IOHIDDeviceScheduleWithRunLoop(inIOHIDDeviceRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode);
     }
     else if(PrimaryUsagePage == 65283 && PrimaryUsage == 0){
         //ai
@@ -113,6 +109,8 @@ static void hidAppearDevice(void *inContext,IOReturn inResult,void *inSender,IOH
         }else{
             NSLog(@"打开AI成功!");
         }
+        CFRetain(inIOHIDDeviceRef);
+        IOHIDDeviceScheduleWithRunLoop(inIOHIDDeviceRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode);
     }
 }
 
@@ -124,6 +122,7 @@ static void hidDisAppearDevice(void *inContext,IOReturn inResult,void *inSender,
 
     if(PrimaryUsagePage == 1 && PrimaryUsage == 0){
         [HidManager shared].deviceInfoCha = nil;
+        [HidManager shared].aiCha = nil;
         [[AiMouse shared] didDisconnect];
     }
 }
@@ -140,6 +139,7 @@ static void hidReceiveData(void* context, IOReturn result, void* sender, IOHIDRe
 
     if(PrimaryUsagePage == 1 && PrimaryUsage == 0){
         [[AiMouse shared] sendDeviceDataToSdk:data];
+        
     }
     else if(PrimaryUsagePage == 65283 && PrimaryUsage == 0){
         [[AiMouse shared] sendAiDataToSdk:data];
@@ -190,14 +190,17 @@ static void hidReceiveData(void* context, IOReturn result, void* sender, IOHIDRe
 //    [self showLog:log];
 }
 
+-(void)hidDataError{
+    [self close];
+    [self open];
+}
+
 // 连接状态改变
 - (void)aiMouseConnectStateDidChange:(BOOL)connected{
     [HidManager shared].connectStateCallBack(connected);
 }
 #pragma mark - public
 -(void)connectDevice{
-    //连上设备
-//    [HidManager shared].connectStateCallBack(true);
     //设置代理
     [AiMouse shared].delegate = self;
     //切换当前连接类型
@@ -214,7 +217,6 @@ static void hidReceiveData(void* context, IOReturn result, void* sender, IOHIDRe
         [self showLog:@"请先连上设备"];
         return;
     }
-//    [self showLog:[NSString stringWithFormat:@"开始发送[send] %@",data]];
     
     IOReturn ret = IOHIDDeviceSetReport(device, kIOHIDReportTypeOutput, 0, data.bytes, data.length);
     if (ret != kIOReturnSuccess) {