SwiftUI 官方教程 (九)

本文介绍了如何在 SwiftUI 中使用 UIPageViewController。通过创建自定义的 PageViewController 视图,实现页面数据源管理,利用状态跟踪页面,并添加自定义的 Page Control。教程覆盖了从创建 SwiftUI 视图到与 UIKit 框架的无缝协作的全过程。
摘要由CSDN通过智能技术生成

由于 API 变动,此文章部分内容已失效,最新完整中文教程及代码请查看 https://github.com/WillieWangWei/SwiftUI-Tutorials

微信技术群

SwiftUI 代表未来构建 App 的方向,欢迎加群一起交流技术,解决问题。

加群现在需要申请了,可以先加我微信,备注 “SwiftUI”,我会拉你进群。

UIKit 接口

SwiftUI 可与所有 Apple 平台上的现有 UI 框架无缝协作。例如我们可以在 SwiftUI view 中放置 UIKit view 和 view controllers,反之亦然。

本文将展示如何把地标从 home screen 中转换到包装 UIPageViewControllerUIPageControl 的实例。我们将使用 UIPageViewController 显示 SwiftUI view 的轮播,并使用状态变量和绑定来协调整个 UI 中的数据更新。

  • 预计完成时间:25 分钟
  • 项目文件:下载

1. 创建表示 UIPageViewController 的 View

要在 SwiftUI 中表示 UIKit view 和 view controllers,我们需要创建遵循 UIViewRepresentableUIViewControllerRepresentable 协议的类型。我们的自定义类型创建和配置它们所代表的 UIKit 类型,而 SwiftUI 管理它们的生命周期并在需要时更新它们。

1.1 创建一个新的 SwiftUI view,命名为 PageViewController.swift ,声明遵循 UIViewControllerRepresentable 协议的 PageViewController 类型。

页面的 view controller 存储了 UIViewController 实例的数组。这些是在地标之间滚动的页面。

PageViewController.swift

import SwiftUI
import UIKit

struct PageViewController: UIViewControllerRepresentable {
    var controllers: [UIViewController]
}

接下添加 UIViewControllerRepresentable 协议的两个需求。

1.2 添加一个 makeUIViewController(context:) 方法,创建一个满足需求的 UIPageViewController

SwiftUI 准备好显示 view 时,它会调用此方法一次,然后管理 view controller 的生命周期。

PageViewController.swift

import SwiftUI
import UIKit

struct PageViewController: UIViewControllerRepresentable {
    var controllers: [UIViewController]

    func makeUIViewController(context: Context) -> UIPageViewController {
        let pageViewController = UIPageViewController(
            transitionStyle: .scroll,
            navigationOrientation: .horizontal)

        return pageViewController
    }
}

1.3 添加一个 updateUIViewController(_:context:) 方法,在其中调用 setViewControllers(_:direction:animated:) 来显示数组中的第一个 view controller。

PageViewController.swift

import SwiftUI
import UIKit

struct PageViewController: UIViewControllerRepresentable {
    var controllers: [UIViewController]

    func makeUIViewController(context: Context) -> UIPageViewController {
        let pageViewController = UIPageViewController(
            transitionStyle: .scroll,
            navigationOrientation: .horizontal)

        return pageViewController
    }

    func updateUIViewController(_ pageViewController: UIPageViewController, context: Context) {
        pageViewController.setViewControllers(
            [controllers[0]], direction: .forward, animated: true)
    }
}

创建另一个 SwiftUI view 来显示我们的 UIViewControllerRepresentable view。

1.4 创建一个新的 SwiftUI view,命名为 PageView.swift,声明一个 PageViewController 作为子 view。

需要注意的是,泛型初始化方法接收一个 view 数组,并将每个 view 嵌套在 UIHostingController 中。 UIHostingController 是一个 UIViewController 的子类,表示 UIKit 上下文中的 SwiftUI view。

PageView.swift

import SwiftUI

struct PageView<Page: View>: View {
    var viewControllers: [UIHostingController<Page>]

    init(_ views: [Page]) {
        self.viewControllers = views.map { UIHostingController(rootView: $0) }
    }

    var body: some View {
        PageViewController(controllers: viewControllers)
    }
}

struct PageView_Preview: PreviewProvider {
    static var previews: some View {
        PageView()
    }
}

1.5 更新 preview provider ,传入必要的 view 数组,之后预览就会开始工作。

PageView.swift

import SwiftUI

struct PageView<Page: View>: View {
    var viewControllers: [UIHostingController<Page>]

    init(_ views: [Page]) {
        self.viewControllers = views.map { UIHostingController(rootView: $0) }
    }

    var body: some View {
        PageViewController(controllers: viewControllers)
    }
}

struct PageView_Preview: PreviewProvider {
    static var previews: some View {
        PageView(features.map { FeatureCard(landmark: $0) })
            .aspectRatio(3/2, contentMode: .fit)
    }
}

1.6 在进行下一步之前,在 canvas 中固定 PageView 的预览,所有的操作都将发生在这个 view 上。

2. 创建 View Controller 的数据源

在几个简短的步骤中,我们已经做了很多工作:PageViewController 使用 UIPageViewControllerSwiftUI view 中显示内容。现在启用滑动交互来从一个页面移动到另一个页面。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值