SwiftUI 是否向后兼容 iOS 12.x 及更早版本?

Is SwiftUI backwards-compatible with iOS 12.x and older?

如果我有一个使用 SwiftUI 制作的应用程序,它是否适用于 iOS 低于 iOS 13?

它与 iOS 13+ 兼容。这是其文档的 link。

https://developer.apple.com/documentation/swiftui/


连Xcode10也不支持。您需要使用截至(2019 年 6 月 3 日)处于测试阶段的 Xcode 11。 https://developer.apple.com/tutorials/swiftui/creating-and-combining-views

根据 Apple 文档,很遗憾,它仅以 iOS 13 开头。

https://developer.apple.com/documentation/swiftui/

没有。 SwiftUI 需要 iOS 13 或更高版本、macOS 10.15 或更高版本、tvOS 13 或更高版本或 watchOS 6 或更高版本的部署目标。该框架包含许多旧版本操作系统上不存在的新类型。

我刚刚在 Xcode 11 中检查过它,可以确认它不会 backwards-compatible,正如在 SwiftUI 的 View 实现中所见:

/// A piece of user interface.
///
/// You create custom views by declaring types that conform to the `View`
/// protocol. Implement the required `body` property to provide the content
/// and behavior for your custom view.
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
public protocol View : _View {

    /// The type of view representing the body of this view.
    ///
    /// When you create a custom view, Swift infers this type from your
    /// implementation of the required `body` property.
    associatedtype Body : View

    /// Declares the content and behavior of this view.
    var body: Self.Body { get }
}

我不这么认为,因为所有库都已针对 iOS 13 或更高版本进行了注释。

此外,在documentation中,Apple明确提到支持的版本:

  • iOS13.0+ 测试版
  • macOS10.15+测试版
  • tvOS 13.0+ 测试版
  • watchOS 6.0+ 测试版

正如大家所说,它不会向后兼容旧的 iOS 版本。但鉴于 Apple 始终拥有其最新 iOS 的高安装基数,并且考虑到 iOS 13 需要 iPhone 6S 或更高版本,iPad Air 2 或更高版本,新 iPad mini 4 和 iPhone SE。绝大多数用户将能够安装 iOS13 并享受可爱的 SwiftUI 应用程序。

如果您打算支持 iPhone 而不是 iPad,您可能预计大多数用户会在 12-18 个月内(​​从发布日期开始)升级到 iOS 13 .也许 85-90%? (我认为 Apple 在这一点上表示仍有 15% 的人不在 iOS 12 上)尽管到你无法立即部署 SwiftUI 应用程序的地方还有很长一段时间,否则可能会疏远很多用户。

还取决于其他 10-15% 是多少,这可能意味着您在 table.

上留下了很多用户(和 $$)

如果您也支持 iPad 那么它就更棘手了,因为人们不会经常升级他们的 iPad。有很多 iPad 2 以及第 3 代和第 4 代 iPad 仍然在野外,它们只有 10.3.3,无法再升级。人们只是不会起床去支付 400 美元到 1,000 美元之间的费用来购买新的 iPad 当他们的工作完全正常时。

总是有更新应用程序的空间和需要,使其变得更好,修复错误,这些不一定与 iOS13 有任何关系。即找到一个你不知道的错误在此之前让很多用户不高兴......不是最新的 iOS 版本。我们甚至还没有谈论许多开发商店支持的企业/公司客户。由于该领域的各种原因,iOS 更新有更多的阻力。

因此,在您对 iOS 13 和 SwiftUI(您绝对应该因为它很棒)感到兴奋之前,回到现实世界,在硅谷之外,这与普通消费者期望并且您将需要支持旧设备并且需要这样做,因为您会疏远太多人。

SwiftUI合并 使用 Opaque-Return-Types[= Swift 5.1 中的 46=],并且由于 Opaque-Return-Types(连同其他功能)在 Swift 5.1 中实现,并且由于其实现的性质,它们不能回部署到 Swift 5.0(不同于 DSLProperty-Wrappers),并且因为 iOS 13是最早的iOSSDK,在OS中包含Swift5.1runtime,所以问题的答案是no和SwiftUICombine 不能用于早期版本的 iOS.

