📜  SwifUI 调用协调器中的函数 (1)

📅  最后修改于: 2023-12-03 14:47:48.336000             🧑  作者: Mango

SwiftUI 调用协调器中的函数

在 SwiftUI 中,协调器(Coordinator)是 View 和外部世界(比如 UIKit 或者 AppKit)之间通信的桥梁。我们可以在协调器中监听和响应 View 的事件,同时也可以从协调器中调用外部世界的方法。

本文将介绍如何在 SwiftUI 中调用协调器中的函数。

步骤

以下是实现的步骤:

  1. 定义一个 Coordinator 类,继承自 NSObjectUIImagePickerControllerDelegate/UINavigationControllerDelegate(取决于你是否需要访问相册);
  2. Coordinator 中实现你需要调用的函数;
  3. View 中创建一个协调器实例;
  4. 将协调器实例作为 View 的 coordinator 属性;
  5. 调用协调器中的函数。

下面是详细的具体实现。

实现
定义一个协调器

我们首先来看一个简单的例子,在这个例子中我们将使用协调器打印出相机拍摄的图片。

class CameraCoordinator: NSObject, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
    
    var parent: CameraView // CameraView 是我们后面创建的 View
    
    init(_ parent: CameraView) {
        self.parent = parent
    }
    
    // MARK: - UIImagePickerControllerDelegate

    func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
        guard let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage else {
            return
        }
        print("Image captured!")
        // 这里可以对图片进行进一步的处理,比如将图片发送到服务器上。
    }

    func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {
        print("Canceled!")
        self.parent.presentationMode.wrappedValue.dismiss()
    }
}

在上面的代码中,我们继承自 UIImagePickerControllerDelegateUINavigationControllerDelegate,这样我们就可以访问相机和相册了。在 init 方法中我们将 parent 绑定到 CameraView。在 imagePickerControllerimagePickerControllerDidCancel 方法中我们打印出相应的消息。

imagePickerControllerDidCancel 中我们还添加了一个方法,该方法用于关闭相机视图。

创建一个 View

接下来,我们来创建一个 View,这个视图将用于打开相机拍摄一张照片。

struct CameraView: UIViewControllerRepresentable {
    
    @Environment(\.presentationMode) var presentationMode
    
    func makeUIViewController(context: UIViewControllerRepresentableContext<CameraView>) -> UIImagePickerController {
        let picker = UIImagePickerController()
        picker.delegate = context.coordinator
        picker.sourceType = .camera
        picker.allowsEditing = false
        return picker
    }

    func updateUIViewController(_ uiViewController: UIImagePickerController, context: UIViewControllerRepresentableContext<CameraView>) {}

    func makeCoordinator() -> CameraCoordinator {
        CameraCoordinator(self)
    }
}

在上面的代码中,我们实现了 UIViewControllerRepresentable 协议。在 makeUIViewController() 方法中,我们创建了一个 UIImagePickerController 实例,并将 delegate 属性设置为 context.coordinator,这意味着我们可以从协调器中调用相应的函数。

makeCoordinator() 方法中,我们返回了一个 CameraCoordinator 实例。

最后,在 presentationMode 中添加了一个属性,该属性用于关闭相机视图。

调用协调器中的函数

我们已经在协调器中实现了需要调用的函数,现在我们需要在 View 中通过协调器来调用那些函数。

像这样:

struct CameraView: UIViewControllerRepresentable {
    
    @Environment(\.presentationMode) var presentationMode

    func makeUIViewController(context: UIViewControllerRepresentableContext<CameraView>) -> UIImagePickerController {
        let picker = UIImagePickerController()
        picker.delegate = context.coordinator
        picker.sourceType = .camera
        picker.allowsEditing = false
        return picker
    }

    func updateUIViewController(_ uiViewController: UIImagePickerController, context: UIViewControllerRepresentableContext<CameraView>) {}

    func makeCoordinator() -> CameraCoordinator {
        CameraCoordinator(self)
    }

    func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
        self.coordinator?.imagePickerController(picker, didFinishPickingMediaWithInfo: info)
    }
}

在上面的代码中,我们添加了一个函数 imagePickerController,并在方法中通过 self.coordinator?.imagePickerController(picker, didFinishPickingMediaWithInfo: info) 调用了协调器中的函数。我们将 pickerinfo 两个参数传递给了协调器中对应的函数。

结论

本文介绍了如何在 SwiftUI 中调用协调器中的函数。协调器是 SwiftUI 和外部世界之间通信的桥梁,它可以让我们更加灵活地实现复杂的交互逻辑。

在实际开发中,我们可以使用协调器来调用系统 API、第三方框架的 API、与其他组件进行通信等等。协调器是 SwiftUI 开发中一个非常重要的组成部分,希望读者可以熟练掌握。