MultipeerConnectivity框架,近场通信的基本使用

Multipeer connectivity是一个使附近设备通过Wi-Fi网络、P2P Wi-Fi以及蓝牙个人局域网进行通信的框架。互相链接的节点可以安全地传递信息、流或是其他文件资源,而不用通过网络服务。此框架是在iOS7以后推出,旨在替代GameKit下的GKPeerPickerController通信。通过此框架我们可以直接连接同一网络下的设备,让其直接进行类似微信,qq那样的即时通讯效果。

原理

其中通讯的原理,是利用节点来进行广播服务(标示符),其他节点可以通过服务(标示符)发现广播。并对此节点进行连接。在项目中可以将广播和发现放在一起实现,这样既可以发现并连接到其他节点,同时也可以被其他节点所搜索链接。服务的命名规则为由ASCII字母、数字和“-”组成的短文本串,最多15个字符。通常,一个服务的名字应该由应用程序的名字开始,后边跟“-”和一个独特的描述符号

相关类

针对于近场通信,在Multipeer connectivity框架中我们所需要学习的类如下:

  1. MCPeerID //代表用户信息

  2.MCSession //启用和管理Multipeer连接会话中的所有人之间的沟通。 通过Sesion,给别人发送和读取数据。

  3.MCNearbyServiceBrowser //用于搜索附近的服务端,并可以对搜索到的服务端发出邀请加入某个会话中。

  4.MCNearbyServiceAdvertiser //广播服务可以接收,并处理用户请求连接的响应。但是,这个类会有回调,告知有用户要与服务端设备连接,需要自定义提示框,以及自定义连接处理。

  5.MCAdvertiserAssistant //广播服务可以接收,并处理用户请求连接的响应。没有回调,会弹出默认的提示框,并处理连接。

  6. MCBrowserViewController //用于搜索附近的用户,是基于MCNearbyServiceBrowse的封装

使用步骤

   MCPeerID,MCSession,MCNearbyServiceAdvertiser,MCNearbyServiceBrowser本文中用这四个类来实现(MCNearbyServiceAdvertiser,MCNearbyServiceBrowserx相对来说更原生态,此处通过这个两个类来编写代码更容易帮助我们理解其内部实现的过程)。

通过MCPeer来生成节点信息

通过MCNearbyServiceAdvertiser来发送广播,告诉别人这里有个节点可连接,其他节点想要发现此节点必须

通过MCNearbyServiceBrowser来搜索服务(标示符)来找到发送广播的节点,并请求连接,
当连接成功后便可以通过MCSession来进行消息的发送和读取。

代码部分

1
2
3
4
5
6
7
8
9
10
11
12
13
//需要遵循以下协议
@interface MultiPeerModule : NSObject<MCSessionDelegate,MCBrowserViewControllerDelegate>

@property(nonatomic,strong)MCPeerID *peerID; //PeerID->连接设备的标志

@property(nonatomic,strong)MCSession *mySession; //会话->用于传输数据

@property(nonatomic,strong)MCBrowserViewController *browser; //系统基于MCNearbyServiceBrowser 封装的一个Controller

@property(nonatomic,strong)MCAdvertiserAssistant *advertiser; //广播->用于向外发送服务,让Browser搜索到开了广播的设备

@end

####初始化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19

_peerID = [[MCPeerID alloc]initWithDisplayName:[UIDevice currentDevice].name];
_mySession = [[MCSession alloc]initWithPeer:_peerID];
_mySession.delegate = self;

//它是由ASCII字母、数字和“-”组成的短文本串,最多15个字符。通常,一个服务的名字应该由应用程序的名字开始,后边跟“-”和一个独特的描述符号。

_browser = [[MCBrowserViewController alloc]initWithServiceType:@"trans-stream" session:_mySession];
_browser.delegate = self;

//初始化广播
_advertiser = [[MCAdvertiserAssistant alloc]initWithServiceType:@"trans-stream" discoveryInfo:nil session:_mySession];

//这是开始广播方法,向四周发送广播
//[_advertiser start];

//同理Stop
//[_advertiser stop];

####代理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68

//连接状态更改
//无论服务端和客户端
//只要连接状态改变,都会进入这个代理
//PS:好像无法获得是服务端还是客户端变化?
-(void)session:(MCSession *)session peer:(MCPeerID *)peerID didChangeState:(MCSessionState)state{
switch (state) {
case MCSessionStateConnected:
NSLog(@"Connected With %@ Success!",peerID.displayName);

//连接成功后发送通知
//做后续逻辑

[[NSNotificationCenter defaultCenter]postNotificationName:@"SuccessConnect" object:peerID];
break;
case MCSessionStateConnecting:
NSLog(@"Connecting With %@ =================>",peerID.displayName);
break;
case MCSessionStateNotConnected:
NSLog(@"Lost Connected With %@ Bye~!",peerID.displayName);
[[NSNotificationCenter defaultCenter]postNotificationName:@"LostConnect" object:peerID];
break;
default:
NSLog(@"Unknown Error=======>");
break;
}
}




//第一个方法在节点改变状态的时候被调用,已连接或已断开。
//有三个状态: MCSessionStateConnected , MCSessionStateConnecting and MCSessionStateNotConnected。最后一个状态在节点从连接断开后依然有效。
//第二个方法在有新数据从节点过来时被调用。
//记住有三种数据可以交换:消息,流和资源。这个是消息的代理。

-(void)session:(MCSession *)session didReceiveData:(NSData *)data fromPeer:(MCPeerID *)peerID{

if (data.length>0) {
NSLog(@"收到的Data长度:%ld",data.length);
[[NSNotificationCenter defaultCenter] postNotificationName:@"didReceiveData" object:data];
}

}

-(void)session:(MCSession *)session didStartReceivingResourceWithName:(NSString *)resourceName fromPeer:(MCPeerID *)peerID withProgress:(NSProgress *)progress{

}

-(void)session:(MCSession *)session didReceiveStream:(NSInputStream *)stream withName:(NSString *)streamName fromPeer:(MCPeerID *)peerID{

}

-(void)session:(MCSession *)session didFinishReceivingResourceWithName:(NSString *)resourceName fromPeer:(MCPeerID *)peerID atURL:(NSURL *)localURL withError:(NSError *)error{

}



//选择设备系统自定义Controller

-(void)browserViewControllerDidFinish:(MCBrowserViewController *)browserViewController{
[self.browser dismissViewControllerAnimated:YES completion:nil];
}

-(void)browserViewControllerWasCancelled:(MCBrowserViewController *)browserViewController{
[self.browser dismissViewControllerAnimated:YES completion:nil];
}
以上就是 Multipeer connectivity 需要实现的代理方法

使用略

MultipeerConnectivity框架,近场通信的基本使用

https://swlfigo.github.io/posts/5a78/

Author

Sylar

Posted on

2019-04-28

Updated on

2021-11-14

Licensed under

Comments