如何在 swift 3.0 中在 UIView 中拖动和缩放 UIImageView



我想使用 swift 3.0 在 UIView 中拖动和缩放 UIImageView,而不是在 UIViewController (self.view) 中。

在这里我声明了主视图和图像视图,

var lastScale: CGFloat = 0.0
@IBOutlet var mainView: UIView!
@IBOutlet var imageView: UIImageView!

我已经设置了平移和捏合手势以进行缩放和拖动图像视图在主视图中

let pinchGestureRecognizer = UIPinchGestureRecognizer(target: self, action: #selector(ViewController.handlePinchGesture(_:)))
    imageView.isUserInteractionEnabled = true
    imageView.addGestureRecognizer(pinchGestureRecognizer)
let panGestureRecognizer = UIPanGestureRecognizer(target: self, action: #selector(ViewController.handlePanGesture(recognizer:)))
    imageView.addGestureRecognizer(panGestureRecognizer)

平移和捏合手势功能

func handlePinchGesture(_ gestureRecognizer: UIPinchGestureRecognizer) {
    if gestureRecognizer.state == .began {
        lastScale = gestureRecognizer.scale
    }
    if gestureRecognizer.state == .began || gestureRecognizer.state == .changed {
        let currentScale: CGFloat = (gestureRecognizer.view!.layer.value(forKeyPath: "transform.scale")! as! CGFloat)
        // Constants to adjust the max/min values of zoom
        //let kMaxScale: CGFloat = 2.0
        let kMinScale: CGFloat = 1.0
        var newScale: CGFloat = 1 - (lastScale - gestureRecognizer.scale)
        //newScale = min(newScale, kMaxScale / currentScale)
        newScale = max(newScale, kMinScale / currentScale)
        let transform = gestureRecognizer.view?.transform.scaledBy(x: newScale, y: newScale)
        gestureRecognizer.view?.transform = transform!
        lastScale = gestureRecognizer.scale
    }
}
func handlePanGesture(recognizer: UIPanGestureRecognizer) {
    let translation = recognizer.translation(in: mainView)
    var recognizerFrame = recognizer.view?.frame
    recognizerFrame?.origin.x += translation.x
    recognizerFrame?.origin.y += translation.y
    // Check if UIImageView is completely inside its superView
    if mainView.bounds.contains(recognizerFrame!) {
        recognizer.view?.frame = recognizerFrame!
    }
    else {
        // Check vertically
        if (recognizerFrame?.origin.y)! < mainView.bounds.origin.y {
            recognizerFrame?.origin.y = 0
        }
        else if (recognizerFrame?.origin.y)! + (recognizerFrame?.size.height)! > mainView.bounds.size.height {
            recognizerFrame?.origin.y = mainView.bounds.size.height - (recognizerFrame?.size.height)!
        }
        // Check horizantally
        if (recognizerFrame?.origin.x)! < mainView.bounds.origin.x {
            recognizerFrame?.origin.x = 0
        }
        else if (recognizerFrame?.origin.x)! + (recognizerFrame?.size.width)! > mainView.bounds.size.width {
            recognizerFrame?.origin.x = mainView.bounds.size.width - (recognizerFrame?.size.width)!
        }
    }
    // Reset translation so that on next pan recognition
    // we get correct translation value
    recognizer.setTranslation(CGPoint(x: CGFloat(0), y: CGFloat(0)), in: mainView)
}

当我运行这段代码时,我正在缩放图像视图,它超出了主视图。那么,我该如何修复?

每当缩放子视图或移动子视图时,都需要更改子视图的框架值。因为框架是UIView的属性,你可以使用KVO来观察它,并为它的更改设置一些规则,比如你对pan等所做的方式。

对于框架的 KVO,您可以从这里找到更好的解释

最新更新