I have a project where I have three labels in a custom cell prototype class (subclass of UITableViewCell) that are linked to three label outlets in the custom cell's .h file.
Then in my main viewcontroller class (which houses the prototype cells and is a subclass of UITableViewController) my delegate method that interacts with these labels looks like this:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier = #"ArticleCell";
ArticleCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
int row = indexPath.row;
cell.articleTitle.text = self.articleTitles[row];
cell.articleURL.text = self.articleURLs[row];
cell.articlePreview.text = self.articleURLs[row];
return cell;
}
Yet I get these three errors:
Connection "articleURL" cannot have a prototype object as its destination.
Connection "articlePreview" cannot have a prototype object as its destination.
Connection "articleTitle" cannot have a prototype object as its destination.
What exactly am I doing wrong? I'm so confused.
You might be connecting the Label outlets wrong in your project. I assume that labels articleURL, articlePreview and articleTitle are defined in the UITableViewCell. They should be connected for outlets in the corresponding customTableViewCell class not in the UIViewController. As you are referencing self.articleTitles in cellForRowAtIndexPath, it suggests that you are connecting them as outlets of current class not the customTableViewCell class. It is good idea to define your customTableCell as a property to your current class which is having UITableView's Delegate implemented.
Have a look at TableView Programming for details.
Related
I am trying to change a cell in a tableview from generic to custom and have created a new tableview cell class. However, I cannot get the cell to recognize the new custom cell. Instead, it is still displaying the generic cell although I've changed the setting in storyboard to custom in the identify inspector and also changed the class for the tableview cell to the new custom one. I have also wired the elements in the cell in storyboard to the new custom class.
My understanding is the tableview VC knows which class to use from the tableView cellForRowAtIndexPath method and I have changed that too with the code below. The project compiles but continues to show old generic cell. Can anyone see error or suggest what else to do?
#import "customCell.h"
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
customCell *cell = (customCell *)[self.tableView dequeueReusableCellWithIdentifier:#"Cell"];
Items *item = [self.fetchedResultsController objectAtIndexPath:indexPath];
return cell;
}
Thanks in advance for any suggestions.
Edit:
A custom cell is created in the storyboard on top of tableview by dragging uielements. Maybe this is an issue:
Style of cell is set to Custom:
You need to create new UITableViewCell and enable the "create XIB file...".
Create your custom cell in the XIB and make it's custom class as your class you just created.
Then in tableView cellForRowAtIndexPath register the Nib: (it's in swift but I bet you can figure out the objective c parallel...)
tableView.registerNib(UINib(nibName: "YourUITableViewCellClass", bundle: nil), forCellReuseIdentifier: "YourCustomIdentifierFromTheCustomClass")
Then access your cell:
var cell = tableView.dequeueReusableCellWithIdentifier("YourCustomIdentifierFromTheCustomClass")
and that's it.
you can create custom cell in your main story board by drag the cell view.
create custom class for that prototype.
mention the class name in identifier inspector.
import that class to your view controller .h file.
and made connection of your custom from main story board to custom class.h file.
it works!.
When you create a custom cell you have to do these things:
Setup the labels, images etc on storyboard cell.
Create a custom cell class (inheriting from
UITableViewCell)(CustomCell.h & .m), CustomCell.h having all of the
properties as iboutlet for labels, images etc. and synthesize them all
in implementation.
After creating this custom class go back to storyboard, select the
custom cell, change its class to the CustomCell and give it some
identifier like "MyCustomCell", then right click on the custom cell
and connect the IBOutlets with labels etc.
Now import CustomCell class in the class where you are implementing
the UITableView and use the properties you defined in CustomCell
class.
- (UITableViewCell *)tableView: (UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *) indexPath
{
static NSString *MyIdentifier = #"MyCustomCell";
CustomCell*cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier];
if (cell == nil)
{
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault
reuseIdentifier:MyIdentifier] autorelease];
}
// Here we use the provided setImageWithURL: method to load the web image
// Ensure you use a placeholder image otherwise cells will be initialized with no image
[cell.imageView setImageWithURL:[NSURL URLWithString:#"http://example.com/image.jpg"]
placeholderImage:[UIImage imageNamed:#"placeholder"]];
cell.myCustomLabel.text = #"My Text";
return cell; }
Select the cell on your Storyboard, and enter the name of your class in this field.
When you dequeue it from the identifier, it'll be an instance of that class.
Please note that each regular tableViewCell has a builtin and hidden UIImageView.
In Objective-C, you simply do this within your cellForRowAtIndexPath,
cell.imageView.image = [UIImage imageNamed:#"My awesome image"];
In Swift, it's pretty close.
cell.imageView?.image = UIImage(named: "My awesome image")
I have seen the other questions about cleaning up the connections in the nibs, but I don't believe that is my problem.
Currently I'm importing a custom UITableViewCell class, registering the nib in the VC with the UITableView in that VC's viewDidLoad as follows:
static NSString *cellIdentifier = #"cell";
UINib* cellNib = [UINib nibWithNibName:#"[nib for the custom cell]" bundle:[NSBundle mainBundle]];
[_theTableView registerNib:cellNib forCellReuseIdentifier:cellIdentifier];
Then later in the VC I implement the method
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString* cellIdentifier = #"cell";
CustomTableCell* cell = [tableView dequeueReusableCellWithIdentifier:outgoingNoteIdentifier forIndexPath:indexPath];
return cell;
}
If I don't connect any of the properties in the custom cell (just labels and buttons), then it loads fine, and I can see the images associated with both the labels and the buttons. When I try to connect just one of the properties in the xib file though, I get the above mentioned error.
it sounds like you are connecting your Nib outlets to the file's owner.
Try connection them directly to the cell instead.
I usually follow this flow:
Set file's owner to your custom cell class
Add outlets to file's owner, to get generated properties
Set cell's Custom Class to be same as the one specified as file's owner
Add all outlets to the cell. XCode will now show the properties your created in step 2
Happy coding
I have created a controller class which extends UITableViewController and "with XIB user interface" option. XCode created 3 files, .h file, .m file and a .xib file. When I open the xib file, it has table view, but I am not able to set the table view content as "static cells" like we are doing in a table view that is there in the story board. Can you please guide me here to how to create a static table view that is created through a table view controller class?
You cannot do that in the Interface Builder when creating a NIB file for the classes. If you want you can include it in a storyboard and set the cells as static there however. If you wish to create it in a Separate NIB file though, you must use the classes that have been generated. These classes will already have all the functions that you will use. If you wish to set 5 rows in the table, each with a city name in them, you'd use the following functions:
#property(nonatomic) NSArray* cities;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
cities = [NSArray arrayWithObjects:#"Alacante",#"Bournmouth",#"London",#"Manchester",#"Tyme", nil];
}
return self;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
//Return the number of rows in the section.
return 5;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
// Configure the cell...
cell.textLabel setText:[cities objectAtIndex:indexPath.row];
return cell;
}
Hey you are saying that you created a controller class which extends UITableViewController. When you extend UITableViewController in your class then you don't need to add table view from object library(appears bottom left corner). Xcode set all the basic requirements for adding tableview and it also set your delegate and datasource method and also implement required delegate method
In this case you to have only add your data(name text, detail text) to table view via programming
You will need to implement the UITableView delegate and datasource methods. Return your static values in the -numberOfSections and -numberOfRowsInSection: methods and return the cells according to indexPath in the -cellForRowAtIndexPath: method.
Who do to set a tableView Cell Identifier in a UIViewController ?
Using UITableViewController I always do it through the interface (see screenshot below)
Now I dont see that option if I use UIViewController
here's my code
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
NSString *messageAtIndexPath = [messageArray objectAtIndex :[indexPath row]];
[[cell textLabel] setText:messageAtIndexPath];
return cell;
}
please advice
Unless I add a prototype cell which messes my interface.
A couple things here:
1) A UITableViewController inherits from UIViewController (which I think is what you are actually talking about, instead of "UIControllerView"). UITableViewControllers have the ability to do prototype cells and set these identifiers...
2) ... which are case sensitive. In your screenshot, you call it "cell" while in your code you call it "Cell".
They need to be spelled exactly the same and in the same upper/lower case way.
It's not super clear what you are trying to do here, but I sense that you want to create a custom cell in your XIB or storyboard and then reference it in your "cellForRowAtIndexPath:" method. Here is a tutorial that talks about prototype cells and identifiers and using them in storyboards, and I hope this helps you out.
I am creating an App with following design:
I have a UITableView with custom UITableViewCell.
Each UITableViewCell contains a scroll view with multiple UIViews of size 150x150
Each of the small UIView contains a UITableView.
Since i am new to this, the forum is not allowing me to upload a picture, which could have explained the design very easily.
I have created the full design in the storyboard. The issue i am having is that the inner UITableView is not getting populated. The cellForRowAtIndexPath, numberOfSections or the numberOfRowsInSection methods of the datasource table view controller class do not get called.
I am using XCode 4.3.2 iOS5.
Following are the class structure:
NewsTableViewController : The ViewController for the mail table.
NewsTableViewCell : Custom TableViewCell which contains object of custom UIScrollView.
NewsScrollView: Custom UIScrollView containing UIViews and UITableView objects which are linked to the Storyboard UITableViews inside the UIViews.
NewsInnerTableViewController : TableViewController to be used as Datasource and Delegate for InnerTableViews.
I have created the object of NewsInnerTableViewController in NewsTableViewController and assigned it as delegate and datasource of the inner tableview.
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSSTring *CellIdentifier = #"NewCell"
NewsTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
newsInnerTableController = [[NewsInnerTableViewController alloc] initWithStyle:UITableViewStylePlain];
cell.scrollView.innerTable.delegate = newsInnerTableController;
cell.scrollView.innerTable.datasource = newsInnerTableController;
return cell;
}
I am unable to understand where i am going wrong. or is something like this needs to be created is some other way. or the Datasource and delegate needs to be assigned at some other level.
Please share your thoughts on this.
the trick is to have the UITableTableViewCell as the Datasource and delegate for the inner UITableView
http://iosstuff.wordpress.com/2011/06/29/adding-a-uitableview-inside-a-uitableviewcell/