Способ рассчитать или получить мощность Wi-Fi на Swift на iOS 11

Ищете способ получить или рассчитать мощность Wi-Fi устройства? Видели примеры очистки строки состояния, но не можете заставить ее работать на iOS 11:

func getSignalStrength() -> Int {
    let application = UIApplication.shared
    let statusBarView = application.value(forKey: "statusBar") as! UIView
    let foregroundView = statusBarView.value(forKey: "foregroundView") as! UIView
    let foregroundViewSubviews = foregroundView.subviews

    var dataNetworkItemView:UIView!

    for subview in foregroundViewSubviews {
        if subview.isKind(of: NSClassFromString("UIStatusBarSignalStrengthItemView")!) {
            dataNetworkItemView = subview
            print("NONE")
            break
        } else {
            print("NONE")

            return 0 //NO SERVICE
        }
    }

    return dataNetworkItemView.value(forKey: "signalStrengthBars") as! Int
}

Есть умные идеи?

Не требует одобрения Apple


person Justin    schedule 30.11.2017    source источник


Ответы (2)


Код, который у вас есть, предназначен для мобильной сети (2G/3G/4G и т. д.), а не для сети Wi-Fi.

Попробуйте приведенный ниже код в Swift4, он работает на моей iOS11:

private func wifiStrength() -> Int? {
    let app = UIApplication.shared
    var rssi: Int?
    guard let statusBar = app.value(forKey: "statusBar") as? UIView, let foregroundView = statusBar.value(forKey: "foregroundView") as? UIView else {
        return rssi
    }
    for view in foregroundView.subviews {
        if let statusBarDataNetworkItemView = NSClassFromString("UIStatusBarDataNetworkItemView"), view .isKind(of: statusBarDataNetworkItemView) {
            if let val = view.value(forKey: "wifiStrengthRaw") as? Int {
                //print("rssi: \(val)")

                rssi = val
                break
            }
        }
    }
    return rssi
}

Как получить мощность WiFi на iPhoneX, проверьте мой ответ в другом сообщении: Использование частного API для чтения значения WiFi RSSI

person DàChún    schedule 03.01.2018
comment
для iPhoneX: stackoverflow.com/questions/44167577/ - person DàChún; 29.01.2018
comment
Это вызывает сбой в 14 с Exception NSException * Приложение с именем -statusBar или -statusBarWindow в UIApplication: этот код необходимо изменить, так как больше нет строки состояния или окна строки состояния. Вместо этого используйте объект statusBarManager на сцене окна. 0x0000000281f5f5a0 - person Tall Dane; 02.03.2021

Вы можете использовать этот код для каждого устройства, включая все новые айфоны.

class DeviceType {

static let deviceType = UIDevice.current.modelName
class func getDevice() -> Devices{
    switch deviceType {
    case "iPhone10,3", "iPhone10,6":
        print("iPhoneX")
        return Devices.iPhoneX
    case "iPhone11,2":
        print("iPhone XS")
        return Devices.iPhoneXS
    case "iPhone11,4":
        print("iPhone XS Max")
        return Devices.iPhoneXSMax
    case "iPhone11,6":
        print("iPhone XS Max China")
        return Devices.iPhoneXSMaxChina
    case "iPhone11,8":
        print("iPhone XR")
        return Devices.iPhoneXR
    default:
        return Devices.none
    }
}

}

extension UIDevice {
    var modelName: String {
        var systemInfo = utsname()
        uname(&systemInfo)
        let machineMirror = Mirror(reflecting: systemInfo.machine)
        let identifier = machineMirror.children.reduce("") { identifier, element in
            guard let value = element.value as? Int8, value != 0 else { return identifier }
            return identifier + String(UnicodeScalar(UInt8(value)))
        }
        return identifier
    }
}


enum Devices {
    case iPhoneX
    case iPhoneXS
    case iPhoneXSMax
    case iPhoneXSMaxChina
    case iPhoneXR
    case none
}

