简体   繁体   中英

How can I get the edges of a UIImageView to snap to the edges of the screen (superview)?

I don't expect anyone to write the code for me. I'm just looking for a push in the right direction toward the framework and/or methods to use. What I want to do is, in iOS Swift, allow the user to select a photo and place it on the screen. I've already got that part working. I also have it working whereby you can drag the image to position it, and pinch to make it larger or smaller. However, the "tricky" part is the following... when an edge (or edges) approach the frame of the superview (the screen), I would like the ImageView to "snap" into place at the edge. Basically, I want the edges of the image to be "magnetically" attracted to the edges of the screen. I'm not quite sure which combination of methods would be best to accomplish this. Any suggestions appreciated.

Edit: Here's what I have so far...

class AdjustableImageView: UIImageView {

    var parent:ViewController!

    // last location for view
    var lastSavedLocation = CGPointZero

    override init(frame: CGRect) {
        super.init(frame: frame)

        // add pan gesture to view
        let panGesture = UIPanGestureRecognizer(target: self, action: "handlePanGesture:")
        let longPressGesture = UILongPressGestureRecognizer(target: self, action: "handleLongPress:")
        let pinchGesture = UIPinchGestureRecognizer(target: self, action: "pinchRecognized:")
        self.addGestureRecognizer(panGesture)
        self.addGestureRecognizer(longPressGesture)
        self.addGestureRecognizer(pinchGesture)
        self.userInteractionEnabled = true
    }

    required init?(coder aDecoder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    func pinchRecognized(pinch: UIPinchGestureRecognizer) {
        // change view scale based on pinch
        self.transform = CGAffineTransformScale(self.transform, pinch.scale, pinch.scale)
        pinch.scale = 1.0
    }

    func handlePanGesture(gesture: UIPanGestureRecognizer) {
        // find translation in main view
        let newTranslation = gesture.translationInView(self.superview)

        // set current object to new position
        self.center = CGPointMake(self.lastSavedLocation.x + newTranslation.x , self.lastSavedLocation.y + newTranslation.y)
    }

    // detect touch for the current view and change last save postion
    override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) {

        // move touched view to front.
        self.superview?.bringSubviewToFront(self)

        self.layer.borderColor = UIColor.greenColor().CGColor
        self.layer.borderWidth = 2

        // save view location
        self.lastSavedLocation = self.center

        parent.imageSelected(self)
    }

    override func touchesEnded(touches: Set<UITouch>, withEvent event: UIEvent?) {
        self.layer.borderWidth = 0
    }
}

Sounds to me you want somthing like a hittest.

Hittest

So i think you'd want to work with drag and drop. As soon the hittest triggers with a marge (5-10 or 15dp/px) you lock the image => stop drag and position the view programmatically... I did not test this, but trhat would be my first approach be.

hittest subview

Although you don't want to test with subview but with an edge of a subview i think it would be possible.

snapping to edge

Above link looks like a smooth edge clipping. Reversing the logic, you should be able to clip to bounds...

You could try using a method that checks if the edge(s) of the UIImageView are within a certain distance of the the superview's frame.

func checkEdge(view: UIImageView) {

    let left   = view.frame.minX
    let right  = view.frame.maxX
    let bottom = view.frame.maxY
    let top    = view.frame.minY

    if left <= 10 {
        // Move view to left side
    } else if right <= 10 {
        // Move view to right side
    } else if bottom <= 10 {
        // Move view to bottom
    } else if top <= 10 {
        // Move view to top
    } else {
        // Do nothing
    }
}

Let me know if that works and/or what you were looking for!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM