iOS開發-藍牙之mutipeerConnectivity

mutipeerConnectivity簡介

  1. iOS 7引入的一個全新框架
  2. 多點連接
    3.替代GameKit框架
    4.多用于文件的傳輸

* iOS設備不聯網也能跟附近的人聊天

* FireChat
* See You Around
* 以上近場聊天App都是基于mutipeerConnectivity框架

* 搜索和傳輸的方式

* 雙方WIFI和藍牙都沒有打開:無法實現
* 雙方都開啟藍牙:通過藍牙發現和傳輸
* 雙方都開啟WIFI:通過WIFI Direct發現和傳輸,速度接近AirDrop
* 雙方同時開啟了WIFI和藍牙:模擬AirDrop,通過低功耗藍牙技術掃描發現握手,然后通過WIFI Direct傳輸 

同樣以發送圖片為例,簡單介紹GameKit的使用。

連接設備

  • 創建MCSession對象用于存放當前連接的會話
// 創建MCSession對象
// initWithPeer:設備的ID
// 用于存放當前的連接的會話
self.mc_Session = [ [MCSession alloc]initWithPeer:[[MCPeerID alloc] initWithDisplayName:[UIDevice currentDevice].name]];
  • 開啟廣播對象,通知正在搜索的設備他們是可用的
/**
 *   只要開啟了可被搜索的廣播,那么連接藍牙按鈕就不可點
 */
- (IBAction)foundConnect:(id)sender {
    UISwitch *switchBtn = (UISwitch *)sender;
    if (switchBtn.isOn) {
        // 廣播對象,告訴其它的設備他們是可用的
        if (self.advertiserAssistant == nil) {
            // 創建廣播對象
            //  initWithServiceType: 廣播類型的標示(因為廣播可能比較多,所以最好每個廣播綁定一個唯一標示)
            //  session:當前會話
            //  discoveryInfo: 廣播信息
            self.advertiserAssistant = [[MCAdvertiserAssistant alloc] initWithServiceType:SERVICE_TYPE discoveryInfo:nil session:self.mc_Session];
        }
        // 開啟廣播
        [self.advertiserAssistant start];
        self.connectBT.enabled = NO;
    }else{
        self.connectBT.enabled = YES;
    }
    
}
  • 開始搜索藍牙設備
- (IBAction)connectBlueTooth {
    // 創建搜索藍牙設備控制器
    MCBrowserViewController *mbVC = [[MCBrowserViewController alloc]initWithServiceType:SERVICE_TYPE session:self.mc_Session];
    // 設置控制器代理
    mbVC.delegate = self;
    // 跳轉到搜索控制器
    [self presentViewController:mbVC animated:YES completion:nil];
}

選擇數據

- (IBAction)selectImage {
    // 1. 創建圖片選擇器
    UIImagePickerController *imgPicker = [[UIImagePickerController alloc]init];
    // 2. 判斷圖片選擇器是否可用
    if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeSavedPhotosAlbum]) {
        // 選擇器打開的類型
        imgPicker.sourceType = UIImagePickerControllerSourceTypeSavedPhotosAlbum;
        // 設置代理
        imgPicker.delegate = self;
        // 打開圖片選擇器
        [self presentViewController:imgPicker animated:YES completion:nil];
    }
}
  • 圖片選擇器代理中獲取數據
// 選擇完畢調用
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary<NSString *,id> *)info
{
//    NSLog(@"info == %@",info);
    // 設置顯示圖片
    self.showImage.image = info[UIImagePickerControllerOriginalImage];
    // 隱藏圖片顯示器
    [picker dismissViewControllerAnimated:YES completion:nil];
}
  • 在搜索控制器的連接完成的代理方法中隱藏搜索控制器
/**
 *  連接完成
 *
 *  @param browserViewController 搜索控制器
 */
- (void)browserViewControllerDidFinish:(MCBrowserViewController *)browserViewController
{
    [browserViewController dismissViewControllerAnimated:YES completion:nil];
    NSLog(@"%s %d",__func__,__LINE__);
}

發送數據

  • 實現搜索控制器的代理方法,獲取連接上的設備ID
#pragma mark - MCBrowserViewControllerDelegate
/**
 *  連接成功
 *
 *  @param browserViewController 搜索控制器
 *  @param peerID                連接上的設備ID
 *  @param info                  連接的信息
 *
 *  @return                      YES : 只發送連接上的用戶
 */
- (BOOL)browserViewController:(MCBrowserViewController *)browserViewController
      shouldPresentNearbyPeer:(MCPeerID *)peerID
            withDiscoveryInfo:(nullable NSDictionary<NSString *, NSString *> *)info
{
    self.peerID = peerID;
    NSLog(@"info == %@   peer = %@",info, peerID);
    return YES;
}
  • 將圖片發送給連接上的ID
- (IBAction)sendImage {
    // 獲取圖片
    UIImage *image = self.showImage.image;
    // 將圖片轉換成NSData類型
    NSData *data = UIImagePNGRepresentation(image);
    /**
     *  發送數據
     *  toPeers : 發給的設備ID的數組
     *  withMode: 發送模式,是否是安全模式
     */
    if (self.peerID != nil) {
        [self.mc_Session sendData:data toPeers:@[self.peerID] withMode:MCSessionSendDataUnreliable error:nil];
    }
}

接收數據

  • 實現MCSession的代理方法接受數據
- (void)session:(MCSession *)session didReceiveData:(NSData *)data fromPeer:(MCPeerID *)peerID
{
    NSLog(@"%s %d",__func__,__LINE__);
    NSLog(@"data = %@ , peer = %@",data,peerID);
}

顯示數據

  • 在MCSeesion代理方法中設置獲取過來的數據
// 接收的數據
- (void)session:(MCSession *)session didReceiveData:(NSData *)data fromPeer:(MCPeerID *)peerID
{
    NSLog(@"%s %d",__func__,__LINE__);
//    NSLog(@"data = %@ , peer = %@",data,peerID);
    UIImage *image = [[UIImage alloc]initWithData:data];
    if(image != nil){
        // 設置數據
        dispatch_async(dispatch_get_main_queue(), ^{
            self.showImage.image = image;
        });
    }
}
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容

  • iOS中提供了4個框架用于實現藍牙連接 GameKit.framework(用法簡單)-只能用于iOS設備之間的同...
    Hyman0819閱讀 1,594評論 0 0
  • 藍牙 注:本文翻譯自https://developer.android.com/guide/topics/conn...
    RxCode閱讀 8,829評論 11 99
  • iOS開發 藍牙相關 最近看了幾個與藍牙相關的框架,這里分享給大家。下面提到的三個框架,大家可以看一下,其實涉...
    過橋的螞蟻閱讀 449評論 0 2
  • 一 三三最近發現,真正很苦悶的時候找不到一個可以傾訴的朋友。 三三最近和關系最好的那個舍友冷戰了,原因是舍友直接把...
    hellokey閱讀 854評論 1 6
  • “像我這種人,在古代是不會成大器的”說罷,蕭兮低頭凝眸,懷中,梓茉靜靜躺著,側耳傾聽自己心臟跳動的聲音。 “你知道...
    吳小夕閱讀 200評論 0 0