Skip to content

ScrollViewWithStickyHeader bug #22

Closed
@NMan1

Description

@NMan1

I am experiencing an odd issue with the sticky header. On the first load of the view the sticky header wont activate; as I scroll down the view it fully disappears. Yet, if I move to a different view and then back (or any process which reloads/redraws the view containing the ScrollViewWithStickyHeader) then the sticky header works as expected.

Its possible this bug is produced as a product of my code, though I'm failing to find where it could be from.

Relevant code snippets & video:


struct homeView: View {
    @EnvironmentObject var authManager: AuthManager

    @EnvironmentObject var firestoreUser: FirestoreUser

    @EnvironmentObject var postsManager: PostsManager

    @State private var pageSelection: Int = 1

    @State private var offset = CGPoint.zero

    @State private var visibleRatio = CGFloat.zero

    func handleOffset(_ scrollOffset: CGPoint, visibleHeaderRatio: CGFloat) {
        self.offset = scrollOffset
        self.visibleRatio = visibleHeaderRatio
    }

    func header() -> some View {
        ZStack(alignment: .bottomLeading) {
            Color.white

            TabBarView(
                tabbarItems: ["world", "explore", "follow"],
                selectedIndex: $pageSelection
            )
            .padding(
                .bottom,
                getTopSafeAreaHeight() - (getTopSafeAreaHeight() / 1.33)
            )
            .opacity(visibleRatio)
        }
    }

    var body: some View {
        ScrollViewWithStickyHeader(
            header: header,
            headerHeight: 50,
            onScroll: handleOffset
        ) {
            switch pageSelection {
            case 0:
                worldView()
            case 1:
                exploreView()
                    .padding(.top, 10)
            case 2:
                followView()
                    .padding(.top, 10)
            default:
                EmptyView()
            }
        }
        .scrollIndicators(.hidden)
        .scrollDisabled(pageSelection == 0)
    }
}

struct TabBarView: View {
    var tabbarItems: [String]

    @Binding var selectedIndex: Int
    @Namespace private var menuItemTransition

    var body: some View {
        HStack {
            Spacer()

            TabbarItem(
                name: tabbarItems[0],
                isActive: selectedIndex == 0,
                namespace: menuItemTransition
            )
            .onTapGesture {
                withAnimation(.easeIn) {
                    selectedIndex = 0
                }
            }

            Spacer()

            TabbarItem(
                name: tabbarItems[1],
                isActive: selectedIndex == 1,
                namespace: menuItemTransition
            )
            .onTapGesture {
                withAnimation(.easeIn) {
                    selectedIndex = 1
                }
            }

            Spacer()

            TabbarItem(
                name: tabbarItems[2],
                isActive: selectedIndex == 2,
                namespace: menuItemTransition
            )
            .onTapGesture {
                withAnimation(.easeIn) {
                    selectedIndex = 2
                }
            }

            Spacer()
        }
        .frame(width: UIScreen.main.bounds.width)
    }
}

struct TabbarItem: View {
    var name: String
    var isActive: Bool = false
    let namespace: Namespace.ID

    var body: some View {
        if isActive {
            Text(name)
                .font(.ibm(.medium, size: 16))
                .foregroundColor(.white)
                .padding(.vertical, 5)
                .padding(.horizontal, 12)
                .background(Capsule().foregroundColor(.black))
                .matchedGeometryEffect(id: "highlightmenuitem", in: namespace)
        } else {
            Text(name)
                .font(.ibm(.medium, size: 16))
                .foregroundColor(.black)
                .padding(.vertical, 5)
                .padding(.horizontal, 12)

        }
    }
}

Thanks for a fantastic library 🥂

Simulator.Screen.Recording.-.iPhone.16.Pro.-.2025-01-08.at.20.41.37.1.mp4

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions