create checkbox inside uitableviewcell - objective-c

I have uitaleviewcell with different sections and rows, I want to have checkbox cell that you can see in the picture
my question is how can I create checkbox in uitableviewcells?(I used storyboard)

Use UISwitch and in the property inspector, set an empty box image for normal state and a checked box image for highlighted state. However checkbox behaviour is represented by switches in ios, a checkbox has a very small hit area and might pose a usabilty problem for your users, especially when they are close to each other as in the image you provided.
UISwitch Reference

Each checkbox cell should be a Custom TableViewCell. Then simply drop an ImageView and a Label in the TableViewCell and use didSelectRowAtIndex: to toggle the image between checked/unchecked.

You need two images for imageView of cell
#define SELECTED_ROW #"selectedRowImage.png" // CheckBox with Selected sign png
#define NOT_SELECTED_ROW #"notSelectedRowImage.png" // Empty CheckBox png
// listSelected is array of indexes selected
in ViewDidLoad:
NSMutableArray *listSelected = [[NSMutableArray alloc]init];
// CellForRowAtIndexPath:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *cellIdentifier = #"select";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier: cellIdentifier];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier] autorelease];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
}
if ([self checkIfIndexPathAlreadySelected:indexPath])
cell.tag = 1;
else cell.tag = 0;
if(cell.tag == 0)
cell.imageView.image = [UIImage imageNamed:NOT_SELECTED_ROW];
else
cell.imageView.image = [UIImage imageNamed:SELECTED_ROW];
return cell;
}
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
if(cell.tag == 0)
{
cell.tag = 1;
[self.listSelected addObject:indexPath]];
cell.imageView.image = [UIImage imageNamed:SELECTED_ROW];
}
else if(cell.tag == 1)
{
cell.tag = 0;
[self.medicineIndexArray removeObject:indexPath];
cell.imageView.image = [UIImage imageNamed:NOT_SELECTED_ROW];
}
}
- (BOOL)checkIfIndexPathAlreadySelected:(NSIndexPath *)indexPath
{
if([self.listSelected containsObject:indexPath])
return YES;
else
return NO;
}

Related

Bug in UITableViewController in Storyboard

