swift - Resize superview with autolayout depending on largest subview -
what best practice resize superview autolayout if have inner nsview columns dynamic heights?
for example. if have 2 column layout, left column height bigger right column, superview height should right column height. than, if change right column height bigger left column height, superview height should change height of right column. how accomplish this?
i made sample project test this:
- initially have layout 2 columns,
.bottomconstraint of leftnsviewattached bottom of superview.

- if press
make right biggerbutton, make height of rightnsviewbigger left one.

so want here superview change height depending on bigger column (right column). there practice so?
code:
import cocoa class viewcontroller: nsviewcontroller { let leftview = nsview() let rightview = nsview() let button = nsbutton() var rightviewheightconstraint: nslayoutconstraint? override func loadview() { self.view = testview() } override func viewdidload() { super.viewdidload() leftview.backgroundcolor = nscolor.redcolor() rightview.backgroundcolor = nscolor.orangecolor() layoutleft(view, insertview: leftview) layoutright(view, insertview: rightview) button.title = "make right bigger" button.target = self button.action = "makebigger:" viewcontrollerlayout.layoutbotton(view, insertview: button, bottom: -20) } func makebigger(sender: anyobject) { rightviewheightconstraint?.animator().constant = 150.0 } func layoutleft(containerview: nsview, insertview: nsview) { insertview.translatesautoresizingmaskintoconstraints = false containerview.addsubview(insertview) let c1 = nslayoutconstraint(item: insertview, attribute: .left, relatedby: .equal, toitem: containerview, attribute: .left, multiplier: 1.0, constant: 0.0) let c2 = nslayoutconstraint(item: insertview, attribute: .width, relatedby: .equal, toitem: containerview, attribute: .width, multiplier: 0.5, constant: 0.0) let c3 = nslayoutconstraint(item: insertview, attribute: .height, relatedby: .equal, toitem: nil, attribute: .notanattribute, multiplier: 1.0, constant: 100.0) let c4 = nslayoutconstraint(item: insertview, attribute: .top, relatedby: .equal, toitem: containerview, attribute: .top, multiplier: 1.0, constant: 0.0) let c5 = nslayoutconstraint(item: insertview, attribute: .bottom, relatedby: .equal, toitem: containerview, attribute: .bottom, multiplier: 1.0, constant: -60.0) containerview.addconstraint(c1) containerview.addconstraint(c2) containerview.addconstraint(c3) containerview.addconstraint(c4) containerview.addconstraint(c5) } func layoutright(containerview: nsview, insertview: nsview) { insertview.translatesautoresizingmaskintoconstraints = false containerview.addsubview(insertview) let c1 = nslayoutconstraint(item: insertview, attribute: .right, relatedby: .equal, toitem: containerview, attribute: .right, multiplier: 1.0, constant: 0.0) let c2 = nslayoutconstraint(item: insertview, attribute: .width, relatedby: .equal, toitem: containerview, attribute: .width, multiplier: 0.5, constant: 0.0) let c3 = nslayoutconstraint(item: insertview, attribute: .height, relatedby: .equal, toitem: nil, attribute: .notanattribute, multiplier: 1.0, constant: 50.0) let c4 = nslayoutconstraint(item: insertview, attribute: .top, relatedby: .equal, toitem: containerview, attribute: .top, multiplier: 1.0, constant: 0.0) let c5 = nslayoutconstraint(item: insertview, attribute: .bottom, relatedby: .equal, toitem: containerview, attribute: .bottom, multiplier: 1.0, constant: -60.0) containerview.addconstraint(c1) containerview.addconstraint(c2) containerview.addconstraint(c3) containerview.addconstraint(c4) // containerview.addconstraint(c5) // cant add .bottom constraint here, because of different column sizes. rightviewheightconstraint = c3 } } struct viewcontrollerlayout { static func layoutbotton(containerview: nsview, insertview: nsview, bottom: double) { insertview.translatesautoresizingmaskintoconstraints = false containerview.addsubview(insertview) containerview.addconstraint(nslayoutconstraint(item: insertview, attribute: .centerx, relatedby: .equal, toitem: containerview, attribute: .centerx, multiplier: 1.0, constant: 0.0)) containerview.addconstraint(nslayoutconstraint(item: insertview, attribute: .bottom, relatedby: .equal, toitem: containerview, attribute: .bottom, multiplier: 1.0, constant: cgfloat(bottom))) } } download test project: github
first create constraint on superview height
let heightconstraint = nslayoutconstraint(item: view, attribute: nslayoutattribute.height, relatedby: nslayoutrelation.equal, toitem: nil, attribute: nslayoutattribute.notanattribute, multiplier: 1, constant: greaterheightamongtwocolumns) as discussed in comment, can post notification , let super view know updated frame. super view check if updated height of of 2 columns greater current height , update heightconstraint declared above , call
[self layoutifneeded] on superview's superview laid out new frame.
Comments
Post a Comment