Storyboard - let view scale itself but within constraints - ios

I'm completely stuck with getting along storyboards.
What I'm trying to do is the view that basically groups two label to look like this:
So I want the quote and the author right under the quote which is anchored to right edge.
This view will be reused multiple times so I created a xib for that which looks like this.
As you can see the view is free form and the quote label centered with the author label anchored to the right edge of it.
What I expect from it that I can place it in the storyboard view controller with the following conditions:
This view has as much width as it needs but it shrinks if too width to make at least 10 points from each side
This view has as much height as it needs but aligns at center of the parent view horizontally.
So I've added it to the view and set the following constaints.
But when I compile I see the following:
What am I doing wrong?

Related

Vertically centering text with an image in a horiztonal stack view (AutoLayout) - iOS

I've been having some problems centering text vertically beside an icon in a horizontal stack view. Here are some facts:
1) I create a view to hold stack view - add constraints
2) I place a horizontal stack view inside of that view - add width and height constraint, add vertically center constraint, add height constraint
3) Add an image and a label to the horizontal stack.
4) I make the image a certain width and match the height
5) I leave the label alone
6) I select the stack view and specify to set the Alignment to Center
In a new view controller this works great! Everything is perfectly aligned vertically. BUT in any existing controller I've created, it doesn't work! The text is rendered a few points above the center of the image, AND not at the top.
The only difference I can see is new view controller vs existing view controller, and simple layout compared to my more complex layout.
I have no auto layout errors, and don't really consider recreating all my view controllers to be an option. Anyone have any ideas?
Wow, so I have this partially figured out. Its the custom font we are using for our app!
This was the primary difference. All my normal app views inherit from a base view where I set the font for the entire view. That is why when I tested in new view controllers (not inheriting from base) it would work.
If you are having trouble getting text perfectly vertically centered and you think you have done everything right, check your font.
Happy coding...

UICollectionViewCell sizeForRowAtIndexPath and Two Views side by side

I am trying to accomplish what the Imgur app has done in one of their UICollectionViewCells in their about view. See below:
I want 1 UICollectionViewCell but instead of 3 sections of views inside the cell, I just want two (comments and posts).
For my UICollectionView I am resizing the cell at runtime to make it fit almost the whole screen minus a bit for margin's sake because I want to make a card view like Imgur.
I followed this stackoverflow post to get 2 views side by side: iOS Autolayout: two buttons of equal width, side by side
and I am able to get 2 views side by side of equal width. Here's what they look like in the storyboard:
but when I run the app, my views get stretched because of the autoresizing. See below:
How can I get the views to both be of equal width and have equal spacing between, before and after the views?
You can use UIStackView. It provides an easy way to lay out a series of views horizontally or vertically.
Select the two views and click on the new Stack button in the Auto Layout toolbar at the bottom right of the storyboard canvas:
Give constraints to your stack view from top, left, right and bottom. Then make your Attributes Inspector of the stack view like this:
NB. If you want to learn more about Stack View, follow this fantastic tutorial in Ray Wenderlich: https://www.raywenderlich.com/114552/uistackview-tutorial-introducing-stack-views
Believe me most of the complexities associated with Autolayout will become trivial once you learned Stack View

iOS UIScrollView, what am I misunderstanding? I cannot get a scrollview to scroll

