Jan 27

Have you every been frustrated with the small circular touch area when setting the accessory type of a UITableViewCell to be UITableViewCellAccessoryDisclosureIndicator? Unless you have child fingers, it’s very difficult to select consistently.

Here’s one way to improve the user experience and create the same effect of a larger touch pad like you see on the YouTube application. To do this, you need to implement a custom table view cell. You can either create your own subclass, or you can add subviews to the cell’s contextView. This example shows how to do the latter.

When setting up my UITableViewCells I like to create methods that provide the elements I wish to use to add to the cell’s contentView. Here I am creating a UIButton of type UIButtonTypeDetailDisclosure to be added to each cell in the table. The button possesses an area of 44 x 44 pixels and occupies the right most area of the table view cell that will be 320 pixels wide and 44 pixels tall. Note here that you define a target and action of your own rather than use the callbacks for the accessory type defined in the UITableViewDelegate protocol.

- (UIButton *) getDetailDiscolosureIndicatorForIndexPath: (NSIndexPath *) indexPath 
{
	UIButton *button = [UIButton buttonWithType: UIButtonTypeDetailDisclosure];
	button.frame = CGRectMake(320.0 - 44.0, 0.0, 44.0, 44.0);
	[button addTarget:self action:@selector(detailDiscolosureIndicatorSelected:) forControlEvents:UIControlEventTouchUpInside];
	return button;
}  

The following shows how to add the button to the cell in the cellForRowAtIndexPath method in your table view controller class. As you add subviews to the contentView, be sure your detailed disclosure indicator is rendered on top. Also, ensure you are properly handling the reuse of your cells.

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath 
{
...
[cell.contentView addSubview: [self getDetailDiscolosureIndicatorForIndexPath: indexPath]];
...
} 

Finally to process the selection event you need the following code:

- (void) detailDiscolosureIndicatorSelected: (UIButton *) sender 
{	
	//
	// Obtain a reference to the selected cell
	//
	UITableViewCell *cell = [self.tableView cellForRowAtIndexPath: [self.tableView indexPathForSelectedRow]];

	//
	// Do something like render a detailed view
	//		
	...
} 

written by Jess \\ tags: , ,