Creating fixed subviews outside of uiscrollview - ios

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!

Related

I need to scroll a floating(fixed) UIView in my storyboard after a specific point in UIScrollView

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.

Vertical space constraint strange behavior

I am trying to implement UIScrollView from Storyboard using Interface Builder. The ViewController im working on have UINavigationBar.
This is the steps i perform within my Storyboard
adding UIScrollView and set the top, bottom, left, right spacing to 0 (not to margins).
add UIView and set it to be a child of the scrollView. set its spacing to: top, left, right to 0 and it width and hight to the value listed, also set spacing to bottom of the viewcontroller.
The strange behavior is that the top constraint get way high than expected,
What am i missing here?
Thanks!
Well what you can do is select your view controller from the heirarchy on the left and in the attributes inspector uncheck "adjust scroll view insets".

Arrange 3 UIButtons(of equal width) side-by-side

How to arrange 3 UIButtons side-by-side.I am using Auto-layout. My requirement is:
1.they should be equal width regardless of device
2.occupy vertically from starting to end of the view
i tried different ways, i failed to achieve that. Is it possible through interface builder
There are 2 ways to do this.
Way 1:
With use of equal width constraint of button
Select all 3 buttons and add
top, left , right, height and equal width
Way 2:
With use of Stack view
Step 1: Add 3 buttons.
Step 2: Select all that buttons, Once you selected, click on the Stack button in the Auto Layout toolbar at the bottom right of the storyboard canvas. see below in image.
Alternatively you can embed in From Editor -> Embed in -> StackView
Step 3:
Add Constraints to StackView. like below.
Step 4:
Select StackView, Once selected go to Attributes inspector. Change the Distribution to Fill Equally:
And its Done!
Select 3 buttons and give this constraints
- leading
- trailing
- bottom
- Height
- equal width
You can check some references from equal width to 3 labels and from setting two buttons of equal width, side by side
Set the constraints as following :
Select all button and set the equal width constraint, this constraint will keep the width of all the buttons same.
Select all buttons and set the bottom margin, this will keep all the button at bottom of the screen in all form factors.
Set the left margin and right margin of first and last button respectively, with the superview.
Select the button in the middle and set left margin and right margin constraint.
It is possible through interface builder. This is what you do
Create a UIViewController from your Storyboard by clicking the Object Library button.
Now select and drag three buttons and add them to your View Controller. Be sure to add the buttons through here. Drag and drop in the View of your View Controller. Be sure to place the buttons at the bottom of your View Controller.
After your three buttons are added , it should look something like this
Now comes the interesting part. Now what you need to do is add constraints to your buttons so that they stay always at the bottom and of equal width. For simplicity let me call the three buttons as left , center and right button. To keep the button at the button , select the center button and press CONTROL on your keyboard and drag the button to the View. Select the constraint
Vertical spacing to Bottom Layout Guide
and keep a constant = 0. Now for the other two buttons you do this. Simply press CONTROL and drag to the central button. Select the constraint
Bottom
and keep constant for that constraint as 0.This ensures that all the buttons stay at the bottom.
Add the Height constraint as much as you want for all the three buttons.
At the end, these are the constraints you must have.
Center Button Constraint
Left Button Constraint
Right Button Constraint
Now all you need to do is Control+drag the Width constraint of your center button to your ViewController.swift file and change the constant of the width to
widthConstraint.constant = UIScreen.mainScreen().bounds.width/3
And that's it.

Using autolayout constraints to define height minus a constant with storyboard

Is it possible to have a View with autolayout , such that the subview has equal height with parent minus a constant?
The Hierarchy is UIView > UIScrollVIew > UITableView. The view is also embedded in a UINavigationController
Yes. You simply pin the subview to the top and bottom of its super view with the constant set to the offset you wish.
As the outside view changes, the inner view will change to match and maintain the offset. You will need to set left and right constraints as well using the same mechanism.
Edit after discussion:
The UIScrollView needs to know the size of your content. You can not simply use auto layout without a few adjustments.
Assumption is your view layout is:
UIViewController -> UIScrollView -> UIView -> UITableView
For your UIView, pin the top, bottom, left and right to the UIScrollView.
To see things properly in storyboard you also seem to have to center the UIView horizontally and vertically. Once you add this you should see the content fill the scroll view bar any edge offsets you set in your pinning.
Pin your UITable to the UIView top, bottom, left and right.
You are going to have to adjust the width in your code somehow to the size you want to scroll horizontally.
In Interface Builder:
Clear constraints on your subview
Select your subview
Choose Pin in right bottom corner of IB view
Select bottom pin and enter your constant (I entered 30), select top pin and enter 0.
Select other constraints if needed.
Accept with button Add x constraints

Autolayout: Add constraint to superview and not Top Layout Guide?

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.

Resources