一: 介紹
近幾年,智慧裝置越來越火,這些智慧裝置中,有很大一部分是通過手機來控制硬體裝置,來達到預期的效果,這中間少不了要使用到藍芽功能,通過藍芽來通訊來控制裝置。 除了藍芽控制裝置之外,還可以通過Wi-Fi來控制裝置,iOS11前只能跳轉到系統設定介面手動連線Wi-Fi,iOS11之後蘋果提供 NEHotspotConfiguration ,NEHotspotConfigurationManager 類直連周邊Wi-Fi。
這篇文章主要和大家分享iOS11之後在App內自動連線Wi-Fi,Wi-Fi資訊獲取,Wi-Fi檢測等功能。
二:許可權配置
蘋果提供的 NEHotspotConfiguration ,NEHotspotConfigurationManager需要在開發者賬號和專案中做如下配置。
1. 開啟App IDs Hotspot 許可權
登陸https://developer.apple.com,如果App ID已經存在,只需增加Hotspot 許可權,如果App ID不存在,新建一個並新增Hotspot 許可權。
配置的App ID需要與專案中的Bundle ID一致。
2. 新增依賴庫NetworkExtension.framework
在專案中Build Phases - Link Binary With Libraries中新增 依賴庫NetworkExtension.framework
3. 開啟Capabilities裡的Hotspot Configuration
Xcode - Capabilities - Hostpot Configuration 開關開啟
三:NEHotspotConfiguration庫分析
在NEHotspotConfiguration庫中有3個屬性,分別是:
- SSID:要連的wifi名稱
- joinOnce:預設是NO,會保留配置過的wifi,YES即是不儲存
- lifeTimeInDays: 配置的生命週期
原始碼如下:
/*!
* @property SSID
* @discussion SSID of the Wi-Fi Network.
*/
@property (readonly) NSString * SSID API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @property joinOnce
* @discussion if set to YES the configuration will not be persisted. Default is NO.
*/
@property BOOL joinOnce API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @property lifeTimeInDays
* @discussion The lifetime of the configuration in days. The configuration is stored for the
* number of days specified by this property. The minimum value is 1 day and maximum value is 365 days.
* A configuration does not get deleted automatically if this property is not set or set to an invalid value.
* This property does not apply to Enterprise and HS2.0 networks.
*/
@property (copy) NSNumber * lifeTimeInDays API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
複製程式碼
有4個例項化方法,分別是:
- 無密碼的開放網路
- 受保護的WEP或WPA / WPA2個人Wi-Fi網路建立由SSID標識的新熱點配置
- 具有EAP設定的WPA / WPA2企業Wi-Fi網路
- 具有HS 2.0和EAP設定的Hotspot 2.0 Wi-Fi網路
原始碼如下:
/*!
* @method initWithSSID:
* @discussion
* A designated initializer to instantiate a new NEHotspotConfiguration object.
* This initializer is used to configure open Wi-Fi Networks.
*
* @param SSID The SSID of the Open Wi-Fi Network.
* Length of SSID must be between 1 and 32 characters.
*/
- (instancetype)initWithSSID:(NSString *)SSID API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method initWithSSID:passphrase:isWEP
* @discussion
* A designated initializer to instantiate a new NEHotspotConfiguration object.
* This initializer is used configure either WEP or WPA/WPA2 Personal Wi-Fi Networks.
*
* @param SSID The SSID of the WEP or WPA/WPA2 Personal Wi-Fi Network
* @param passphrase The passphrase credential.
* For WPA/WPA2 Personal networks: between 8 and 63 characters.
* For Static WEP(64bit) : 10 Hex Digits
* For Static WEP(128bit) : 26 Hex Digits
* @param isWEP YES specifies WEP Wi-Fi Network else WPA/WPA2 Personal Wi-Fi Network
*/
- (instancetype)initWithSSID:(NSString *)SSID
passphrase:(NSString *)passphrase isWEP:(BOOL)isWEP API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method initWithSSID:eapSettings
* @discussion
* A designated initializer to instantiate a new NEHotspotConfiguration object.
* This initializer is used configure WPA/WPA2 Enterprise Wi-Fi Networks.
*
* @param SSID The SSID of WPA/WPA2 Enterprise Wi-Fi Network
* @param eapSettings EAP configuration
*/
- (instancetype)initWithSSID:(NSString *)SSID
eapSettings:(NEHotspotEAPSettings *)eapSettings API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method initWithHS20Settings:eapSettings
* @discussion
* A designated initializer to instantiate a new NEHotspotConfiguration object.
* This initializer is used configure HS2.0 Wi-Fi Networks.
*
* @param hs20Settings Hotspot 2.0 configuration
* @param eapSettings EAP configuration
*/
- (instancetype)initWithHS20Settings:(NEHotspotHS20Settings *)hs20Settings
eapSettings:(NEHotspotEAPSettings *)eapSettings API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
複製程式碼
四:NEHotspotConfigurationManager庫分析
在NEHotspotConfigurationManager庫中提供了四個方法,分別是:
- 應用你的Configuration,會彈出系統框詢問是否加入
- 通過ssid刪除一個配置
- 刪除Hotspot 2.0域名標識的Wi-Fi熱點配置
- 獲取配置過的wifi名稱。如果你設定joinOnce為YES,這裡就不會有了
原始碼如下:
/*!
* @method applyConfiguration:
* @discussion This function adds or updates a Wi-Fi network configuration.
* @param configuration NEHotspotConfiguration object containing the Wi-Fi network configuration.
* @param completionHandler A block that will be called when add/update operation is completed.
* This could be nil if application does not intend to receive the result.
* The NSError passed to this block will be nil if the configuration is successfully stored, non-nil otherwise.
* If the configuration is found invalid or API encounters some other error then completionHandler is called
* with instance of NSError containing appropriate error code. This API attempts to join the Wi-Fi network
* if the configuration is successfully added or updated and the network is found nearby.
*
*/
- (void)applyConfiguration:(NEHotspotConfiguration *)configuration
completionHandler:(void (^ __nullable)(NSError * __nullable error))completionHandler API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method removeConfigurationForSSID:
* @discussion This function removes Wi-Fi configuration.
* If the joinOnce property was set to YES, invoking this method will disassociate from the Wi-Fi network
* after the configuration is removed.
* @param SSID Wi-Fi SSID for which the configuration is to be deleted.
*/
- (void)removeConfigurationForSSID:(NSString *)SSID API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method removeConfigurationForNetworkName:
* @discussion This function removes Wi-Fi configuration.
* @param domainName HS2.0 domainName for which the configuration is to be deleted.
*/
- (void)removeConfigurationForHS20DomainName:(NSString *)domainName API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
/*!
* @method getConfiguredSSIDsWithCompletionHandler:
* @discussion This function returns array of SSIDs and HS2.0 Domain Names that the calling application has configured.
* It returns nil if there are no networks configurred by the calling application.
*/
- (void)getConfiguredSSIDsWithCompletionHandler:(void (^)(NSArray<NSString *> *))completionHandler API_AVAILABLE(ios(11.0)) API_UNAVAILABLE(macos, watchos, tvos);
複製程式碼
到這裡配置及原始碼分析的前期工作已經做完。
五:加入Wi-Fi實現解析
首先引入 NetworkExtension 庫
#import <NetworkExtension/NetworkExtension.h>
複製程式碼
然後需要呼叫NEHotspotConfiguration庫方法,根據不同的情況,選擇使用不同的方法,這裡使用受保護的WEP或WPA舉例
NEHotspotConfiguration *hotspotConfig = [[NEHotspotConfiguration alloc]initWithSSID:_wifiName.text passphrase:_wifiPassword.text isWEP:NO];
複製程式碼
然後開始連線 ,呼叫applyConfiguration此方法後系統會自動彈窗確認,根據返回的error.code來判斷Wi-Fi是否加入成功,error code = 7 為使用者點選了彈框取消按鈕,error code = 13 為已連線
[[NEHotspotConfigurationManager sharedManager] applyConfiguration:hotspotConfig completionHandler:^(NSError * _Nullable error) {
if (error && error.code != 13 && error.code != 7) {
NSLog(@"加入失敗");
}else if(error.code ==7){
NSLog(@"已取消");
}else{
NSLog(@"已連線");
}
}];
複製程式碼
五:Wi-Fi列表實現解析
在Android中裝置周圍的Wi-Fi資訊是可以掃面獲取到的,iOS裝置至今也沒有完全開放相關介面,如果真有該需求 ,需要填寫申請表申請,通過後方可使用,我們們這裡分享的Wi-Fi列表,是NEHotspotConfigurationManager庫中的getConfiguredSSIDsWithCompletionHandler方法,可以獲取到已經儲存過的Wi-Fi資訊,實現原始碼如下:
[[NEHotspotConfigurationManager sharedManager] getConfiguredSSIDsWithCompletionHandler:^(NSArray<NSString *> * array) {
for (NSString * str in array) {
self.WiFiListTextView.text = [NSString stringWithFormat:@"%@\n%@",self.WiFiListTextView.text,str];
NSLog(@"加入過的WiFi:%@",str);
}
}];
複製程式碼
六:Wi-Fi測速實現解析
通過Wi-Fi測速可以獲取到Wi-Fi強度、上行速度、下行速度,我在demo中封裝了SpeedController類來實現該功能,通過下面兩個方法來實現:
//獲取訊號強度(0到1)
+(void)getSignalStrength:(void(^)(float signalStrength))resultBlock;
//獲取下行速度,上行速度(單位是 MB/S)
-(void)getDownstreamSpeedAndUpstreamSpeed:(void(^)(float downstreamSpeed,float upstreamSpeed))resultBlock;
複製程式碼
原始碼Demo獲取方法
關注 【網羅開發】微信公眾號,回覆【93】便可領取。 網羅天下方法,方便你我開發,更多iOS技術乾貨等待領取,所有文件會持續更新,歡迎關注一起成長!
歡迎關注我的公眾號:網羅開發