# Rotate with DragGesture

Published by @SoNiceInfo at 6/24/2020

`DragGesture`

can only get the coordinates of the moved position or distance. how to get the rotation angle and how to implement it, which is necessary to handle the rotation using atan2.

## Calculate the angle of rotation

You need to understand the how to calculate the rotation angle before implementing the rotation in `DragGesture`

In `DragGesture`

, you need to calculate the rotation angle yourself.

The figure shows the idea needed to find the rotation from which can be obtained with `location:CGPoint`

from `DragGesture`

.

Blue is the coordinate system of `DragGesture`

, and orange is the coordinate of the rotating body It is necessary to find the rotation angle θ in the system.

the point P become `(v.location.x - self.length / 2, self.length / 2 - v.location.y)`

with them and the diameter of the rotating body `self.length`

.

And the rotation angle is θ=arctan(v.location.x - self.length / 2 , self.length / 2 - v.location.y) * 180 * π (θ < 0 ? θ += 360).

## Implementing with `DragGesture`

Part 1

Rotation angle of the object = Rotation angle of the gesture

This is an implementation method where the angle is reset each time the object is rotated.

We use `atan2`

(arc tangent) to find the rotation angle θ and pass it to `rotationEffect`

.

```
//
// ContentView.swift
//
import SwiftUI
struct ContentView: View {
@State private var angle: CGFloat = 0
@State private var length : CGFloat = 400
var body: some View {
Image("ice")
.resizable()
.aspectRatio(contentMode: .fill)
.clipShape(Circle())
.frame(width: length, height: length)
.rotationEffect(.degrees(Double(self.angle)))
.gesture(DragGesture()
.onChanged{ v in
self.angle = atan2(v.location.x - self.length / 2, self.length / 2 - v.location.y) * 180 / .pi
if (self.angle < 0) { self.angle += 360 }
}
)
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
```

## Implementing with `DragGesture`

Part 2

Rotation angle of the object += Rotation angle of the gesture

I'll also show you how to implement it by adding a rotation angle each time you rotate the object. `atan2`

(arc-tangent) for the starting point to find the difference between the rotation angle and the rotation angle θ of the point being moved.

When the rotation is complete, save the final angle in `lastAngle`

and add it to the rotation angle difference for the next rotation.

```
//
// ContentView.swift
//
import SwiftUI
struct ContentView: View {
@State private var angle: CGFloat = 0
@State private var lastAngle: CGFloat = 0
@State private var length : CGFloat = 400
var body: some View {
Image("ice")
.resizable()
.aspectRatio(contentMode: .fill)
.clipShape(Circle())
.frame(width: length, height: length)
.rotationEffect(.degrees(Double(self.angle)))
.gesture(DragGesture()
.onChanged{ v in
var theta = (atan2(v.location.x - self.length / 2, self.length / 2 - v.location.y) - atan2(v.startLocation.x - self.length / 2, self.length / 2 - v.startLocation.y)) * 180 / .pi
if (theta < 0) { theta += 360 }
self.angle = theta + self.lastAngle
}
.onEnded { v in
self.lastAngle = self.angle
}
)
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
```

## References

Gestures | Apple Developer Documentationgeometry - calculating angle between two points on edge of circle Swift SpriteKit - Stack Overflow