Is there any way to add constraint between a view and the top layout guide in a xib file?

后端 未结 7 2342
时光说笑
时光说笑 2020-12-07 15:44

In iOS 7, we can now add a constraint between a view and the top layout guide, which I think is very useful to solve the status bar offset issue in iOS7(especially when ther

7条回答
  •  生来不讨喜
    2020-12-07 15:57

    Until now even using XCode 6 I cannot align controls to top layout guide on .xib files. Instead, I am using an alternative way.

    First, on interface builder, I still align controls to top border of viewcontroler's view.

    Then, in viewDidLoad method, I replace some constraints so they will align to top layout guide instead of main view:

    - (void)viewDidLoad
    {
        [super viewDidLoad];
    
        NSArray *constraints = self.view.constraints;
        for (NSLayoutConstraint *constraint in constraints) {
            if ( (constraint.firstItem == self.view) && (constraint.firstAttribute == NSLayoutAttributeTop) ) {
                NSLayoutConstraint *newConstraint = [self constraint:constraint replaceFirstItemBy:self.topLayoutGuide attribute:NSLayoutAttributeBottom];
                [self.view removeConstraint:constraint];
                [self.view addConstraint:newConstraint];
            } else if ( (constraint.secondItem == self.view) && (constraint.secondAttribute == NSLayoutAttributeTop) ) {
                NSLayoutConstraint *newConstraint = [self constraint:constraint replaceSecondItemBy:self.topLayoutGuide attribute:NSLayoutAttributeBottom];
                [self.view removeConstraint:constraint];
                [self.view addConstraint:newConstraint];
            }
        }
    }
    
    - (NSLayoutConstraint*)constraint:(NSLayoutConstraint*)constraint replaceFirstItemBy:(id)newItem attribute:(NSLayoutAttribute)newAttribute {
        UILayoutPriority priority = constraint.priority;
        NSLayoutRelation relation = constraint.relation;
        id secondItem = constraint.secondItem;
        NSLayoutAttribute secondAttribute = constraint.secondAttribute;
        CGFloat multiplier = constraint.multiplier;
        CGFloat constant = constraint.constant;
    
        NSLayoutConstraint *newConstraint = [NSLayoutConstraint constraintWithItem:newItem attribute:newAttribute relatedBy:relation toItem:secondItem attribute:secondAttribute multiplier:multiplier constant:constant];
        newConstraint.priority = priority;
        return newConstraint;
    }
    
    - (NSLayoutConstraint*)constraint:(NSLayoutConstraint*)constraint replaceSecondItemBy:(id)newItem attribute:(NSLayoutAttribute)newAttribute {
        UILayoutPriority priority = constraint.priority;
        id firstItem = constraint.firstItem;
        NSLayoutAttribute firstAttribute = constraint.firstAttribute;
        NSLayoutRelation relation = constraint.relation;
        CGFloat multiplier = constraint.multiplier;
        CGFloat constant = constraint.constant;
    
        NSLayoutConstraint *newConstraint = [NSLayoutConstraint constraintWithItem:firstItem attribute:firstAttribute relatedBy:relation toItem:newItem attribute:newAttribute multiplier:multiplier constant:constant];
        newConstraint.priority = priority;
        return newConstraint;
    }
    

    Think this is not the best way because we replace objects that we define on interface builder. But it may be an alternative way that we can think about.

提交回复
热议问题