Знайте, если устройство iOS имеет возможности сотовой передачи данных - PullRequest
31 голосов
/ 18 августа 2011

У меня в приложении есть переключатель "загрузка только по WiFi". Однако это переключение бесполезно для iPod touch или WiFi-iPad.

Есть ли способ узнать, поддерживает ли устройство кодирование данных сотовой связи? Что-то, что будет работать в будущем, тоже было бы замечательно (например, если выйдет iPod touch 5-го поколения с 3G).

Ответы [ 8 ]

32 голосов
/ 24 января 2013

Привет, ты должен быть в состоянии проверить, имеет ли он интерфейс pdp_ip0

#import <ifaddrs.h>

- (bool) hasCellular {
    struct ifaddrs * addrs;
    const struct ifaddrs * cursor;
    bool found = false;
    if (getifaddrs(&addrs) == 0) {
        cursor = addrs;
        while (cursor != NULL) {
            NSString *name = [NSString stringWithUTF8String:cursor->ifa_name];
            if ([name isEqualToString:@"pdp_ip0"]) {
                found = true;
                break;
            }
            cursor = cursor->ifa_next;
        }
        freeifaddrs(addrs);
    }
    return found;
}

Это не использует частные API.

16 голосов
/ 18 августа 2011

3G сам по себе кажется трудным для поиска. Вы можете узнать, может ли устройство совершать звонки , используя [[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:@"tel://"]]. Вы можете проверить, может ли устройство подключиться к Интернету, точка (и каким способом это может в настоящее время произойти), используя Достижимость код:

NetworkStatus currentStatus = [[Reachability reachabilityForInternetConnection] 
                               currentReachabilityStatus];

if(currentStatus == kReachableViaWWAN) // 3G

else if(currentStatus == kReachableViaWifi) // ...wifi

else if(currentStatus == kNotReachable) // no connection currently possible

.. но кроме этого, я не думаю, что вы можете проверить наличие модема 3G в устройстве. ***** Если он не может позвонить, и в настоящее время не имеет сотового данные включены и Wi-Fi выключен выключен , вы не сможете узнать, поддерживает ли он 3G.

Альтернативный способ (хотя и не совместимый с прямым обращением, так что вы, вероятно, не хотите этого делать) - сравнить модель устройства с исчерпывающим списком, зная, какие из них имеют модемы 3G, как показано здесь .

***** Согласно ответу Bentech, если вы хотите копаться с именами устройств (это может перестать работать без предварительного предупреждения, если Apple решит изменить имя интерфейса 3g), позвоните по номеру getifaddrs и проверьте, pdp_ip0 интерфейс.

6 голосов
/ 03 марта 2017

Swift 3.0 (UIDevice + Extension) ответа @ bentech

Добавьте эту строку в ваш BridgingHeader.h:

#import <ifaddrs.h>

Где-то еще:

extension UIDevice {
    /// A Boolean value indicating whether the device has cellular data capabilities (true) or not (false).
    var hasCellularCapabilites: Bool {
        var addrs: UnsafeMutablePointer<ifaddrs>?
        var cursor: UnsafeMutablePointer<ifaddrs>?

        defer { freeifaddrs(addrs) }

        guard getifaddrs(&addrs) == 0 else { return false }
        cursor = addrs

        while cursor != nil {
            guard
                let utf8String = cursor?.pointee.ifa_name,
                let name = NSString(utf8String: utf8String),
                name == "pdp_ip0"
                else {
                    cursor = cursor?.pointee.ifa_next
                    continue
            }
            return true
        }
        return false
    }
}
4 голосов
/ 13 июля 2013

В iOS 6.1 я смог использовать Core Telephony для успешной проверки наличия возможностей сотовой базовой полосы.Это работает на всех iPad, которые я тестировал: Verizon с активированным сервисом и без него, AT & T с сервисом, который в данный момент деактивирован, вход и выход с SIM-карты и iPad с поддержкой только Wi-Fi.

CTTelephonyNetworkInfo* ctInfo = [[CTTelephonyNetworkInfo alloc] init];
CTCarrier* carrier = ctInfo.subscriberCellularProvider;
self.hasWWANCapability = carrier != nil;

Для всех iPad с аппаратным оборудованием сотовой связи carrier не равно нулю.Для iPad только с Wi-Fi carrier - ноль.

2 голосов
/ 24 января 2013

Я думаю, вы сможете использовать CoreTelephony Framework .

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

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

1 голос
/ 26 февраля 2014

Apple предоставил код здесь. https://developer.apple.com/library/ios/samplecode/Reachability/Introduction/Intro.html

Вы должны скопировать Reachability.h и Reachability.m в свой проект и импортировать Reachability.h до вашего класса, тогда

Reachability *networkReachability = [Reachability reachabilityForInternetConnection];
NetworkStatus networkStatus = [networkReachability currentReachabilityStatus];

while (networkStatus==NotReachable) {
    NSLog(@"not reachable");
//no  internet connection 
    return;
}
while (networkStatus==ReachableViaWWAN) {
    NSLog(@" ReachableViaWWAN ");
}

while (networkStatus==ReachableViaWiFi) {
    NSLog(@"ReachableViaWiFi");
}
1 голос
/ 18 января 2013

Один из способов сделать это - узнать местоположение пользователя. Когда это будет как можно точнее, вы узнаете, есть ли на устройстве GPS. Все устройства с GPS будут иметь 3G. А те, которые не имеют GPS, не будут иметь 3G.

0 голосов
/ 16 июля 2014

Другой способ состоит в том, чтобы расширить это: https://github.com/monospacecollective/UIDevice-Hardware/blob/master/UIDevice-Hardware.m с помощью этого:

-(bool) hasCellular:(NSString*)modelIdentifier {
    if ([modelIdentifier hasPrefix:@"iPhone"]) return YES;
    if ([modelIdentifier hasPrefix:@"iPod"]) return NO;

    if ([modelIdentifier isEqualToString:@"iPad1,1"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad2,1"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad2,2"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad2,3"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad2,4"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad2,5"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad2,6"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad2,7"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad3,1"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad3,2"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad3,3"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad3,4"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad3,5"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad3,6"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad4,1"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad4,2"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad2,5"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad2,6"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad2,7"])      return YES;
    if ([modelIdentifier isEqualToString:@"iPad4,4"])      return NO;
    if ([modelIdentifier isEqualToString:@"iPad4,5"])      return YES;

    if ([modelIdentifier isEqualToString:@"i386"])         return NO;
    if ([modelIdentifier isEqualToString:@"x86_64"])       return NO;

return YES;

}

(Очевидно, его можно отредактировать, чтобы удалить только NO или YESв зависимости от того, как вы хотите ошибиться в случае появления новой модели ...)

...