如何通过Pan手势限制可移动视图

时间:2013-07-23 21:45:10

标签: ios ios6 uiimageview orientation uipangesturerecognizer

我有UIImageView可通过平移手势移动。

UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
[self.photoMask addGestureRecognizer:pan];

我想限制可以在屏幕上移动的区域。而不是用户能够将视图直接拖动到屏幕的一侧,我想限制它的某种边距。我怎么能这样做?

此外,旋转后如何处理?

编辑---

#pragma mark - Gesture Recognizer
-(void)handlePan:(UIPanGestureRecognizer *)gesture {
    NSLog(@"Pan Gesture");
    gesture.view.center = [gesture locationInView:self.view];
}

这是我目前处理平底锅的方法。我需要做的是继续按中心点移动图像视图,并在靠近屏幕边缘时将其移动限制为50。

4 个答案:

答案 0 :(得分:7)

一个可能的解决方案是在您的handlePan方法中,检查屏幕上点的位置,并且只有在您希望将其限制为的范围内时才提交更改。

对于前。

-(void) handlePan:(UIGestureRecognizer*)panGes{

    CGPoint point = [panGes locationInView:self.view];

    //Only allow movement up to within 100 pixels of the right bound of the screen
    if (point.x < [UIScreen mainScreen].bounds.size.width - 100) {

        CGRect newframe = CGRectMake(point.x, point.y, theImageView.frame.size.width, theImageView.frame.size.height);

        theImageView.frame = newframe;

    }

}

我相信这也可以正确处理任何屏幕旋转

修改

要将图片视图移动到其框架的中心,handlePan方法可能看起来像这样。

-(void)handlePan:(UIPanGestureRecognizer *)gesture {

    CGPoint point = [gesture locationInView:self.view];

    //Only allow movement up to within 50 pixels of the bounds of the screen
    //Ex. (IPhone 5)
    CGRect boundsRect = CGRectMake(50, 50, 220, 448);

    if (CGRectContainsPoint(boundsRect, point)) {
        imgView.center = point;
    }       
}

检查点是否在您想要的范围内,如果是,请将图像视图框的中心设置为该点。

答案 1 :(得分:3)

我不确定我是否过于简单化,但我认为你可以通过使用if子句来实现这一点。

-(void)handlePan:(UIPanGestureRecognizer*)gesture {

    UIImageView *viewToDrag = gesture.view; // this is the view you want to move

    CGPoint translation = [gesture translationInView:viewToDrag.superview]; // get the movement delta

    CGRect movedFrame = CGRectOffset(viewToDrag.frame, translation.x, translation.y); // this is the new (moved) frame

    // Now this is the critical part because I don't know if your "margin"
    // is a CGRect or maybe some int values, the important thing here is
    // to compare if the "movedFrame" values are in the allowed movement area

    // Assuming that your margin is a CGRect you could do the following:
    if (CGRectContainsRect(yourPermissibleMargin, movedFrame)) {
        CGPoint newCenter = CGPointMake(CGRectGetMidX(movedFrame), CGRectGetMidY(movedFrame));
        viewToDrag.center = newCenter; // Move your view
    }

    // -OR-

    // If you have your margins as int values you could do the following:
    if ( (movedFrame.origin.x + movedFrame.size.width) < 50) {
        CGPoint newCenter = CGPointMake(CGRectGetMidX(movedFrame), CGRectGetMidY(movedFrame));
        viewToDrag.center = newCenter; // Move your view
    }
}

您可能需要对其进行调整以满足您的特定需求。

希望这有帮助!

答案 2 :(得分:0)

- (void)dragAction:(UIPanGestureRecognizer *)gesture{
     UILabel *label = (UILabel *)gesture.view;
     CGPoint translation = [gesture translationInView:label];
     if (CGRectContainsPoint(label.frame, [gesture locationInView:label] )) {
         label.center = CGPointMake(label.center.x,
                                label.center.y);
        [gesture setTranslation:CGPointZero inView:label];
   }
   else{
       label.center = CGPointMake(label.center.x,
                                label.center.y + translation.y);
        [gesture setTranslation:CGPointZero inView:label];
   }
}

答案 3 :(得分:0)

以下是Swift 4中的答案 - 将视图的移动限制为超级视图

@objc func handlePan(_ gestureRecognizer: UIPanGestureRecognizer)
{
    // Allows smooth movement of stickers.
    if gestureRecognizer.state == .began || gestureRecognizer.state == .changed
    {
        let point = gestureRecognizer.location(in: self.superview)
        if let superview = self.superview
        {
            let restrictByPoint : CGFloat = 30.0
            let superBounds = CGRect(x: superview.bounds.origin.x + restrictByPoint, y: superview.bounds.origin.y + restrictByPoint, width: superview.bounds.size.width - 2*restrictByPoint, height: superview.bounds.size.height - 2*restrictByPoint)
            if (superBounds.contains(point))
            {
                let translation = gestureRecognizer.translation(in: self.superview)
                gestureRecognizer.view!.center = CGPoint(x: gestureRecognizer.view!.center.x + translation.x, y: gestureRecognizer.view!.center.y + translation.y)
                gestureRecognizer.setTranslation(CGPoint.zero, in: self.superview)
            }
        }
    }
}

如果您想要更多地控制它,请将restrictByPoint值与可移动视图的帧匹配。