我正在尝试将网络连接检测功能整合到我的应用中,但似乎在线路的某处我犯了一个错误,因为我的网络更改未被检测/打印到控制台。
如帖子中所述,我目前正在使用以下课程和工具:
{.h, .m}
NSNotificationCenter
代码
在 AppDelegate.Swift 中,我设置NSNotificationCenter
来检测更改:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
// ...
// A: Checks if the device is connected to the internet
var defaultCenter: Void = NSNotificationCenter().addObserver(self, selector:"checkForReachability", name: kReachabilityChangedNotification, object: nil)
}
在同一个班级AppDelegate
中,我还创建了此功能,以便在发生变化时触发:
func checkForReachability () {
var networkReachability = Reachability.reachabilityForInternetConnection()
networkReachability.startNotifier()
var remoteHostStatus = networkReachability.currentReachabilityStatus()
if (remoteHostStatus.value == NotReachable.value) {
println("Not Reachable")
} else if (remoteHostStatus.value == ReachableViaWiFi.value) {
println("Reachable via Wifi")
} else {
println("Reachable")
}
}
但是,当使用网络链接调节器来操作和模拟条件的变化时,我还没有能够看到控制台中反映出的任何变化。任何帮助都会膨胀!
答案 0 :(得分:32)
您必须先创建一个可访问性对象 ,然后才能从中接收通知。另外,请务必在您创建的Reachability对象上调用startNotifier()
方法。这将是一个如何在您的应用程序委托中执行此操作的示例:
class AppDelegate: UIResponder, UIApplicationDelegate
{
private var reachability:Reachability!;
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: NSDictionary?) -> Bool
{
NSNotificationCenter.defaultCenter().addObserver(self, selector:"checkForReachability:", name: kReachabilityChangedNotification, object: nil);
self.reachability = Reachability.reachabilityForInternetConnection();
self.reachability.startNotifier();
}
func checkForReachability(notification:NSNotification)
{
// Remove the next two lines of code. You cannot instantiate the object
// you want to receive notifications from inside of the notification
// handler that is meant for the notifications it emits.
//var networkReachability = Reachability.reachabilityForInternetConnection()
//networkReachability.startNotifier()
let networkReachability = notification.object as Reachability;
var remoteHostStatus = networkReachability.currentReachabilityStatus()
if (remoteHostStatus.value == NotReachable.value)
{
println("Not Reachable")
}
else if (remoteHostStatus.value == ReachableViaWiFi.value)
{
println("Reachable via Wifi")
}
else
{
println("Reachable")
}
}
}
我建议您查看NSNotificationCenter和NSNotification的文档。通过这种方式,您可以更加熟悉下次出现此类通知时如何使用通知。
Swift 3
NotificationCenter.default.addObserver(self, selector:Selector(("checkForReachability:")), name: NSNotification.Name.reachabilityChanged, object: nil)
let reachability: Reachability = Reachability.forInternetConnection()
reachability.startNotifier()
答案 1 :(得分:8)
根据@ Hardik.T
更新了Swift 4 1。在您的XCode项目中从https://github.com/ashleymills/Reachability.swift/archive/master.zip导入Reachability.swift
个文件
2. :创建一个新的Swift类:ConnectionManager.swift
class ConnectionManager {
static let sharedInstance = ConnectionManager()
private var reachability : Reachability!
func observeReachability(){
self.reachability = Reachability()
NotificationCenter.default.addObserver(self, selector:#selector(self.reachabilityChanged), name: NSNotification.Name.reachabilityChanged, object: nil)
do {
try self.reachability.startNotifier()
}
catch(let error) {
print("Error occured while starting reachability notifications : \(error.localizedDescription)")
}
}
@objc func reachabilityChanged(note: Notification) {
let reachability = note.object as! Reachability
switch reachability.connection {
case .cellular:
print("Network available via Cellular Data.")
break
case .wifi:
print("Network available via WiFi.")
break
case .none:
print("Network is not available.")
break
}
}
}
3。在AppDelegate
文件中使用它:
func application(_ application: UIApplication,didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
ConnectionManager.sharedInstance.observeReachability()
return true
}
答案 2 :(得分:5)
我建议不要用观察者回调来污染SELECT * FROM `foobar` WHERE weight+0.0 <= '0,7 kg'
,而是建议只将观察者添加到相关的视图控制器中。
<强> SELECT * FROM `foobar` WHERE REPLACE(weight+0.0,',','.') <= REPLACE('0,7 kg',',','.')
强>
AppDelegate.swift
ViewController示例:
AppDelegate.swift
答案 3 :(得分:4)
升级为快速2.1&amp; XCode 7:
尝试此第三方高度评价 Reachablity Class
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: NSDictionary?) -> Bool
{
// Allocate a reachability object
self.reach = Reachability.reachabilityForInternetConnection()
// Tell the reachability that we DON'T want to be reachable on 3G/EDGE/CDMA
self.reach!.reachableOnWWAN = false
// Here we set up a NSNotification observer. The Reachability that caused the notification
// is passed in the object parameter
NSNotificationCenter.defaultCenter().addObserver(self,
selector: "reachabilityChanged:",
name: kReachabilityChangedNotification,
object: nil)
self.reach!.startNotifier()
return true
}
//Reachbality Notification Response
func reachabilityChanged(notification: NSNotification) {
if self.reach!.isReachableViaWiFi() || self.reach!.isReachableViaWWAN() {
print("Service avalaible!!!")
} else {
print("No service avalaible!!!")
AppHelper.showALertWithTag(0, title: constants.AppName.rawValue, message: "Please Check Your Internet Connection!", delegate: self, cancelButtonTitle: "OK", otherButtonTitle: nil)
}
}
答案 4 :(得分:3)
更新了A. R. Younce对Swift 2的回答:
application_readable
答案 5 :(得分:1)
Swift 2.0 - 使用可访问性检查网络,NSNotification
<强> AppDelegate.swift 强>
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool
{
NSNotificationCenter.defaultCenter().addObserver(self, selector:#selector(self.checkNetworkStatus(_:)), name: "ReachabilityChangedNotification", object: nil);
do{self.reachability = try Reachability.reachabilityForInternetConnection()}catch{}
do{try self.reachability.startNotifier()}catch{}
self.checkNetworkStatus()
return true
}
声明networkStatus变量
var networkStatus : Reachability.NetworkStatus!
checkNetworkStatus()函数
func checkNetworkStatus()
{
networkStatus = reachability.currentReachabilityStatus
if (networkStatus == Reachability.NetworkStatus.NotReachable)
{
print("Not Reachable")
}
else
{
print("Reachable")
}
}
<强> OtherClass.Swift 强>
let delegate = UIApplication.sharedApplication().delegate as! AppDelegate
if (delegate.networkStatus!=Reachability.NetworkStatus.NotReachable)
{
// Call Webservice
}
else
{
delegate.checkNetworkStatus() //Not Reachable print
}
答案 6 :(得分:1)
1)安装pod或在项目中添加 ReachabilitySwift
2)在 AppDelegate.swift
中func checkForReachability(notification:NSNotification) {
let networkReachability = notification.object as! Reachability;
let remoteHostStatus = networkReachability.currentReachabilityStatus
if (remoteHostStatus == .NotReachable) {
print("Not Reachable")
}
else if (remoteHostStatus == .ReachableViaWiFi || remoteHostStatus == .ReachableViaWWAN) {
print("Reachable via Wifi or via WWAN")
}
}
3)
{{1}}
答案 7 :(得分:0)
基于this open source solution 包装上课
快速5
import Foundation
final class ReachabilityHandler {
private var reachability: Reachability? = Reachability()
// MARK: - LifeCycle
init() {
configure()
}
deinit {
NotificationCenter.default.removeObserver(self)
reachability?.stopNotifier()
}
// MARK: - Private
private func configure() {
NotificationCenter.default.addObserver(self,
selector: #selector(ReachabilityHandler.checkForReachability(notification:)),
name: Notification.Name.reachabilityChanged,
object: nil)
try? reachability?.startNotifier()
}
@objc private func checkForReachability(notification: NSNotification) {
let networkReachability = notification.object as? Reachability
if let remoteHostStatus = networkReachability?.connection {
switch remoteHostStatus {
case .none:
case .wifi,
.cellular:
}
}
}
}
在AppDelegate
class AppDelegate: UIResponder, UIApplicationDelegate {
private var rechabilityObserver: ReachabilityHandler?
var window: UIWindow?
// MARK: - LifeCycle
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
rechabilityObserver = ReachabilityHandler()
return true
}
}
答案 8 :(得分:0)
使用ReachabilitySwift框架,它是用闭包在Swift中重写的Apple可达性的替代方法
安装ReachabilitySwift Cocoapod
创建NetworkReachability
包装类以观察可达性更改
导入ReachabilitySwift
extension Notification.Name {
static let ReachabilityStatusChanged = Notification.Name("ReachabilityStatusChangedNotification")
}
//MARK: NetworkReachability
final class NetworkReachability {
enum ReachabilityStatus: Equatable {
case connected
case disconnected
}
static let shared = NetworkReachability()
private let reachability = try! Reachability()
var reachabilityObserver: ((ReachabilityStatus) -> Void)?
private(set) var reachabilityStatus: ReachabilityStatus = .connected
private init() {
setupReachability()
}
/// setup observer to detect reachability changes
private func setupReachability() {
let reachabilityStatusObserver: ((Reachability) -> ()) = { [unowned self] (reachability: Reachability) in
self?.updateReachabilityStatus(reachability.connection)
}
reachability.whenReachable = reachabilityStatusObserver
reachability.whenUnreachable = reachabilityStatusObserver
}
/// Start observing reachability changes
func startNotifier() {
do {
try reachability.startNotifier()
} catch {
print(error.localizedDescription)
}
}
/// Stop observing reachability changes
func stopNotifier() {
reachability.stopNotifier()
}
/// Updated ReachabilityStatus status based on connectivity status
///
/// - Parameter status: Reachability.Connection enum containing reachability status
private func updateReachabilityStatus(_ status: Reachability.Connection) {
switch status {
case .unavailable, .none:
notifyReachabilityStatus(.disconnected)
case .cellular, .wifi:
notifyReachabilityStatus(.connected)
}
}
/// Notifies observers about reachability status change
///
/// - Parameter status: ReachabilityStatus enum indicating status eg. .connected/.disconnected
private func notifyReachabilityStatus(_ status: ReachabilityStatus) {
reachabilityStatus = status
reachabilityObserver?(status)
NotificationCenter.default.post(
name: Notification.Name.ReachabilityStatusChanged,
object: nil,
userInfo: ["ReachabilityStatus": status]
)
}
/// returns current reachability status
var isReachable: Bool {
return reachability.connection != .unavailable
}
/// returns if connected via cellular or wifi
var isConnectedViaCellularOrWifi: Bool {
return isConnectedViaCellular || isConnectedViaWiFi
}
/// returns if connected via cellular
var isConnectedViaCellular: Bool {
return reachability.connection == .cellular
}
/// returns if connected via cellular
var isConnectedViaWiFi: Bool {
return reachability.connection == .wifi
}
deinit {
stopNotifier()
}
}
在 AppDelagete.Swift
中func application(_ application: UIApplication,
didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
NetworkReachability.shared.startNotifier()
reahabilityObserver()
}
func reachabilityObserver() {
NetworkReachability.shared.reachabilityObserver = { [weak self] status in
switch status {
case .connected:
print("Reachability: Network available ?")
case .disconnected:
print("Reachability: Network unavailable ?")
}
}
}
答案 9 :(得分:0)
Swift 5.0,Xcode 11.3
创建一个名为 NetworkListner.swift
的新文件class NetworkListner : NSObject {
static let shared = NetworkListner()
var reachabilityStatus: Reachability.Connection = .unavailable
let reachability = try! Reachability()
var isNetworkAvailable : Bool {
return reachabilityStatus != .unavailable
}
func startNWListner() {
NotificationCenter.default.addObserver(self, selector: #selector(reachabilityChanged(note:)), name: .reachabilityChanged, object: reachability)
reachability.whenReachable = { reachability in
if reachability.connection == .wifi {
print("Reachable via WiFi")
} else {
print("Reachable via Cellular")
}
}
reachability.whenUnreachable = { _ in
print("Not reachable")
}
do {
try reachability.startNotifier()
} catch {
print("Unable to start notifier")
}
}
@objc func reachabilityChanged(note: Notification) {
let reachability = note.object as! Reachability
switch reachability.connection {
case .wifi:
print("Reachable via WiFi")
case .cellular:
print("Reachable via Cellular")
case .unavailable:
print("Network not reachable")
case .none:
print("Network none")
}
}
}
现在在您的appDelegate方法中。
NetworkListner.shared.startNWListner()
仔细阅读
在模拟器上
在模拟器上发现了这个问题。
在真实设备上效果很好,因此无需担心
答案 10 :(得分:0)
适用于 ios 12 及更高版本;
import Network
创建一个类
@available(iOS 12.0, *)
class NetworkListener{
let monitor = NWPathMonitor()
init() {
monitor.pathUpdateHandler = { path in
if path.status == .satisfied {
print("network is now connected")
// Put your logic code
}else {
print("No connection.")
// Put your logic code
}
}
let queue = DispatchQueue.main // if your logic works on background edit accordingly
monitor.start(queue: queue)
}
}
你需要的初始化类
if #available(iOS 12.0, *) {
let net = NetworkListener()
}
你也可以监控特定的界面
let cellMonitor = NWPathMonitor(requiredInterfaceType: .cellular)