Modify constraint programmatically Swift

I have the following view controller in my storyboard :

It will always have 6 image views that are, by default, equal in widths and heights. Each image view is constrained to the superview with : "equal heights" and a multiplier of 1/2.

However, before I load images inside, I read a property that gives me the desired height for an image (width will never be modified).

So my interface (at runtime) can look like this :

I think I need to modify the multiplier constant but it's read-only.

I saw posts saying that we can update the constant property of the constraint but it's in points, I need it to work on every device.

Now what would you recommend ? Should I remove the constraint and add a new one ? If I don't remove it and try to apply a new height constraint, will it be removed automatically for me ?

Do I have to use pods like snapkit to do the job ?

Thanks for your help.

EDIT

Here is the code I tried, but did not succeeded :

        for (index, (drawing, ratio)) in drawingElements.enumerate() {
            drawingViews[index].image = UIImage(named: drawing)
            // update height constraint if ratio is different than defaut ratio of 1/2
            if ratio != 0.5 {
                heightConstraints[index].active = false
                let newHeightConstraint = NSLayoutConstraint(item: drawingViews[index], attribute: NSLayoutAttribute.Height, relatedBy: NSLayoutRelation.Equal, toItem: nil, attribute: NSLayoutAttribute.Height, multiplier: ratio, constant: 0)
                drawingViews[index].addConstraint(newHeightConstraint)
                self.view.layoutIfNeeded()
            }
        }

Am I doing it wrong ? I am unsure about the new height constraint though

Answers


So this is the way I achieved this :

  • Create a constraint programmatically (height in my case) :

    // Drawing height property
    var drawingHeightConstraint: NSLayoutConstraint?
    
  • Deactivate old constraint and set the new one if needed

Note: heightContraints is an array of NSLayoutConstraint which contains my outlets

        for (index, (drawing, ratio)) in drawingElements.enumerate() {
        drawingViews[index].image = UIImage(named: drawing)

        // update height constraint if ratio is different than defaut ratio of 1/2
        if ratio != 0.5 {
            heightConstraints[index].active = false
            drawingHeightConstraint = NSLayoutConstraint(item: drawingViews[index], attribute: .Height, relatedBy: .Equal, toItem: drawingView, attribute: .Height, multiplier: CGFloat(ratio), constant: 0)
            drawingHeightConstraint!.active = true
        }

    }
  • Call layoutIfNeeded() right after (note: not sure when to call it)

The constraints constants are related to the content of the constrained element. That why you're getting such screen. The easiest way - create image with clear color and set it by default. After downloading completed just set new image for your imageView

Or you can set IBOutlet for your height constraint - and change it value for different situations i.e.

if(download.completed)
ibHeightOutlet.constant = imageView.frame.size.height;
else
ibHeightOutlet.constant = initialImageViewHeght.frame.size.height;

You can not change the multiplier for reasons unknown to me (some kind of Apple's implementation detail probably). You can remove a constraint and create a new one, however. You have to remove the old constraint, because it will not be removed automatically, and you'll get a conflict. Alternatively, you could create the first constraint (with the 0.5 multiplier) with lower priority. This way you could keep it (autolayout would just ignore it), but I don't think it is a way to go, since why would you need that unnecessary constraint? Just delete it. As for third-party layout engines and libraries – unfortunately, I can't give you any advice here.


Need Your Help

Hide download files from SD Card Gallery - PhoneGap

javascript android cordova phonegap-build

I have an app where the user logs in and downloads some images and audio files to their devices SD card.

Issue(s) with the constructing http POST request

java http rest post apache-httpclient-4.x

I'm able to do a POST request in SOAP UI. But I cannot do the same from java, been trying for about 5-6 hours and can't find the wining combination. Here is my xsd schema part for the post I'm tryi...