¿Cómo puedo deshabilitar la selección UITableView?

1193

Cuando toca una fila en a UITableView, la fila se resalta y se selecciona. ¿Es posible deshabilitar esto, así que tocar una fila no hace nada?

DavidM
fuente
17
La pregunta original tiene un mal título. OP quiere principalmente deshabilitar selection, y por supuesto highlightingse deshabilita con eso. Muchas respuestas altamente votadas explican cómo disable selectiony no aborda la desactivación highlighting. Para deshabilitar solo el uso de resaltado cell.selectionStyle = .Noneo vaya astoryboard / cell / Selection = None
Andrej
Actualiza el título o la publicación. Estoy confundido. Y en base a esta pregunta, no tengo idea de lo que las respuestas proporcionadas están destinadas a hacer.
Daniel Springer

Respuestas:

604

Para mí, lo siguiente funcionó bien:

tableView.allowsSelection = false

Esto significa que didSelectRowAt#simplemente no funcionará. Es decir, tocar una fila de la mesa, como tal, no hará absolutamente nada. (Y por lo tanto, obviamente, nunca habrá una animación seleccionada).

(Tenga en cuenta que si, en las celdas, tiene UIButtonu otros controles, por supuesto, esos controles seguirán funcionando. Cualquier control que tenga en la celda de la tabla no tiene ninguna relación con la capacidad de UITableView para permitirle "seleccionar una fila" usando didSelectRowAt#.)

Otro punto a tener en cuenta es que: Esto no funciona cuando UITableViewestá en modo de edición. Para restringir la selección de celdas en el modo de edición, use el código de la siguiente manera:

tableView.allowsSelectionDuringEditing = false 
Vamos a crear
fuente
66
Esto finalmente funcionó para mí, intenté usar cell.selectionStyle = UITableViewCellSelectionStyleNone; Pero no funcionó. Una cosa a tener en cuenta: debe ser: tableView.allowsSelection = NO; No falso.
tony.tc.leung
66
Creo que esta es la mejor opción. Los botones en las celdas están activos con esto, pero el texto no está activo.
Fahim Parkar
513
¿Cómo es esta la respuesta aceptada y tiene tantos votos? ¡No responde a la pregunta en absoluto! Debe establecer la selectionStylepropiedad en la celda: cell.selectionStyle = UITableViewCellSelectionStyle.Noneen Swift o cell.selectionStyle = UITableViewCellSelectionStyleNoneen Objective-C.
nodobase
55
Esto funciona para mí en tableView.allowSelection = false
Swift
15
Hay algunas formas de hacerlo dependiendo de lo que se desee. Ningún estilo de selección y ninguna selección pueden funcionar, o ambos pueden fallar. Aquí hay un ejemplo. Si desea seleccionar la celda y tableViewDidSelectRowAtIndexPathdesea que se llame, cell.selectionStyle = .Nonese desea. Si no desea o no desea que se llame a esa función delegada (es decir, tener un campo de texto en una tabla ViewCell), tableView.allowsSelection = falseestá bien.
Made2k
1964

Todo lo que tiene que hacer es establecer el estilo de selección en la UITableViewCellinstancia usando:

C objetivo:

cell.selectionStyle = UITableViewCellSelectionStyleNone;

o

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];

Swift 2:

cell.selectionStyle = UITableViewCellSelectionStyle.None

Swift 3 y 4.x:

cell.selectionStyle = .none

Además, asegúrese de no implementar -tableView:didSelectRowAtIndexPath:en su delegado de vista de tabla o excluir explícitamente las celdas en las que no desea realizar ninguna acción si lo implementa.

Más información aquí y aquí

Martin Gordon
fuente
122
@ Tony Es mala idea si tienes un UITextField dentro de la celda.
Aniruddh Joshi
73
@TonyMillion también es una mala idea si desea utilizar controles de edición integrados, como deslizar para eliminar. Si establece userInteractionEnabled en NO, el botón Eliminar no responde a los eventos táctiles del usuario.
Carlos P
47
tarde a este hilo, pero en lugar de userInteraction, use cell.allowsSelection. Eso detiene los métodos de interacción de la celda pero no bloquea el material de respuesta UIView normal.
Chris C
44
Establecer cell.userInteractionEnable = No no detendrá la activación de didSelectRowAtIndexPath.
user4951
25
Voy a votar la respuesta, pero para que quede claro, el OP solo solicitó deshabilitar el "resaltado", no para deshabilitar la interacción celular completa, por lo que todos estos comentarios son tópicos.
Frederic Yesid Peña Sánchez
353

Como he leído esta publicación recientemente y me ha ayudado, quería publicar otra respuesta para consolidar todas las respuestas (para la posteridad).



Entonces, en realidad hay 5 respuestas diferentes dependiendo de la lógica y / o resultado deseado:

