美文网首页
iOS app跳转到手机系统页面

iOS app跳转到手机系统页面

作者: 草原烈鹰 | 来源:发表于2017-03-01 11:48 被阅读1804次

    在iOS10之前,跳转到系统设置界面的某个指定界面的方式如下:

    //打开定位服务界面
    NSURL*url=[NSURL URLWithString:@"prefs:root=Privacy&path=LOCATION"];
    if ([[UIApplication sharedApplication] canOpenURL:url]) {
    [[UIApplication sharedApplication] openURL:url];
    };

    跳转到其他的界面的字段
    About — prefs:root=General&path=About

    Accessibility — prefs:root=General&path=ACCESSIBILITY

    AirplaneModeOn— prefs:root=AIRPLANE_MODE

    Auto-Lock — prefs:root=General&path=AUTOLOCK

    Brightness — prefs:root=Brightness

    Bluetooth — prefs:root=General&path=Bluetooth

    Date& Time — prefs:root=General&path=DATE_AND_TIME

    FaceTime — prefs:root=FACETIME

    General— prefs:root=General

    Keyboard — prefs:root=General&path=Keyboard

    iCloud — prefs:root=CASTLE iCloud

    Storage & Backup — prefs:root=CASTLE&path=STORAGE_AND_BACKUP

    International — prefs:root=General&path=INTERNATIONAL

    Location Services — prefs:root=LOCATION_SERVICES

    Music — prefs:root=MUSIC

    Music Equalizer — prefs:root=MUSIC&path=EQ

    Music VolumeLimit— prefs:root=MUSIC&path=VolumeLimit

    Network — prefs:root=General&path=Network

    Nike + iPod — prefs:root=NIKE_PLUS_IPOD

    Notes — prefs:root=NOTES

    Notification — prefs:root=NOTIFICATIONS_ID

    Phone — prefs:root=Phone

    Photos — prefs:root=Photos

    Profile — prefs:root=General&path=ManagedConfigurationList

    Reset — prefs:root=General&path=Reset

    Safari — prefs:root=Safari Siri — prefs:root=General&path=Assistant

    Sounds — prefs:root=Sounds

    SoftwareUpdate— prefs:root=General&path=SOFTWARE_UPDATE_LINK

    Store — prefs:root=STORE

    Twitter — prefs:root=TWITTER

    Usage — prefs:root=General&path=USAGE

    VPN — prefs:root=General&path=Network/VPN

    Wallpaper — prefs:root=Wallpaper

    Wi-Fi — prefs:root=WIFI

    Setting—prefs:root=INTERNET_TETHERING

    电池电量 Prefs:root=BATTERY_USAGE
    通用设置 Prefs:root=General
    存储空间 Prefs:root=General&path=STORAGE_ICLOUD_USAGE/DEVICE_STORAGE
    蜂窝数据 Prefs:root=MOBILE_DATA_SETTINGS_ID
    Wi-Fi 设置 Prefs:root=WIFI
    蓝牙设置 Prefs:root=Bluetooth
    定位设置 Prefs:root=Privacy&path=LOCATION
    辅助功能 Prefs:root=General&path=ACCESSIBILITY
    关于手机 Prefs:root=General&path=About
    键盘设置 Prefs:root=General&path=Keyboard
    显示设置 Prefs:root=DISPLAY
    声音设置 Prefs:root=Sounds
    App Store 设置 Prefs:root=STORE
    墙纸设置 Prefs:root=Wallpaper
    打开电话 Mobilephone://
    世界时钟 Clock-worldclock://
    闹钟 Clock-alarm://
    秒表 Clock-stopwatch://
    倒计时 Clock-timer://
    打开相册 Photos://

    (在项目中的info中添加 URL types,添加 URL Schemes 为 prefs)

    但是在iOS10上,调用canOpenURL:打开系统设置界面时控制台会报如下错误,并且无法跳转:

    -canOpenURL: failed for URL: "Prefs:root=Privacy&path=LOCATION" - error: "The operation couldn’t be completed. (OSStatus error -10814.)"
    原因是iOS10只允许如下方式跳转到设置里自己app的界面,对跳转到其他界面做了限制:

    [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];

    (iOS10之后用:openURL:(NSURL*)url options:(NSDictionary<NSString *, id> *)options completionHandler:(void (^ __nullable)(BOOL success))completion
    Options 参数:
    UIApplication 的头文件中列了一个可用在 options字典中的key:

    • UIApplicationOpenURLOptionUniversalLinksOnly:可以设置布尔值,如果设置为true(YES),则只能打开应用里配置好的有效通用链接。如果应用程序没有配置,或者用于禁止打开这个链接,则 completion handler 回调里的success为false(NO)。
      为了覆写程序的默认动作(默认这个key的值是NO),我们需要创建一个字典,将对应的key 设置为true(YES),然后将字典传给 options 参数:
      NSDictionary *options = @{UIApplicationOpenURLOptionUniversalLinksOnly : @YES};
      [application openURL:URL options:options completionHandler:nil];
      举个例子,我把这个值设置为 true 并尝试打开https://twitter.com/kharrison, 如果我没有安装 Twitter 应用,它将会执行失败,而不是在Safari中打开这个链接。
      (译者注:在iOS 9 使用 openURL:方法打开这个链接时,会在首先调起Safari,然后在Safari中打开这个链接))

    解决方法

    可以使用MobileCoreServices.framework里的私有API:

    • (BOOL)openSensitiveURL:(id)arg1 withOptions:(id)arg2;
      头文件参考:LSApplicationWorkspace.h
      使用方法:

    //注意首字母改成了大写,prefs->Prefs
    NSURL*url=[NSURL URLWithString:@"Prefs:root=Privacy&path=LOCATION"];
    Class LSApplicationWorkspace = NSClassFromString(@"LSApplicationWorkspace");
    [[LSApplicationWorkspace performSelector:@selector(defaultWorkspace)] performSelector:@selector(openSensitiveURL:withOptions:) withObject:url withObject:nil];
    MobileCoreServices.framework不是私有库,所以直接使用performSelector:即可调用私有API。
    (app需要添加一个Prefs的URL Schemes,即添加到info.plist的LSApplicationQueriesSchemes项中)

    注意

    iOS10的系统URLScheme改成了首字母大写,使用小写的方式会无法打开。
    使用私有API的app无法通过App Store审核。你也可以尝试把私有类名和selector字符串混淆一下,绕过审核。例如这位仁兄用ASCII混淆的方法:

    • (UIView *)statusBarView {
      UIView *statusBar = nil;
      NSData *data = [NSData dataWithBytes:(unsigned char []){0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x42, 0x61, 0x72} length:9];
      NSString *key = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
      id object = [UIApplication sharedApplication];
      if ([object respondsToSelector:NSSelectorFromString(key)]) {
      statusBar = [object valueForKey:key];
      }
      return statusBar;
      }
      不过,还是不建议使用私有API,因为它是不可靠的。也许某天苹果就把它移除了。

    但是还是都可以跳到设置页面的: if([[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]]) {
    [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString] options:@{} completionHandler:nil];}

    相关文章

      网友评论

          本文标题:iOS app跳转到手机系统页面

          本文链接:https://www.haomeiwen.com/subject/ybyqgttx.html