1

Using SwiftUI, how can I achieve something like the Apple Music app? they have a now playing bar that is visible across all tabs. Is this something I can recreate using SwiftUI?

music

I have tried using overlay:

TabView {
    NavigationStack(path: $coordinator.path) {
        ContentView()
            .navigationDestination(for: Destination.self) { destination in
                ViewFactory.viewForDestination(destination)
            }
    }
    .tabItem {
        Text("Home")
    }
    DownloadsView()
        .tabItem {
            Text("Downloads")
        }
}
.overlay(alignment: .bottom) {
    MediaControlBar()
}

but the bar overlaps the tabs and does not adjust the content of the views

EDIT:

I am a bit closer with this custom implementation, but it will not let me switch views:

struct MyTabView: View {
    var items: [MyTabItem]
    @State var selectedItem: MyTabItem
    var body: some View {
        VStack {
            selectedItem.view
            MediaControlBar()
            Picker("tabs", selection: $selectedItem) {
                ForEach(items) { item in
                    Text(item.title)
                }
            }
            .pickerStyle(.segmented)
        }
    }
    struct MyTabItem: Hashable, Equatable, Identifiable {
        static func == (lhs: MyTabView.MyTabItem, rhs: MyTabView.MyTabItem) -> Bool {
            lhs.id == rhs.id
        }
        func hash(into hasher: inout Hasher) {
            hasher.combine(id)
        }
        let id = UUID()
        let view: AnyView
        let title: String
    }
}
Halpo
  • 2,982
  • 3
  • 25
  • 54

1 Answers1

1

Toolbar is the perfect element for your needs. You can declare its placement as .bottomBar which means it will always stay attached to the TabBar and share its transparency. It also works correctly with ScrollViews:

var body: some View {
    TabView {
        Group {
            NavigationStack {
                Spacer()
                    .navigationTitle("Home")
            }
            .tabItem {
                Image(systemName: "house")
                Text("Home")
            }
            NavigationStack {
                Spacer()
                    .navigationTitle("Dowloads")
            }
            .tabItem {
                Image(systemName: "arrow.down.circle")
                Text("Downloads")
            }
        }
        .toolbar {
            ToolbarItem(placement: .bottomBar) {
                HStack {
                    Text("This is a toolbar")
                       .bold()
                    Spacer()
                    Image(systemName: "play.fill")
                    Image(systemName: "forward.fill")
                }
            }
        }
    }
}

Toolbar in action 1 Toolbar in action 2

LuLuGaGa
  • 13,089
  • 6
  • 49
  • 57