I'm having a view with 3 Table views.
Each table view will use one "Custom Cell View". I'm using the following code. But its showing only one table view. Can some one point me why? (All the arrays are filled with necessary objects)
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString* cellID = #"CustomSyncCell";
CustomCellView* cell = (CustomCellView*)[tableView dequeueReusableCellWithIdentifier:cellID];
if(cell == nil)
{
NSArray* nibObjects = [[NSBundle mainBundle] loadNibNamed:#"CustomCellView" owner:nil options:nil];
for(id currentObject in nibObjects)
{
if([currentObject isKindOfClass:[CustomCellView class]])
{
cell = (CustomCellView*)currentObject;
}
}
}
ObjectDetails* obj;
if(tableView == phoneNumbersTable)
{
obj = [phoneNumbersArray objectAtIndex:indexPath.row];
}
else if(tableView == mailIDsTable)
{
obj = [mailIDsArray objectAtIndex:indexPath.row];
}
else if(tableView == socialUpdatesTable)
{
obj = [socialUpdatesArray objectAtIndex:indexPath.row];
}
cell.keyLabel.text = [self returnPhoneType:obj.objKey];
cell.valueLabel.text = obj.objValue;
return cell;}
You have 2 options.
Set tag property on your tableViews and in the dataSource and Delegates methods test for that tag.
Make 3 objects and each objet set it for is specific tableView delegate and data source and put your code in that objects.
Hope that helps. If you will add all your data source and delegate methods more people will try to help.
The problem might be with the reuse identifier. Since you are using the cell with the same identifier for all the table views so, I think that is the cause of the problem. I also had this problem fixed it with the same manner. Create separate cells for each tableview with different identifier and reuse them.
Related
I was wondering if anyone knows how to solve this problem:
I have a UITableview, where the datasource can continue to grow. The issue is when I add elements to the data source, the table cells get messed up.
Each table cell has a text field where the user can enter data into it, but whenever I add data to the datasource the comments replicate to other cells.
- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *cellIdentifier = #"ImageTableCell";
ImageTableCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
Picture *aPicture = (Picture *) [self.imageData objectAtIndex:[indexPath row]];
if (cell == nil)
{
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"ImageTableCell" owner:self options:NULL];
cell = (ImageTableCell *)[nib objectAtIndex:0];
}
NSLog(#"comment %# index %d", aPicture.comment, [indexPath row]);
cell.cellImage.image = aPicture.picture;
cell.commentField.delegate = self;
cell.commentField.text = aPicture.comment;
cell.index = [indexPath row];
cell.tag = [indexPath row];
return cell;
}
self.imagedata is a NSMutabaleArray.
EDIT
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return [self.imageData count];
}
-(void) reloadImages:(NSNotification *) aNotification {
self.imageData = ((AppDelegate *)[[UIApplication sharedApplication] delegate]).currentUserData.images;
[self.imageTableView reloadData];
}
a screenshot http://www.mikerizzello.com/pic.png
Thanks
EDIT:
I think you might have a bad MVC pattern. Here's what I would do:
Take your custom cell, ImageViewCell, and make that class your textField delegate. Add a property for your custom Picture object, and set that in cellForRow...
Then, in your textFieldDelegate methods inside the custom cell class, you can change set the contents of your PictureObject there. I have a feeling that you're handling text input in the viewController, and the index of the data object in your array is getting mixed up and you're applying the comment field text to the wrong item in the array.
EDIT
I think it has something to do with cell reuse. The contents of your cell are not getting wiped out upon reusing a cell.
Try this block before you return the cell:
if (!aPicture.comment) {
cell.commentField.text = #"";
} else {
cell.commentField.text = aPicture.comment;
}
Have you try with
if (cell == nil) {
cell = (ImageTableCell*)[[ImageTableCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
}
Anyway you can also set different reuseIdentifier for each of cells but it will be bad idea, I would like to help you but i think need to run this project.
Please let me know if code above give better solution.
Create a Table View.
then create a customize table View cell and place a button on cell and Now I try to get Table View index when click on index.
But when I click on button that place on cell It's not giving me the Index of list.
My Table View class name is SubMenuViewController and cell class name is SubMenuCell
and my code of SubMenuViewController is:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
ModelLocator *model = [ModelLocator getInstance];
static NSString *simpleTableIdentifier = #"SubMenuCell";
SubMenuCell *cell = (SubMenuCell *)[tableView dequeueReusableCellWithIdentifier:simpleTableIdentifier];
if (cell == nil)
{
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"SubMenuCell" owner:self options:nil];
cell = [nib objectAtIndex:0];
}
if (model.foodSubItemList) {
FoodSubItemVO* foodSubItemTemp = [model.foodSubItemList objectAtIndex:indexPath.row];
[cell.lbSubFoodItem setText: foodSubItemTemp.foodSubItemName];
[cell.lbPrice setText: foodSubItemTemp.price];
[cell setIndexPath:indexPath];
}
return cell;
}
and My SubMenuCell code here
- (IBAction)addItemIntoOrder:(id)sender {
NSLog(#"#%",indexPath);
NSLog(#"#%",indexPath.row);
}
indexPath declare in SubMenuCell.h
Your NSLog's are faulty; try this instead (mind that changed % and # order).
- (IBAction)addItemIntoOrder:(id)sender
{
NSLog(#"%#",indexPath);
NSLog(#"%#",indexPath.row);
}
Make sure that the addItemIntoOrder: action is hooked up to your delegate correctly in IB.
I have a table that has its content filled using one of the two datasets provided based on the value of the segmented control attached. The data is pulled from the web.
The application crashes when I move back and forth between the two datasets and then select a table cell. The application works without hiccups when I use two separate table rather than a single table with a segmented control. Somehow combining them renders the application unstable.
One of the most error is when I tapped one the Acells of A table and while its loading I tapped the segment index=1, which will load B. it cause unrecognized selector being sent. meaning of the parameter o A table to being sent to B table.
// Customize the appearance of table view cells.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier0;
if (choice == 0) {
CellIdentifier0 = #"ACell";
} else if (choice == 1) {
CellIdentifier0 = #"BCell";
}
UITableViewCell *cell;
cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier0];
if (cell == nil) {
if (choice == 0) {
[[NSBundle mainBundle] loadNibNamed:#"ACell" owner:self options:nil];
cell = ACell;
self.ACell = nil;
} else if (choice == 1) {
[[NSBundle mainBundle] loadNibNamed:#"BCell" owner:self options:nil];
cell = BCell;
self.BCell = nil;
}
}
if (choice == 0) {
[(ACell *)cell setA:(A*)[contentArray objectAtIndex:indexPath.row]];
} else if (choice == 1) {
[(BCell *)cell setB:(B*)[contentArray objectAtIndex:indexPath.row]];
}
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if ( choice == 0) {
A = [contentArray objectAtIndex:indexPath.row];
[[NSNotificationCenter defaultCenter] postNotificationName:#"showA" object:A];
} else if (choice ==1) {
B = [contentArray objectAtIndex:indexPath.row];
[[NSNotificationCenter defaultCenter] postNotificationName:#"showB" object:B];
}
}
Assuming that ACell has the retained value when the nib file is loaded, doing self.ACell = nil; will release the older value and set ACell to nil. Now the older value is the one pointed to by cell. So technically it would be pointing to junk as it would've been deallocated because ACell is the only variable retaining the object. You can fix this by replacing,
cell = ACell;
with,
cell = [[ACell retain] autorelease];
As a sidenote, in the didSelectRowAtIndexPath: method you're doing } else if (choice = 1) {. Make sure you use == rather than = which will always evaluate to true along with changing the value of choice although it is unlikely in this case.
check choice spellings
if (choicee==0) {
[[NSBundle mainBundle] loadNibNamed:#"ACell" owner:self options:nil];
cell = ACell;
self.ACell = nil;}
else if (choice==1) {
I have a simple cell - designed in IB - and with the reuseIdentifier set. Below code works quite nicely. HOWever - the NSLog() reveals that the results are never cached.
Table view controller class:
- (UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
switch/case for various cell types
{
Foo * item = [results objectAtIndex:indexPath.row];
return [MyCell tableView:tableView populatedCellWith:item];
}
}
MyCell class..
+(UITableViewCell *)tableView:(UITableView *)tableView populatedCellWith:(Foo *)item
{
static NSString * identifier = #"XXX";
MyCell *cell = (MyCell *) [tableView dequeueReusableCellWithIdentifier:identifier];
if (cell == nil) {
NSArray * items = [[NSBundle mainBundle] loadNibNamed:#"MyCell"
owner:self options:nil];
cell = [items objectAtIndex:0];
assert( cell && [cell.reuseIdentifier isEqualToString:identifier]);
NSLog(#"That was a load - rather than a nice cache for %#", self.class);
}
fill out some stuff.
return cell;
}
Why is this - as it makes things a lot more efficient ?
Thanks,
Dw.
The way you create the table view cell can not make sure to put the cell into the reusable queue in table view. Only way to do that is to use
initWithStyle:reuseIdentifier:
Initializes a table cell with a style and a reuse identifier and returns it to the caller.
My another question
Are you sure the cells have been set with a cell identifier? UITableView will not cache those without.
I'm getting "Reaching end of non-void function" warning, but don't have anything else to return for the compiler. How do I get around the warning??
I'm using customCells to display a table with 3 Sections. Each CustomCell is different, linked with another viewcontroller's tableview within the App, and is getting its data from its individual model. Everything works great in the Simulator and Devices, but I would like to get rid of the warning that I have. It is the only one I have, and it is pending me from uploading to App Store!!
Within the - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {, I have used 3 separate If() statements-(i.e.==0,==1,==2) to control which customCells are displayed within each section throughout the tableview's cells. Each of the customCells were created in IB, pull there data from different models, and are used with other ViewController tableViews.
At the end of the function, I don't have a "cell" or anything else to return, because I already specified which CustomCell to return within each of the If() statements.
Because each of the CustomCells are referenced through the AppDelegate, I can not set up an empty cell at the start of the function and just set the empty cell equal to the desired CustomCell within each of the If() statements, as you can for text, labels, etc...
My question is not a matter of fixing code within the If() statements, unless it is required. My Questions is in "How to remove the warning for reaching end of non-void function-(cellForRowAtIndexPath:) when I have already returned a value for every possible case: if(section == 0); if(section == 1); and if(section == 2).
*Code-Reference: The actual file names were knocked down for simplicity, (section 0 refers to M's, section 1 refers to D's, and section 2 refers to B's).
Here is a sample Layout of the code:
//CELL FOR ROW AT INDEX PATH:
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
//Reference to the AppDelegate:
MyAppDelegate *appDelegate = (MyAppDelegate *)[[UIApplication sharedApplication] delegate];
//Section 0:
if(indexPath.section == 0) {
static NSString *CustomMCellIdentifier = #"CustomMCellIdentifier";
MCustomCell *mCell = (MCustomCell *)[tableView dequeueReusableCellWithIdentifier:CustomMCellIdentifier];
if (mCell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"MCustomCell" owner:tableView options:nil];
for (id oneObject in nib)
if ([oneObject isKindOfClass:[MCustomCell class]])
mCell = (MCustomCell *)oneObject;
}
//Grab the Data for this item:
M *mM = [appDelegate.mms objectAtIndex:indexPath.row];
//Set the Cell
[mCell setM:mM];
mCell.selectionStyle =UITableViewCellSelectionStyleNone;
mCell.root = tableView;
return mCell;
}
//Section 1:
if(indexPath.section == 1) {
static NSString *CustomDCellIdentifier = #"CustomDCellIdentifier";
DCustomCell *dCell = (DCustomCell *)[tableView dequeueReusableCellWithIdentifier:CustomDaddyCellIdentifier];
if (dCell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"DCustomCell" owner:tableView options:nil];
for (id oneObject in nib)
if ([oneObject isKindOfClass:[DCustomCell class]])
dCell = (DCustomCell *)oneObject;
}
//Grab the Data for this item:
D *dD = [appDelegate.dds objectAtIndex:indexPath.row];
//Set the Cell
[dCell setD:dD];
//Turns the Cell's SelectionStyle Blue Highlighting off, but still permits the code to run!
dCell.selectionStyle =UITableViewCellSelectionStyleNone;
dCell.root = tableView;
return dCell;
}
//Section 2:
if(indexPath.section == 2) {
static NSString *CustomBCellIdentifier = #"CustomBCellIdentifier";
BCustomCell *bCell = (BCustomCell *)[tableView dequeueReusableCellWithIdentifier:CustomBCellIdentifier];
if (bCell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:#"BCustomCell" owner:tableView options:nil];
for (id oneObject in nib)
if ([oneObject isKindOfClass:[BCustomCell class]])
bCell = (BCustomCell *)oneObject;
}
//Grab the Data for this item:
B *bB = [appDelegate.bbs objectAtIndex:indexPath.row];
//Set the Cell
[bCell setB:bB];
bCell.selectionStyle =UITableViewCellSelectionStyleNone;
bCell.root = tableView;
return bCell;
}
//** Getting Warning "Control reaches end of non-void function"
//Not sure what else to "return ???" all CustomCells were specified within the If() statements above for their corresponding IndexPath.Sections.
}
Any Suggestions ??
You need a return at the End of the function, regardless of whether you're handling the return inside of a {} block. Try:
return nil;
It'll never get executed, but you'll have a return for the compiler. I'd frankly redesign the statement.
Instead of using three separate if statements, change it to if() - else if() - else