2010-11-16 7 views

Odpowiedz

1

Mam rozwiązanie.

Pierwszy krok, każda sekcja pokaże UIView, który utworzony przez - (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section, który będzie przechowywany w tablicy.

Gdy przewijam widok TableView, chcę uwolnić niewidzialny widok przekroju, więc potrzebuję wiedzieć, która sekcja jest widoczna lub nie, wykonaj kod funkcji wykrywa w tym celu, jeśli widok jest widoczny, a następnie zwolnij go.

-(BOOL)isVisibleRect:(CGRect)rect containerView:(UIScrollView*)containerView 
{ 
    CGPoint point = containerView.contentOffset; 
    CGFloat zy = point.y ; 

    CGFloat py = rect.origin.y + rect.size.height; 
    if (py - zy <0) { 
      return FALSE; 
    } 
    CGRect screenRect = containerView.frame; 

    CGFloat by = screenRect.size.height + zy ; 
    if (rect.origin.y > by) { 
      return FALSE; 
    } 
    return TRUE; 
} 

(rect jest rama sekcji UIView; containerView jest UITableView)

W ten sposób można uzyskać widoczne odcinki UITableView, ale nadzieję SDK zapewnić API w tym celu bezpośrednio.

7

UITableViews przechowuje komórki za pomocą NSIndexPath. W rezultacie nie ma obiektu dla sekcji. Za pomocą poniższego kodu możemy przemierzać tabelę i wykonywać operacje przy użyciu indeksów widocznych sekcji (nie jestem pewien, dlaczego chcesz widoczne sekcje, ponieważ widoczne tylko oznacza, że ​​są aktualnie na ekranie, ale cokolwiek).

for (NSIndexPath* i in [yourTableViewName indexPathsForVisibleRows]) 
{ 
    NSUInteger sectionPath = [i indexAtPosition:0]; 
    //custom code here, will run multiple times per section for each visible row in the group 
} 
+3

ale jeśli nie ma komórki w sekcjach wówczas metoda „indexPathsForVisibleRows” zwróci wartość null ..... – iXcoder

+0

Chcę wiedzieć, czy sekcja jest widoczna na ekranie, a następnie mogę za darmo lub utwórz go dynamicznie, czy też trzeba go zachować, by zjeść dużo pamięci ... – iXcoder

+0

Dodałem odpowiedź, która obsługuje sekcje bez komórek tutaj http://stackoverflow.com/a/23538021/895099 – adamsiton

2

Extract odcinki z listy widocznych wierszy:

NSArray *indexPathsForVisibleRows = [tableView indexPathsForVisibleRows]; 
NSMutableIndexSet *indexSet = [NSMutableIndexSet indexSet]; 
for (NSIndexPath *indexPath in indexPathsForVisibleRows) { 
    [indexSet addIndex:indexPath.section]; 
} 
NSLog(@"indexSet %@",indexSet); 
// indexSet <NSMutableIndexSet: 0x11a5c190>[number of indexes: 5 (in 1 ranges), indexes: (9-13)] 

czyli

NSArray *indexPathsForVisibleRows = [detailTableView indexPathsForVisibleRows]; 
NSMutableSet *sectionSet = [NSMutableSet set]; 
for (NSIndexPath *indexPath in indexPathsForVisibleRows) { 
    [sectionSet addObject:[NSNumber numberWithInt:indexPath.section]]; 
} 
NSLog(@"sectionSet %@",sectionSet); 
// sectionSet {(13, 11, 9, 10, 12)} 
0

Innym rozwiązaniem, użyj 1 bit w znaczniku sekcji nagłówka widoku danych, tak

#define _TBL_TAG_SECTION(_TAG) ((_TAG)|(1<<30)) 
#define _TBL_TAG_CLEAR(_TAG) ((_TAG)&((1<<30)-1)) 
#define _TBL_TAG_IS_SECTION(_TAG) ((_TAG)>>30) 

- (UIView*)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section 
{ 
    // alloc header view 
    UIView *header = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 1, 1)]; 
    header.tag = _TBL_TAG_SECTION(section); 
    return header; 
} 

