我喜欢使用UITableView来创建具有2级层次结构的表,如下图所示。每次用户点击标题时,内容就会折叠或展开。经过三天的研究,我发现有两种技术:

1.自定义UITableViewCell本身带有另一个表

2.使用节标题视图。

现在,我决定使用第二个。并且由于UITableView does not re-use section view(尽管UITableView包含2个 private 变量:_reusableHeaderViews和_reusableFooterViews :),所以我创建了一些自定义方法来执行此任务。一切正常,除了1个错误:当我使用 UITableViewRowAnimationFade 方法 reloadSections:withRowAnimation 时,标头视图变为空白视图。

这是我的代码:

#import "MasterViewController.h"

@interface MasterViewController ()
//remember current section
@property (assign, nonatomic) NSInteger curSession;
@property (strong, nonatomic) NSMutableDictionary *reusableHeaderViews;
@end

@implementation MasterViewController

@synthesize reusableHeaderViews = _reusableHeaderViews;
@synthesize tableView = _tableView;
@synthesize curSession = _curSession;
@synthesize detailViewController = _detailViewController;

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        self.title = NSLocalizedString(@"Master", @"Master");
    }
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    self.curSession = -1;
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    // Release any retained subviews of the main view.
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}

//method for adding header view into reuse-array
-  (void)registerHeaderView:(UITableViewCell *)headerView forReuseIdentifier:(NSString *)reuseIdentifier
{
    NSMutableDictionary *reusableDictionary  = [self reusableHeaderViews];
    if (reusableDictionary == nil)
    {
        reusableDictionary = [[NSMutableDictionary alloc] init];  //creates a storage dictionary if one doesn’t exist
        self.reusableHeaderViews = reusableDictionary;
    }

    NSMutableArray *arrayForIdentifier = [[self reusableHeaderViews] objectForKey:reuseIdentifier];
    if (arrayForIdentifier == nil)
    {
        //creates an array to store views sharing a reuse identifier if one does not exist
        arrayForIdentifier = [[NSMutableArray alloc] init];
        [reusableDictionary setObject:arrayForIdentifier forKey:reuseIdentifier];
    }

    [arrayForIdentifier addObject:headerView];
}

//get header view in reuse-array
- (UITableViewCell *)reuseableHeaderForIdentifier:(NSString *)reuseIdentifier
{
    NSMutableArray *arrayOfViewsForIdentifier = [[self reusableHeaderViews]  objectForKey:reuseIdentifier];

    if (arrayOfViewsForIdentifier == nil)
    {
        return nil;  //We don’t have any of this kind!
    }

    NSInteger indexOfAvailableHeaderView = [arrayOfViewsForIdentifier indexOfObjectPassingTest:^BOOL(id obj, NSUInteger idx, BOOL *stop)
                                            {
                                                //If my view doesn’t have a superview, it’s not on-screen.
                                                return ![obj superview];
                                            }];

    if (indexOfAvailableHeaderView != NSNotFound)
    {
        UITableViewCell *headerView = [arrayOfViewsForIdentifier objectAtIndex:indexOfAvailableHeaderView];
        return headerView;    //Success!
    }

    return nil;
}

#pragma mark - Table View

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return 15;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    if (_curSession == section)
        return section;
    return 0;
}

- (UIView*) tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
    static NSString *headerReuseIdentifier = @"Header";
    UITableViewCell *cell = [self reuseableHeaderForIdentifier:headerReuseIdentifier];
    if(cell == nil)
    {
        //Didn’t locate a reusable
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@""];
        [self registerHeaderView:cell forReuseIdentifier:headerReuseIdentifier];
        UITapGestureRecognizer *tapGR = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(openSection:)];
        tapGR.numberOfTapsRequired = 1;
        [cell addGestureRecognizer:tapGR];
        cell.backgroundColor = [UIColor redColor];
    }
    cell.tag = section;
    cell.textLabel.text = [NSString stringWithFormat:@"Section title %i", section];

    return cell;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
        cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
    }

    cell.textLabel.text = [NSString stringWithFormat:@"Row %i - section %i", indexPath.row, indexPath.section];
    return cell;
}

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

}

- (void) openSection:(id)sender

{
    NSInteger section = [[(UITapGestureRecognizer*)sender view] tag];
    if(_curSession == -1)
    {
        _curSession = section;
        [_tableView reloadSections:[NSIndexSet indexSetWithIndex:_curSession] withRowAnimation:UITableViewRowAnimationFade];
    }
    else if(_curSession == section)
    {
        _curSession = -1;
        [_tableView reloadSections:[NSIndexSet indexSetWithIndex:section] withRowAnimation:UITableViewRowAnimationFade];
    }
    else if(_curSession != section)
    {
        NSInteger temp = _curSession;
        _curSession = -1;
        [_tableView reloadSections:[NSIndexSet indexSetWithIndex:temp] withRowAnimation:UITableViewRowAnimationFade];
        _curSession = section;
        [_tableView reloadSections:[NSIndexSet indexSetWithIndex:section] withRowAnimation:UITableViewRowAnimationFade];
    }
}

@end

最佳答案

已经有点晚了,但也许有人会有类似的问题。

您可以尝试使用此组件:https://github.com/serverdensity/ios-SDNestedTable

关于ios - UITableView重用节标题 View :使用UITableViewRowAnimationFade时标题 View 消失,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/12723871/

10-14 21:11
查看更多