IOSLayoutConstraint - How the heck do you set a width???

So I’ve discovered the most horrible aspect of Xojo. It’s worse than anything I could imagine and I think my little dabbling with Objective-C doesn’t have anything this crazy bad. It’s the IOSLayoutConstraint. It’s something where you have to have an incredibly complex and non-understandable statement that to even make it readable you have to break it into 4 or 5 lines in the editor. Call that user friendly would ya! You know if this is the “new” Xojo, I’ll stick with the old that was easy to pick up and learn.

Anyhow, I digress but maybe not really.

So how do you set a width of a control with this “I need to be a rocket scientist to understand it” statement?

Constructor(firstItem As Object, firstAttribute As AttributeTypes, relation As RelationTypes, secondItem As Object, secondAttribute As AttributeTypes, multiplier As Double, addend As Double)

OK. So I have:

firstitem - so that’s the control I am wanting to set the width - right? OK Good.
firstattribute - OK so then this is iOSLayoutConstraint.AttributeTypes.Width

OK. So this makes sense. So far so good. Here’s where it breaks down.

Now for relation what do I put? I just want to set a width in pixels. So do I put: iOSLayoutConstraint.RelationTypes.Equal ???

OK so let’s assume I do. But now what do I use for the seconditem? The view? But equal to what in the view? I don’t want to use a formula. I just want to set a width for the control. I don’t want it equal to left left edge of the hypotenuse of the sine of the angle of the orbital path to Pluto. Yes, I know that didn’t make any sense but neither does this layout constraint bit when all I want to do is set a width.

And please don’t tell me to go look in the auto layout examples. Yeah, that’s a setting of a width there, but that is for a control that is already in the IDE not a dynamically created control.

So how do I just set a width or height of a control???

Constraints are mathemetical expressions but not written in mathematical form

so say you want to express

  control_A.edge_A = control_B.edge_B * factor + offset

thats a layout constraint but broken into all the pieces

using this example

firstItem As Object = control_A firstAttribute As AttributeTypes = edge_A relation As RelationTypes = "=" secondItem As Object = control_B secondAttribute As AttributeTypes = edge_B multiplier As Double = factor addend = offset

Typically you do NOT set the width or height - you set it relative to some other edge of the containing view or another control
You set a relation that says “keep this edge this far from some other edge” so that if you rotate the screen the control remains say 20 pixels from the edge of the view its in

Now IF you want to say “keep this to 10 pixels high” remember control_A.edge_A = control_B.edge_B * factor + offset

firstItem As Object = control_A = whatever control firstAttribute As AttributeTypes = edge_A = HEIGHT relation As RelationTypes = "=" secondItem As Object = control_B = NONE since there IS no other control involved (use NIL) secondAttribute As AttributeTypes = edge_B = NONE (yes there is an edge called none) multiplier As Double = factor = 1.0 (but in reality for this its ignored) addend = offset = 10
and then you have

control.height = (nothing.no edge) * 1.0 + 10

and (nothing.no edge) * 1.0 evaluates to 0 so you have

control.height = 10

Jon, I’m not sure if it will help you, but in the extensions module of iOSKit there are a few convenience extension methods to add a control dynamically to a view. Maybe you want to check them out to see if they can help you?

https://github.com/kingj5/iOSKit/blob/master/Modules/Extensions.xojo_code

iOSLayoutConstraint is a bit painful but so is a lot of the code we have to write each day. I find that if I have a cup of coffee first, and concentrate for a couple of minutes, it all makes sense. Oh and Jason King’s aforementioned AddControlWithBounds/AtPoint extension methods are a sanity saver! :slight_smile:

[quote=203621:@Jason King]Jon, I’m not sure if it will help you, but in the extensions module of iOSKit there are a few convenience extension methods to add a control dynamically to a view. Maybe you want to check them out to see if they can help you?

https://github.com/kingj5/iOSKit/blob/master/Modules/Extensions.xojo_code[/quote]

Jason - thank you. Looks like some really good stuff in there.

[quote=203618:@Norman Palardy]Constraints are mathemetical expressions but not written in mathematical form

Typically you do NOT set the width or height - you set it relative to some other edge of the containing view or another control
You set a relation that says “keep this edge this far from some other edge” so that if you rotate the screen the control remains say 20 pixels from the edge of the view its in

[/quote]

I get that. At this point, I’m just trying to walk slowly up the learning curve and get a few controls placed on the page. I don’t really care about dynamic resizing at this point.

[quote]
Now IF you want to say “keep this to 10 pixels high” remember control_A.edge_A = control_B.edge_B * factor + offset

firstItem As Object = control_A = whatever control firstAttribute As AttributeTypes = edge_A = HEIGHT relation As RelationTypes = "=" secondItem As Object = control_B = NONE since there IS no other control involved (use NIL) secondAttribute As AttributeTypes = edge_B = NONE (yes there is an edge called none) multiplier As Double = factor = 1.0 (but in reality for this its ignored) addend = offset = 10
and then you have

control.height = (nothing.no edge) * 1.0 + 10

and (nothing.no edge) * 1.0 evaluates to 0 so you have

control.height = 10

Thank you! Now this is a good example/explanation. I had no idea you could set second item to Nil. And this is my point in the examples, if they were commented in a similar way to what you show here, then it would be a lot easier to figure out/understand.

I’ve asked paul to add this explanation to the ones on http://developer.xojo.com/ios-auto-layout and http://developer.xojo.com/ioslayoutconstraint

Thanks Norman! That would help a lot…

I’ve added additional info to these pages based on Norman’s helpful post:

For reference, there are a couple simple AutoLayout example projects here (but they don’t cover Jon’s original question):
Examples/iOS/Auto-Layout/

In a module add:

Function withConstraint(extends o as iOSControl, width as double, relation as iOSLayoutConstraint.RelationTypes=iOSLayoutConstraint.RelationTypes.Equal) As iOSLayoutConstraint Return new iOSLayoutConstraint(o,iOSLayoutConstraint.AttributeTypes.Width, Relation, nil, iOSLayoutConstraint.AttributeTypes.None, 1.0, width) End Function
so instead of the long syntax just to set the width you can call:

AddConstraint myControl.withConstraint(250)