- (void)scrollViewDidScroll:(UIScrollView *)scrollView 
{ 
    CGRect r = CGRectMake(scrollView.contentOffset.x, scrollView.contentOffset.y, 
         CGRectGetWidth(scrollView.frame), 
         CGRectGetHeight(scrollView.frame)); 
    for (UIView *v in [_tableView subviews]) { 
     if (CGRectIntersectsRect(r, v.frame)) { 
      if (_TBL_TAG_IS_SECTION(v.tag)) { 
       NSLog(@"visible section tag %d", _TBL_TAG_CLEAR(v.tag)); 
      } 
     } 
    } 
} 
17

Lub naprawdę łatwy sposób byłoby skorzystać z valueForKeyPath i klasy NSSet:

NSSet *visibleSections = [NSSet setWithArray:[[self.tableView indexPathsForVisibleRows] valueForKey:@"section"]]; 

Zasadniczo otrzymuje się tablicę wartości przekrojów w widocznych wierszach, a następnie wypełnia się zestawem, aby usunąć duplikaty. Rozwiązanie krok

+1

Co za pięknie prosta odpowiedź. Dzięki! – ArtSabintsev

+1

To nie będzie działać dla sekcji bez wierszy w nich. –

+0

@ MikkelSelsøe Jeśli w sekcji nie ma żadnych wierszy, sekcja też nie jest widoczna ... więc nie jestem pewien, co mówisz, nie działa. –

1

2, aby uzyskać widoczne sekcje w UITableView:

1) Dodać widoki głowicy do zmienny tablicy w viewForHeaderInSection
2) Aktualizacja tablicę gdy przewija Tableview w scrollViewDidScroll

nocie korzystanie z nieruchomości tag posiadać numer sekcji

@property (nonatomic, strong, readwrite) NSMutableArray *headerArray; 

- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section { 
    UIView *headerView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, tableView.bounds.size.width, 40)]; 
    headerView.backgroundColor = [UIColor greenColor]; 
    headerView.tag = section; 
    [_headerArray addObject:headerView]; 
    return headerView; 
} 

- (void)scrollViewDidScroll:(UIScrollView *)scrollView { 
    [self updateHeaderArray]; 
    NSLog(@"------------"); 
    for (UIView *view in _headerArray) { 
     NSLog(@"visible section:%d", view.tag); 
    } 
} 

- (void)updateHeaderArray { 
    // remove invisible section headers 
    NSMutableArray *removeArray = [NSMutableArray array]; 
    CGRect containerRect = CGRectMake(_tableView.contentOffset.x, _tableView.contentOffset.y, 
             _tableView.frame.size.width, _tableView.frame.size.height); 
    for (UIView *header in _headerArray) { 
     if (!CGRectIntersectsRect(header.frame, containerRect)) { 
      [removeArray addObject:header]; 
     } 
    } 
    [_headerArray removeObjectsInArray:removeArray]; 
} 
1

odpowiedź jest dużo prostsza i neater z KVC

NSArray *visibleSections = [self.tableView.indexPathsForVisibleRows valueForKey:@"section"]; 

może to dać tablicę z podwójnymi wartościami, ale możesz nią zarządzać.

+0

Jeśli czytasz moją odpowiedź jako wysłaną 3 miesiące przed twoją już korzystam z tej techniki, a następnie użyj zestawu, aby pozbyć się duplikatów . –

+0

@ ChristopherKing, moje złe. Nie sprawdzaj w momencie opublikowania odpowiedzi. – thesummersign

1
for (NSUInteger section = 0; section < self.tableView.numberOfSections; ++section) { 
    UIView *headerView = [self.tableView headerViewForSection:section]; 
    if (headerView.window) { 
     NSLog(@"its visible"); 
    } 
} 
6

wersja Swift

if let visibleRows = tableView.indexPathsForVisibleRows { 
    let visibleSections = visibleRows.map({$0.section}) 
} 
Powiązane problemy