@interface BleManager ()<CBCentralManagerDelegate,CBPeripheralDelegate>
@property(nonatomic, strong) CBCentralManager *centralManager;///蓝牙管理
-@property(nonatomic, strong) CBPeripheral *crrentPeripheral;//连接的设备
+@property(nonatomic, strong) CBPeripheral *curentPeripheral;//连接的设备
@property(nonatomic, strong) CBCharacteristic *deviceInfoCha;//设备信息特征
@property (nonatomic,strong) NSMutableData *recordData;//录音的数据
}
- (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI{
- if ([self isContainInSearchList:peripheral.name]) {
- [self connectPeripheral:peripheral];
- }
+// [self showLog:[NSString stringWithFormat:@"%@",peripheral]];
+// if ([self isContainInSearchList:peripheral.name]) {
+// [self connectPeripheral:peripheral];
+// }
}
- (void)centralManager:(CBCentralManager *)central didConnectPeripheral:(CBPeripheral *)peripheral{
// [self showLog:[NSString stringWithFormat:@"连接成功 name = %@",peripheral.name]];
- peripheral.delegate = self;
[peripheral discoverServices:nil];
- self.crrentPeripheral = peripheral;
}
-(void)centralManager:(CBCentralManager *)central didDisconnectPeripheral:(CBPeripheral *)peripheral error:(NSError *)error{
[self showLog:[NSString stringWithFormat:@"断开连接。。。%@",error.description]];
- self.connectStateCallBack(self.crrentPeripheral.name,false);
- self.crrentPeripheral = nil;
+ self.connectStateCallBack(self.curentPeripheral.name,false);
+ self.curentPeripheral = nil;
}
- (void)centralManager:(CBCentralManager *)central didFailToConnectPeripheral:(CBPeripheral *)peripheral error:(nullable NSError *)error{
[self showLog:[NSString stringWithFormat:@"连接失败。。。%@",error.description]];
- self.connectStateCallBack(self.crrentPeripheral.name,false);
- self.crrentPeripheral = nil;
+// self.connectStateCallBack(self.curentPeripheral.name,false);
+ self.curentPeripheral = nil;
}
+
#pragma mark - CBPeripheralDelegate
//发现服务
- (void)peripheral:(CBPeripheral *)peripheral didDiscoverServices:(NSError *)error {
// 发现特征
- (void)peripheral:(CBPeripheral *)peripheral didDiscoverCharacteristicsForService:(CBService *)service error:(NSError *)error {
- if([peripheral.name isEqualToString:@"VMouse"]){
- for (CBCharacteristic *characteristic in service.characteristics){
- if ([characteristic.UUID.UUIDString isEqualToString:kFrkVoiceUUID]) {
- //语音特征
- [peripheral setNotifyValue:YES forCharacteristic:characteristic];
- }
- else if ([characteristic.UUID.UUIDString isEqualToString:kFrkDeviceInfoUUID]) {
- //通知设备信息特征
- [peripheral setNotifyValue:YES forCharacteristic:characteristic];
- self.deviceInfoCha = characteristic;
+
+ for (CBCharacteristic *characteristic in service.characteristics){
+ if ([characteristic.UUID.UUIDString isEqualToString:kFrkVoiceUUID]) {
+ //语音特征
+ [peripheral setNotifyValue:YES forCharacteristic:characteristic];
+ self.productType = AiMouseProductType_frk;
+
+ dispatch_time_t delayTime = dispatch_time(DISPATCH_TIME_NOW, 1 * NSEC_PER_SEC);
+ dispatch_after(delayTime, dispatch_get_main_queue(), ^{
[self showLog:[NSString stringWithFormat:@"连接成功 = %@",peripheral.name]];
- self.connectStateCallBack(self.crrentPeripheral.name,true);
- }
+ self.connectStateCallBack(self.curentPeripheral.name,true);
+ });
}
+ else if ([characteristic.UUID.UUIDString isEqualToString:kFrkDeviceInfoUUID]) {
+ //通知设备信息特征
+ [peripheral setNotifyValue:YES forCharacteristic:characteristic];
+ self.deviceInfoCha = characteristic;
+ }
}
- else{
- for (CBCharacteristic *characteristic in service.characteristics){
- if ([characteristic.UUID.UUIDString isEqualToString:kTlwVoiceUUID]) {
- //语音特征
- [peripheral setNotifyValue:YES forCharacteristic:characteristic];
- }
- else if ([characteristic.UUID.UUIDString isEqualToString:kTlwNotifyDeviceInfoUUID]) {
- //通知设备信息特征
- [peripheral setNotifyValue:YES forCharacteristic:characteristic];
- }
- else if ([characteristic.UUID.UUIDString isEqualToString:kTlwSetDeviceInfoUUID]) {
- //设备信息特征
- self.deviceInfoCha = characteristic;
+
+ for (CBCharacteristic *characteristic in service.characteristics){
+ if ([characteristic.UUID.UUIDString isEqualToString:kTlwVoiceUUID]) {
+ //语音特征
+ [peripheral setNotifyValue:YES forCharacteristic:characteristic];
+ self.productType = AiMouseProductType_tlw;
+
+ // 使用dispatch_after来延迟执行任务
+ dispatch_time_t delayTime = dispatch_time(DISPATCH_TIME_NOW, 1 * NSEC_PER_SEC);
+ dispatch_after(delayTime, dispatch_get_main_queue(), ^{
[self showLog:[NSString stringWithFormat:@"连接成功 = %@",peripheral.name]];
- self.connectStateCallBack(self.crrentPeripheral.name,true);
- }
+ self.connectStateCallBack(self.curentPeripheral.name,true);
+ });
+
+ }
+ else if ([characteristic.UUID.UUIDString isEqualToString:kTlwNotifyDeviceInfoUUID]) {
+ //通知设备信息特征
+ [peripheral setNotifyValue:YES forCharacteristic:characteristic];
+ }
+ else if ([characteristic.UUID.UUIDString isEqualToString:kTlwSetDeviceInfoUUID]) {
+ //设备信息特征
+ self.deviceInfoCha = characteristic;
}
}
}
//收到蓝牙数据
- (void)peripheral:(CBPeripheral *)peripheral didUpdateValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error {
- if ([peripheral.name isEqualToString:@"VMouse"]) {
+ if (self.productType == AiMouseProductType_tlw) {
NSData *data = characteristic.value;
- if([characteristic.UUID.UUIDString isEqualToString:kFrkVoiceUUID]){
+ if([characteristic.UUID.UUIDString isEqualToString:kTlwVoiceUUID]){
self.receiveVoiceDataCallBack(data);
}
- else if([characteristic.UUID.UUIDString isEqualToString:kFrkDeviceInfoUUID]){
+ else if([characteristic.UUID.UUIDString isEqualToString:kTlwNotifyDeviceInfoUUID]){
self.receiveInfoDataCallBack(data);
}
}
else{
NSData *data = characteristic.value;
- if([characteristic.UUID.UUIDString isEqualToString:kTlwVoiceUUID]){
- //AI数据
+ if([characteristic.UUID.UUIDString isEqualToString:kFrkVoiceUUID]){
self.receiveVoiceDataCallBack(data);
}
- else if([characteristic.UUID.UUIDString isEqualToString:kTlwNotifyDeviceInfoUUID]){
- //设备信息数据
+ else if([characteristic.UUID.UUIDString isEqualToString:kFrkDeviceInfoUUID]){
self.receiveInfoDataCallBack(data);
}
}
}
+- (void)checkRightDevice{
+ for (CBService *s in self.curentPeripheral.services) {
+ for (CBCharacteristic *c in s.characteristics) {
+ if([c.UUID.UUIDString isEqualToString:kFrkVoiceUUID] ||[c.UUID.UUIDString isEqualToString:kTlwVoiceUUID] ){
+ return;
+ }
+ }
+ }
+ [self.centralManager cancelPeripheralConnection:self.curentPeripheral];
+}
#pragma mark - public
- (void)startScanWithName:(NSArray *)bleList{
- self.bleList = bleList;
- //如果是已连接或者正在连接,不需要在链接了
-// if (self.crrentPeripheral != nil ) {
-// if ([self.crrentPeripheral.name isEqualToString:bleName]) {
-// if (self.crrentPeripheral.state == CBPeripheralStateConnected || self.crrentPeripheral.state == CBPeripheralStateConnecting) {
-// return;
-// }
-// }
-// else {
-// [self.centralManager cancelPeripheralConnection:self.crrentPeripheral];
-// }
-// }
-//
-// self.bleName = bleName;
-
NSArray<CBPeripheral *> *devices = [self.centralManager retrieveConnectedPeripheralsWithServices:@[[CBUUID UUIDWithString:kFrkServiceUUID],[CBUUID UUIDWithString:kTlwServiceUUID]]];
- if (devices.count > 0 && [self isContainInSearchList: devices[0].name]) {
+ [self showLog:[NSString stringWithFormat:@"匹配过的设备%@",devices]];
+
+ if (devices.count > 0) {
[self showLog:[NSString stringWithFormat:@"匹配过的设备%@",devices[0].name]];
[self connectPeripheral:devices[0]];
}
}
}
-- (BOOL)isContainInSearchList:(NSString *)name{
- for (NSString *item in self.bleList) {
- if ([item isEqualToString:name]) {
- return true;
- }
- }
- return false;
-}
-
- (void)stopScan{
if (self.centralManager.isScanning) {
/// 连接设备
- (void)connectPeripheral:(CBPeripheral *)peripheral{
- if(self.crrentPeripheral != nil && self.crrentPeripheral.state == CBPeripheralStateConnected){
+ if(self.curentPeripheral != nil && self.curentPeripheral.state == CBPeripheralStateConnected){
[self showLog:@"当前蓝牙已处理连接状态,不会重连!!!"];
return;
}
[self showLog:[NSString stringWithFormat:@"连接设备 %@",peripheral.description]];
- self.crrentPeripheral = peripheral;
+ self.curentPeripheral = peripheral;
+ self.curentPeripheral.delegate = self;
[self.centralManager connectPeripheral:peripheral options:@{CBConnectPeripheralOptionNotifyOnConnectionKey : [NSNumber numberWithBool:YES]}];
+ [self performSelector:@selector(checkRightDevice) withObject:nil afterDelay:1];
}
-(void)writeToDevice:(NSData *)data{
- if (self.crrentPeripheral ==nil) {
+ if (self.curentPeripheral ==nil) {
return;
}
if (self.deviceInfoCha ==nil) {
}
[self showLog:[NSString stringWithFormat:@"向蓝牙设备发送数据 %@",data]];
- if ([self.crrentPeripheral.name isEqualToString:@"VMouse"]) {
- [self.crrentPeripheral writeValue:data forCharacteristic:self.deviceInfoCha type:CBCharacteristicWriteWithoutResponse];
+ if (self.productType == AiMouseProductType_tlw) {
+ [self.curentPeripheral writeValue:data forCharacteristic:self.deviceInfoCha type:CBCharacteristicWriteWithResponse];
}
else{
- [self.crrentPeripheral writeValue:data forCharacteristic:self.deviceInfoCha type:CBCharacteristicWriteWithResponse];
+ [self.curentPeripheral writeValue:data forCharacteristic:self.deviceInfoCha type:CBCharacteristicWriteWithoutResponse];
}
}
[[HidManager shared] showLog:(@"当前处于连接状态,对监听到有USB 插入 的事件不做处理")];
return;
}
- if([HidManager shared].productType == AiMouseProductType_tlw){
+ uint32_t pid = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDProductIDKey));
+ uint32_t vid = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDVendorIDKey));
+// uint32_t PrimaryUsage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsageKey));
+// uint32_t PrimaryUsagePage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsagePageKey));
+ [[HidManager shared] showLog:([NSString stringWithFormat:@"发现设备 %@",inIOHIDDeviceRef])];
+ [[HidManager shared] showLog:([NSString stringWithFormat:@"pid = %d,vid = %d",pid,vid])];
+// return;
+ if(vid == 0x10D6 && pid == 0x8601){
+ [HidManager shared].productType = AiMouseProductType_tlw;
[HidManager shared].deviceInfoCha = inIOHIDDeviceRef;
- [[HidManager shared] showLog:([NSString stringWithFormat:@"发现设备 %@",inIOHIDDeviceRef])];
-
//注册消息回调
unsigned char InputBuffer[64];
IOHIDDeviceRegisterInputReportCallback(inIOHIDDeviceRef, InputBuffer, sizeof(InputBuffer), &hidReceiveData, NULL);
CFRetain([HidManager shared].deviceInfoCha);
IOHIDDeviceScheduleWithRunLoop([HidManager shared].deviceInfoCha, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode);
}
- else{
+ else if(vid == 0x6675 && pid == 0x8601){
+ [HidManager shared].productType = AiMouseProductType_frk;
uint32_t PrimaryUsagePage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsagePageKey));
uint32_t PrimaryUsage = IOHIDDevGetUInt32Property(inIOHIDDeviceRef, CFSTR(kIOHIDPrimaryUsageKey));
NSString *tmpPrimaryUsagePage = [NSString stringWithFormat:@"%u",PrimaryUsagePage];
static void hidReceiveData(void* context, IOReturn result, void* sender, IOHIDReportType type, uint32_t reportID, uint8_t *report,CFIndex reportLength){
+ NSData *data = [[NSData alloc] initWithBytes:report length:reportLength];
+ [[HidManager shared] showLog:[NSString stringWithFormat:@"receive data = %@",data]];
if([HidManager shared].productType == AiMouseProductType_tlw){
if (report[0] == 0x01 || report[0] == 0x02) {
//鼠标键盘活动事件
[self showLog:(@"打开hid成功!")];
}
//设置匹配设备
- ////供应商id
- const long vendorID = 0x6675;
- //产品id
- const long productID = 0x8601;
+// ////供应商id
+// const long vendorID = 0x6675;
+// //产品id
+// const long productID = 0x8601;
// //供应商id
// const long vendorID = 0x10D6;
// //产品id
// const long productID = 0xB008;
NSMutableDictionary* dict= [NSMutableDictionary dictionary];
- [dict setValue:[NSNumber numberWithLong:productID] forKey:[NSString stringWithCString:kIOHIDProductIDKey encoding:NSUTF8StringEncoding]];
- [dict setValue:[NSNumber numberWithLong:vendorID] forKey:[NSString stringWithCString:kIOHIDVendorIDKey encoding:NSUTF8StringEncoding]];
+// [dict setValue:[NSNumber numberWithLong:productID] forKey:[NSString stringWithCString:kIOHIDProductIDKey encoding:NSUTF8StringEncoding]];
+// [dict setValue:[NSNumber numberWithLong:vendorID] forKey:[NSString stringWithCString:kIOHIDVendorIDKey encoding:NSUTF8StringEncoding]];
IOHIDManagerSetDeviceMatching(self.hidManager, (__bridge CFMutableDictionaryRef)dict);
//设置匹配到设备回调
IOHIDManagerRegisterDeviceMatchingCallback(self.hidManager, &hidAppearDevice, NULL);