1.Para desactivar el resaltado azul sin cambiar ninguna otra interacción de la celda:

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];

Lo uso cuando tengo un UIButton - o algún otro control (es) - alojado en una UITableViewCell y quiero que el usuario pueda interactuar con los controles pero no con la celda en sí.

NOTA : Como señaló Tony Million anteriormente, esto NO impidetableView:didSelectRowAtIndexPath:. Me salgo de esto con simples declaraciones "if", que a menudo prueban la sección y evitan acciones para una sección en particular.

Otra forma en la que pensé para probar el golpeteo de una celda como esta es:

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    // A case was selected, so push into the CaseDetailViewController
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
    if (cell.selectionStyle != UITableViewCellSelectionStyleNone) {
        // Handle tap code here
    }
}



Para hacer esto para una tabla completa, puede aplicar la solución anterior a cada celda de la tabla, pero también puede hacer esto:

[tableView setAllowsSelection:NO];

En mis pruebas, esto todavía permite que los controles dentro de la UITableViewCellsean interactivos.


3.Para hacer que una celda sea de "solo lectura", simplemente puede hacer esto:

[cell setUserInteractionEnabled:NO];



4. Para hacer una tabla completa "solo lectura"

[tableView setUserInteractionEnabled:NO];



5.Para determinar sobre la marcha si resaltar una celda (que según esta respuesta incluye implícitamente la selección), puede implementar el siguiente UITableViewDelegatemétodo de protocolo:

- (BOOL)tableView:(UITableView *)tableView 
   shouldHighlightRowAtIndexPath:(NSIndexPath *)indexPath
mbm29414
fuente
3
Si carga el diseño de celda desde una punta, la casilla de verificación (en IB) funcionará bien para el n. ° 3 (y en las tablas para el n. ° 4). Para # 4 vs # 2, ¿es la diferencia si los controles dentro de la celda serán interactivos o no?
lilbyrdie
44
Si. Si desea deshabilitar la selección pero permitir que UIButtons, etc ... continúen apoyando la interacción del usuario, use # 2. Si desea una celda completamente de solo lectura, use el # 4. Por supuesto, no sé por qué tendrías algo más que UIViews o UILabels en una celda no interactiva. Quizás alguien quiera deshabilitar toda interacción mientras ocurre algo más.
mbm29414
8
# 4 es una idea terrible, hacer esto también deshabilitará el desplazamiento en la vista de tabla
Simon
44
@simon En realidad, no es una idea terrible; Es una opción que puede o no ser una buena opción dependiendo de sus circunstancias. Además, # 4 deshabilita el desplazamiento del USUARIO; aún puede implementar el suyo, si es necesario. Estoy de acuerdo # 4 no es útil MUCHO, pero no es una idea terrible.
mbm29414
3
Para completar, ¿podría agregar un agradecimiento tableView:shouldHighlightRowAtIndexPath:, que generalmente (no siempre) es mi enfoque preferido.
Benjohn
82

Para resumir, creo que son las respuestas correctas basadas en mi propia experiencia en la implementación de esto:

Si desea deshabilitar la selección de solo algunas de las celdas, use:

cell.userInteractionEnabled = NO;

Además de evitar la selección, esto también detiene tableView: didSelectRowAtIndexPath: se llama para las celdas que lo tienen configurado. (El crédito va a Tony Million por esta respuesta, ¡gracias!)

Si tiene botones en sus celdas en los que se debe hacer clic, debe:

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];

y también debe ignorar cualquier clic en la celda - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath.

Si desea deshabilitar la selección para toda la tabla, use:

tableView.allowsSelection = NO;

(¡Gracias a Paulo De Barros, gracias!)

JosephH
fuente
¿Qué pasa si tenemos un botón en nuestra celda?
Umair Afzal el
56

A partir de iOS 6.0, UITableViewDelegatetiene tableView:shouldHighlightRowAtIndexPath:. (Lea sobre esto en la documentación de iOS ).

Este método le permite marcar filas específicas como no resaltables (e implícitamente, no seleccionables) sin tener que cambiar el estilo de selección de una celda, interfiriendo con el manejo de eventos de la celda userInteractionEnabled = NOo con cualquier otra técnica documentada aquí.

cbowns
fuente
2
Tropecé con este hilo y me sorprendió ver tantas otras respuestas antes de esta. Esta es sin duda la forma correcta.
beebcon
2
De hecho, esta es la respuesta correcta y única que debe considerarse. Cualquier otra cosa que mencione userInteraction es completamente incorrecta.
mattyohe
50

También puede deshabilitar la selección de fila desde el propio generador de interfaces seleccionando NoSelectionla selectionopción (de Propiedades de UITableView) en el panel del inspector como se muestra en la imagen a continuación

