Horizontal UILabels inside a self sizing UITableViewCell - ios

Question: How can I use constraints in a UITableViewCell using UITableViewAutomaticDimension when there are labels side by side which can each contain a different number of lines?
I have a table with cells that contain labels side by side:
I'm having a hard time getting the cell to size properly if one of the labels on one side have more lines than the corresponding label on the other side. One of the labels always gets cut off. If both labels have the same number of lines, the cell resizes perfectly and all text can be seen.
I've tried a number of constraint tweaks but nothing is working perfectly as desired.
I've tried adding hidden label for height...but it doesn't work well for the cell with 4 labels
I've tried placing the labels in a view but then the height of the view still needs to be calculated.
Currently the constraints are setup normally: top, bottom, left , right, labels are set to 0 lines etc and works great when both labels have the same text or same number of lines.
Is there any way I can do this with constraints? Or do I need to revert to the old height for row at index path? =(

There is a way to achieve what you want to do just using constraints. The trick is to set the relation of the constraints between the two lower labels and the bottom to Greater Than or Equal instead of equal.
Here is how I set the constraints:
Which has this result:
Or you could set the constraints between the labels top and bottom to Greater Than or Equal and leave the bottom constraint at equal:
To get this result:

I found a solution where I did not have to revert to using tableView:heightForRowAtIndexPath.
I added a label to the cell with the text color set to clearColor and called it 'heightLabel'. I added constraints to the heightLabel so the cell would resize based on the heightLabel's constraints.
Then whichever of the left or right labels had the most text, I placed that label's text inside the heightLabel.
The cells still were not resizing and I had to call 'layoutIfNeeded' on the cell before returning the cell in tableView:cellForRowAtIndexPath.
The heightLabel constraints are now what is being used to resize the cell and UITableViewAutomaticDimensions is working properly.
This may not be the best solution but it's working out pretty well. If there is a more proper way of doing this I'm open to suggestions.

Related

Create UITableViewCell constraints to match with built-in cells and avoid "fixed width constraints my cause clipping."

In my UITableViews I have a mixture of built-in cells and custom cells that mimic the look of built-in cells. For example, I use Left Detail Cell UITableViewCells as well as custom cells that also LOOK like a Left Detail Cell but have custom elements (like a left UILabel, but a textfield instead of the right UILabel and maybe other elements like a checkmark image to let the user know when they have entered valid info).
I originally set up the constraints on my custom cells so that blue left-side label would have a width constraint = 91 because that is what the built-in cell's label's width was.
However, for the last few versions of Xcode, it has been complaining at me about "Fixed width constraints may cause clipping."
I've seen all of the myriad Stack Overflow posts telling me to just make my constraint <= or >=, but that does NOT do what I want. I don't want those labels to get bigger, because then the various rows will not have a consistent width on those left detail labels. The screenshot below wouldn't have a consistent layout from row to row.
So, how can I set my constraints on that left detail UILabel so that it will match with the built-in Left Detail Cell's sizing behaviors without getting that stupid warning clogging up my build results?
I tried setting a proportional width on the label, but when I rotate the device my label gets much wider while the built-in Left Detail cell's detail label stays the same width and my UI looks janky because they aren't lined up anymore.
I tried making my fixed width constraint a lower priority (750) and adding a second <= constraint at priority 1000, but then it just complained about both constraints.
Example below:

UITableView cell vertical centering of label when another is empty

I have a UITableViewCell that contains two labels positioned vertically one on top of another, and I am using AutoLayout.
The cell works (and looks) fine when both labels have some text.
Sometimes, though, the top label does not contain any text, and in this case I would the cell to have the same height, but the bottom label to be centered vertically. Is it possible to do it with AutoLayout without modifying the constraints at run time?
I don't believe this can be accomplished without modifying something at run time. I see a few options if you'd like to do this without changing constraints programmatically, some messier than others:
First option, you could set three labels in the cell. Two labels that are stacked vertically and one that covers the whole cell vertically, fully overlapping both other labels. At runtime you can determine if the bottom label shouldn't contain text and then set the overlapping top label with the text you would have previously set on the top vertically stacked label.
Second option, you could utilize a label that has the height of both labels you currently have. Set this new (2x height) label to allow for 2 lines (can be done in InterfaceBuilder side options). Then at runtime interpolate the label.text attribute with both label's text. Put a new line character in between the labels if the second label has text. It would look something like this
In Swift:
my2xLabel.text = "\(firstLabelString) \n \(secondLabelString)"
In Obj-C:
my2xLabel.text = [NSString stringWithFormat:#"%# \n %#", firstLabelString, secondLabelString];
All of this being said, modifying the constraints at runtime may be a less hacky way to achieve this formatting.
Make two prototype cells then. One will be the one you have right now, the other would contain only one label but centred vertically. Check if the text would be empty, return the cell with the vertically centred label. Otherwise, return the other cell.

Xcode - Swift - iOS - Expanding TableView Cells Based on Title & Subtitle Sizes

I have a TableView that uses custom cells. These custom cells have three labels in them. The UIViewController looks like this:
I am trying to make it so that depending on the length of the title, location, and time labels, the cell will expand accordingly. I have set the number of lines each of the labels can take up to 0 (infinite). The TableView itself is constrained to the sides and bottom of the ViewController, and on the top to the thin blue UIView. The constraints of the three labels within the cell are as follows:
"Title" label constraints:
"Location" label constraints:
"Time" label constraints:
The problem is that when I run the simulator, I see that the labels, when the are too long for the cell, simply have "..." on the end, and don't go to the next line. They always stay one line. I want the text of the labels to go to next lines as needed and for the cell to expand accordingly.
In the code I have the lines:
tableView.rowHeight = UITableViewAutomaticDimension
tableView.estimatedRowHeight = 100.0
And I have the appropriate code the set the cells for the tableView, making sure to use the custom cell I have set up.
Make sure to set the appropriate Content Compression Resistance Priority. This means that the label should try to resist "being squished" or compressed. Try making them slightly different for each label in case the constraints "compete" for some reason. For example, make the TitleLabel's vertical priority 752, LocationLabel 751, and TimeLabel 750.
I ran into the same problem. After battling for ages I found that reducing the horizontal compression resistance settings for the labels to 250 (top label) and 251 (bottom label) worked!
I don't fully understand why, and have posted a question here to try find answers: https://stackoverflow.com/questions/33236691/how-does-reducing-horizontal-compression-resistance-for-a-label-affect-row-heigh

TableViewCell with multiple columns

I have an application in which I want to have a tableView with custom tableViewCell that has five columns.
I want them to be like 20%, 30%, 15%, 20% and 15% of the whole cell's width, because I want my application to launch on iPhone and iPad.
What is the best way to do this?
Now I have created a tableViewCell prototype with 5 labels. I also added constraints to them but the width constraint is just a constant. Also when I added width constraints to labels, some collisions appeared there and I don't know how to fix them.
Here is a screenshot.
You can create table view cell with collection view. By that, you can get different part in cell as well as you can change each column width programmatically based on your needs.
Thanks
A table view has only one column and allows vertical scrolling only. link
If you want to use a few columns, you can use UICollectionViewController
I also added constraints to them but the width constraint is just a constant. Also when I added width constraints to labels, some collisions appeared there and I don't know how to fix them
To fix it change width constraints to be a multiplier of superview width.

UITableViewCell with two labels wont center

I have a UITableView below that has a custom uitableview cell. I am trying to get the two labels inside it do be 50% in width and have the left cell have right aligned text and the right cell to have left aligned. Any clue why this isnt working correctly below?
Use auto-layout, and set both the labels an equal width constraint, it should do the trick.
Edit:
Without auto-layout you can try something like that:

Resources