I'm creating a UITableViewController to list names of people and a star next to their name to indicating favorite people like so
The stars light up when touched, indicting a favorite, the row number of that cell goes into an NSMutableArray which is called in this method.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
When I tap a cell and add the index to the array, everything works, until I scroll down, and more stars are filled. They are in random, I believe, a few popup every time I scroll up then down, and look like this, faded stars...
This is the full star
Somehow the stars that shouldn't be filled are faded.
I cannot pin point where the stars are getting switched to on. The log only shows setting the star to on when I scroll to the particular cell.
My problem is that stars are switched on when they should not be, my array is good, I've checked that multiple times, it has to be the UITableView.
This is my code,
I only have two images of that star, one filled and one empty, and the
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
CustomCell *cell = [tableView cellForRowAtIndexPath:indexPath];
// NSLog(#"%i",[[cell.contentView subviews] count]);
// NSMutableArray *array = [[NSMutableArray alloc] initWithArray:[cell.contentView subviews]];
[tableView reloadData];
UIImageView *star = cell.star;
NSLog(#"Star Tag: %i",star.tag);
if (star.tag == kStarEmpty) {
[[Global sharedGlobal].favTeachers addObject:[NSString stringWithFormat:#"%i",cell.identifierTag]];
NSLog(#"Added: %i",cell.identifierTag);
// NSLog(#"setting star image: 1");
[star setImage:[UIImage imageNamed:#"star.png"]];
[star setTag:kStarFilled];
} else if (star.tag == kStarFilled) {
[[Global sharedGlobal].favTeachers removeObject:[NSString stringWithFormat:#"%i",cell.identifierTag]];
NSLog(#"Removed: %i",cell.identifierTag);
// NSLog(#"setting star image: 2");
[star setImage:[UIImage imageNamed:#"star_empty.png"]];
[star setTag:kStarEmpty];
}
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *teacher = [[Global sharedGlobal].teachers objectAtIndex:indexPath.row];
static NSString *CellIdentifier = #"Cell";
CustomCell *cell = [tableView dequeueReusableCellWithIdentifier:#"Cell"];
if (cell == nil) {
cell = [[CustomCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
UIImageView *starView = [[UIImageView alloc] init];
starView.image = [UIImage imageNamed:#"star_empty.png"];
starView.frame = CGRectMake(720, 2, 29, 29); //748,22
[starView setTag:kStarEmpty];
cell.star = starView;
[cell addSubview:starView];
cell.identifierTag = indexPath.row;
NSLog(#"This cell's identifier tag: %i",cell.identifierTag);
cell.textLabel.text = [[Global sharedGlobal].teachers objectAtIndex:indexPath.row];
for (int i = 0; i < [[Global sharedGlobal].favTeachers count]; i++) {
int favTeacherTag = [[[Global sharedGlobal].favTeachers objectAtIndex:i] intValue];
NSLog(#"%i",i);
NSLog(#"Fav Teacher Tag: %i",favTeacherTag);
if (cell.identifierTag == favTeacherTag) {
NSLog(#"found fav teacher: %i",cell.identifierTag);
NSLog(#"------------------------------------------");
// NSMutableArray *array = [[NSMutableArray alloc] initWithArray:[cell.contentView subviews]];
NSLog(#"setting star image");
[starView setImage:[UIImage imageNamed:#"star.png"]];
NSLog(#"Previous star tag: %i",starView.tag);
[starView setTag:kStarFilled];
break;
}
NSLog(#"--------------------------------");
}
return cell;
}
EXTRA INFO:
I have a custom class for the cells, which adds the cell.identifierTag as an int.
I am using Storyboard
I use static cells in Storyboard
Thank you! If you need any more information please comment and ask.
You need to make sure to set the UIImage to nil in the else block here:
if (cell.identifierTag == favTeacherTag) {
//your existing code
} else {
[starView setImage:nil];
};
This is because the cells are reused, and you may be getting a cell that had previously had the star image added.
call [tableView reloadData] at end of (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath method
After two days of this I finally figured it out. :D
I added this code, because I was using the same UIImageView sometimes and kept adding image views every time this - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath was called.
UIImageView *starView = [[UIImageView alloc] init];
if (cell.star == nil) {
starView.image = [UIImage imageNamed:#"star_empty.png"];
starView.frame = CGRectMake(720, 2, 29, 29); //748,22
[starView setTag:kStarEmpty];
cell.star = starView;
[cell addSubview:starView];
} else if (cell.star != nil) {
starView = cell.star;
}

Dragging from a tableviewcell to a viewcontroller not auto segueing

I am trying to use Storyboards on this project. I cntrl drag from a static tableview cell to a new viewcontroller select push.
When I run the app and click the tableviewcell, which I dragged from in the previous step, nothing happens?
I am not sure if I have screwed things up by also putting in my tableviewcontroller class the following method.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier1 = #"Cell1";
UITableViewCell *cell = (UITableViewCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier1];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier1];
}
[cell.textLabel setFont:[UIFont fontWithName:#"GothamRounded-Light" size:18]];
cell.textLabel.backgroundColor = [UIColor clearColor];
cell.detailTextLabel.backgroundColor = [UIColor clearColor];
[cell.detailTextLabel setFont:[UIFont fontWithName:#"GothamRounded-Light" size:12]];
cell.contentView.backgroundColor = [UIColor statOffWhite];
if (indexPath.row == 0) {
cell.textLabel.text = #"Profile";
}
else if (indexPath.row == 1) {
cell.textLabel.text = #"Support";
}
else if (indexPath.row == 2) {
cell.textLabel.text = #"Share";
}
else if (indexPath.row == 3) {
cell.textLabel.text = #"About";
}
else if (indexPath.row == 4){
cell.textLabel.text = #"";
cell.frame = CGRectMake(0, 0, self.view.bounds.size.width, 200);
UIImageView *watermark = [[UIImageView alloc] initWithImage:[UIImage imageNamed:#"watermark.png"]];
watermark.frame = CGRectMake((cell.frame.size.width/2) - (watermark.image.size.width/2), 80, watermark.image.size.width, watermark.image.size.height );
[cell addSubview:watermark];
}
return cell;
}
// UPDATE ////////
I took out the cellForRowAt method and the storyboard thing worked. But since I have taken out that method how can I set my font on my cell to be a custom font that isn't in Xcode's selections? I have included the font in my project, which I use everywhere.
What happen with your implementation of cellForRowAtIndexPath: is that your are creating cells from scratch and overwriting the storyboard's cells (hence your segue not being triggered).
If you defined static cells in your storyboard, you should not dequeue and create cells yourself. If your class is a subclass of UITableViewCellController, you could call the implementation of super and use the returned cell.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [super tableView:tableView cellForRowAtIndexPath:indexPath];
// Customize your cell here
}
Note however that doing so makes little sense : all the things you are doing in your cellForRowAtIndexPath: method could and should for simplicity sake be done in the storyboard.
If you really need to customize a static cell programmatically, the way to go is to define an outlet to this cell in your view controller and customize the cell in the appropriate method (viewDidLoad for example).

Default CellAccessory

How can I set first row of tableview checkmarked when the app started? I mean when I start app now, there are few rows in tableview and when I click on some of them its accessory change to checkmark. When click another one, the another one comes checkmarked and previous checkmark dissapears. So now I want first row of tableview to be checkmarked when app is started and then when I click another row it 'uncheckmark' and 'checkmark' new row etc...
Try the options suggested in these posts how to apply check mark on table view in iphone using objective c? or iPhone :UITableView CellAccessory Checkmark
Basically you need to keep track of the checkmarks using say a dictionary or so. And In viewDidLoad or init method make the first cell as checked in the dictionary. While drawing cells, always check if the corresponding entry in the dictionary is checked or not and display check mark accordingly. When user taps on a cell, modify the value in dictionary to checked/unchecked.
Update:
Here is a sample code.
In .h file declare a property as
#property(nonatomic) NSInteger selectedRow;
Then use the below code,
- (void)viewDidLoad {
//some code...
self.selectedRow = 0; //if nothing should be selected for the first time, then make it as -1
//create table and other things
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
// create cell and other things here
if (indexPath.row == self.selectedRow)
{
cell.accessoryType = UITableViewCellAccessoryCheckmark;
} else {
cell.accessoryType = UITableViewCellAccessoryNone;
}
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
// some other code..
if (indexPath.row != self.selectedRow) {
self.selectedRow = indexPath.row;
}
[tableView reloadData];
}
You could set an integer to a variable similar to "checkedCell", have that value default to cell 0, and in the cellForRowAtIndexPath check to see if the cell is already checked, if not change the accessory to make it checked and update your variable.
-(void)viewWillAppear{
currentCheckedCell = 0;
}
- (UITableViewCell *)tableView:(UITableView *)aTableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
//
// Create cells -- if indexpath.row is equal to current checked cell reload the table with the correct acessories.
//
static NSString *cellIdentifier = #"RootMenuItemCell";
MyCell *cell = (MyCell *)[tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil) {
cell = [[MyCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellIdentifier];
NSArray *nibContents = [[NSBundle mainBundle] loadNibNamed:#"MyCell" owner:self options:nil];
for (UIView *view in nibContents) {
if ([view isMemberOfClass:[MyCell class]]) {
cell = (MyCell *)view;
break;
}
}
//OTHER CELL CREATION STUFF HERE
// cell accessory
UIImage *accessory = [UIImage imageNamed:#"menu-cell-accessory-default.png"];
UIImage *highlighted = [UIImage imageNamed:#"menu-cell-accessory-selected.png"];
if(indexPath.row == currentCheckedCell){
//DEFAULT ACCESSORY CHECK
// cell.accessoryType = UITableViewCellAccessoryCheckmark;
UIImageView *accessoryView = [[UIImageView alloc] initWithImage:accessory highlightedImage:highlighted];
}else{
//DEFAULT ACCESSORY NONE
// cell.accessoryType = UITableViewCellAccessoryNone;
UIImageView *accessoryView = [[UIImageView alloc] initWithImage:accessory highlightedImage:accessory];
}
[cell setAccessoryView:accessoryView];
}
return cell;
}
- (void)tableView:(UITableView *)aTableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
//UPDATE SELECTED CELL & RELOAD TABLE
currentCheckedCell = indexPath.row;
[self.tableview reloadData];
}
Also worth noting that my examples uses custom images for accessories.
If you check out the link #ACB provided you'll find a very similar concept.
You can use,
if (firstCellSelected)
{
cell.accessoryType = UITableViewCellAccessoryCheckmark;
}
Set the firstCellSelected flag in viewDidLoad method.

add background image for sections in UITableView

is it possible to change background image of each sections in uitableview?
I want to add background image for each sections in uitableview
does anyone know how can I do that?
Thanks in advance!
like this picture --> put different background images for wednesday , Thursday and friday separately
Edit I want to add image 1 for wednesday image 2 for Thursday image 3 for friday and .....
how can I specify that ?
Edit
this the code for creating sections header I want to have background also
- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
if(section == 0)
return #"Monday";
else if(section == 1){
return #"Tuesday";
}else if(section == 2){
return #"Wednesday";
} else if(section == 3){
return #"Thuesday";
} else if(section == 4){
return #"Friday";
} else if(section == 5){
return #"Saturday";
}else
return #"Sunday";
}
You could change the background in the cellForRowAtIndexPath delegate method based on the indexPath, like so:
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"TaskCellRow";
UITableViewCell *cell = (UITableViewCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
int maxRow = 3;
if (cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
cell.backgroundView = [[UIImageView alloc] initWithImage:[UIImage imageNamed: [NSString stringWithFormat: #"background_image%i.png", MIN(indexPath.row, maxRow)]]];
}
else
{
UIImageView *background = (UIImageView *)cell.backgroundView;
background.image = [UIImage imageNamed: [NSString stringWithFormat: #"background_image%i.png", MIN(indexPath.row, maxRow)]];
}
return cell;
}
// To change header backgrounds
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
int maxRow = 3;
UIImageView *headerView = [[UIImageView alloc] initWithImage:[UIImage imageNamed: [NSString stringWithFormat: #"background_image%i.png", MIN(section, maxRow)]]];
return headerView;
}
You would then just create images, numbered for the desired amount header/rows, ie. background_image0.png, background_image1.png, background_image2.png, ... and so forth. The MIN will cap the amount off at the whatever you decide is the max backgrounds. Hope that helps.
EDIT: Changed cellForRowAtIndexPath based on Henri's comments. I overlooked that, thanks! This is for ARC compatibility.
You can use:
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
to specify any kind of UIView for a section header. This other delegate method:
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
lets you specify the height.
Just alloc/init the UIView in the first one using the table's width and the height from the second method and then add any number of views to it, such as a UIImageView for a background then a label for the title.
Iterating (and mostly correcting) example given by ezekielDFM. Note, this code is not ARC compatible (which previous example may have been).
// To change cell backgrounds
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier = #"TaskCellRow";
UITableViewCell *cell = (UITableViewCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
int maxRow = 3;
if (cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
UIImageView *imageView = [[UIImageView alloc] initWithImage: [UIImage imageNamed: [NSString stringWithFormat: #"background_image%i.png", MIN(indexPath.row, maxRow)]]] autorelease];
cell.backgroundView = imageView;
} else {
// Reusing, we need to swap out the image of the background
cell.backgroundView.image = [UIImage imageNamed: [NSString stringWithFormat: #"background_image%i.png", MIN(indexPath.row, maxRow)]];
}
return cell;
}
// To change header backgrounds
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section {
int maxRow = 3;
UIImageView *headerView = [[[UIImageView alloc] initWithImage:[NSString stringWithFormat:#"background_image%i.png", MIN(section, maxRow)]] autorelease];
return headerView;
}
As i guess it is not possible to change the background image for Table view Sections. If you want to do such a requirement, please try with cell for row as Sections. i.e. for each row treat as section of table & in that add 1 more table view with different tag. It will full your req. or else for each row take

didSelectRowAtIndexPath selecting more than one row at a time

I have a UITableView populated with 27 rows. I am trying to change the accessoryType of the selected cell. I do that in the didSelectRowAtIndexPath: delegate method.
The problem I am facing is that, when selecting a row and changing the accessoryType of the cell, the eleventh row from that row also gets modified.
I have tried printing the [indexPath row] value, but it's showing only the row that was selected and not another one.
I am really puzzled by such stuff; please help me out.
ADDED THE CODE cellForRowAtIndexPath method
UITableViewCell *cell;
if ([indexPath row] == 0) {
cell = [tableView dequeueReusableCellWithIdentifier:#"acell"];
}
else {
cell = [tableView dequeueReusableCellWithIdentifier:#"bcell"];
}
cell.selectionStyle = UITableViewCellSelectionStyleNone;
if (cell == nil && [indexPath row] != 0) {
cell = [[[UITableViewCell alloc] initWithStyle:
UITableViewCellStyleSubtitle reuseIdentifier:#"bcell"] autorelease];
}
else if(cell == nil && [indexPath row] == 0){
cell = [[[UITableViewCell alloc] initWithStyle:
UITableViewCellStyleSubtitle reuseIdentifier:#"acell"] autorelease];
}
if ([cell.contentView subviews]){
for (UIView *subview in [cell.contentView subviews]) {
[subview removeFromSuperview];
}
}
if ([indexPath row] == 0) {
cell.textLabel.text = #"Select All";
cell.textLabel.font = [UIFont boldSystemFontOfSize:13.0f];
}
else {
cell.textLabel.text = #"Some Text Here"
cell.detailTextLabel.text = #"Another piece of text here"
}
return cell;
I am doing %10 because the behaviour is repeating after 11th row, hence trying to create new object for every 11th row.
My didSelectRowAtIndexPath methos code is
UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
if (cell.accessoryType == UITableViewCellAccessoryCheckmark) {
if ([indexPath row] != 0) {
NSIndexPath *tempIndex = [NSIndexPath indexPathForRow:0 inSection:0];
UITableViewCell *tempCell = [tableView cellForRowAtIndexPath:tempIndex];
tempCell.accessoryType = UITableViewCellAccessoryNone;
}
cell.accessoryType = UITableViewCellAccessoryNone;
}
else{
cell.accessoryType = UITableViewCellAccessoryCheckmark;
}
if ([indexPath row] == 0) {
for (int i = 0; i < [dataSource count]; i++) {
NSIndexPath *tempIndex = [NSIndexPath indexPathForRow:i+1 inSection:0];
UITableViewCell *tempCell = [tableView cellForRowAtIndexPath:tempIndex];
if (cell.accessoryType == UITableViewCellAccessoryCheckmark) {
tempCell.accessoryType = UITableViewCellAccessoryCheckmark;
}
else{
tempCell.accessoryType = UITableViewCellAccessoryNone;
}
}
}
Please help me in multiple selection or anyother way to solve the problem of multiple selection.
Thanks in advance!!
Here's one way to do it:
- (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] autorelease];
}
[cell.textLabel setText:[NSString stringWithFormat:#"Row %d", indexPath.row]];
NSIndexPath* selection = [tableView indexPathForSelectedRow];
if (selection && selection.row == indexPath.row) {
cell.accessoryType = UITableViewCellAccessoryCheckmark;
} else {
cell.accessoryType = UITableViewCellAccessoryNone;
}
// Configure the cell.
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[tableView cellForRowAtIndexPath:indexPath].accessoryType = UITableViewCellAccessoryCheckmark;
}
- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
[tableView cellForRowAtIndexPath:indexPath].accessoryType = UITableViewCellAccessoryNone;
}
Remember every cell in the table view is actually the same object being re-used. If you don't set the accessory type every time cellForRowAtIndexPath is called, when new cells scroll onto the screen they're going to all have the same accessory.
Multiple Select
For multiple selection it's a bit more complicated.
Your first option: Undocumented API
Note that this only works when the table's in editing mode. Set each cell's editing style to the undocumented UITableViewCellEditingStyleMultiSelect. Once you do that, you can get the table view's selection via an undocumented member of UITableView: indexPathsForSelectedRows. That should return an array of the selected cells.
You can expose this bit of functionality by putting this in a header:
enum {
UITableViewCellEditingStyleMultiSelect = 3,
};
#interface UITableView (undocumented)
- (NSArray *)indexPathsForSelectedRows;
#end
Then set the editing style for each cell like so:
- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath {
return UITableViewCellEditingStyleMultiSelect;
}
When the table is in editing mode you'll see the multi-select controls on your cells.
To look through other undocumented API, you can use the nm command line utility like this:
nm /Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS4.3.sdk/System/Library/Frameworks/UIKit.framework/UIKit
Your second option: Manage the selection yourself
Have your UITableView subclass contain an array that indicates which cells are selected. Then in cellForRowAtIndexPath, configure the cell's appearance using that array. Your didSelectRowAtIndexPath method should then look something like this:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if ([tableView indexPathIsSelected:indexPath]) {
[tableView removeIndexPathFromSelection:indexPath];
} else {
[tableView addIndexPathToSelection:indexPath];
}
// Update the cell's appearance somewhere here
[tableView deselectRowAtIndexPath:indexPath animated:NO];
}
This assumes you create indexPathIsSelected, removeIndexPathFromSelection, and addIndexPathToSelection methods in your UITableView subclass. These methods should do exactly what their names imply: Add, remove, and check for index paths in an array. You wouldn't need a didDeselectRowAtIndexPath implementation if you go with this option.
Remember every cell in the table view is actually the same object being re-used. If you don't set the accessory type every time cellForRowAtIndexPath is called, when new cells scroll onto the screen they're going to all have the same accessory." - daxnitro
This is where I got caught. I had mine set up so that in my "cellForRowAtIndexPath" function, I would only change the accessory for those specified in my array of checked cells, when what I should have done was update the accessory for all cells in the table.
In other words:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
//normal set up
//retrieve key
NSUserDefaults *settings = [NSUserDefaults standardUserDefaults];
id obj = [settings objectForKey:#yourKey];
//if the array is not populated, keep standard format for all cells
if (obj == nil){
selectedStyles = [[NSMutableArray alloc] initWithObjects:nil];
[cell setAccessoryType:UITableViewCellAccessoryNone]; //no check mark
[cell textLabel].textColor = [[UIColor alloc] initWithRed:0.0/255 green:0.0/255 blue:0.0/255 alpha:1.0]; //keep black color
}
//else retrieve information from the array and update the cell's accessory
else{
//if the cell is in your array, add a checkbox
[cell setAccessoryType:UITableViewCellAccessoryCheckmark]; //add check box
[cell textLabel].textColor = [[UIColor alloc] initWithRed:50.0/255 green:79.0/255 blue:133.0/255 alpha:1.0]; //change color of text label
//if the cell is not in your array, then keep standard format
[cell setAccessoryType:UITableViewCellAccessoryNone]; //no check mark
[cell textLabel].textColor = [[UIColor alloc] initWithRed:0.0/255 green:0.0/255 blue:0.0/255 alpha:1.0]; //keep black color
Hope this helps!