I am a pretty new iOS developer and am coming across my first need for a scroll view. The page I need to design is a little complex. Since I was struggling to get that to layout correctly, I decided to create a super simple scene just so I could make sure I understood how to get UIScrollViews to work. Apparently it didn't help as things aren't working and I am stuck after following several tutorials.
I'm working in Xcode 8.1 and Swift 3.
Screenshots at the end of this post.
I have a scene that consists of a scrollview and a child view with two labels in it. I’ve set the labels to be ~700pt apart to try to make scrolling happen. Nothing scrolls and you can only see the first label. Additionally, the child view does not expand to be full height.
You can see in the screen shots that my scroll view has constraints to pin it to the sides of the superview.
The child view has the same.
The label constraints position them within the child view and 700pt from each other. I thought that this would give the views the height they need to make scrolling happen. There are no constraint errors.
I am hoping for the red childview to fill the vertical space and then scroll. At this point I’d take any layout as long as something was scrolling. Nothing is though, what do I not get?
Screenshots:
(removed due to link limit because I'm still a new SO user)
EDIT (6/12/16):
I've made some changes and gotten a little closer. Primarily, it was suggested to me elsewhere to set one of the labels to be equal height with the scroll view. This now gives me the "bounce" effect which means stuff is sort of scrolling; however, we're still only dealing with one screen of content as the second label which is hidden below is clipped off.
Here's where things stand:
edited hierarchy
edited screenshot
When you are using a UIScrollView in a storyboard, you need to ensure that the scroll view is able to compute the size of its content. If you don't have sufficient constraints then you will get an error in Interface Builder:
Scrollable Content Size Ambiguity
Clicking the Info icon on this error will advise you that there needs to be constraints touching all sides of the scroll view and to ensure that you can trace a continual line of constraints from left-to-right and top-to-bottom.
You can achieve this with or without the content view you have added. I will show you how to do it without the content view in scroll view, simply because there are fewer constraints that way and therefore less typing.
Add the scroll view to the root view
Constrain the top/left/top/bottom of the scroll view to its superview (the root view). Remember to turn off constrain to margins if you want the full width of the screen
Add label 1 and label 2 to the scroll view
Constrain top/leading/bottom of label 1 to the scroll view
Constrain top/trailing/bottom of label 2 to the scroll view
Constrain the trailing edge of label 1 to the leading edge of label 2 with 0 space
Constrain label 1 width to be equal to the width of the scroll view
Constrain label 1 height to be equal to the height of the scroll view
Constrain the width and height of label 2 to be equal to the width and height of label 1
There is no step 10 :)
ScrollViews are particular in that they like to know explicitly how much they are supposed to scroll. The best way I have found to handle this is to have the following hierarchy with some constraints:
-Scroll View
-Content View
-View (constrained to top, bottom, leading, trailing anchors)
-Your other views (e.g. Label)
By having one View living underneath the Content View and then containing all of your other Views within that View, the ScrollView then knows how much it's supposed to scroll (it just uses the size of the one child View) no matter how much stuff you have inside of the child View.
Let me see if I can snap a picture of an example from one of my projects. In the meantime, give this hierarchy a try and let me know if it works for you. You would probably constrain the Label to the top and leading anchors of the child View and then constrain the height to something taller than the screen (e.g. 1000 units).
Let me know if you have any questions.
Edit: Example hierarchy below

Snapping arranged views to top of UIStackView

I have a Vertical UIStackView with 7 elements inside. These elements are not collectively tall enough to fill the entire view, so they get spaced based on the distribution value. I would like the arranged views to stack at the top of the view, with no space at the top and empty space at the bottom. I would also like to be able to control the spacing below each view as well, if possible.
I have tried every available distribution option, none of them accomplish what I'm trying to do. Help is appreciated!
Update: Adding an image of my desired result to make it easier to understand
The views have variable heights (no problem, I have this working)
The views should appear in the order I add them (also working)
The functionality I want is this: The first view is anchored to the top of the stack view, the second view is anchored to the bottom of the first view, etc.
Have you tried using a stack view that embeds another stack view and an empty view. This could give you the results that you require. Create your view hierarchy this way.
Stackview
Stackview
FirstView
SecondView
ThirdView
....
SeventhView
PaddingView
By embedding your 7 views inside a stack view and then use a padding view and then embed the first stack view and the padding view inside another stack view you could achieve all the things that you want.

iOS autolayout to center my view between two views

How to set up autolayout in Interface Builder to arrange views vertically as shown on image:
Top view pinned to top screen edge, Bottom view pinned to bottom screen edge. My view should be centered between top and bottom views (so distance to Top view equals to distance to Bottom view)
The way to do this is to have 2 invisible "spacer" views between you visible views.
You can't make spaces have equal height. But you use the "spacer" views and place them between your views (with 0 gap to the surrounding views).
Then you give these views equal heights and they will push your views around to centre the My View with equal gap to the Bottom View and Top View.
i.e. like this...
V:|[Top View][spacer1][My View][spacer2(==spacer1)][Bottom View]|
EDIT - Another way
I just thought of another way of doing this. You could have an invisible container UIView that is between Top View and Bottom View with no gap.
Then you place My View inside this invisible view and centre it vertically.
One more solution is to add an invisible view between top view and botom view and place my view in center of this view:
(5 years later) I've found the most canonical solution:
UILayoutGuide is specially introduced to solve this kind of tasks (since iOS 9).
Use layout guides to replace the dummy views you may have created to represent inter-view spaces or encapsulation in your user interface - Ref docs
It works pretty fine in code, but unfortunately Interface Builder doesn't support custom layout guides.

Resources