UITableview: Jak wyłączyć Zaznaczanie dla niektórych wierszy, ale nie dla innych

Wyświetlam w grupie tableview Zawartość przetworzoną z XML. Chcę wyłączyć Zdarzenie click na nim (nie powinno być w stanie go kliknąć w ogóle) tabela zawiera dwie grupy. Chcę wyłączyć zaznaczanie tylko dla pierwszej grupy, ale nie dla drugiej grupy. Klikając pierwszy wiersz drugiej grupy navigates do mojej tuby player view.

Jak mogę wybrać tylko określone grupy lub wiersze?

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath 
{
    if(indexPath.section!=0)
    if(indexPath.row==0)    

    [[UIApplication sharedApplication] openURL:[NSURL URLWithString:tubeUrl]];   
}
Dzięki.
Author: P.J.Radadiya, 2010-02-15

23 answers

Wystarczy umieścić ten kod w cellForRowAtIndexPath

Aby wyłączyć właściwość wyboru komórki: (podczas stukania komórki)

cell.selectionStyle = UITableViewCellSelectionStyleNone;
Aby włączyć możliwość wybrania (dotknięcia) komórki: (dotknięcie komórki)
// Default style
cell.selectionStyle = UITableViewCellSelectionStyleBlue;

// Gray style
cell.selectionStyle = UITableViewCellSelectionStyleGray;

Zauważ, że komórka z selectionStyle = UITableViewCellSelectionStyleNone; nadal będzie powodować Wywołanie interfejsu użytkownika didSelectRowAtIndexPath Po dotknięciu przez użytkownika. Aby tego uniknąć, wykonaj zgodnie z poniższymi wskazówkami i ustaw.

cell.userInteractionEnabled = NO;
Zamiast tego. Zwróć również uwagę, że możesz ustawić cell.textLabel.enabled = NO; na szaro.
 507
Author: Pugalmuni,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-31 15:25:55

Jeśli chcesz, aby wiersz (lub podzbiór wierszy) nie był wybierany , zaimplementuj metodę UITableViewDelegate -tableView:willSelectRowAtIndexPath: (również wspomnianą przez TechZen). Jeśli indexPath nie powinno być do wyboru , zwróć nil, w przeciwnym razie zwróć indexPath. Aby uzyskać domyślne zachowanie selekcji, po prostu zwracasz indexPath przekazaną do metody delegate, ale możesz również zmienić wybór wiersza, zwracając Inny indexPath.

Przykład:

- (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    // rows in section 0 should not be selectable
    if ( indexPath.section == 0 ) return nil;

    // first 3 rows in any section should not be selectable
    if ( indexPath.row <= 2 ) return nil;

    // By default, allow row to be selected
    return indexPath;
}
 385
Author: Brian Chapados,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-23 10:52:33

Począwszy od iOS 6, możesz użyć

-tableView:shouldHighlightRowAtIndexPath:

Jeśli zwrócisz NO, wyłącza zarówno podświetlenie zaznaczenia, jak i wyzwalane segmenty storyboardu podłączone do tej komórki.

Metoda jest wywoływana, gdy dotyk schodzi na rząd. Zwrócenie NO do tego komunikatu zatrzymuje proces selekcji i nie powoduje, że aktualnie wybrany wiersz traci swój wybrany wygląd, gdy dotyk jest wyłączony.

Uitableviewdelegate Protocol Reference

 65
Author: Keller,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2019-11-08 12:01:00

Żadna z powyższych odpowiedzi nie rozwiązuje problemu poprawnie. Powodem jest to, że chcemy wyłączyć zaznaczanie komórki, ale niekoniecznie podwidywań wewnątrz komórki.

W moim przypadku przedstawiałem UISwitch w środku wiersza i chciałem wyłączyć zaznaczanie dla reszty wiersza (który jest pusty), ale nie dla przełącznika! Właściwy sposób wykonania tego jest więc w metodzie

- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath

Gdzie wyrażenie formularza

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];

Wyłącza wybór dla konkretna komórka, a jednocześnie pozwala użytkownikowi manipulować przełącznikiem, a tym samym korzystać z odpowiedniego selektora. Nie jest to prawdą, jeśli ktoś wyłącza interakcję użytkownika za pomocą

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

Metoda, która jedynie przygotowuje komórkę i nie pozwala na interakcję z Uiswitchem.

Ponadto, stosując metodę

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath

W celu usunięcia zaznaczenia komórki wyrażeniem postaci

[tableView deselectRowAtIndexPath:indexPath animated:NO];

Nadal pokazuje wybrany wiersz, gdy użytkownik naciska na oryginalna zawartość komórki.

Tylko moje dwa centy. Jestem pewien, że wielu uzna to za przydatne.
 16
Author: MightyMouse,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-22 23:26:39

Za pomocą metod źródłowych danych można przechwytywać selekcje.

