为什么swift视图不使用UIKit更新?
我有带动画的swiftUI选项卡栏,还有包含此swiftUI视图的UITabbarViewController 迅捷为什么swift视图不使用UIKit更新?,swift,swiftui,uikit,tabbar,Swift,Swiftui,Uikit,Tabbar,我有带动画的swiftUI选项卡栏,还有包含此swiftUI视图的UITabbarViewController 迅捷 struct MainTabBarView: View { @ObservedObject var viewModel: MainTabBarViewModel var body: some View { VStack { HStack(spacing: 0) { TabItem(curr
struct MainTabBarView: View {
@ObservedObject var viewModel: MainTabBarViewModel
var body: some View {
VStack {
HStack(spacing: 0) {
TabItem(currentIndex: $viewModel.index, tabIndex: 0, tab: .home)
Spacer()
TabItem(currentIndex: $viewModel.index, tabIndex: 1, tab: .search)
Spacer()
TabItem(currentIndex: $viewModel.index, tabIndex: 2, tab: .library)
}.padding(.top, 8).padding(.leading, 28).padding(.trailing, 28)
.padding(.bottom, 8)
.frame(width: UIScreen.main.bounds.width)
.animation(.easeIn(duration: 0.2))
}
UITABBARVIEW控制器:
final class MainTabBarViewController: UITabBarController, Navigatable {
private var viewModel = MainTabBarViewModel()
// MARK: - Lifecycle
override func viewDidLoad() {
super.viewDidLoad()
bindViewModel()
}
override func viewDidLoad() {
super.viewDidLoad()
configTabBarView()
}
private func configTabBarView() {
let view = UIHostingController(rootView: MainTabBarView(viewModel: viewModel))
addChild(child)
tabBar.addSubview(view.view)
view.didMove(toParent: self)
tabBar.setValue(true, forKey: "hidesShadow")
view.view.snp.makeConstraints { make in
make.leading.trailing.top.equalToSuperview()
make.height.equalTo(100)
}
}
视图模型:
final class MainTabBarViewModel: NSObject, ObservableObject {
@Published var index: Int = 0
}
这是带有选项卡的自定义视图的代码。
当我按tab->index from viewModel在该视图中更改,然后
struct TabItem: View {
@Binding var currentIndex: Int
var tabIndex: Int
var isCurrentTab: Bool {
return currentIndex == tabIndex
}
var tab: Tabs
var body: some View {
HStack {
Image(uiImage: tab.icon).resizable().frame(width: 25, height: 25, alignment: /*@START_MENU_TOKEN@*/.center/*@END_MENU_TOKEN@*/)
.foregroundColor(isCurrentTab ? R.color.primaryColor()!.swiftUI : R.color.grayScaleDark()!.swiftUI)
Text(isCurrentTab ? tab.title : "").font(Font(R.font.poppinsRegular(size: 16)! as CTFont))
.foregroundColor(isCurrentTab ? R.color.primaryColor()!.swiftUI : R.color.grayScaleDark()!.swiftUI)
}.padding(15)
.onTapGesture {
self.currentIndex = tabIndex
logWarn(String(tabIndex))
}
.background(self.tabIndex == currentIndex ? Color(R.color.pink()!) : Color.white)
.frame(height: 44.0)
.cornerRadius(22.0)
.clipped()
}
}
索引正在更改,但选项卡不更新视图的问题。看起来,视图没有更新。虽然编译给定代码会有帮助,但我认为我已经拼凑出一个解决方案,允许当前索引保留在
MainTabBarViewModel
中,前提是它打算在将来保存其他内容。我还假设TabItem
应该足够通用,它不必特别依赖于MainTabVarViewModel
我的想法是在创建TabItem
时提供当前索引的关键路径。如果不是因为TabItem
更新了当前索引这一事实,那么就足够简单了。但是,因为它确实更新了它,所以在ontapsignate
闭包中,编译器抱怨它无法通过键路径进行写入,因为self
是不可变的。所以我用大卫·惠勒(David Wheeler)召唤鬼魂,尝试通过TabItem.init
中保存的闭包来完成。。。它不存在,所以添加它是解决方案的一部分
第一个TabItem
成为通用项:
struct选项卡项:视图{
@ObservedObject变量视图模型:TabBarViewModel
let indexKeyPath:WritableKeyPath
让tapClosure:(Int)->Void
//@Binding var currentIndex:Int
var currentIndex:Int{viewModel[keyPath:indexKeyPath]}
...
init(CurrentIndexinViewModel:TabBarViewModel,在indexKeyPath:WritableKeyPath,tabIndex:Int,tab:Tabs)
{
self.viewModel=viewModel
self.indexKeyPath=indexKeyPath
self.tabIndex=tabIndex
self.tab=tab
self.tapClosure={self.viewModel[keyPath:indexKeyPath]=$0}
}
因此,TabItem
中的所有内容都将编译(在删除对未提供代码的引用之后),除了正文中的此位
.ontaps手势{
currentIndex=tabIndex
打印(字符串(选项卡索引))
}
我将其更改为使用在init
中保存的闭包:
.ontaps手势{
tapClosure(tabIndex)
打印(字符串(选项卡索引))
}
然后在MainTabBarView
的body
中创建一个TabItem
将从此更改:
TabItem(当前索引:$viewModel.index,tabIndex:0,tab:.home)
对此
TabItem(currentIndexIn:viewModel,at:\.index,tabIndex:0,tab:.home)
由于有太多的代码缺失,我无法编译和测试它,这有点猜测。我剔除缺失的代码只是为了消除错误,所以我可以说,至少这个解决方案可以编译。它需要在实际应用程序中应用和测试,以验证它是否有效
无论如何,假设它确实起作用,这个解决方案仍然允许将索引保留在一个可观察对象中,而不依赖该对象的特定类型。您缺少了很多必要的代码,以便有人能够测试此结果。我只是想我不熟悉
TabItem
。我熟悉TabView
。除非TabItem
是SwiftUI的一个新添加项,并且没有找到它(我只是搜索了一下,结果空手而归),我认为查看它的定义很重要。@ChipJarred这是我自己的观点。我添加了此代码。请看上面,可能我有刷新问题,但它看起来像是同一个代码。您是否添加了一个代码片段,说明如何定义TabItem
?@ChipJarred我用我的选项卡添加了代码)您能再看一次吗