首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >在SwiftUI中限制拖动到圆形边界

在SwiftUI中限制拖动到圆形边界
EN

Stack Overflow用户
提问于 2020-01-20 12:59:38
回答 1查看 2.2K关注 0票数 5

我想在SwiftUI中实现循环拖动,但不确定实现它的最佳方法。

下面是基本的拖动代码--有一个小的可拖圆,我想把它限制在updating阶段的DragGesture中较大的循环的边界上。此刻,黑色的圆圈在整个视野中都是可拉的。

代码语言:javascript
运行
复制
import SwiftUI

struct ContentView: View {

  @State private var position = CGSize.zero
  @GestureState var dragOffset: CGSize = .zero

  private var dragRadius: CGFloat = 200.0

    var body: some View {
      ZStack {
        Circle()
          .fill(Color.red)
          .frame(width: dragRadius, height: dragRadius)

        Circle()
          .fill(Color.black)
          .frame(width: dragRadius / 4, height: dragRadius / 4)
          .offset(x: position.width + dragOffset.width, y: position.height + dragOffset.height)
          .gesture(
            DragGesture()
              .updating($dragOffset, body: { (value, state, transaction) in
                // Need to clamp to circular bounds here??
                state = value.translation
              })
              .onEnded({ (value) in
                self.position.height += value.translation.height
                self.position.width += value.translation.width
              })
          )
      }
    }
}

我想知道是用三角学和极坐标来计算距离中心的距离,并在被拖动的圆的方向上限制半径,还是有更容易的方法让SwiftUI“看到”一个视图的圆形边界?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-01-20 16:28:17

实现这一点的代码并不多。我只是计算点之间的距离(在that question中做了一个扩展),并使用这个系数使实际距离变短。这就是你想达到的目标吗?

代码语言:javascript
运行
复制
import SwiftUI

extension CGPoint {
    func distance(to point: CGPoint) -> CGFloat {
        return sqrt(pow((point.x - x), 2) + pow((point.y - y), 2))
    }
}

struct ContentView: View {

    @State private var position = CGPoint(x: 100, y: 100)
    private var dragDiametr: CGFloat = 200.0
    var body: some View {

    return
        VStack{
            Text("current position = (x: \(Int(position.x)), y: \(Int(position.y)))")
            Circle()
              .fill(Color.red)
              .frame(width: dragDiametr, height: dragDiametr)
              .overlay(
                Circle()
                  .fill(Color.black)
                  .frame(width: dragDiametr / 4, height: dragDiametr / 4)
                  .position(x: position.x, y: position.y)
                  .gesture(DragGesture()
                  .onChanged(){value in
                    let currentLocation = value.location
                    let center = CGPoint(x: self.dragDiametr/2, y: self.dragDiametr/2)
                    let distance = center.distance(to:currentLocation)
                    if distance > self.dragDiametr / 2 {
                        let k = (self.dragDiametr / 2) / distance
                        let newLocationX = (currentLocation.x - center.x) * k+center.x
                        let newLocationY = (currentLocation.y - center.y) * k+center.y
                        self.position = CGPoint(x: newLocationX, y: newLocationY)
                    }else{
                        self.position = value.location
                    }
                  })
              )
        }
    }
}
票数 13
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59823840

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档