Inspector UITableView

vignesh kumar
fuente
2
La mejor solución en mi humilde opinión
Itai Spector
A menudo utilizo esta solución
Evsenev
46

SOLUCIÓN FIJA PARA SWIFT 3

cell.selectionStyle = .none
MANISH PATHAK
fuente
36

En su UITableViewCell's XI ter en el atributo valor establecido inspector de Selectiona None.

ingrese la descripción de la imagen aquí

Zaid Pathan
fuente
Esto es exactamente lo que necesitaba. Todavía quería la notificación didSelect ... pero sin la indicación visible de selección. ¡Gracias!
Timothy Tripp
Me alegro de que haya ayudado! :)
Zaid Pathan
35

Si desea que la selección solo parpadee, no permanezca en el estado seleccionado, puede llamar, en

didSelectRowAtIndexPath

el seguimiento

[tableView deselectRowAtIndexPath:indexPath animated:YES];

entonces parpadeará el estado seleccionado y revertirá.

Chris Fox
fuente
3
Con este enfoque, la fila se resalta instantáneamente y luego se desvanece durante medio segundo. Así es como Apple diseña sus menús de configuración, por lo que me parece bien.
VinceFior
34

En caso de que alguien necesite una respuesta para Swift :

cell.selectionStyle = .None
Aks
fuente
1
también podemos utilizar este cell.selectionStyle = UITableViewCellSelectionStyle.None
bably
29

Esto es lo que uso, en cellForRowAtIndexPathescribir este código .:

cell.selectionStyle = UITableViewCellSelectionStyleNone;
Ahsan Ebrahim
fuente
28

Desde el UITableViewDelegateProtocolo puede usar el método willSelectRowAtIndexPath y return nilsi no desea que se seleccione la fila.

De la misma manera, puede usar el willDeselectRowAtIndexPathmétodo y return nilsi no desea que la fila anule la selección.

usuario41806
fuente
55
No me gusta este método porque todavía muestra la celda en su estado resaltado hasta el retoque.
kbanman
2
eso es exactamente por qué me gusta :-)
Joris Weimar
24

1- Todo lo que tienes que hacer es establecer el estilo de selección en laUITableViewCell instancia usando:


C objetivo:

cell.selectionStyle = UITableViewCellSelectionStyleNone;

o

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];


Swift 2:

cell.selectionStyle = UITableViewCellSelectionStyle.None


Swift 3:

cell.selectionStyle = .none


2 - No implementar - tableView:didSelectRowAtIndexPath:en su vista de tabladelegate o excluya explícitamente las celdas que no desea que se realicen si lo implementa.

3 - Además, también puedes hacerlo desde el guión gráfico. Haga clic en la celda de vista de tabla y en el inspector de atributos en Celda de vista de tabla, cambie el menú desplegable junto a Selección a Ninguno.


4 - Puede deshabilitar el resaltado de la celda de la tabla usando el código siguiente en (iOS) Xcode 9, Swift 4.0

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {


        let cell = tableView.dequeueReusableCell(withIdentifier: "OpenTbCell") as! OpenTbCell
        cell.selectionStyle = .none
        return cell


}
parvind
fuente
20

C objetivo:

  1. Debajo del fragmento, deshabilite el resaltado, pero también deshabilita la llamada a didSelectRowAtIndexPath. Entonces, si no está implementando didSelectRowAtIndexPath, use el siguiente método. Esto debe agregarse cuando está creando la tabla. Sin UITextFieldembargo, esto funcionará en los botones y dentro de la celda.

    self.tableView.allowsSelection = NO;
  2. A continuación, el fragmento deshabilita el resaltado y no deshabilita la llamada a didSelectRowAtIndexPath. Establezca el estilo de selección de celda en Ninguno encellForRowAtIndexPath

    cell.selectionStyle = UITableViewCellSelectionStyleNone;
  3. Debajo del fragmento, deshabilite todo en la celda. Esto desactivará la interacción a buttons, textfields:

    self.tableView.userInteractionEnabled = false;

Rápido:

A continuación se encuentran el Swiftequivalente de las Objective-Csoluciones anteriores :

  1. Reemplazo de la primera solución

    self.tableView.allowsSelection = false
  2. Reemplazo de la segunda solución

    cell?.selectionStyle = UITableViewCellSelectionStyle.None
  3. Reemplazo de la tercera solución

    self.tableView.userInteractionEnabled = false
Arun Gupta
fuente
19

Intenta escribir:

cell.selected = NO;

Deseleccionará su fila cuando sea necesario.

En Swift3 ...

override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    let r = indexPath.row
    print("clicked .. \(r)")
    tableView.cellForRow(at: indexPath)?.setSelected(false, animated: true)
}
Denis Kutlubaev
fuente
14

