UIStoryboard how to replace constraints programmatically?

autolayout, ios6, nslayoutconstraint, objective-c, uistoryboard

Solution

It sounds like you want to just remove all the constraints on a view. Since constraints on a view are often held by an ancestor of the view, it's not obvious how to remove all of the constraints easily. But it is actually pretty easy.

Removing a view from the view hierarchy removes any constraints betwixt the view and other views outside of it. So just remove your view from its superview and then add it back:

// Remove constraints betwixt someView and non-descendants of someView.
UIView *superview = someView.superview;
[someView removeFromSuperview];
[superview addSubview:someView];

If there are any constraints betwixt `someView` and its descendants, those constraints might be held by `someView` itself (but cannot be held by any descendants of `someView`). If you want to remove those constraints also, you can do so directly:

// Remove any remaining constraints betwixt someView and its descendants.
[someView removeConstraints:[someView constraints]];

Problem

I have a view controller laid out in a storyboard with autolayout enabled and am looking for a way to change constraints to allow for my view to rotate into landscape and rearrange buttons on the screen. When I try the code below, I get about two dozen "unable to satisfy constraints, breaking constraint..." messages that I cannot really decode. Is there a way to dynamically replace constraints from a storyboard with constraints that I specify programmatically? I want to completely override the layout of the buttons that I defined in a storyboard. ``` -(void)updateViewConstraints { [super updateViewConstraints]; self.loginButton.translatesAutoresizingMaskIntoConstraints = NO; self.getStartedButton.translatesAutoresizingMaskIntoConstraints = NO; self.takeTourButton.translatesAutoresizingMaskIntoConstraints = NO; [self.loginButton removeConstraints:self.loginButton.constraints]; [self.getStartedButton removeConstraints:self.getStartedButton.constraints]; [self.takeTourButton removeConstraints:self.takeTourButton.constraints]; one = self.loginButton; two = self.getStartedButton; three = self.takeTourButton; NSDictionary *metrics = @{@"height":@50.0,@"width":@100.0,@"leftSpacing":@110.0}; NSDictionary *views = NSDictionaryOfVariableBindings(one,two,three); [self.view removeConstraints:activeTestLabelConstraints]; [activeTestLabelConstraints removeAllObjects]; if(isRotatingToLandscape) { [self registerConstraintsWithVisualFormat:@"|-[one(two)]-[two(three)]-[three]-|" options:NSLayoutFormatAlignAllTop | NSLayoutFormatAlignAllBottom metrics:metrics views:views]; [self registerConstraintsWithVisualFormat:@"V:[one(height)]-|" options:0 metrics:metrics views:views]; }else { [self registerConstraintsWithVisualFormat:@"|-leftSpacing-[one(width)]" options:0 metrics:metrics views:views]; [self registerConstraintsWithVisualFormat:@"[two(width)]" options:0 metrics:metrics views:views]; [self registerConstraintsWithVisualFormat:@"[three(width)]" options:0 metrics:metrics views:views]; [self registerConstraintsWithVisualFormat:@"V:[one(height)]-[two(75)]-[three(100)]-|" options:NSLayoutFormatAlignAllCenterX metrics:metrics views:views]; } } ``` Updated with Rob's answer, here's the method to remove constraints that I use ``` -(void)removeConstraintForView:(UIView*)viewToModify { UIView* temp = viewToModify; [temp removeFromSuperview]; [self.view addSubview:temp]; } ```

Original source

Related problems