除非,Apple 提供了一种将 Swift 5.1 运行时(或未来版本)与应用程序捆绑在一起的方法,就像以前 Swift 那样版本,但由于它会增加 App-size 并再次增加整个系统的开销,我怀疑这是否会发生。

可能向后兼容

Swift 5.1 尚未发布,SwiftUI 使用 opaque return types, DSL, propertyDelegate 等功能(在 WWDC 中作为 propertyWrapper) 等,在 Swift 5.1 中 可用。由于 Swift 5 是二进制稳定的,我想不可能在 Xcode11 中使用嵌入式 swift-frameworks,因此它们在 Cocoa 中具有 re-implemented 这些功能' s 核心并将它们标记为 iOS13+ 可用,直到 Swift 5.1 发布。

我的假设是基于这样一个事实,即Ordered Collection Diffing and DSL are going to be available in Swift 5.1 and have no correlations with Xcode or Apple’s eco-system, but they’re also marked as @available(iOS13,...). This means that they had to mark everything using Swift 5.1 features with the iOS availability attribute. Some of them will get removed once Swift 5.1 gets released, but we can’t be sure about SwiftUI and Combine unless Apple tells otherwise. This is also mentioned in DSL的提议:

Implementation: PR. Note that the implementation in the Xcode developer preview uses a somewhat simpler transformation than that described here. The linked PR reflects the implementation in the preview but is under active development to match this proposal.

因此当 Swift 5.1 发布时可能会取消向后不兼容限制,但确实 需要 Apple 团队 澄清。

仅适用于 ios 13 或更高版本

您仍然可以使用

附上您的 SwiftUI 代码
@available(iOS 13.0, *)

如果你还在使用 Xcode below Xcode 11 并且有 SwiftUI 代码,你可以用

包装它
#if canImport(SwiftUI)
...
#endif

这可以解决在 Xcode 以下 Xcode 11

下编译时出现的问题

正如我前面的所有人所提到的,很明显它需要 iOS 13 或更高版本。但作为一名新的 iOS 开发人员,我担心与 UIKit 相比,我应该在多大程度上采用 SwiftUI。我已经用 UIKit 构建了一些小项目,并用它取得了进步。

但是随着SwiftUI的起步,他们之间如何结合。以下 link 中的文章将所有内容放在上下文中: https://www.hackingwithswift.com/quick-start/swiftui/answering-the-big-question-should-you-learn-swiftui-uikit-or-both

我现在唯一担心的是,我注意到 Xcode 11 一个 Xcode 项目不能结合 Storyboards 和 SwiftUI。

遗憾的是不可以,SwiftUI 只允许在 iOS 13 及更高版本中使用。它是在 iOS 13 框架中引入的。在iOS 13之前,一切都是使用Obj-C框架构建的(包括Swift)。

在开发文档的右侧,显示了iOS、macOS、tvOS、watchOS等支持的版本

https://developer.apple.com/documentation/swiftui/

希望对您有所帮助!

创建两个故事板,一个使用 UIKit,另一个使用 UIHostingController 和 SwiftUI。

然后使用 if #available() 检查 OS 是否支持 SwiftUI。

    // SwiftUI
    
    let storyboard_swiftUI = UIStoryboard(name: "Main-SwiftUI", bundle: nil)
    let controller_swiftUI = storyboard_swiftUI.instantiateViewController(withIdentifier: "ViewControllerSwiftUI")

    // UIKit
    
    let storyboard_UIKit = UIStoryboard(name: "Main-UIKit", bundle: nil)
    let controller_UIKit = storyboard_UIKit.instantiateViewController(withIdentifier: "ViewControllerUIKit")

    if #available(macCatalyst 14.0, iOS 14.0, *){

        // SwiftUI

        self.present(controller_swiftUI, animated: true)

    } else {
        
        // UIKit
        
        self.present(controller_UIKit, animated: true)

    }