He estado luchando con esto muy profusamente, teniendo un control en mi UITableViewCellprohibido el uso de la userInteractionEnabledpropiedad. Tengo una tabla estática de 3 celdas para la configuración, 2 con fechas, 1 con un interruptor de encendido / apagado. Después de jugar en Storyboard / IB, pude hacer que el inferior no sea seleccionable, pero cuando lo tocas, la selección de una de las filas superiores desaparece. Aquí hay una imagen WIP de mi configuración UITableView:

Configuraciones UITableView

Si toca la tercera fila, no pasa nada, la selección permanecerá en la segunda fila. La funcionalidad es prácticamente una copia de la pantalla de selección de hora de agregar evento de la aplicación Calendario de Apple.

El código es sorprendentemente compatible, hasta IOS2 = /:

- (NSIndexPath *)tableView: (UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    if (indexPath.row == 2) {
        return nil;
    }
    return indexPath;
}

Esto funciona junto con la configuración del estilo de selección en none, por lo que la celda no parpadea en eventos de touchdown

Yarek T
fuente
11

Podemos escribir código como

 cell.selectionStyle = UITableViewCellSelectionStyleNone;

pero cuando tenemos xib celda personalizado por encima de la línea de advertencia dar en ese momento para

xib celular personalizado

necesitamos establecer el estilo de selección Ninguno desde el generador de interfaces

iDhaval
fuente
11

Solo tiene que poner este código en cellForRowAtIndexPath

Para deshabilitar la propiedad de selección de la celda: (Mientras toca la celda).

cell.selectionStyle = UITableViewCellSelectionStyle.None
Gaurav Patel
fuente
Gracias, tengo una imagen en mi celda y una etiqueta encima. Establecí el fondo de la etiqueta, pero cada vez que hacía clic en el fondo desaparecía, esto lo solucionó.
Darko
10

prueba esto

cell.selectionStyle = UITableViewCellSelectionStyleNone;

y

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];

y también puede establecer el estilo de selección usando el creador de interfaces.

v_1
fuente
10

Estoy usando esto, que funciona para mí.

cell?.selectionStyle = UITableViewCellSelectionStyle.None
priyanka gautam
fuente
7

Si bien esta es la mejor y más fácil solución para evitar que una fila muestre el resaltado durante la selección

cell.selectionStyle = UITableViewCellSelectionStyleNone;

También me gustaría sugerir que ocasionalmente es útil mostrar brevemente que la fila ha sido seleccionada y luego desactivarla. Esto alerta a los usuarios con una confirmación de lo que pretendían seleccionar:

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
     [tableView deselectRowAtIndexPath:indexPath animated:NO];
...
}
Steve Barden
fuente
7

Deshabilite directamente el resaltado de TableViewCell en el guión gráfico

ingrese la descripción de la imagen aquí

Kamani Jasmin
fuente
6

Para deshabilitar el resaltado de UItableviewcell

cell.selectionStyle = UITableViewCellSelectionStyleNone;

Y no debe permitir que el usuario interactúe con la célula.

cell.userInteractionEnabled = NO;
Sharme
fuente
6

También puede establecer el color de fondo en Borrar para lograr el mismo efecto que UITableViewCellSelectionStyleNone, en caso de que no quiera / no pueda usar UITableViewCellSelectionStyleNone.

Usaría un código como el siguiente:

UIView *backgroundColorView = [[UIView alloc] init];
backgroundColorView.backgroundColor = [UIColor clearColor];
backgroundColorView.layer.masksToBounds = YES;
[cell setSelectedBackgroundView: backgroundColorView];

Esto puede degradar su rendimiento al agregar una vista de color adicional a cada celda.

virindh
fuente
6

Puedes usar :

cell.selectionStyle = UITableViewCellSelectionStyleNone;

en la celda para la fila en el método de ruta de índice de su UITableView.

También puedes usar:

[tableView deselectRowAtIndexPath:indexPath animated:NO];

en la vista de tabla didselectrowatindexpath método.

Annu
fuente
Ahora está cell.selectionStyle = UITableViewCellSelectionStyle.noneen Swift 3.
Dan
5

Puedes usar esto

cell.selectionStyle = UITableViewCellSelectionStyleNone;
iEinstein
fuente
5

Puedes usar ....

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];
Mak083
fuente
5
cell.selectionStyle = UITableViewCellSelectionStyleNone;
iDeveloper
fuente
5
UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:indexPath];
[cell setSelected:NO animated:NO];
[cell setHighlighted:NO animated:NO];

Feliz codificación !!!

Rinku Sadhwani
fuente
5

También puedes hacerlo desde el guión gráfico. Haga clic en la celda de vista de tabla y en el inspector de atributos en Celda de vista de tabla, cambie el menú desplegable junto a Selección a Ninguno.

Cindy
fuente