JustPaste.it

SwiftUI TabView based Carousel

struct WildlifeCarouselView: View {

    var imageNames: [String] {

        Array(0...4).map {"wildlife-\($0)"}

    }

    

    var titles: [String] {

        ["American Eagle", "Tiger", "Lion", "Ram", "Hummingbird"]

    }

    

    @State var currentTabIndex = 0

    

    var body: some View {

        VStack(spacing: 0) {

            ZStack {

                GeometryReader(content: { screen in

                    

                    Image(imageNames[currentTabIndex])

                        .resizable()

                        .aspectRatio(contentMode: .fill)

                        .frame(width: screen.size.width, height: 320)

                        .clipped()

 

                    TabView(selection: $currentTabIndex) {

                        Spacer().tag(-1)

                        ForEach(titles.indices, id: \.self) { index in

                            GeometryReader { geometry in

                                VStack {

                                    Spacer()

                                    Text(titles[index])

                                        .font(.largeTitle.bold())

                                        .foregroundStyle(.white)

                                        .frame(width: geometry.size.width)

                                        .frame(height: 80)

                                        .opacity(1.0 - (min(abs(geometry.frame(in: .global).origin.x)/100.0, 1.0)))

                                }.tag(index)

                            }

                        }

                        Spacer().tag(titles.count)

                    }

                    .tabViewStyle(.page)

                    .indexViewStyle(.page(backgroundDisplayMode: .never))

                    .onChange(of: currentTabIndex) {

                        if currentTabIndex == titles.count {

                            currentTabIndex = 0

                        } else if currentTabIndex == -1 {

                            currentTabIndex = titles.count - 1

                        }

                    }

                    .frame(height: 320)

                    .accessibilityIdentifier("CarouselView")

                })

            }

            .frame(height: 320)

 

            Spacer()

        }

        .background(.black)

        .ignoresSafeArea()

    }

}