Just created a demo single view controller project. Controller view contains collection view, and it contains cell view (orange). Cell view contains a view (selected inside) and I need to align it to bottom of cell view. However, when I select orange view inside cell view, press Ctrl and drag it to cell view I don't see "Align bottom to container view" or similar. There's only "Bottom Space to Container" selection and I'm not sure does it have the same behaviour:
And if I select "Bottom Space to Container" and don't get desired "Align bottom to parent" system constraint:
I need to add a new label in existing code base with auto layout, and the label must be positioned next to existing label that has "Align bottom to: parent cell" system constraint:
There's some setting "Bottom edges" if I select my new label and press align button icon at the bottom. However, this selection is disabled anyways and I assume this is user constraint but I need system constraint "Align bottom to: parent cell". Any suggestions why existing label has this constraint but I can't add a similar one to the new label?
Just faced the situation in which the bottom constraint was being pinned to the Bottom Layout Guide (a TabBar, in my case) instead of to the superview, as I wanted.
After tinkering around with programmatically created and or modified constraints, I found that you could actually do it through Autolayout's Pin Popover, just by selecting View instead of Bottom Layout Guide in the drop down that appears if you clic on the little arrow of the constraint's textfield.
That was, probably, not very clear, so here:
Adding a Bottom Space to Container constraint is the correct way to go. It will align a view to a constant distance from it's parent's bottom edge. If you add that constraint and it doesn't result in the correct behaviour when resizing the view, there might be other constraints on the view that might need to be removed first (think a top constraint).
You could also align your label to the other label totally ignoring the container of course if you find that easier to setup.
Related
In my storyboard, I have a parent UIScrollView in which I have a UIView of height about 2000px.
I have designed the whole view & placed an another UIView at bottom of parent scroll view so that it will be fixed in the UI. But at the specific point, I need to place that UIView(i.e.fixed) to get scrolled. Like after I scroll a UILabel, I want to scroll that UIView below that & get disappeared from the bottom.
I know its hard to explain but I am stuck at it for so long.
P.S. I'm using AutoLayout.
In this case it is probably best to have the view outside the scroll view but connect constraints to the inner view as well. You use priorities to control those constraints.
In your case you would decrease your bottom constraint priority (to 500 for instance). And you would add a constraint like outsideView.top <= insideView.bottom. So connect the outside view to one of the views inside the scroll view and create the relation be smaller (or greater if the 2 items are reversed) or equal to that view point.
To create a demo of this start a new project and open Main.storyboard:
Add a scroll view with constraints to leading, trailing, top, bottom
Add a blank UIView (now called innerView) inside the scroll view and add leading, trailing, top, bottom constraints
Add a height constraint to innerView to 2000
Add an equal width constraint between innerView and your scroll view
Set bottom constraint between innerView and scroll view to 100
Set a distinct color to innerView to see the effect
All other constraints should be set to 0
Add another UIView on the top level (now called outerView)
Pin outer view to leading, trailing and bottom. Also add a height constraint to 50
Set a distinct color to outerView to see the effect.
By now you should have a scrollable scroll view and a fixed view at the bottom if you run the app.
Now connect outerView with innerView and select "vertical spacing"
Double click the newly created constraint and modify it:
(If needed) Reverse first and second item so that the outer view is first item
Change relation to "less then or equal"
(If needed) select outerView.top
(If needed) select innerView.bottom
Set constant to zero
Select outerView and find bottom constraint to safe area (or superview) and set its priority to 500.
Now run the app. If all is correct your fixed view will be fixed until you scroll down far enough. After 2000px is visible the fixed view will be scrolling with scroll view.
You can naturally pin it to any view in scroll view to get any possible effect you need.
I hope this is descriptive enough. Good luck.
I'm attempting to put a generic view above and a tab bar underneath a scroll view, but can't figure out how to do it. Can someone explain how to properly place these constraints? Ideally I would like a solution non-programmatically, i.e. one that uses the storyboard. Thanks!
I've applied no constraints so far.
This is the desired output:
Well, In a UITabbarVC
Add UIView constraint top, leading and trailing to the self.view and assign height constraint to about 30% of self.view.height
Add UIScrollView add constraint bottom, leading, trailing to self.view and top constraint to bottom of the added UIView
First you have to give leading, trailing, top and a height constraint to your top view like so:
Then you need to give your scrollview, top, leading, trailing and bottom constraints like this:
And finally you give your tabbar leading, trailing and bottom constraints as shown:
First of all you need three things
UITabBarController
UIView
UIScrollView
Now, Firstly, you need to go in your .storyboard file and drag and drop a UITabBarController from the left hand panel
NOTE: If you are using XCode 10 , then that panel is renamed as Library which is available at the top bar with a Apple Home Button type button
Now, when you dragged UITabBarController, you will get some View Controllers attached with it by default.
Drag and drop a UIView to one of the view controller( preferably the first one) and set some Auto Layout constraints by selecting that View and clicking on the Add New Constraints button in the bottom bar ( where your Current zoom size is available) . You can add the following constraints :
Leading (aka left) = 0
Top = 0
Trailing (aka right) = 0
You also need to provide a height .
If you want to provide a constant height, then you can provide it using the same Add New Constraints option
However, if you want to provide a variable height like in Percentage , then hold Control on keyboard and click and drag from View that you dragged previously to the View Controller's View . Select the option Equals Height. Now it will take the height of the complete View Controller as it is taking 100% of the height of View Controller by default and we need to change that.
To change that, click on the View again , click Hide/Show inspectors (available on the top right corner) and select Size Inspector . There will be a constraint named Height which will be shown equal to superview . Click on the Edit button next to it and change the value of text field named Multiplier to the percent you want (make sure the value of constant text field is 0). If you want the height to be 20%, then input 0.2 and so on.
Next, You need to drag and drop a UIScrollView just below the custom view (that we just created and added the constraint to). Now set the constraints for the Scroll View in the same way you did for View.
For the Scroll View, you need to set the following constraints :
Leading (aka left) = 0
Top = 0
Trailing (aka right) = 0
Bottom = 0
and hit the Add Constraints button.
Now you will get the desired output . The only thing that will remain will be changing the colour of the View and changing the text label and icons for the UITabBarController items. You can change that via Storyboard easily.
Do let me know if you need any further assistance!
I have a weird behavior when I use scrollView.
As you can see in the picture bellow the button called "Back" has a bottom space constraint with value 0. But we can see is not even near to the bottom of the scroll view.
I already set the scrollview to have equals width and height of the superView and top,bottom,trailing and leading space with 0 value.
How can I fix this? I want the Back button still inside of the scrollview and put it at the bottom of the view.
Update
I have the code here https://github.com/rchampa/NDParallaxIntroView and the xib is called PageB.xib
Ricardo: you've added two constraint regarding manage y position of Validate Code button where your top constraint stop to move Validate Code button towards the bottom. So please remove top constraint of Validate Code only add bottom constraint.
you need to manage all constraint like your scrollview content view height will be equal to height. Please increase some top constraint from top.
So, if I understand correctly, the problem you are running into is that your back button is unable to be positioned based on the bottom of the scroll view.
A scroll has two sets of constraints in a storyboard, one that defines the size of the scroll view, and the other that defines the content size. The top, left, bottom, right to superview constraints on the scroll view will define the size.
The part that is causing your problem is that the content size is defined by the subviews inside the scroll view. So the button cannot be placed relative to the bottom of the scroll view since the scroll view doesn't know how large its content size is. All of the subviews of a scroll view must be placed in relation to each other.
So, create constraints for your logo, text fields, and all the buttons in relation to each other. Then create constraints from the outer most subviews to the scroll view.
In your example, you would constraints from the logo to the text field, 1st text field to 2nd text field, then 2nd text flied to the label, label to the "Send email..." button, and finally "Send email..." to the "Validate Code". For the "Back" button, it would need a left align with the text fields and then a center align with the "Validate Code" button. Create a top constraint from the logo to the scroll view. Then have leading and trailing constraints from one of the text fields to the scroll view. Finally, create a bottom constraint from either the "Back" or "Validate Code" buttons to the scroll view. You will also need some alignment constraints (logo center to the text field is an example of one). After that is all setup, your view will be fully defined for the content size of the scroll view.
If I understand you, my new question is: how can I make the subviews
make the height of scroll fit 100% screen device height? Is there a
way to define weights like Android? I don't know how achieve this
since the canvas is 600*600 which is different to every device.
Response would be too long for a comment:
So you wouldn't use a scroll view for that. A scroll view is specifically for containing content that will not fit on the screen (so the user can scroll to reach the new content).
The simplest solution is to add a regular view that has TopLeftBottomRight 0 distance constraints (so it is the max height and width of the screen) and setup the view like you have here to position the bottom in the bottom left all the time.
There is also a weight system, I can explain that if you want, but it wouldn't be required thus far.
I feel like your next response will be something like "what if I want it to scroll when its too small for the current screen?". The only way I know of doing that in encapsulating all your interface into a single UIView, and changing its sized in the viewDidLoad/viewDidAppear based on the size of the scroll view. Something like this:
func viewDidLoad() {
super.viewDidLoad()
containerViewHeightConstraint.constant = scrollView.frame.size.height
containerViewWidthConstraint.constant = scrollView.frame.size.width
}
Why the pin constraint doesnt work? I have no constraints, and I want to pin one view to bottom of main view, so I select the child view, then I click the icon from "w:Any h:Any row" in Interface Builder bottom right (Pin), then i click the bottom "I" to create bottom constraint, but if I resize the controller view (in design mode) the view is not moved but something like this appears: (The red line with number - instead of moving the blue view to bottom).
I have pinned it to "bottom layout guide". I also tried to pin it to "view" from dropdown while pinning, but that doesnt work too.
If I look on the "Issue navigator" there is only warning saying "Position and size are ambigious for View"
Without any other other constraints there is no way for Xcode to know what you want to do with the view, all it knows is that you want the bottom of your subview to stay 99pts away from the bottom of the superview, but doesn't know what to do with the top, left, or right edges.
Try adding constraints for the remaining 3 edges, it can be as simple as setting the width and height (the options under the bottom edge in your screenshot), or something more complex depending on what you want to achieve.
You need to define the position of view properly. So that constraints can define position and size of the object.
Like in your case you have only provided constraint from the bottom, which will not be sufficient to define position. So you need to define either Height and Width constraints or top, left and right constraints.
And as long as long red line is being shown keep adding constraints.
I have a UIView in my UIViewController in storyboard which I want to add a constraint on to space that view a distance from the top edge.
Now, when I do the usual by ctrl + drag to the ViewController's main view I only get option to set it to top layout guide.
This is a problem for me because at one point in the app Im going to move the main view up around 20-50px and what happens then is that view I have will not move... because its not aligned to superview.
How can I manually do this in storyboard or do I have to add it programatically?
Im using xcode 6.
There is an arrow to the right of the constraint constant value. If you click on it, a menu pops out where you can choose what is it that you want to make your constraint relative to. If you choose 'View', than it will pin it to the top of the view.
You should be able to do it by highlighting the view you want in the storyboard and then selecting Editor > Pin > Top Space to Superview in the top menu.
This is outdated in XCode 7, see #PaulGurov's answer instead.
TL;DR: You can constrain to the margin by pressing the Alt key on the keyboard.
One can also add that if the view you are trying to pin is not a direct subview of the view that you want to pin it to, the suggested approach is not really valid. Let's say the view hierarchy looks like that and you want to pin the image view (Parallax Image View in this case) to the view controller's view (View in this case).
To do that you just Control + Drag from the Parallax Image View to the View. That presents the default choices where you can see Vertical Spacing to Top Layout Guide to pin the Parallax Image View to the top layout guide.
What you want is to pin it to the top (margin) of the view. To do that you have to switch to the other set of constraints by pressing Alt
I had a whole bunch of constraints already there and I just wanted to change them rather than break them. Turns out if you double click on the constraint to edit, then click on the item that has the ".Margin", you can just turn off the "Relative to Margin" by selecting that item.
Dan's answer works. I just wanted to state that if you set your view in storyBoard at y < 20, and configure constraints through the pin panel, it will set top to superview:
If the height of the view is set to 0 by accident, Vertical Space to Top Layout Guide will NOT appear. Vertical Space to Bottom Layout Guide will appear, however, which must have made sense to someone inside Apple circa 2004.
None of the above answers worked for me, instead I have to do a hack to set my subview's top with superview's top instead with Top layout guide.
First, set the subview center vertically with superview.
Then, change the Center Y constraints for subview as well as superview to Top constraint.
You are good to go now.