はじめに
アニメーションを持つCustom TabBarをつくる
そのためにはGeometryReader
を利用する必要がある
環境
Xcode: 13.3.1
Code
enum TabIndex {
case home, cart, profile
}
struct customTabView: View {
@State var tabindex : TabIndex
func tabCirclePostion(tabIndex: TabIndex, geometry : GeometryProxy) -> CGFloat {
switch tabIndex{
case .home:
return -(geometry.size.width/3)
case .cart:
return 0
case .profile:
return geometry.size.width/3
}
}
var body: some View {
GeometryReader { geometry in
ZStack(alignment: .bottom) {
Circle()
.frame(width: 90, height: 90)
.offset(x: self.tabCirclePostion(tabIndex: self.tabindex, geometry: geometry), y: 18)
.foregroundColor(Color.white)
VStack{
Spacer()
HStack(spacing:0) {
//Tab Items
Image(systemName: "house.fill")
.foregroundColor(self.tabindex == .home ? .black : .gray)
.font(.system(size: 24))
.scaleEffect(self.tabindex == .home ? 1.5 : 1.0)
.frame(width: geometry.size.width/3, height: 40)
.background(Color.white)
.onTapGesture {
withAnimation {
self.tabindex = .home
}
}
Image(systemName: "cart.fill")
.foregroundColor(self.tabindex == .cart ? .black : .gray)
.font(.system(size: 24))
.scaleEffect(self.tabindex == .cart ? 1.5 : 1.0)
.frame(width: geometry.size.width/3, height: 40)
.background(Color.white)
.onTapGesture {
withAnimation {
self.tabindex = .cart
}
}
Image(systemName: "person.fill")
.foregroundColor(self.tabindex == .profile ? .black : .gray)
.font(.system(size: 24))
.scaleEffect(self.tabindex == .profile ? 1.5 : 1.0)
.frame(width: geometry.size.width/3, height: 40)
.background(Color.white)
.onTapGesture {
withAnimation {
self.tabindex = .profile
}
}
}
}
}
}
.background(Color.green)
}
}
理解のためにTabItemを並べただけだが、for文で簡潔に書くこともできる。