func getSignalStrength() -> Int {


var classNameForStatusBar = ""
var valueForSignalValue = ""

classNameForStatusBar = "UIStatusBarSignalStrengthItemView"
valueForSignalValue = "signalStrengthBars"

let app = UIApplication.shared
let statusBarView = app.value(forKey: "statusBar") as! UIView
if UIDevice().userInterfaceIdiom == .phone {
    switch UIScreen.main.nativeBounds.height {
    case 2436, 2688, 1792:
        print("iPhone X, XS")
        return checkStatus(statusBarView)
    default:
        if(statusBarView.frame.width == 1024.0 ||  statusBarView.frame.width == 1112.0 || statusBarView.frame.width == 1024.0 || statusBarView.frame.width == 768.0){
            if let viewStatus = statusBarView.value(forKey: "statusBar") as? UIView{
                if let foregroundView = viewStatus.value(forKey: "foregroundView") as? UIView{
                    let subViews = foregroundView.subviews
                    var dataNetworkItemView:UIView?
                    for subview in subViews {

                        if subview.isKind(of: NSClassFromString(classNameForStatusBar)!){
                            dataNetworkItemView = subview;
                            break
                        }
                    }
                    guard let signal = dataNetworkItemView?.value(forKey: valueForSignalValue) as? Int else { return 0 }
                    return signal
                }
            }
            return 0
        }
        print("Unknown")
        if let foregroundView = statusBarView.value(forKey: "foregroundView") as? UIView{
            let subViews = foregroundView.subviews

            var dataNetworkItemView:UIView?
            for subview in subViews {

                if subview.isKind(of: NSClassFromString(classNameForStatusBar)!){
                    dataNetworkItemView = subview;
                    break
                }
            }
            guard let signal = dataNetworkItemView?.value(forKey: valueForSignalValue) as? Int else { return 0 }
            return signal
        }
    }
}
return 0

}

private func checkStatus(_ statusBarView: UIView) -> Int{
    if DeviceType.getDevice() == .iPhoneX{
        if let viewStatus = statusBarView.value(forKey: "statusBar") as? UIView{
            if let foregroundView = viewStatus.value(forKey: "foregroundView") as? UIView{
                let subViews = foregroundView.subviews
                var dataNetworkItemView:UIView?
                for subview in subViews {
                    for localSubView in subview.subviews{
                        if localSubView.isKind(of: NSClassFromString("_UIStatusBarCellularSignalView")!){
                            dataNetworkItemView = localSubView
                            break
                        }
                    }
                }
                if dataNetworkItemView == nil{
                    return 0
                }else{
                    return 1
                }
//                guard let signal = dataNetworkItemView?.value(forKey: "signalStrengthBars") as? Int else { return 0 }
//                return signal
            }
        }
    }else{
        if let viewStatus = statusBarView.value(forKey: "statusBar") as? UIView{
            if let foregroundView = viewStatus.value(forKey: "foregroundView") as? UIView{
                let subViews = foregroundView.subviews
                var dataNetworkItemView:UIView?
                print(foregroundView)
                print(viewStatus)
                print(statusBarView)
                for subview in subViews {
                    for localSubview in subview.subviews{
                        if localSubview.isKind(of: NSClassFromString("_UIStatusBarDualCellularSignalView")!){
                            dataNetworkItemView = subview;
                            break
                        }else if localSubview.isKind(of: NSClassFromString("_UIStatusBarCellularSignalView")!){
                            print("Check this")
                        }
                    }
                }
                if dataNetworkItemView == nil{
                    return 0
                }else{
                    return 1
                }
            }
        }
    }
    return 0
}

Просто скопируйте и вставьте этот код в любой файл Swift.

person Gurinder Batth    schedule 13.08.2019
comment
Обратите внимание, что здесь используются частные API Apple, которые не разрешены в App Store и могут быть изменены в будущем обновлении. - person Barnyard; 13.08.2019