– tableView:willSelectRowAtIndexPath: 
– tableView:didSelectRowAtIndexPath: 
– tableView:willDeselectRowAtIndexPath: 
– tableView:didDeselectRowAtIndexPath:

W tych metodach sprawdzasz, czy wybrany wiersz jest taki, który chcesz wybrać. Jeśli tak, podejmij działanie, jeśli nie, nic nie rób.

Niestety, nie można wyłączyć wyboru tylko dla jednej sekcji. Cały stół albo nic.

Można jednak ustawić właściwość table cells selectionStyle na UITableViewCellSelectionStyleNone. Wierzę, że to uczyni wybór niewidzialnym. W połączeniu z powyższymi metodami, które powinny sprawić, że komórki wyglądaj całkowicie obojętnie z perspektywy użytkownika.

Edit01:

Jeśli masz tabelę, w której można wybrać tylko niektóre wiersze, ważne jest, aby komórki wybranych wierszy były wizualnie odrębne od wierszy niewykrywalnych. Domyślnym sposobem jest przycisk akcesorium szewron.

Jakkolwiek to robisz, nie chcesz, aby użytkownicy próbowali wybierać wiersze i myśleli, że aplikacja została uszkodzona, ponieważ wiersz nic nie robi.

 12
Author: TechZen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-02-15 18:35:39

Dla Swift 4.0 na przykład:

cell.isUserInteractionEnabled = false
cell.contentView.alpha = 0.5
 12
Author: Alessandro Ornano,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-05 08:03:26

Aby wyłączyć zaznaczanie komórek w metodzie cellForRowAtIndexPath, musisz zrobić coś takiego:

[cell setSelectionStyle:UITableViewCellSelectionStyleNone];
[cell setUserInteractionEnabled:NO];

Aby pokazać szarą komórkę, umieść następującą metodę tableView:WillDisplayCell:forRowAtIndexPath:

[cell setAlpha:0.5];

Jedna metoda pozwala kontrolować interaktywność, druga pozwala kontrolować wygląd interfejsu użytkownika.

 9
Author: azfar,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-08 19:06:55

Dla swift:

cell.selectionStyle = .None
cell.userInteractionEnabled = false
 7
Author: Esqarrouth,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-11-02 19:34:46

Dla swift 4.0 To wystarczy. Spowoduje to wyłączenie komórki w metodzie disselectrowatindexpath, ale zachowa podwidywalność.

func tableView(_ tableView: UITableView, willSelectRowAt indexPath: IndexPath) -> IndexPath? {
         if (indexPath.row == clickableIndex ) { 
            return indexPath
         }else{
            return nil
        }
    }
 7
Author: Nilesh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-11-30 06:43:11

Aby zatrzymać wybieranie tylko niektórych komórek użyj:

cell.userInteractionEnabled = NO;

Oprócz zapobiegania zaznaczeniu, zatrzymuje to również wywołanie tableView:didSelectRowAtIndexPath: dla komórek, które go ustawiły.

 5
Author: JosephH,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-06-01 13:36:47

Możesz użyć metody tableView:willDisplayCell, Aby wykonać wszystkie rodzaje dostosowywania do tableViewCell.

- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
     [cell setSelectionStyle:UITableViewCellSelectionStyleNone];
     [cell setUserInteractionEnabled:NO];

     if (indexPath.section == 1 && indexPath.row == 0)
     {
         [cell setSelectionStyle:UITableViewCellSelectionStyleGray];
         [cell setUserInteractionEnabled:YES];
     }
} 

W powyższym kodzie użytkownik może wybrać tylko pierwszy wiersz w drugiej sekcji tableView. Reszta nie może być zaznaczona. Dzięki!~

 5
Author: Abdul Rahman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-29 07:42:00

Moje rozwiązanie oparte na modelu danych:

func tableView(_ tableView: UITableView, willSelectRowAt indexPath: IndexPath) -> IndexPath? {
    let rowDetails = viewModel.rowDetails(forIndexPath: indexPath)
    return rowDetails.enabled ? indexPath : nil
}

func tableView(_ tableView: UITableView, shouldHighlightRowAt indexPath: IndexPath) -> Bool {
    let rowDetails = viewModel.rowDetails(forIndexPath: indexPath)
    return rowDetails.enabled
}
 5
Author: SoftDesigner,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-12 08:12:07

Użyj tego, aby komórka wyglądała tak, jakby była wyłączona i niewykrywalna:

cell.selectionStyle = UITableViewCellSelectionStyleNone;

Ważne: zauważ, że jest to tylko właściwość stylizacji i w rzeczywistości nie wyłącza komórki. Aby to zrobić, musisz sprawdzić, czy selectionStylew swojej didSelectRowAtIndexPath: implementacji delegata:

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
    if(cell.selectionStyle == UITableViewCellSelectionStyleNone) {
        return;
    }

    // do your cell selection handling here
}
 1
