iOS : 새로운 자동 레이아웃 제약 (높이)에 애니메이션을 적용하는 방법


123

이전 에는 자동 레이아웃 제약 조건으로 작업 한 적이 없습니다 . 작업중인 작은 새 앱이 있는데 NIB의보기가 기본적으로 자동 레이아웃으로 설정되어 있음을 알았습니다. 그래서 나는 그것을 함께 일할 기회를 잡고 애플이 이것으로 어디로 가고 있는지 알아 내려고 노력할 것이라고 생각했습니다.

첫 번째 도전 :

MKMapView의 크기를 조정해야하며 새 위치로 애니메이션을 적용하고 싶습니다. 내가 익숙한 방식으로 이렇게하면 :

[UIView animateWithDuration:1.2f
     animations:^{
         CGRect theFrame = worldView.frame;
         CGRect newFrame = CGRectMake(theFrame.origin.x, theFrame.origin.y, theFrame.size.width, theFrame.size.height - 170);
         worldView.frame = newFrame;
}];

... 그러면 MKMapView는 형제 뷰가 업데이트 될 때마다 원래 높이로 '스냅'됩니다 (내 경우에는 UISegmentedControl의 제목이 업데이트되고 있음 [myUISegmentedControl setTitle:newTitle forSegmentAtIndex:0]).

그럼, 내가 생각 나는 그것이 그 UISegmentedControl의 상단에 상대가되기 위해서는 부모 뷰의 높이와 동일되는 것을 MKMapView의 제약을 변경되고 싶지 커버 :V:[MKMapView]-(16)-[UISegmentedControl]

내가 원하는 것은 맵 뷰 아래의 일부 컨트롤이 드러나도록 MKMapView 높이를 줄이는 것입니다. 이렇게하려면 제약 조건을 고정 전체 크기보기에서 하단이 UISegmentedControl의 상단으로 제한되는보기로 변경해야 한다고 생각 합니다. 그리고보기가 새로운 크기로 축소 될 때 애니메이션을 적용하고 싶습니다.

이것에 대해 어떻게 갑니까?

편집- 이 애니메이션은 보기 하단이 즉시 170 위로 이동하지만 애니메이션이 적용 되지 않습니다 .

    [UIView animateWithDuration:1.2f
         animations:^{
             self.nibMapViewConstraint.constant = -170;

    }];

그리고는 nibMapViewConstraint바닥 수직 공간의 제약으로 IB에 연결되어 있습니다.


1
[UIView animateWithDuration ..] 블록에서 제약 조건의 상수 값을 쉽게 변경하여 높이 변경에 애니메이션을 적용 할 수 있다는 것을 알고 있습니다. 해당 제약 조건에 대한 IBOutlet을 만들고 xib에 연결하거나, 그렇지 않으면 코드에서 만든 경우 참조를 유지해야합니다 (또는 모든 제약 조건을 통해 루프를 검색하여 찾습니다). relatedBy 변경 사항을 애니메이션하는 방법을 잘 모르겠지만 제약 조건의 다른 값이 아닌 상수 만 변경해야한다는 것을 읽었습니다 (다른 값의 경우 새 제약 조건 생성).
yuf

흠. 할 수 있다고 생각했지만 애니메이션이 아닙니다. 성공적으로 변경되고 애니메이션 블록에 있지만 애니메이션 되지 않습니다 !?!
Meltemi 2011

여기에서 내 대답을 찾았습니다. < stackoverflow.com/questions/12926566/… >
Meltemi

1
[view layoutIfNeeded]를 잊지 마세요, 그것도 내 문제 였어요 haha. 그것은 내 문제를 해결 한 것과 같은 질문입니다.
yuf 2011

답변:


179

제약 조건을 업데이트 한 후 :

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

self.view포함하는 뷰에 대한 참조로 바꿉니다 .


4
뷰 자체에 대해 작동하지만 해당 뷰에 대한 제약이있는 뷰는 즉시 이동합니다. 어떡하죠? ty
dietbacon 2013-08-06

7
이러한 뷰에서도 필요한 경우 레이아웃을 호출해야합니다. 그러나 이것은 뷰 새로 고침에 애니메이션을 적용하기 때문에 제대로 작동하지 않습니다. 다른 뷰에서만 제약 조건 조정을 어떻게 애니메이션합니까?
ngb 2013-08-24

