以前,写了一篇文章:下拉刷新的实现,只讲到了下拉刷新的功能,这篇文章描述了下拉刷新以及上拉加载更多的功能。
这里只列出核心功能的代码,其他的代码请参考附件。
DemoTableViewController.h
#import <UIKit/UIKit.h> #import "STableViewController.h" @interface DemoTableViewController : STableViewController { NSMutableArray *items; } @end
DemoTableViewController.m
#import "DemoTableViewController.h" #import "DemoTableHeaderView.h" #import "DemoTableFooterView.h" @interface DemoTableViewController () - (void) addItemsOnTop; - (void) addItemsOnBottom; - (NSString *) createRandomValue; @end @implementation DemoTableViewController - (void) viewDidLoad { [super viewDidLoad]; self.title = @"STableViewController Demo"; [self.tableView setBackgroundColor:[UIColor lightGrayColor]]; NSArray *nib = [[NSBundle mainBundle] loadNibNamed:@"DemoTableHeaderView" owner:self options:nil]; DemoTableHeaderView *headerView = (DemoTableHeaderView *)[nib objectAtIndex:0]; self.headerView = headerView; nib = [[NSBundle mainBundle] loadNibNamed:@"DemoTableFooterView" owner:self options:nil]; DemoTableFooterView *footerView = (DemoTableFooterView *)[nib objectAtIndex:0]; self.footerView = footerView; items = [[NSMutableArray alloc] init]; for (int i = 0; i < 10; i++) [items addObject:[self createRandomValue]]; } #pragma mark - Pull to Refresh - (void) pinHeaderView { [super pinHeaderView]; DemoTableHeaderView *hv = (DemoTableHeaderView *)self.headerView; [hv.activityIndicator startAnimating]; hv.title.text = @"Loading..."; } - (void) unpinHeaderView { [super unpinHeaderView]; [[(DemoTableHeaderView *)self.headerView activityIndicator] stopAnimating]; } - (void) headerViewDidScroll:(BOOL)willRefreshOnRelease scrollView:(UIScrollView *)scrollView { DemoTableHeaderView *hv = (DemoTableHeaderView *)self.headerView; if (willRefreshOnRelease) hv.title.text = @"Release to refresh..."; else hv.title.text = @"Pull down to refresh..."; } - (BOOL) refresh { if (![super refresh]) return NO; [self performSelector:@selector(addItemsOnTop) withObject:nil afterDelay:2.0]; return YES; } #pragma mark - Load More - (void) willBeginLoadingMore { DemoTableFooterView *fv = (DemoTableFooterView *)self.footerView; [fv.activityIndicator startAnimating]; } - (void) loadMoreCompleted { [super loadMoreCompleted]; DemoTableFooterView *fv = (DemoTableFooterView *)self.footerView; [fv.activityIndicator stopAnimating]; if (!self.canLoadMore) { fv.infoLabel.hidden = NO; } } - (BOOL) loadMore { if (![super loadMore]) return NO; [self performSelector:@selector(addItemsOnBottom) withObject:nil afterDelay:2.0]; return YES; } #pragma mark - Dummy data methods - (void) addItemsOnTop { for (int i = 0; i < 3; i++) [items insertObject:[self createRandomValue] atIndex:0]; [self.tableView reloadData]; [self refreshCompleted]; } - (void) addItemsOnBottom { for (int i = 0; i < 5; i++) [items addObject:[self createRandomValue]]; [self.tableView reloadData]; if (items.count > 50) self.canLoadMore = NO; else self.canLoadMore = YES; [self loadMoreCompleted]; } - (NSString *) createRandomValue { NSDateFormatter *dateFormatter = [[[NSDateFormatter alloc] init] autorelease]; [dateFormatter setTimeStyle:NSDateFormatterMediumStyle]; return [NSString stringWithFormat:@"%@ %@", [dateFormatter stringFromDate:[NSDate date]], [NSNumber numberWithInt:rand()]]; } #pragma mark - Standard TableView delegates - (NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { return items.count; } - (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] autorelease]; } cell.textLabel.text = [items objectAtIndex:indexPath.row]; return cell; } @end