Author: pt2ph8,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-14 11:21:01

Lubię Brian Chapados odpowiedź powyżej. Oznacza to jednak, że logika może być zduplikowana zarówno w cellForRowAtIndexPath, jak i w willSelectRowAtIndexPath, które mogą łatwo wyjść z synchronizacji. Zamiast powielać logikę, po prostu sprawdź styl wyboru:

- (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
    if (cell.selectionStyle == UITableViewCellSelectionStyleNone)
        return nil;

    else
        return indexPath;
}
 1
Author: Eric D'Souza,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-03 20:45:32

Uznałem to za przydatne, ponieważ działa zarówno z tabelami statycznymi, jak i dynamicznymi. Ustawiam tylko wskaźnik ujawnienia na tych komórkach, które chcę zezwolić na wybór.

- (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
    if (cell.accessoryType != UITableViewCellAccessoryDisclosureIndicator) {
        return nil;
    }
    return indexPath;
}
 1
Author: Jeffery Jones,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-08-19 15:08:32

Na Xcode 7 bez kodowania możesz po prostu wykonać następujące czynności:

W widoku kontur wybierz komórkę widoku tabeli. (Komórka jest zagnieżdżona w obszarze scena kontrolera widoku tabeli > kontroler widoku tabeli > Widok tabeli. Może być konieczne ujawnienie tych obiektów, aby zobaczyć komórkę widoku tabeli)

W Inspektorze atrybutów znajdź pole oznaczone zaznaczenia i wybierz Brak. atribute inspector Dzięki tej opcji komórka nie otrzyma podświetlenia wizualnego, gdy użytkownik ją dotknie.

 1
Author: Tung Fam,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-06-08 08:34:49

Appart from tableView.allowsMultipleSelection = true Po wybraniu opcji Usuń zaznaczenie pozostałych komórek sekcji:

func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    if indexPath.section does not support multiple selection {
        // deselect the rest of cells
        tableView
            .indexPathsForSelectedRows?.compactMap { $0 }
            .filter { $0.section == indexPath.section && $0.row != indexPath.row }
            .forEach { tableView.deselectRow(at: $0, animated: true) }
    }
}
 1
Author: rgkobashi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-03-09 17:21:24

SIMPLE

Po prostu użyj cell.userInteractionEnabled = YES; do komórki, jeśli może nawigować i cell.userInteractionEnabled = NO; w przeciwnym razie

 0
Author: Rick Royd Aban,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-09-02 10:02:17

Zaimplementuj tylko metodę tableView:willSelectRowAtIndexPath: w źródle danych dla Twojej tabeli. Jeśli chcesz, aby wiersz na ścieżce był podświetlany, zwróć podaną ścieżkę indeksowania. Jeśli nie, zwróć zero.

Przykład z mojej aplikacji:

- (NSIndexPath *)tableView:(UITableView *)tableView
    willSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    MySelectableObj* obj = [self objectAtPath:indexPath];
    if(obj==nil) return nil;
    return indexPath;
}

Fajną rzeczą w tym jest to, że shouldPerformSegueWithIdentifier:sender: nie zostanie wywołana, jeśli powyższa metoda zwróci zero, chociaż powtórzę powyższy test tylko dla kompletności.

 0
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-12-21 23:12:41

Dla Xcode 6.3:

 cell.selectionStyle = UITableViewCellSelectionStyle.None;
 0
Author: uplearnedu.com,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-10 02:23:19

Zgadzam się z odpowiedzią Bryana

If I do

cell.isUserInteractionEnabled = false 

Wtedy podwidywacze w komórce nie będą wchodzić w interakcje z użytkownikiem.

Na drugiej stronie, ustawienie

cell.selectionStyle = .none

Uruchomi metodę didSelect pomimo braku aktualizacji koloru zaznaczenia.

Używanie willSelectRowAt jest sposobem, w jaki rozwiązałem mój problem. Przykład:

func tableView(_ tableView: UITableView, willSelectRowAt indexPath: IndexPath) -> IndexPath? {

    if indexPath.section == 0{

        if indexPath.row == 0{
            return nil
        }

    }
    else if indexPath.section == 1{

        if indexPath.row == 0{
            return nil
        }

    }

    return indexPath

}
 0
Author: Reimond Hill,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2019-04-26 06:31:58

Swift 5 : Umieść następującą linię wewnątrz swojej funkcji cellForRowAt:

cell.selectionStyle = UITableViewCell.SelectionStyle.none
 0
Author: Helton Malambane,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-22 07:18:22

Dla swift 3.0 możesz użyć poniższego kodu, aby wyłączyć interakcję użytkownika z komórką UITableView

 cell.isUserInteractionEnabled = false
 -1
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-09-13 05:14:56