UITableView pulse para deseleccionar celda

Tengo una UITableViewCell que se selecciona cuando se UITableViewCell . Durante este estado seleccionado, si el usuario vuelve a tocar la celda, quiero que la celda deselect.

No puedo encontrar ninguna de las llamadas de delegado afectadas. ¿Alguna idea de cómo implementar esto? ¿Realmente va a ser un reconocimiento de gestos?

De hecho, puede hacer esto utilizando el método de delegado willSelectRowAtIndexPath:

 - (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath { UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath]; if ([cell isSelected]) { // Deselect manually. [tableView.delegate tableView:tableView willDeselectRowAtIndexPath:indexPath]; [tableView deselectRowAtIndexPath:indexPath animated:YES]; [tableView.delegate tableView:tableView didDeselectRowAtIndexPath:indexPath]; return nil; } return indexPath; } 

Tenga en count que deselectRowAtIndexPath: no llamará a los methods de delegado automáticamente, por lo que debe realizar esas llamadas manualmente.

en Swift:

 func tableView(tableView: UITableView, willSelectRowAtIndexPath indexPath: NSIndexPath) -> NSIndexPath? { if let indexPathForSelectedRow = tableView.indexPathForSelectedRow { if (indexPathForSelectedRow.isEqual(indexPath)) { tableView.deselectRowAtIndexPath(indexPath, animated: false) return nil } } return indexPath } 

Aquí hay una solución aún más limpia:

 - (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath { if ([[tableView indexPathForSelectedRow] isEqual:indexPath]) { [tableView deselectRowAtIndexPath:indexPath animated:YES]; return nil; } return indexPath; } 

Creo que usar la selección azul para cambiar de color puede dar una printing extraña. ¿Por qué no usar un accesorio como una marca de verificación? Esta es una técnica mucho más familiar para alternar la selección (ya sea de celdas múltiples o celdas individuales).

Consulte esta respuesta para get información: UITableView Multiple Selection

 - (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath { UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath]; if ([cell isSelected]) { // Deselect manually. if ([tableView.delegate respondsToSelector:@selector(tableView:willDeselectRowAtIndexPath:)]) { [tableView.delegate tableView:tableView willDeselectRowAtIndexPath:indexPath]; } [tableView deselectRowAtIndexPath:indexPath animated:YES]; if ([tableView.delegate respondsToSelector:@selector(tableView:didDeselectRowAtIndexPath:)]) { [tableView.delegate tableView:tableView didDeselectRowAtIndexPath:indexPath]; } return nil; } return indexPath; } 

Cuando selecciona una celda, se desencadena este método delegado.

 - (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{ UITableViewCell *theUITableViewCell = [tableView cellForRowAtIndexPath:path]; if (theUITableViewCell.selected == YES){ self.tableView deselectRowAtIndexPath:<#(NSIndexPath *)#> animated:<#(BOOL)#> // Do more thing }else{ // By default, it is highlighted for selected state } } 

Es un pseudo código.

Puedes probar esto, es para mí (para una selección única o para múltiples selects):

A. asigna un NSMutableArray privado en viewDidLoad como:

 @interface XXXViewController : UIViewController <UITableViewDataSource, UITableViewDelegate> { NSMutableArray * selectedZoneCellIndexPaths; } - (void)viewDidLoad { selectedZoneCellIndexPaths = [[NSMutableArray alloc] init]; } 

B. en UITableViewDelegate didSelectRow agregar las siguientes líneas

 - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath { for (NSIndexPath * iter in selectedZoneCellIndexPaths) { if (indexPath.section == iter.section && indexPath.row == iter.row) { [tableView deselectRowAtIndexPath:indexPath animated:YES]; [selectedZoneCellIndexPaths removeObject:iter]; return; } } [selectedZoneCellIndexPaths addObject:indexPath]; return; } 

Versión rápida de la respuesta de prisonerjohn:

 public func tableView(tableView: UITableView, willSelectRowAtIndexPath indexPath: NSIndexPath) -> NSIndexPath? { let cell = tableView.cellForRowAtIndexPath(indexPath) if (cell?.selected ?? false) { // Deselect manually. tableView.delegate!.tableView?(tableView, willDeselectRowAtIndexPath: indexPath) tableView.deselectRowAtIndexPath(indexPath, animated: true) tableView.delegate!.tableView?(tableView, didDeselectRowAtIndexPath: indexPath) return nil } return indexPath; } 

Cuando se utiliza el modo "Selección múltiple", "didSelectRowAtIndexPath" no se llamará cuando click una fila que ya esté seleccionada. Más de una fila todavía se puede seleccionar de forma progtwigda en el modo "Selección única" y las filas dispararán a ifSelectRowAtIndexPath en todos los clics.

Solo un consejo para cualquiera que tuviera los mismos problemas.

Desde @prisonerjohn, en caso de que alguien se pregunte cómo verificar si el delegado responde al selector como dijo @ Patrick, en Swift 3 :

 override func tableView(_ tableView: UITableView, willSelectRowAt indexPath: IndexPath) -> IndexPath? { guard let cell = tableView.cellForRow(at: indexPath) else { // Handle invalid cell ... } if cell.isSelected { if let respond = tableView.delegate?.responds( to: #selector(tableView(_:willDeselectRowAt:))), respond == true { tableView.delegate?.tableView!(tableView, willDeselectRowAt: indexPath) } tableView.deselectRow(at: indexPath, animated: true) if let respond = tableView.delegate?.responds( to: #selector(tableView(_:didDeselectRowAt:))), respond == true { tableView.delegate?.tableView!(tableView, didDeselectRowAt: indexPath) } return nil } return indexPath } 

Estaba buscando lo mismo pero la respuesta de @occulus me proporcionó la pista que me faltaba.

Me hizo darme count de que la forma de hacerlo es permitir la selección múltiple en la vista de tabla y anular manualmente las filas seleccionadas previamente cuando se selecciona una nueva fila usando uno de los methods delegates.

Parece bastante natural que en el modo de selección única, la vista de la tabla trate de dejar una fila seleccionada lo más posible, por lo tanto, no se anule la selección de una fila seleccionada.

Tal vez mi pregunta no fue lo suficientemente específica, pero las dos respuestas son un poco amplias de lo que buscaba.

Parece que esto no es posible, y fui con un gestor reconocedor de la celda para establecer manualmente el estado seleccionado / no seleccionado.