如何复刻Safari标签页的平滑缩放过渡动画效果?
问题:内嵌浏览器多标签页缩放动画中WebView内容保持静态的实现
我正在开发一款内嵌浏览器,希望支持多标签页功能。作为初始方案,我尝试复刻Safari的卡片网格UI/UX。目前想实现点击卡片时,像Safari那样平滑缩放至全屏的过渡动画,但无法做到缩放过程中WebView内容保持静态——当前WebView会随视图尺寸变化重新渲染,视口也会被调整。
以下是相关代码:
struct CardGridView: View { @Namespace var animation @State var selectedIndex: Int? @State var viewModels: [CardGridViewModel] private let gridItemLayout = [GridItem(.flexible()), GridItem(.flexible())] var body: some View { NavigationStack { ZStack { ScrollView { LazyVGrid(columns: gridItemLayout, spacing: 0) { ForEach(Array(viewModels.enumerated()), id: \.offset) { index, viewModel in CardView(title: viewModel.title, color: viewModel.color) .matchedGeometryEffect(id: index, in: animation) .frame(width: 175, height: 280) .padding() .scaleEffect(selectedIndex == nil || selectedIndex == index ? 1 : 0.75) // Other cards will scale down slightly while selected card grows .onTapGesture { withAnimation { selectedIndex = index } } .overlay { // Card's close button VStack { HStack(spacing: 0) { Spacer() Button { removeCard(at: index) } label: { Image(systemName: "x.circle.fill") .font(.system(size: 20)) .tint(.primary) } .padding(.top, 4) .padding(.trailing, 4) } Spacer() } .padding() } } } } .onAppear { selectedIndex = 0 // Default to DetailView of first item in array } .navigationTitle("Card View") .navigationBarTitleDisplayMode(.inline) if let selectedIndex { // Show DetailView once a card is selected DetailView(title: viewModels[selectedIndex].title, color: viewModels[selectedIndex].color) .matchedGeometryEffect(id: selectedIndex, in: animation) .frame(maxWidth: .infinity, maxHeight: .infinity) .ignoresSafeArea() } } } } }
Safari标签页动画示例:
内容的提问来源于stack exchange,提问作者JimmyJammed
相关产品推荐
相关产品推荐

