I downloaded the Collection View example and I replaced the ImageView with textfield.
I want to make the textfield as big as the UICollectionViewCell (which is a square shape). But the shape of the textfield didn't change.
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{
static NSString *identifier = #"Cell";
UICollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:identifier forIndexPath:indexPath];
// height and width in the parent cell
double height = cell.frame.size.height;
double width = cell.frame.size.width;
// get the child textfield
UITextField *textField = (UITextField *)[cell viewWithTag:100];
// make the textfield as big as the cell
CGRect frame = CGRectMake(0, 0, width, height);
textField.frame =frame;
textField.text = #"testing";
return cell;
}
Do you have set the Tag of your UITextfield to 100 in XCode Designer? You have to set the Tag to 100 before calling your code, to ensure the UITextfield to be found.
Changing Border Style is not necessary, because you can do it with every Borderstyle.... I have done it already...
Go to your cellItem Nib in XCode Designer, select the UITextField and in the right properties, change the tag to 100... This will solve it
You can do that by changing the border style of UITextField.
See this Stackoverflow post: How to set border style of a UITextfield
I have found the root cause of this problem. The root cause is the auto layout, it resizes the width, height and the space between the cell and the textfield at the runtime. Once I removed the auto layout, the code work fine.... And the border style is not a matter.
I am looking for another way to solve this problem.
just try this..
NSInteger myCustomHeight = 237;
UITextField *textField = [[UITextField alloc] initWithFrame:CGRectMake(10, 10, 200, myCustomHeight)];
Related
Hi I'm able to achieve auto-resizing table view cells (based on amount of text) by pinning textLabel's top, bottom, left and right to content view's top, bottom, left and right. I was able to get different cell height for cell with different text length. But I want to achieve same auto-resizing result with button added as subview to cell. I have added exact same contrains to button as I have it with textLabel. Any help is greatly appreciate .
Summary : Here is an hand-made example about this problem.
First, read the answer about autoresizing tableviewcell with UILabel because you will do like that with a little changes.
The difference between UILabel and UIButton is UILabel has Intrinsic Content Size based on Width and Height. So you need to subclass UIButton and override method :
-(CGSize)intrinsicContentSize {
return CGSizeMake(self.frame.size.width, self.titleLabel.frame.size.height);
}
In your CustomCell class, override method
- (void)layoutSubviews{
[super layoutSubviews]; //btnTest is your Button
[self.contentView setNeedsLayout];
self.btnTest.titleLabel.preferredMaxLayoutWidth = CGRectGetWidth(self.btnTest.titleLabel.frame);
}
In your ViewController :
- (void)configureCell:(UITableViewCell *)cell forRowAtIndexPath: (NSIndexPath *)indexPath{
if ([cell isKindOfClass:[TestCell class]]) {
TestCell *testCell = (TestCell *)cell;
[testCell.btnTest setTitle:#"An example autoresizing UITableViewCell height based on UIButton added as subview by Matie.An example autoresizing UITableViewCell height based on UIButton added as subview by Matie.An example autoresizing UITableViewCell height based on UIButton added as subview by Matie." forState:UIControlStateNormal];
#warning You need to have this below line, to calculate height when the first time viewDidLoad.
testCell.btnTest.titleLabel.text = #"An example autoresizing UITableViewCell height based on UIButton added as subview by Matie.An example autoresizing UITableViewCell height based on UIButton added as subview by Matie.An example autoresizing UITableViewCell height based on UIButton added as subview by Matie.";
}
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath{
[self configureCell:self.prototypeCell forRowAtIndexPath:indexPath];
//
self.prototypeCell.bounds = CGRectMake(0.0f, 0.0f, CGRectGetWidth(self.tableView.bounds), CGRectGetHeight(self.prototypeCell.bounds));
[self.prototypeCell setNeedsLayout];
[self.prototypeCell layoutIfNeeded];
CGSize size = [self.prototypeCell.contentView systemLayoutSizeFittingSize:UILayoutFittingCompressedSize];
return size.height +1;
}
Hi I am using sizetofit on my UILabel field, it works fine when I load the tableview controller, but then starts cutting of letters and wrapping to another line when I scroll up and down. Here is the code I use in CellForRowAtIndexPath:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"subjectCell" forIndexPath:indexPath];
// Configure the cell...
// Load and display subject photo image
UIImageView *subjectImageView = (UIImageView *)[cell viewWithTag:200];
subjectImageView.image = [UIImage imageNamed:subjectImages[indexPath.row]];
// Load and display subject label
UILabel *subjectLabel = (UILabel *)[cell viewWithTag:201];
subjectLabel.text = [subjectItems objectAtIndex:indexPath.row];
[subjectLabel sizeToFit];// call this to fit size of the label according to text
return cell;
}
And here is a screen shot of my tableviewcontroller originaly loaded:
And here after scrolling up and down you can see the descriptions have been cut
Thanks for any help you can give to solve this.
Cheers
Carson
Using sizeToFit for UILabel can cause a mess like this in UITableView with reusing cells. One of solutions I can think of is to set the width of the frame for your label width before you call sizeToFit and you have to do this every time you assign text to the label. It should look something like this:
CGRect frame = subjectLabel.frame;
frame.size.width = 100.0; //try to adjust this value
subjectLabel.frame = frame;
[subjectLabel sizeToFit];
MY OBJECTIVE: I need to load an image on the UICollectionView, but changing the Y position of it on the UIImageView frame, because the loaded image is taller than the cell display window, and I need to display a specific part of it.
SETTINGS: The UICollectionView and the UIImageView were manually added to the storyboard (not programmatically). The UIImageView view mode is set to Aspect Fill on the Attributes Inspector.
THE PROBLEM: I've tried changing the UIImageView frame after (and also before) loading the image, but the change only takes effect after the UICollectionView is scrolled up and down, and I need the image position updated when it first loads.
PS: I've also tried all the different types of view mode on the UIImageView, but it doesn't seem to make any difference.
Here's the coding I'm using for it:
- (UICollectionViewCell *) collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
PhotoCell *cell = (PhotoCell *)[collectionView dequeueReusableCellWithReuseIdentifier:#"PhotoCell" forIndexPath:indexPath];
cell.photoImageView.image = [UIImage imageNamed:_stringImageURL];
CGRect oldFrame = cell.photoImageView.frame;
CGRect newFrame = CGRectMake(oldFrame.origin.x, -45, oldFrame.size.width, oldFrame.size.height);
cell.photoImageView.frame = newFrame;
cell.backgroundColor = [UIColor redColor];
return cell;
}
Any help would be greatly appreciated! Thanks in advance!
Hi everyone I have problem with my tableview, i make Cell with uilabel with SizeToFit and then calculate the UILabel Height for set the cell Height everything work well except when i scrolling my tableView the text get weird like one char per line:
My TableViewVell Method is:
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
}
UILabel *label = (UILabel *)[cell viewWithTag:1];
label.text = [someArray objectAtIndex:indexPath.row];
// Set the UILabel to fit my text;
messageLabel.lineBreakMode = UILineBreakModeWordWrap;
messageLabel.numberOfLines = 0;
[messageLabel sizeToFit];
return cell;
}
The Cell Height stay in the correct Size the problem only with the UILabel ...
this the result when i load the view:
First screenshot
And this is after i start scroll the TableView:
Second screenshot
Any Help???
The method sizeToFit respects the width of the frame and adjust the height. And table view cell reuse the cells. Combining those two behaviors can cause the issue you described.
One of your label, which is very short in content (e.g. in the 4th cell with the word "jio"), is resized with sizeToFit and the resulting width is smaller than the original width you intended.
After that, table view reuse the cell and sizeToFit still respects the small width calculated from previous call of sizeToFit.
Solutions:
1) set the width of the frame to your original intended label width everytime before you call sizeToFit:
CGRect frame = messageLabel.frame;
frame.size.width = 100.0; //you need to adjust this value
messageLabel.frame = frame;
2) use your row height calculation and set the frame height instead. No need to use sizeToFit.
you should probably subclass your cell and clean the UILabel on
override func prepareForReuse() {
super.prepareForReuse()
self.label.text = nil
}
This might help
http://www.cimgf.com/2009/09/23/uitableviewcell-dynamic-height/
The approach in given reference and solution provided by #Verbumdei is nearby same.
If you are not using autolayout, this can also be solved by adding a category on UIView
public func sizeToFit(constrainedSize: CGSize) -> CGSize {
var newSize = sizeThatFits(constrainedSize)
newSize.width = min(newSize.width, constrainedSize.width)
newSize.height = min(newSize.height, constrainedSize.height)
self.size = newSize
return newSize
}
The idea is to use sizeThatFits with a constrained size to determine the size to adopt and then use the min expected width/height.
Then you just have to do something like
yourLabel.sizeToFit(self.contentView.size) // or
yourLabel.sizeToFit(CGSize(width: maxWidth, height: self.contentView.size.height))
You can set preferred Width property of label. That worked for me
preferred Width
I'm attempting to create a custom UITableViewCell with its own XIB, of which contains two important, editable components:
UILabel
UIImage with 'end-cap insets' - this image sits behind the label, and resizes with it
When I create my UITableViewCell I can set its label's text easily, but in the same method I also try to change the UIImage's frame to match that of the UILabel's. However, this is not happening until I 'reload' the cell by scrolling the table view to dequeue it and bring it back into view.
I create the custom table view cell in my view controller's .m:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *UITableViewCellIdentifier = #"msgCell";
RMMessageCell *cell = [tableView dequeueReusableCellWithIdentifier:UITableViewCellIdentifier];
if (cell == nil) {
NSArray *topLevelObjects = [[NSBundle mainBundle] loadNibNamed:#"MessageCell" owner:self options:nil];
cell = [topLevelObjects objectAtIndex:0];
[cell customInit]; //This sets up the ImageView's image etc
}
[cell setMessageValue:[_messages objectAtIndex:indexPath.row]]; //SEE BELOW
return cell;
}
...And in my custom cell's .m, I deal with setting the text label and resizing the image with this method:
- (void)setMessageValue:(NSString *)message {
_testLabel.text = message;
// Assume the text label's frame has already been set to the message's length
// (will add this in once I figure out how to change the imageView's
// frame correctly)
// Set the image view's frame to the label's
// THIS DOES NOT TAKE EFFECT UNTIL THE TABLE VIEW IS RE-SCROLLED
CGRect frame = _imageView.frame;
frame.size.width = _testLabel.frame.size.width + 8;
_imageView.frame = frame;
}
This is caused because a table view cell is created at one size, and then it is resized when it is displayed after being added to the table. If you log the bounds or frame of your cell, you will see that it is one size (smaller) when you load it from the nib, and another size (bigger) when you "refresh" the cell by scrolling it off of the screen and back on.
The simplest approach would be to make sure that the label and image both have the same auto-sizing rules, so that when the cell is resized, they both grow together.
you can use UITableView delegate method,
– (CGFloat)tableView:(UITableView*)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath;
inside this you can set the height of row dynamically like..
// This is only for Example that you can set your cell height
-(CGFloat)tableView:(UITableView *)aTableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
NSString *text;
text = [_messages objectAtIndex:indexPath.row];
CGSize constraint = CGSizeMake(280, 2000);
CGSize size = [text sizeWithFont:[UIFont boldSystemFontOfSize:12] constrainedToSize:constraint lineBreakMode:UILineBreakModeWordWrap];
return size.height + 5;
}
You should be able to control the size of the subviews if you programmatically create them and add them to your tableview cell (i.e.,so that they are not set in storyboard, and thus are not subjected to explicit auto-contraints).
In my implementation, I created a customCell subclass. In the .h:
#property (strong, nonatomic) UILabel *customLabel;
Then in the .m:
- (id)initWithCoder:(NSCoder *)aDecoder {
METHOD;
self = [super initWithCoder:aDecoder];
if (self) {
// Initialization code
self.customLabel = [[UILabel alloc] initWithFrame:CGRectMake(0, 0, 320, 40)];
[self addSubview:self.customLabel];
}
return self;
}
In your tableViewController's .m file, in the method tableView:cellForRowAtAtIndexPath:
theCell.customLabel.frame = CGRectMake(0, 0, 320, 40);
theCell.customLabel.text = #"Whatever text you want";
This will give you instant and complete control over your custom label right when the tableview and cell loads.
In response to #inafziger, I tried programmatically removing the constraints on the label but it did not resolve this auto-resizing issue.
Update: making a temporary reference to the subview, then removing it from superview, and then adding it back to the subview, this worked just as well, with the slight exception that the in my case where I'm using a label, the height of the label was fit to the height of the text it contained (whereas programmatically creating the label in my example above, the label will have whatever height you assign it.) The advantage being that you don't have to create any custom labels, or even touch the subclass tableviewCell. Just use whatever you created in storyboard. Here's tableView:cellForRowAtIndexPath:
UILabel *theLabel = theCell.theLabel;
[theCell.theLabel removeFromSuperview];
[theCell addSubview:theLabel];
theCell.theLabel.frame = CGRectMake(0, 0, 320, 40);