Post

Replies

Boosts

Views

Activity

How to recreate Apple Music mini player transition in SwiftUI
Hello, I am building an audio player app in SwiftUI and trying to recreate the behavior of Apple Music's mini player and full player. I'm struggling to get the animation to seamlessly transition between the mini player and the full player. Currently, it feels disconnected and doesn't resemble the smooth animation seen in Apple Music. What I want to achieve: Full player that expands/collapses from/to the mini player Smooth artwork transition between both states Drag down to collapse the full player Support both newer APIs like tabViewBottomAccessory and older iOS versions Questions: What is the best way to build this transition in SwiftUI? Should I use matchedGeometryEffect or something else? Should this be a custom container instead of fullScreenCover? How would you support both new and older iOS versions? What is the best way to implement drag to dismiss? Thanks for any help! Example code: struct ContentView: View { @State private var isFullPlayerPresented = false var body: some View { TabView { Tab("Home", systemImage: "house") { Text("Home") .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.green) } Tab("Library", systemImage: "rectangle.stack.fill") { Text("Library") .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.brown) } } .tabViewBottomAccessory(isEnabled: !isFullPlayerPresented) { MiniPlayerView(isFullPlayerPresented: $isFullPlayerPresented) } .fullScreenCover(isPresented: $isFullPlayerPresented) { // Maybe it's not a full screen cover presentation in Apple Music? FullPlayerView(isFullPlayerPresented: $isFullPlayerPresented) } } } Mini player: struct MiniPlayerView: View { @Binding var isFullPlayerPresented: Bool var body: some View { Button { isFullPlayerPresented = true } label: { HStack { Image(systemName: "photo") .resizable() .scaledToFit() .frame(width: 30, height: 30) .clipShape(.rect(cornerRadius: 8)) Spacer() Text("Tap to open full player") Spacer() Button("", systemImage: "play.fill", action: {}) } .padding(.horizontal) .padding(.vertical, 4) } .foregroundStyle(.white) } } Full player: struct FullPlayerView: View { @Binding var isFullPlayerPresented: Bool var body: some View { // This art work needs to snaps to the artwork in mini player Image(systemName: "photo") .resizable() .scaledToFit() .frame(width: 250, height: 250) .clipShape(.rect(cornerRadius: 20)) .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.red) .overlay(alignment: .topTrailing) { Button(role: .close) { isFullPlayerPresented = false } .foregroundStyle(.white) .padding() } } }
0
0
111
1d
How to recreate Apple Music mini player transition in SwiftUI
Hello, I am building an audio player app in SwiftUI and trying to recreate the behavior of Apple Music's mini player and full player. I'm struggling to get the animation to seamlessly transition between the mini player and the full player. Currently, it feels disconnected and doesn't resemble the smooth animation seen in Apple Music. What I want to achieve: Full player that expands/collapses from/to the mini player Smooth artwork transition between both states Drag down to collapse the full player Support both newer APIs like tabViewBottomAccessory and older iOS versions Questions: What is the best way to build this transition in SwiftUI? Should I use matchedGeometryEffect or something else? Should this be a custom container instead of fullScreenCover? How would you support both new and older iOS versions? What is the best way to implement drag to dismiss? Thanks for any help! Example code: struct ContentView: View { @State private var isFullPlayerPresented = false var body: some View { TabView { Tab("Home", systemImage: "house") { Text("Home") .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.green) } Tab("Library", systemImage: "rectangle.stack.fill") { Text("Library") .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.brown) } } .tabViewBottomAccessory(isEnabled: !isFullPlayerPresented) { MiniPlayerView(isFullPlayerPresented: $isFullPlayerPresented) } .fullScreenCover(isPresented: $isFullPlayerPresented) { // Maybe it's not a full screen cover presentation in Apple Music? FullPlayerView(isFullPlayerPresented: $isFullPlayerPresented) } } } Mini player: struct MiniPlayerView: View { @Binding var isFullPlayerPresented: Bool var body: some View { Button { isFullPlayerPresented = true } label: { HStack { Image(systemName: "photo") .resizable() .scaledToFit() .frame(width: 30, height: 30) .clipShape(.rect(cornerRadius: 8)) Spacer() Text("Tap to open full player") Spacer() Button("", systemImage: "play.fill", action: {}) } .padding(.horizontal) .padding(.vertical, 4) } .foregroundStyle(.white) } } Full player: struct FullPlayerView: View { @Binding var isFullPlayerPresented: Bool var body: some View { // This art work needs to snaps to the artwork in mini player Image(systemName: "photo") .resizable() .scaledToFit() .frame(width: 250, height: 250) .clipShape(.rect(cornerRadius: 20)) .frame(maxWidth: .infinity, maxHeight: .infinity) .background(.red) .overlay(alignment: .topTrailing) { Button(role: .close) { isFullPlayerPresented = false } .foregroundStyle(.white) .padding() } } }
Replies
0
Boosts
0
Views
111
Activity
1d