如何将 .onHover 应用于 SwiftUI 中的单个元素
How to apply .onHover to individual elements in SwiftUI
我正在尝试在鼠标悬停时为单个项目设置动画。我遇到的问题是 每个 项目都会在鼠标悬停在某个项目上而不只是那个特定项目上时得到动画。
这是我拥有的:
struct ContentView : View {
@State var hovered = false
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) {_ in
HStack(spacing: 90) {
ForEach(0..<4) {_ in
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
self.hovered.toggle()
}
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}
它需要在每个视图的基础上更改 onHover 视图,即。存储悬停视图的一些标识符。
这是可能的解决方案。使用 Xcode 11.4.
进行测试
struct TestOnHoverInList : View {
@State var hovered: (Int, Int) = (-1, -1)
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) {i in
HStack(spacing: 90) {
ForEach(0..<4) {j in
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered == (i,j) ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
if hover {
self.hovered = (i, j) // << here !!
} else {
self.hovered = (-1, -1) // reset
}
}
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}
目前每个项目都具有动画效果,因为它们都依赖于 hovered
来查看 Circle
是否悬停在上方。为了解决这个问题,我们可以让每个圈子都有自己的 hovered
状态。
struct CircleView: View {
@State var hovered = false
var body: some View {
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
self.hovered.toggle()
}
}
}
在 ForEach
中,我们可以调用新的 CircleView
,其中每个 Circle
都有自己的真实来源。
struct ContentView : View {
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) { _ in
HStack(spacing: 90) {
ForEach(0..<4) { _ in
CircleView()
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}
我正在尝试在鼠标悬停时为单个项目设置动画。我遇到的问题是 每个 项目都会在鼠标悬停在某个项目上而不只是那个特定项目上时得到动画。 这是我拥有的:
struct ContentView : View {
@State var hovered = false
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) {_ in
HStack(spacing: 90) {
ForEach(0..<4) {_ in
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
self.hovered.toggle()
}
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}
它需要在每个视图的基础上更改 onHover 视图,即。存储悬停视图的一些标识符。
这是可能的解决方案。使用 Xcode 11.4.
进行测试struct TestOnHoverInList : View {
@State var hovered: (Int, Int) = (-1, -1)
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) {i in
HStack(spacing: 90) {
ForEach(0..<4) {j in
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered == (i,j) ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
if hover {
self.hovered = (i, j) // << here !!
} else {
self.hovered = (-1, -1) // reset
}
}
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}
目前每个项目都具有动画效果,因为它们都依赖于 hovered
来查看 Circle
是否悬停在上方。为了解决这个问题,我们可以让每个圈子都有自己的 hovered
状态。
struct CircleView: View {
@State var hovered = false
var body: some View {
Circle().fill(Color.red).frame(width: 50, height: 50)
.scaleEffect(self.hovered ? 2.0 : 1.0)
.animation(.default)
.onHover { hover in
print("Mouse hover: \(hover)")
self.hovered.toggle()
}
}
}
在 ForEach
中,我们可以调用新的 CircleView
,其中每个 Circle
都有自己的真实来源。
struct ContentView : View {
var body: some View {
VStack(spacing: 90) {
ForEach(0..<2) { _ in
HStack(spacing: 90) {
ForEach(0..<4) { _ in
CircleView()
}
}
}
}
.frame(minWidth:300,maxWidth:.infinity,minHeight:300,maxHeight:.infinity)
}
}