使用约束移动视图

6

当向上滑动被检测到时,我的视图控制器中有一些视图会上移,然后当向下滑动被检测到时会下移。我曾经通过调整y坐标原点来强制视图移动。现在,我已经使用IB将约束应用于我的视图,但是我不确定如何最好地移动视图,以便它们在iPhone 5、6和6+上以正确的位置结束。

目前,我正在做类似这样的事情:

[self.view layoutIfNeeded];

    self.panFrameVerticalConstraint.constant = self.panFrameVerticalConstraint.constant +338;

    [UIView animateWithDuration:5
                     animations:^{
                         [self.view layoutIfNeeded];
                     }];

更好的做法是使用比例来改变常数吗?因此,对于以上约束条件,是否最好这样做:

    self.panFrameVerticalConstraint.constant = self.panFrameVerticalConstraint.constant + (self.panView.frame.size.height/1.680);

    //self.panView.frame.size.height = 568
    //(568/1.680) = 338

请看这个链接 - https://dev59.com/xITba4cB1Zd3GeqP-sIF#26668575 - Kampai
@Brosef,能问一下你是如何实现上下滑动手势来移动视图的吗?我也想做类似的事情,但不知道从哪里开始。谢谢。 - Pangu
1
@Pangu 我基本上按照下面回答中的步骤进行操作。我创建了一个 IBOutlet NSLayoutConstraint 属性,并将其连接到我想要在界面构建器中调整的约束。然后,当我需要将我的视图向上移动时,我像这样更改了我的常量 self.panFrameVerticalConstraint.constant = -(self.panedView.frame.size.height/1.68);。在更改常量之前,我调用了 layoutIfNeeded。更改常量后,我调用了 animateWithDuration 并在块中再次调用了 layoutIfNeeded,就像下面的回答一样。 - Brosef
@Brosef,很抱歉我还在学习中,但是您是如何检测到您想要向上移动的UIView的滑动手势以调用动画的呢? - Pangu
1
@pangu 在 viewDidLoad 中,您需要添加一个 UISwipeGestureRecognizer 和当检测到滑动时调用的方法。UISwipeGestureRecognizer * swipeUpRec = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:@selector(handleUpSwipe:)]; 然后将手势识别器添加到应该检测滑动的任何框架 [self.someView addGestureRecognizer:swipeUpRec]; - Brosef
@brose非常感谢您的耐心和帮助!圣诞快乐 :) - Pangu
1个回答

25

改变常数不会有问题,关键是要适当设置约束条件。

让我们来看一个例子。我在Storyboard中有一个UIView,我想改变它的宽度。 它的默认宽度是1024

经过一些动画后,我们将把它的宽度改为900

按照以下步骤实现:

  1. 选择我们想要更新约束的UIView。这里我们需要更新width,所以我们将添加一个宽度约束。
enter image description here
  1. 现在我们可以看到新的约束已添加到UIView中。
enter image description here
  1. 单击该约束。它将显示约束属性。现在我们想将宽度从1024减小到900,因此在约束属性中将Relation属性更改为Less Than or Equal。同样,如果您想将宽度增加到1024,则关系将是Greater Than or Equal
enter image description here
  1. 现在创建一个NSLayoutConstraintIBOutlet变量,并将其连接到上述宽度约束。
  2. 更改宽度常数

Swift 5.0

@IBOutlet weak var viewWidthConstraint : NSLayoutConstraint!

func reduceWidth() {
    // Reduce width of view.
    UIView.animate(withDuration: 0.35, animations: { () -> Void in
        self.viewWidthConstraint.constant = 900
        self.view.layoutIfNeeded()
    })
}

func normalWidth() {
    // Change to the default width of view.
    UIView.animate(withDuration: 0.35, animations: { () -> Void in
        self.viewWidthConstraint.constant = 1024
        self.view.layoutIfNeeded()
    })
}

Objective C

@property (weak, nonatomic) IBOutlet NSLayoutConstraint     *viewWidthConstraint; 

- (void) reduceWidth {
    // Reduce width of view.
    [UIView animateWithDuration:0.35f animations:^{
        self.viewWidthConstraint.constant = 900;
        [self.view layoutIfNeeded];
    }];
}

- (void) normalWidth {
    // Change to default width of view.
    [UIView animateWithDuration:0.35f animations:^{
        self.viewWidthConstraint.constant = 1024;
        [self.view layoutIfNeeded];
    }];
}

这非常有帮助。你说你想将宽度从1024更改为900,但为什么要将约束常量更改为705呢? - Brosef
这只是一个例子。在代码中,我需要将宽度减少到705。 - Kampai
1
很好的解释。我欣赏。+1 - viral
3
非常好的答案,而且正确。我只想补充一点,设置约束并不需要在 UIView.animateWithDuration 块内完成。你可以在动画块之前设置约束,然后在块内调用 layoutIfNeeded - Markus
有人知道如何捕获约束变化吗?我的意思是,宽度约束从1024更改为900,反之亦然。如果我想捕获约束等于1000的时刻怎么办? - Luchi Parejo Alcazar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接