gpt4 book ai didi

ios - SwiftUI 通用拉动刷新 View

转载 作者:行者123 更新时间:2023-12-01 21:54:37 25 4
gpt4 key购买 nike

我有这个 CustomScrollView,它包装了我的 HomeView,如果您下拉它,它会获取新数据。它工作正常,但问题是我想在多个 View 中重复使用它,我不想为我的每个 View 创建一个副本。我曾尝试执行此操作 var rootView: View 但它会抛出一条错误消息,指出 View is not convertible to HomeView

所以有两件事女巫应该是通用的。 HomeView()HomeViewModel

知道如何实现吗?

struct CustomScrollView : UIViewRepresentable {
var width : CGFloat
var height : CGFloat

let viewModel = HomeViewModel()

func makeCoordinator() -> Coordinator {
Coordinator(self, homeViewModel: viewModel)
}

func makeUIView(context: Context) -> UIScrollView {
let control = UIScrollView()
control.refreshControl = UIRefreshControl()
control.refreshControl?.addTarget(context.coordinator, action: #selector(Coordinator.handleRefreshControl), for: .valueChanged)

let childView = UIHostingController(rootView: HomeView())

childView.view.frame = CGRect(x: 0, y: 0, width: width, height: height)

control.addSubview(childView.view)
return control
}

func updateUIView(_ uiView: UIScrollView, context: Context) { }

class Coordinator: NSObject {
var control: CustomScrollView
var homeViewModel: HomeViewModel
init(_ control: CustomScrollView, homeViewModel: HomeViewModel) {
self.control = control
self.homeViewModel = homeViewModel
}

@objc func handleRefreshControl(sender: UIRefreshControl) {
sender.endRefreshing()
homeViewModel.loadPackages()
}
}
}

最佳答案

这是可能的方法(使用 Xcode 11.4 编译)

用法:

CustomScrollView(width: 100, height: 100, 
viewModel: HomeViewMode()) {
HomeView()
}

通用类型:

protocol CustomViewModel {
func loadPackages()
}


// It is used generic ViewBuilder pattern for content
struct CustomScrollView<Content: View, VM: CustomViewModel> : UIViewRepresentable {
var width : CGFloat
var height : CGFloat

let viewModel: VM
let content: () -> Content

init(width: CGFloat, height: CGFloat, viewModel: VM, @ViewBuilder content: @escaping () -> Content) {
self.width = width
self.height = height
self.viewModel = viewModel
self.content = content
}

func makeUIView(context: Context) -> UIScrollView {
let control = UIScrollView()
control.refreshControl = UIRefreshControl()
control.refreshControl?.addTarget(context.coordinator, action: #selector(Coordinator.handleRefreshControl), for: .valueChanged)

let childView = UIHostingController(rootView: content())

childView.view.frame = CGRect(x: 0, y: 0, width: width, height: height)

control.addSubview(childView.view)
return control
}

func updateUIView(_ uiView: UIScrollView, context: Context) { }

class Coordinator: NSObject {
var control: CustomScrollView<Content, VM>
var viewModel: VM

init(_ control: CustomScrollView, viewModel: VM) {
self.control = control
self.viewModel = viewModel
}

@objc func handleRefreshControl(sender: UIRefreshControl) {
sender.endRefreshing()
viewModel.loadPackages()
}
}
}

关于ios - SwiftUI 通用拉动刷新 View ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61371525/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com