如何从Swift中确定设备类型?(OS X或iOS)

use*_*561 32 macos ios swift

我知道Swift相对较新,但我想知道是否有办法确定设备类型?

(就像你曾经能够做到的那样#define)?

主要是我想知道如何区分OS X或iOS.我在这个问题上一无所获.

ric*_*ter 71

如果您正在为iOS和OS X构建(现在也可能用于watchOS和tvOS),那么您至少需要构建两次代码:每个平台一次.如果要在每个平台上执行不同的代码,则需要构建时条件,而不是运行时检查.

Swift没有预处理器,但它确实有条件构建指令 - 并且在大多数情况下,它们看起来像C等价物.

#if os(iOS) || os(watchOS) || os(tvOS)
    let color = UIColor.redColor()
#elseif os(OSX)
    let color = NSColor.redColor()
#else
    println("OMG, it's that mythical new Apple product!!!")
#endif
Run Code Online (Sandbox Code Playgroud)

您还可以使用生成配置来测试架构(x86_64,arm,arm64,i386),或者-D编译器标志(包括DEBUG通过标准的Xcode模板中定义的标志).

预处理器指令使用雨燕与可可和Objective-C .

(如果您想要区分运行时使用的iOS设备,请使用UIDevice类似于ObjC的类.通常,查看对您而言重要的设备属性而不是设备名称更为有用和安全或成语 - 例如,使用特征和大小类来布置UI,查询OpenGL以获得所需的GPU功能等.)

  • 'else`案例为+1.始终处理边缘情况!:-P (7认同)
  • 请注意,根据[Swift文档](https://docs.swift.org/swift-book/ReferenceManual/Statements.html#//apple_ref/doc/uid/ TP40014097-CH33-ID539) (2认同)

ada*_*dev 19

这应该为您提供每个用例:

#if os(OSX)
    print("macOS")
#elseif os(watchOS)
    print("watchOS")
#elseif os(tvOS)
    print("tvOS")
#elseif os(iOS)
    #if targetEnvironment(macCatalyst)
        print("macOS - Catalyst")
    #else
        print("iOS")
    #endif
#endif
Run Code Online (Sandbox Code Playgroud)

  • iPadOS 有任何更新吗?或者它仍然被识别为iOS? (2认同)

rae*_*aed 7

从 Swift 4.2 开始,您可以替换

#if os(iOS) || os(watchOS) || os(tvOS)
    let color = UIColor.redColor()
#elseif os(OSX)
    let color = NSColor.redColor()
#else
     println("OMG, it's that mythical new Apple product!!!")
#endif
Run Code Online (Sandbox Code Playgroud)

经过

#if canImport(UIKit)
    let color = UIColor.redColor()
#elseif os(OSX)
    let color = NSColor.redColor()
#else
    #error("OMG, it's that mythical new Apple product!!!")
#endif
Run Code Online (Sandbox Code Playgroud)

  • 我认为这不再有效,因为 macOS 事实上可以导入 UIKit 作为 Mac Catalyst 的一部分。 (2认同)

小智 7

Mac Catalyst 的更新。您现在还可以使用以下内容来确定是 iOS 还是 Mac Catalyn:

let color: UIColor
#if targetEnvironment(macCatalyst)
color = .systemRed
#else
color = .systemBlue
#endif
Run Code Online (Sandbox Code Playgroud)

例如。


dph*_*ans 6

Swift 4(2020 年 7 月 21 日更新)

enum TargetDevice {
    case nativeMac
    case iPad
    case iPhone
    case iWatch
    
    public static var currentDevice: Self {
        var currentDeviceModel = UIDevice.current.model
        #if targetEnvironment(macCatalyst)
        currentDeviceModel = "nativeMac"
        #elseif os(watchOS)
        currentDeviceModel = "watchOS"
        #endif
        
        if currentDeviceModel.starts(with: "iPhone") {
            return .iPhone
        }
        if currentDeviceModel.starts(with: "iPad") {
            return .iPad
        }
        if currentDeviceModel.starts(with: "watchOS") {
            return .iWatch
        }
        return .nativeMac
    }
}
Run Code Online (Sandbox Code Playgroud)

用法:

print(TargetDevice.currentDevice)
Run Code Online (Sandbox Code Playgroud)


Mr.*_*Oak 5

Swift 5Xcode 13

如果您使用“缩放接口来匹配iPad”,则不能使用UIDevice.current.userInterfaceIdiom,因为它会返回一个.iPad值。但建议改用targetEnvironment。以下是示例代码:

    #if targetEnvironment(macCatalyst)
            //execute your code for mac device
    #endif
Run Code Online (Sandbox Code Playgroud)

如果您不使用缩放界面来匹配 iPad,而是使用“优化 mac 界面”,您可以使用此代码来确定设备:

UIDevice.current.userInterfaceIdiom == .mac
Run Code Online (Sandbox Code Playgroud)

这是提供更多信息的苹果文档

Mac 项目设置