3
주의 :UIViewAnimationOptionBeginFromCurrentState 레이아웃 제약을 사용하는 경우 애니메이션 전에 설정됩니다 !
Robert

12
layoutIfNeeded이러한 각 뷰 를 호출하는 대신 다음과 같이 호출 하십시오.[[self.view superview] layoutIfNeeded];
Flying_Banana 2014 년

2
@ngb 애니메이션 블록 에서 제약 상수를 변경해야합니다 . 이렇게하면 제약 조건이 애니메이션과 함께 변경되고 UIViewAnimationOptionBeginFromCurrentState.
Eran Goldin 2015

86

이것은 나를 위해 작동합니다 (iOS7 및 iOS8 + 모두). 조정하려는 자동 레이아웃 제약을 클릭합니다 (인터페이스 빌더에서 예 : 상단 제약). 다음으로 이것을 IBOutlet으로 만드십시오.

@property (strong, nonatomic) IBOutlet NSLayoutConstraint *topConstraint;

위쪽으로 애니메이션;

    self.topConstraint.constant = -100;    
    [self.viewToAnimate setNeedsUpdateConstraints]; 
    [UIView animateWithDuration:1.5 animations:^{
        [self.viewToAnimate layoutIfNeeded]; 
    }];

원래 위치로 다시 애니메이션

    self.topConstraint.constant = 0;    
    [self.viewToAnimate setNeedsUpdateConstraints];  
    [UIView animateWithDuration:1.5 animations:^{
        [self.viewToAnimate layoutIfNeeded];
    }];

2
와!! 이것은 실제로 작동합니다! 이 대답은 저에게 눈을 뜨게했습니다. 정말 감사합니다! - 에릭
에릭 반 Neut 데르

2
@ErikvanderNeut 나에게도 도움이 되었기 때문에 기뻤습니다. 이제부터는 프레임 위치가 아닌 제약 조건을 애니메이션으로 만들 것입니다.
DevC 2014 년

추가하는 것도 놓치지 마세요 : [containerView layoutIfNeeded]; 보류중인 모든 레이아웃 작업이 animateWithDuration 블록 전에 완료되었는지 확인합니다.
ingconti

11

자동 레이아웃과 함께 애니메이션을 사용하는 방법을 설명하는 애플 자체의 아주 좋은 튜토리얼이 있습니다. 이 링크를 따라 "예제 별 자동 레이아웃"이라는 비디오를 찾으십시오. 자동 레이아웃에 대한 흥미로운 내용을 제공하고 마지막 부분은 애니메이션 사용 방법에 대한 것입니다.



1

대부분의 사람들은 자동 레이아웃을 사용하여 뷰의 항목을 레이아웃하고 레이아웃 제한을 수정하여 애니메이션을 만듭니다.

많은 코드없이이 작업을 수행하는 쉬운 방법은 Storyboard에서 애니메이션하려는 UIView를 만든 다음 UIView를 종료 할 숨겨진 UIView를 만드는 것입니다. xcode에서 미리보기를 사용하여 두 UIView가 원하는 위치에 있는지 확인할 수 있습니다. 그 후 종료 UIView를 숨기고 레이아웃 제약 조건을 바꿉니다.

직접 작성하고 싶지 않은 경우 SBP라는 레이아웃 제한을 스왑하기위한 podfile이 있습니다.

여기에 튜토리얼이 있습니다.


0

필요가 더 사용하지하는 IBOutlet reference대신 직접 수있는이의 제약 access또는 update이미 제약 조건을 적용하거나 적용 Programmatically또는에서 Interface Builder사용하는보기에 KVConstraintExtensionsMaster라이브러리를. 이 라이브러리는 또한의 Cumulative동작을 관리합니다 NSLayoutConstraint.

containerView에 높이 제약 조건을 추가하려면

 CGFloat height = 200;
 [self.containerView applyHeightConstrain:height];

containerView의 높이 제약 조건을 애니메이션으로 업데이트하려면

[self.containerView accessAppliedConstraintByAttribute:NSLayoutAttributeHeight completion:^(NSLayoutConstraint *expectedConstraint){
        if (expectedConstraint) {
            expectedConstraint.constant = 100;

            /* for the animation */ 
            [self.containerView  updateModifyConstraintsWithAnimation:NULL];
      }
    }];
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.