ios SwiftUI TabView未在“更多”菜单中显示编辑按钮

kqqjbcuj  于 2023-08-08  发布在  iOS
关注(0)|答案(1)|浏览(121)

在TabView中有5个以上的选项卡会添加一个“更多”选项卡,其中包含无法在选项卡栏中放置的选项卡。在UIKit中,UITabBarControllers也有这个功能,另外还有一个内置的编辑按钮作为右导航栏项,这将允许用户更改顺序。但SwiftUI的TabView似乎没有这个功能。如何启用它?
这里有一些基本的代码。

struct TabBarView: View {
    @State var tabs = Tabs.allCases
    
    var body: some View {
        TabView {
            ForEach(tabs) { tab in
                NavigationView {
                    tab.body.navigationTitle(tab.rawValue)
                }.tabItem {
                    Label(tab.rawValue, systemImage: tab.systemImage)
                }
            }
        }
    }
}

字符串
作为参考,这是我正在使用的Tabs枚举。

enum Tabs: String, Identifiable, CaseIterable {
    case songs = "Songs"
    case albums = "Albums"
    case artists = "Artists"
    case playlists = "Playlists"
    case genres = "Genres"
    case compilations = "Compilations"
    case composers = "Composers"
    
    var systemImage: String {
        switch self {
        case .songs: return "music.note"
        case .albums: return "square.stack"
        case .artists: return "music.mic"
        case .playlists: return "music.note.list"
        case .genres: return "guitars"
        case .compilations: return "person.2.crop.square.stack"
        case .composers: return "music.quarternote.3"
        }
    }
    
    @ViewBuilder var body: some View {
        switch self {
        case .songs: SongListView()
        case .albums: Text("Unimplemented")
        case .artists: Text("Unimplemented")
        case .playlists: PlaylistsView()
        case .genres: Text("Unimplemented")
        case .compilations: Text("Unimplemented")
        case .composers: Text("Unimplemented")
        }
    }
    
    var id: String { rawValue }
}


我已经尝试添加.moveDisabled(false)并让TabView引用这些标签作为绑定。我不确定在TabView上下文中这两个的预期用途。

struct TabBarView: View {
    @State var tabs = Tabs.allCases
    
    var body: some View {
        TabView(selection: $tabs) {
            ForEach(tabs) { tab in
                NavigationView {
                    tab.body.navigationTitle(tab.rawValue)
                }.tabItem {
                    Label(tab.rawValue, systemImage: tab.systemImage)
                }.moveDisabled(false)
            }
        } // .moveDisabled(false)
    }
}


What I'm seeing
What I want to see (what I see in UIKit by default)
我试着在谷歌上搜索了很多,但找不到任何人谈论它。而且我发誓编辑按钮在一两年前做的时候就在那里。
如何启用SwiftUI TabView的更多菜单上的编辑按钮?

mpbci0fu

mpbci0fu1#

我发誓一两年前我做的时候编辑按钮就在那里了。
事实上,正如this Medium article所示,Edit按钮确实存在。然而,同一篇文章还说,编辑按钮实际上并不尊重标签的新顺序,只是重置自己回来。
从文章中,他们提出的解决方案是简单地将UITabController Package 成UIViewControllerRepresentable
在这里引用他们的代码:

fileprivate struct UITabBarControllerWrapper: UIViewControllerRepresentable {
    var viewControllers: [UIViewController]
    
    func makeUIViewController(context: UIViewControllerRepresentableContext<UITabBarControllerWrapper>) -> UITabBarController {
        let tabBar = UITabBarController()
        
        // Configure Tab Bar here, if needed
        
        return tabBar
    }
    
    func updateUIViewController(_ uiViewController: UITabBarController, context: UIViewControllerRepresentableContext<UITabBarControllerWrapper>) {
        uiViewController.setViewControllers(self.viewControllers, animated: true)
    }
    
    func makeCoordinator() -> Coordinator {
        return Coordinator(self)
    }
    
    class Coordinator: NSObject {
        var parent: UITabBarControllerWrapper
        
        init(_ controller: UITabBarControllerWrapper) {
            self.parent = controller
        }
    }
}

struct UITabBarWrapper: View {
    var controllers: [UIHostingController<TabBarElement>]
    
    @MainActor
    init(_ elements: [TabBarElement]) {
        self.controllers = elements.enumerated().map {
            let hostingController = UIHostingController(rootView: $1)
            
            hostingController.tabBarItem = UITabBarItem(
                title: $1.tabBarElementItem.title,
                image: UIImage.init(systemName: $1.tabBarElementItem.systemImageName),
                tag: $0 // 4
            )
            
            return hostingController
        }
    }
    
    var body: some View {
        UITabBarControllerWrapper(viewControllers: self.controllers)
    }
}

struct TabBarElementItem {
    var title: String
    var systemImageName: String
}

protocol TabBarElementView: View {
    associatedtype Content
    
    var content: Content { get set }
    var tabBarElementItem: TabBarElementItem { get set }
}

struct TabBarElement: TabBarElementView {
    internal var content: AnyView
    
    var tabBarElementItem: TabBarElementItem
    
    init<Content: View>(tabBarElementItem: TabBarElementItem,
         @ViewBuilder _ content: () -> Content) {
        self.tabBarElementItem = tabBarElementItem
        self.content = AnyView(content())
    }
    
    var body: some View { self.content }
}

字符串
在你的情况下,你可以这样使用它:

var body: some View {
    UITabBarWrapper(Tabs.allCases.map { t in
        TabBarElement(tabBarElementItem: .init(title: t.rawValue, systemImageName: t.systemImage)) {
            NavigationView {
                t.body.navigationTitle(t.rawValue)
            }
        }
    })
    
}

相关问题