All,
I have an issue with my NSMutable array LogoURL. when the UITable reloads it only shows at array location [0] and not at [1] or [2]. Here is my code, can someone look at see where I am going wrong. Its very minor problem but its driving me crazy!
#import "ViewController.h"
#interface ViewController ()
#property (nonatomic, strong) MSTable *table;
#property (nonatomic, strong) NSMutableArray *items;
#property (weak, nonatomic) IBOutlet UITableView *MainTableView;
#end
#implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
// create the activity indicator in the main queue
self.MainTableView.hidden = YES;
UIActivityIndicatorView *ac = [[UIActivityIndicatorView alloc]
initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
[self.view addSubview:ac];
[ac startAnimating];
self.client = [MSClient clientWithApplicationURLString:#"https://outnight-mobile.azure-mobile.net/" applicationKey:#"okYeRGfBagYrsbkaqWIRObeDtktjkF10"];
self.table = [self.client tableWithName:#"notifications"];
self.logoURL = [[NSMutableArray alloc] init];
self.rowitems = [[NSMutableArray alloc] init];
MSQuery *query = [self.table query];
query.fetchLimit = 3;
[query readWithCompletion:^(NSArray *items, NSInteger totalCount, NSError *error)
{
self.rowitems = [items mutableCopy];
//[self.MainTableView reloadData];
int a;
for (a = 0; a < 3; a++)
{
NSDictionary *apt = [self.rowitems objectAtIndex:a];
NSLog(#"%#", apt[#"barID"]);
NSDictionary *barIDDictionary = #{ #"myParam": apt[#"barID"]};
self.client = [MSClient clientWithApplicationURLString:#"https://outnight-mobile.azure-mobile.net/" applicationKey:#"okYeRGfBagYrsbkaqWIRObeDtktjkF10"];
[self.client invokeAPI:#"photos" body:barIDDictionary HTTPMethod:#"POST" parameters:nil headers:nil completion:^(id result, NSHTTPURLResponse *response, NSError *error) {
if (error) {
NSLog(#"Error %#", error );
}
else {
NSString *string = [NSString stringWithFormat:#"%#", [result objectForKey:#"rows"]];
NSString *stringWithoutbracketsend = [string stringByReplacingOccurrencesOfString:#")" withString:#""];
NSString *stringWithoutbracketsfront = [stringWithoutbracketsend stringByReplacingOccurrencesOfString:#"(" withString:#""];
NSString *completion = [stringWithoutbracketsfront stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
NSString *newStr = [completion substringFromIndex:1];
NSString *finalstring = [newStr substringToIndex:newStr.length-(newStr.length>0)];
[self.logoURL addObject:finalstring];
[self.MainTableView reloadData];
}
}];
}
}];
self.MainTableView.hidden = NO;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [self.rowitems count];
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:#"cell"];
NSDictionary *stress = [self.rowitems objectAtIndex:indexPath.row];
cell.textLabel.text = stress[#"content"];
switch (indexPath.row) {
case 0:
[cell.imageView setImageWithURL:[NSURL URLWithString:[self.logoURL objectAtIndex:(0)]] placeholderImage:[UIImage imageNamed:#"greybox40.png"]];
break;
case 1:
[cell.imageView setImageWithURL:[NSURL URLWithString:[self.logoURL objectAtIndex:(1)]] placeholderImage:[UIImage imageNamed:#"greybox40.png"]];
break;
case 2:
//[cell.imageView setImageWithURL:[NSURL URLWithString:[self.logoURL objectAtIndex:(2)]] placeholderImage:[UIImage imageNamed:#"greybox40.png"]];
break;
}
return cell;
}
#end
It is erroring at CASE (1), cos it cannot see the object. any help would be brilliant, thanks.
Error at case (1) happens because you reload your table view 3 times. and every time you say to your tableView that it has 3 rows via numberOfRowsInSection: method. But in first and second iteration your self.logoURL has only 1 and then 2 objects. try this code:
if (self.logoURL.count > indexPath.row) {
[cell.imageView setImageWithURL:[NSURL URLWithString:self.logoURL[indexPath.row]] placeholderImage:[UIImage imageNamed:#"greybox40.png"]];
}
else
cell.imageView.image = nil;
also, you dont need to create NSMutableArray instance self.rowitems = [[NSMutableArray alloc] init]; because you then reassign self.rowitems property self.rowitems = [items mutableCopy];
because your for loop is override the array value and store last value only.
[array insertObject:finalString atIndex:i];
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [self.logoURL count];
}
Related
I have added search bar for collection view using programatically .But when i enter the names to search nothing shows.I have some section also and each section contains some data.
Here is my code:
#interface ViewController ()
{
NSMutableArray *arrayPDFName;
NSMutableArray *titleArray;
}
#property (nonatomic,strong) NSArray *dataSourceForSearchResult;
#property (nonatomic) BOOL searchBarActive;
#property (nonatomic) float searchBarBoundsY;
#property (nonatomic,strong) UISearchBar *searchBar;
#property (nonatomic,strong) UIRefreshControl *refreshControl;
#end
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.dataSourceForSearchResult = [NSArray new];
titleArray = [NSMutableArray array];
[self getdata];
self.mycollectionView.dataSource = self;
self.mycollectionView.delegate = self;
[self.mycollectionView reloadData];
}
-(NSString*)sha256HashFor:(NSString*)input
{
const char* str = [input UTF8String];
unsigned char result[CC_SHA256_DIGEST_LENGTH];
CC_SHA256(str, strlen(str), result);
NSMutableString *ret = [NSMutableString stringWithCapacity:CC_SHA256_DIGEST_LENGTH*2];
for(int i = 0; i<CC_SHA256_DIGEST_LENGTH; i++)
{
[ret appendFormat:#"%02x",result[i]];
}
return ret;
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
-(void)viewWillAppear:(BOOL)animated{
[super viewWillAppear:animated];
[self prepareUI];
}
-(void)getdata {
NSString *userName = #“username#yahoo.com";
NSString *password = #“password”;
NSData *plainData = [password dataUsingEncoding:NSUTF8StringEncoding];
NSString *base64String = [plainData base64EncodedStringWithOptions:0];
base64String=[self sha256HashFor: base64String];
NSString *urlString = #"https://api.exampleport/user/orderid/files";
NSMutableURLRequest *request= [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:urlString]];
[request setHTTPMethod:#"GET"];
// basic authendication
NSString *authStr = [NSString stringWithFormat:#"%#:%#", userName, base64String];
NSData *authData = [authStr dataUsingEncoding:NSUTF8StringEncoding];
//header-field
NSString *authValue = [NSString stringWithFormat:#"Basic %#", [authData base64Encoding]];
[request setValue:authValue forHTTPHeaderField:#"Authorization"];
NSData *returnData = [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
NSString *str = [[NSString alloc] initWithData:returnData encoding:NSUTF8StringEncoding];
NSError * error;
self->arrayPDFName = [[NSMutableArray alloc]init];
NSDictionary *jsonResults = [NSJSONSerialization JSONObjectWithData:returnData options:NSJSONReadingMutableContainers error:nil];
NSDictionary *dictOriginal = jsonResults[#“dark”];
[titleArray addObject:[NSString stringWithFormat:#"dark(%#)”, dictOriginal[#"count"]]];
NSDictionary *dictOriginal2 = jsonResults[#"orange”];
[titleArray addObject:[NSString stringWithFormat:#"orange(%#)”, dictOriginal2[#"count"]]];
NSDictionary *dictOriginal3 = jsonResults[#"pencill”];
[titleArray addObject:[NSString stringWithFormat:#"pencill(%#)”, dictOriginal3[#"count"]]];
NSDictionary *dictOriginal4 = jsonResults[#"smart”];
[titleArray addObject:[NSString stringWithFormat:#"smart(%#)”, dictOriginal4[#"count"]]];
NSArray *arrayFiles = [NSArray arrayWithObjects: dictOriginal, dictOriginal2, dictOriginal3, dictOriginal4, nil];
NSLog(#"str: %#", titleArray);
for (NSDictionary *dict in arrayFiles) {
NSMutableArray *arr = [NSMutableArray array];
NSArray *a = dict[#"files"];
for(int i=0; i < a.count; i ++) {
NSString *strName = [NSString stringWithFormat:#"%#",[[dict[#"files"] objectAtIndex:i] valueForKey:#"name"]];
// NSLog(#"str: %#", strName);
[arr addObject:strName];
}
[arrayPDFName addObject:arr];
}
//Get plist path
NSString *errorDesc;
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory1 = [paths objectAtIndex:0];
NSString *plistPath = [documentsDirectory1 stringByAppendingPathComponent:#"SampleData.plist"];
//NSLog(#"plistPath : %#",plistPath);
//Save data from json to plist
NSString *error1;
returnData = [NSPropertyListSerialization dataFromPropertyList:jsonResults
format:NSPropertyListXMLFormat_v1_0
errorDescription:&error];
if(returnData ) {
if ([returnData writeToFile:plistPath atomically:YES]) {
NSLog(#"Data successfully saved.");
}else {
NSLog(#"Did not managed to save NSData.");
}
}
else {
NSLog(#"%#",errorDesc);
}
// NSArray *stringsArray = [NSArray arrayWithContentsOfFile:plistPath];
NSDictionary *stringsDictionary = [NSDictionary dictionaryWithContentsOfFile:plistPath];
// NSLog(#"str: %#", stringsDictionary);
}
//delegate method for header
-(UICollectionReusableView*) collectionView:(UICollectionView *)collectionView viewForSupplementaryElementOfKind:(NSString *)kind atIndexPath:(NSIndexPath *)indexPath {
HeaderView * header = [collectionView dequeueReusableSupplementaryViewOfKind:UICollectionElementKindSectionHeader withReuseIdentifier:#"myHeader" forIndexPath:indexPath];
header.myHeaderLabel.text = titleArray[indexPath.section];
return header;
}
#pragma mark - UICollectionView Datasource
-(NSInteger) numberOfSectionsInCollectionView:(UICollectionView *)collectionView {
return titleArray.count;
}
-(NSInteger) collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section {
if (self.searchBarActive) {
return self.dataSourceForSearchResult.count;
}
NSArray *a = arrayPDFName[section];
if (a.count == 0)
{
return 1;
}
else
{
return a.count;
}
}
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout referenceSizeForHeaderInSection:(NSInteger)section {
return CGSizeMake(0, 80);
}
- (UICollectionViewCell *)collectionView:(UICollectionView *)cv cellForItemAtIndexPath: (NSIndexPath *)indexPath {
VenueCell *cell = [cv dequeueReusableCellWithReuseIdentifier:#"mycell" forIndexPath:indexPath];
cell.backgroundColor = [UIColor whiteColor];
cell.imgV.image = [UIImage imageNamed:#"doc1.png"];
if (self.searchBarActive) {
cell.myLabel.text = _dataSourceForSearchResult[indexPath.section][indexPath.row];
}else{
NSArray *a = arrayPDFName[indexPath.section];
if (a.count == 0) {
cell.myLabel.text = #"NO DATA";
return cell;
}
cell.myLabel.text = a[indexPath.row];
}
return cell;
}
//////////////////////////for search bar //////////
#pragma mark - actions
-(void)refreashControlAction{
[self cancelSearching];
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
// stop refreshing after 2 seconds
[self.mycollectionView reloadData];
[self.refreshControl endRefreshing];
});
}
#pragma mark - search
- (void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope{
NSPredicate *resultPredicate = [NSPredicate predicateWithFormat:#"self contains[c] %#", searchText];
self.dataSourceForSearchResult = [self->arrayPDFName filteredArrayUsingPredicate:resultPredicate];
}
- (void)searchBar:(UISearchBar *)searchBar textDidChange:(NSString *)searchText{
// user did type something, check our datasource for text that looks the same
if (searchText.length>0) {
// search and reload data source
self.searchBarActive = YES;
[self filterContentForSearchText:searchText
scope:[[self.searchDisplayController.searchBar scopeButtonTitles]
objectAtIndex:[self.searchDisplayController.searchBar
selectedScopeButtonIndex]]];
[self.mycollectionView reloadData];
}else{
// if text lenght == 0
// we will consider the searchbar is not active
self.searchBarActive = NO;
}
}
- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar{
[self cancelSearching];
[self.mycollectionView reloadData];
}
- (void)searchBarSearchButtonClicked:(UISearchBar *)searchBar{
self.searchBarActive = YES;
[self.view endEditing:YES];
}
- (void)searchBarTextDidBeginEditing:(UISearchBar *)searchBar{
// we used here to set self.searchBarActive = YES
// but we'll not do that any more... it made problems
// it's better to set self.searchBarActive = YES when user typed something
[self.searchBar setShowsCancelButton:YES animated:YES];
}
- (void)searchBarTextDidEndEditing:(UISearchBar *)searchBar{
// this method is being called when search btn in the keyboard tapped
// we set searchBarActive = NO
// but no need to reloadCollectionView
self.searchBarActive = NO;
[self.searchBar setShowsCancelButton:NO animated:YES];
}
-(void)cancelSearching{
self.searchBarActive = NO;
[self.searchBar resignFirstResponder];
self.searchBar.text = #"";
}
#pragma mark - prepareVC
-(void)prepareUI{
[self addSearchBar];
[self addRefreshControl];
}
-(void)addSearchBar{
if (!self.searchBar) {
self.searchBarBoundsY = self.navigationController.navigationBar.frame.size.height + [UIApplication sharedApplication].statusBarFrame.size.height;
self.searchBar = [[UISearchBar alloc]initWithFrame:CGRectMake(0,self.searchBarBoundsY, [UIScreen mainScreen].bounds.size.width, 50)];
self.searchBar.searchBarStyle = UISearchBarStyleMinimal;
self.searchBar.tintColor = [UIColor whiteColor];
self.searchBar.barTintColor = [UIColor whiteColor];
self.searchBar.delegate = self;
self.searchBar.placeholder = #"Search here";
[[UITextField appearanceWhenContainedIn:[UISearchBar class], nil] setTextColor:[UIColor whiteColor]];
// add KVO observer.. so we will be informed when user scroll colllectionView
[self addObservers];
}
if (![self.searchBar isDescendantOfView:self.view]) {
[self.view addSubview:self.searchBar];
}
}
-(void)addRefreshControl{
if (!self.refreshControl) {
self.refreshControl = [UIRefreshControl new];
self.refreshControl.tintColor = [UIColor whiteColor];
[self.refreshControl addTarget:self
action:#selector(refreashControlAction)
forControlEvents:UIControlEventValueChanged];
}
if (![self.refreshControl isDescendantOfView:self.mycollectionView]) {
[self.mycollectionView addSubview:self.refreshControl];
}
}
-(void)startRefreshControl{
if (!self.refreshControl.refreshing) {
[self.refreshControl beginRefreshing];
}
}
Where i am doing mistake and what i need to change to work.Thanks in advance!
It seems your arrayPDFName have array object and each array object have string object. There are two ways to filter you array.
Way - 1
If you want to get the list of array which has the search string the use SUBQUERY with your predicate. Like below.
NSArray *a1 = #[#"a1", #"a2", #"a3"];
NSArray *a2 = #[#"a1", #"a2", #"a3"];
NSArray *a3 = #[#"a1", #"a2", #"a3"];
NSArray *a4 = #[#"a2", #"a3"];
NSArray *allA = #[a1, a2, a3, a4];
NSPredicate *pre = [NSPredicate predicateWithFormat:#"SUBQUERY(SELF, $a, $a == %#).#count > 0", #"a1"];
NSArray *a = [allA filteredArrayUsingPredicate:pre];
Way - 2
If you want to get the search string alone from each array object then follow the below,
NSMutableArray *fa = [[NSMutableArray alloc] init];
for (NSArray *a in allA) {
NSPredicate *p = [NSPredicate predicateWithFormat:#"self CONTAINS[c] %#", #"a3"];
[fa addObjectsFromArray:[a filteredArrayUsingPredicate:p]];
}
Note: Above code done with same sample data. Replace it as you want.
As per your code replace the below code
-(void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope {
NSMutableArray *fa = [[NSMutableArray alloc] init];
for (NSArray *a in arrayPDFName) {
NSPredicate *p = [NSPredicate predicateWithFormat:#"self CONTAINS[c] %#", searchText];
[fa addObjectsFromArray:[a filteredArrayUsingPredicate:p]];
}
self.dataSourceForSearchResult = [NSArray arrayWithArray:fa];
}
-(NSInteger) numberOfSectionsInCollectionView:(UICollectionView *)collectionView {
if(self.searchBarActive)
return 1;
return titleArray.count;
}
In cellForItemAtIndexPath
cell.myLabel.text = _dataSourceForSearchResult[indexPath.row];
Had a little bit of trouble replacing my TableViewController with PFQueryTableViewController, but I got it working with pull to refresh and pagination. However, I can't get the cache to work (at the very bottom of the .m file). Any ideas on what's going on?
The only other change I made here was subclass the image in the cell as PFImage.
ContactsTableViewController.h
#import <UIKit/UIKit.h>
#import <Parse/Parse.h>
#import "FilterViewController.h"
#interface ContactsTableViewController : PFQueryTableViewController <UITableViewDelegate>
#property (nonatomic) NSString *titleName;
#property (nonatomic) NSString *date;
#property (nonatomic) NSString *price;
#property (nonatomic) NSString *imageName;
#property (nonatomic) NSString *venue;
#property (nonatomic) UIImage *image;
#property (nonatomic) NSString *filter;
#property (nonatomic) NSArray *eventsArray;
-(void)retrieveEvents;
-(void)filterEvents;
#end
ContactsTableViewController.m
#import "ContactsTableViewController.h"
#import "CustomCellTableViewCell.h"
#import "DetailViewController.h"
#interface ContactsTableViewController ()
#end
#implementation ContactsTableViewController
- (id)initWithCoder:(NSCoder *)aCoder
{
self = [super initWithCoder:aCoder];
if (self) {
// The className to query on
self.parseClassName = #"eventsList";
// The key of the PFObject to display in the label of the default cell style
// self.textKey = #"name";
// Whether the built-in pull-to-refresh is enabled
self.pullToRefreshEnabled = YES;
// Whether the built-in pagination is enabled
self.paginationEnabled = NO;
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
[self performSelector:#selector(retrieveEvents)];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(filterEvents) name:#"updateParent" object:nil];
self.view.backgroundColor = [UIColor colorWithRed:245/255.0 green:243/255.0 blue:240/255.0 alpha:1];
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Return the number of rows in the section.
return [self.eventsArray count];
}
// Parse Method
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object
{
static NSString *CellIdentifier = #"cellID";
CustomCellTableViewCell *customCell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
NSDictionary *tempDict = [self.eventsArray objectAtIndex:indexPath.row];
self.titleName = [tempDict objectForKey:#"eventTitle"];
self.price = [tempDict objectForKey:#"eventPrice"];
self.date = [tempDict objectForKey:#"eventDate"];
self.venue = [tempDict objectForKey:#"eventVenue"];
PFFile *imageFile = [tempDict objectForKey:#"eventImage"];
[imageFile getDataInBackgroundWithBlock:^(NSData *data, NSError *error) {
if (!error) {
customCell.customImageView.image = [UIImage imageWithData:data];
}
}];
customCell.titleLabel.text = self.titleName;
customCell.priceLabel.text = self.price;
customCell.customDateLabel.text = self.date;
customCell.venueNameLabel.text = self.venue;
return customCell;
}
- (void) tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath {
[cell setBackgroundColor:[UIColor darkGrayColor]];
tableView.separatorColor = [UIColor clearColor];
}
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:#"showEventDetail"]) {
DetailViewController *destinationVC = [[DetailViewController alloc] init];
destinationVC = segue.destinationViewController;
NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
NSDictionary *tempDict = [self.eventsArray objectAtIndex:indexPath.row];
destinationVC.eventTitle = [tempDict objectForKey:#"eventTitle"];
destinationVC.eventPrice = [tempDict objectForKey:#"eventPrice"];
destinationVC.eventDate = [tempDict objectForKey:#"eventDate"];
destinationVC.venueName = [tempDict objectForKey:#"eventVenue"];
destinationVC.navigationItem.title = [tempDict objectForKey:#"eventTitle"];
// Image
PFFile *imageFile = [tempDict objectForKey:#"eventImage"];
[imageFile getDataInBackgroundWithBlock:^(NSData *data, NSError *error) {
if (!error) {
destinationVC.eventImageView.image = [UIImage imageWithData:data];
destinationVC.eventImage = [UIImage imageWithData:data];
}
}];
// GeoPoint
destinationVC.geoPoint = [tempDict objectForKey:#"GeoPoint"];
} else if ([segue.identifier isEqualToString:#"showFilterTable"]){
FilterViewController *vc = (FilterViewController *)[[[segue destinationViewController] viewControllers] objectAtIndex:0];
[vc setDelegate:self];
}
}
-(void)retrieveEvents
{
PFQuery *retrieveEvents = [PFQuery queryWithClassName:#"eventsList"];
[retrieveEvents setLimit:300];
[retrieveEvents orderByAscending:#"eventTitle"];
[retrieveEvents findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
if (!error) {
self.eventsArray = [[NSArray alloc] initWithArray:objects];
}
[self.tableView reloadData];
}];
}
-(void)filterEvents
{
if ([self.filter isEqualToString:#"All Events"]) {
[self performSelector:#selector(retrieveEvents)];
return;
}
NSLog(#"retrieveEvents: %#", self.filter);
PFQuery *retrieveEvents = [PFQuery queryWithClassName:#"eventsList"];
[retrieveEvents whereKey:#"eventType" equalTo:self.filter];
[retrieveEvents setLimit:300];
[retrieveEvents orderByAscending:#"eventTitle"];
[retrieveEvents findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
if (!error) {
self.eventsArray = [[NSArray alloc] initWithArray:objects];
NSLog(#"%#", self.eventsArray);
}
[self.tableView reloadData];
}];
}
// Parse Method
- (PFQuery *)queryForTable
{
PFQuery *query = [PFQuery queryWithClassName:self.parseClassName];
query.cachePolicy = kPFCachePolicyCacheThenNetwork;
return query;
}
#end
From the looks of it you are not using the queryForTable to populate the tableview, you are using your separate query.
This query never gets used in your tableview
- (PFQuery *)queryForTable
{
PFQuery *query = [PFQuery queryWithClassName:self.parseClassName];
query.cachePolicy = kPFCachePolicyCacheThenNetwork;
return query;
}
Instead this one does:
-(void)retrieveEvents
{
PFQuery *retrieveEvents = [PFQuery queryWithClassName:#"eventsList"];
[retrieveEvents setLimit:300];
[retrieveEvents orderByAscending:#"eventTitle"];
[retrieveEvents findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
if (!error) {
self.eventsArray = [[NSArray alloc] initWithArray:objects];
}
[self.tableView reloadData];
}];
}
kPFCachePolicyCacheThenNetwork means to use both cache and network (first get from cache for quickness, then get from network for up-to-date-ness the next time). Try instead using kPFCachePolicyCacheElseNetwork.
Try this code. It may not be perfect. But I believe it should at least head you in the right direction.
#import "ContactsTableViewController.h"
#import "CustomCellTableViewCell.h"
#import "DetailViewController.h"
#interface ContactsTableViewController ()
#end
#implementation ContactsTableViewController
- (id)initWithCoder:(NSCoder *)aCoder
{
self = [super initWithCoder:aCoder];
if (self) {
// The className to query on
self.parseClassName = #"eventsList";
// The key of the PFObject to display in the label of the default cell style
// self.textKey = #"name";
// Whether the built-in pull-to-refresh is enabled
self.pullToRefreshEnabled = YES;
// Whether the built-in pagination is enabled
self.paginationEnabled = NO;
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(filterEvents) name:#"updateParent" object:nil];
self.view.backgroundColor = [UIColor colorWithRed:245/255.0 green:243/255.0 blue:240/255.0 alpha:1];
tableView.separatorColor = [UIColor clearColor];
}
-(void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
//This reloaded the PFQueryTableView
[self loadObjects];
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Return the number of rows in the section.
return self.objects.count;
}
// Parse Method
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object
{
static NSString *CellIdentifier = #"cellID";
CustomCellTableViewCell *customCell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
PFObject *object = [self objectAtIndexPath:indexPath];
customCell.titleLabel.text = object[#"eventTitle"];
customCell.priceLabel.text = object[#"eventPrice"];
customCell.customDateLabel.text = object[#"eventDate"];
customCell.venueNameLabel.text = object[#"eventVenue"];
PFFile *imageFile = [tempDict objectForKey:#"eventImage"];
[imageFile getDataInBackgroundWithBlock:^(NSData *data, NSError *error) {
if (!error) {
customCell.customImageView.image = [UIImage imageWithData:data];
}
}];
return customCell;
}
- (void) tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath {
[cell setBackgroundColor:[UIColor darkGrayColor]];
}
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:#"showEventDetail"]) {
DetailViewController *destinationVC = [[DetailViewController alloc] init];
destinationVC = segue.destinationViewController;
NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
NSDictionary *tempDict = [self.eventsArray objectAtIndex:indexPath.row];
destinationVC.eventTitle = [tempDict objectForKey:#"eventTitle"];
destinationVC.eventPrice = [tempDict objectForKey:#"eventPrice"];
destinationVC.eventDate = [tempDict objectForKey:#"eventDate"];
destinationVC.venueName = [tempDict objectForKey:#"eventVenue"];
destinationVC.navigationItem.title = [tempDict objectForKey:#"eventTitle"];
// Image
PFFile *imageFile = [tempDict objectForKey:#"eventImage"];
[imageFile getDataInBackgroundWithBlock:^(NSData *data, NSError *error) {
if (!error) {
destinationVC.eventImageView.image = [UIImage imageWithData:data];
destinationVC.eventImage = [UIImage imageWithData:data];
}
}];
// GeoPoint
destinationVC.geoPoint = [tempDict objectForKey:#"GeoPoint"];
} else if ([segue.identifier isEqualToString:#"showFilterTable"]){
FilterViewController *vc = (FilterViewController *)[[[segue destinationViewController] viewControllers] objectAtIndex:0];
[vc setDelegate:self];
}
}
// Parse Method
-(NSString *)filter
{
return _filter;
}
-(void)setFilter
{
_filter = filter;
[self loadObjects];
}
- (PFQuery *)queryForTable
{
PFQuery *query = [PFQuery queryWithClassName:self.parseClassName];
query.cachePolicy = kPFCachePolicyCacheThenNetwork;
if (self.filter && ![self.filter isEqualToString:#"All Events"]) [query whereKey:#"eventTitle" equalTo:self.filter];
[query setLimit:300];
[query orderByAscending:#"eventTitle"];
return query;
}
#end
I have a well-functioning search bar. Only one thing that I want to improve is NSTimer. I don`t know why, but when I start typing, it search me results after some delay.It woks perfectly. But I get for every typed letter 1 API each. It mean that if I put into search bar for example Sudan. I get 5 API instead of 1. Could you someone help me?
Thanks
TableViewControllerTOP.h
#interface TableViewControllerTOP : UITableViewController<UISearchDisplayDelegate, UISearchBarDelegate,UIScrollViewDelegate,UITableViewDataSource, UITableViewDelegate>
{
NSTimer *myTimer;
}
#property (strong, nonatomic) IBOutlet UITableView *MainTable;
#property (nonatomic, strong) UISearchBar *searchBar;
#property (nonatomic, strong) UISearchDisplayController *searchController;
#property (nonatomic, strong) NSMutableArray *searchResults;
#property (nonatomic, retain) NSTimer *myTimer;
#property (nonatomic, assign) BOOL isAscending;
TableViewControllerTOP.m
#interface TableViewControllerTOP ()
#property (strong,nonatomic) NSMutableArray *itemss;
#end
#implementation TableViewControllerTOP
#synthesize myTimer;
#synthesize searchBar;
#synthesize searchController;
#synthesize searchResults;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.isAscending = YES;
UIRefreshControl *refreshControl = [[UIRefreshControl alloc] init]; [refreshControl addTarget:self action:#selector(pulltorefresh) forControlEvents:UIControlEventValueChanged];
self.refreshControl = refreshControl;
PFQuery *query = [PFQuery queryWithClassName:#"Countries"];
query.cachePolicy = kPFCachePolicyIgnoreCache;
[query addDescendingOrder:#"createdAt"];
[query setLimit:10];
[query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
if (!error) {
NSMutableArray *items = [NSMutableArray array];
for (id obj in objects)
{
[items addObject:obj];
}
self.itemss = items;
NSLog(#"%#", objects);
NSLog(#"%lu", (unsigned long)[objects count]);
[_MainTable reloadData];
} else {
NSLog(#"Error: %# %#", error, [error userInfo]);
}
}];
[self searchitems];
}
-(void)searchitems
{
self.searchBar = [[UISearchBar alloc] initWithFrame:CGRectMake(0, 0, self.view.frame.size.width, 44)];
self.tableView.tableHeaderView = self.searchBar;
self.searchController = [[UISearchDisplayController alloc] initWithSearchBar:self.searchBar contentsController:self];
self.searchController.searchResultsDataSource = self;
self.searchController.searchResultsDelegate = self;
self.searchController.delegate = self;
self.searchResults = [NSMutableArray array];
self.tableView.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:#"background.png"]];
[self.navigationController.navigationBar setBarTintColor:[UIColor lightGrayColor]];
}
-(void)filterResults:(NSString *)searchTerm {
myTimer = [NSTimer scheduledTimerWithTimeInterval:3.0
target:self
selector:#selector(queryask)
userInfo:_itemss
repeats:NO];
}
-(void)queryask{
PFQuery *queryCapitalizedString = [PFQuery queryWithClassName:#"Countries"];
[queryCapitalizedString whereKey:#"CountryTitle" containsString:[searchBar.text capitalizedString]];
PFQuery *queryLowerCaseString = [PFQuery queryWithClassName:#"Countries"];
[queryLowerCaseString whereKey:#"CountryTitle" containsString:[searchBar.text lowercaseString]];
PFQuery *querySearchBarString = [PFQuery queryWithClassName:#"Countries"];
[querySearchBarString whereKey:#"CountryTitle" containsString:searchBar.text];
PFQuery *finalQuery = [PFQuery orQueryWithSubqueries:[NSArray arrayWithObjects:queryCapitalizedString,queryLowerCaseString, querySearchBarString,nil]];
[finalQuery findObjectsInBackgroundWithTarget:self selector:#selector(callbackWithResult:error:)];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchString:(NSString *)searchString {
[self filterResults:searchString];
return YES;
}
- (void)callbackWithResult:(NSArray *)items error:(NSError *)error
{
if(!error) {
[self.searchResults removeAllObjects];
[self.searchResults addObjectsFromArray:items];
[self.searchDisplayController.searchResultsTableView reloadData];
}
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
if (tableView == self.tableView) {
return self.itemss.count;
} else {
return self.searchResults.count;
}
}
- (void)searchDisplayController:(UISearchDisplayController *)controller didLoadSearchResultsTableView:(UITableView *)tableView
{
tableView.rowHeight = 70.0f;
}
- ( UITableViewCell * ) tableView : ( UITableView * ) tableView cellForRowAtIndexPath : ( NSIndexPath * ) indexPath
{
static NSString *uniqueIdentifier = #"MainCell";
CustomCell3 *cell = nil;
cell = (CustomCell3 *) [self.tableView dequeueReusableCellWithIdentifier:uniqueIdentifier];
if (!cell) {
NSArray *topLevelObjects = [[NSBundle mainBundle] loadNibNamed:#"MainCell" owner:nil options:nil];
for (id currentObject in topLevelObjects)
{
if([currentObject isKindOfClass:[CustomCell3 class]])
{
cell = (CustomCell3 *)currentObject;
break;
}
}
}
if (tableView == self.tableView) {
cell.MainTitle.text = [[self.itemss objectAtIndex:indexPath.row] objectForKey:#"CountryTitle"];
cell.DescriptTitle.text = [[self.itemss objectAtIndex:indexPath.row] objectForKey:#"DescriptTitle"];
[cell.FlagTitle setImageWithURL:[NSURL URLWithString:[[self.itemss objectAtIndex:indexPath.row] objectForKey:#"ImaURL"]]
placeholderImage:[UIImage imageNamed:#"placeholder.png"]];
cell.backgroundView = [[UIImageView alloc] initWithImage:[ [UIImage imageNamed:#"background.png"] stretchableImageWithLeftCapWidth:0.0 topCapHeight:5.0] ];
cell.selectedBackgroundView = [[UIImageView alloc] initWithImage:[ [UIImage imageNamed:#"background.png"] stretchableImageWithLeftCapWidth:0.0 topCapHeight:5.0] ];
}
if(tableView == self.searchDisplayController.searchResultsTableView) {
PFObject *searchedUser = [self.searchResults objectAtIndex:indexPath.row];
NSString *content = [searchedUser objectForKey:#"CountryTitle"];
NSString *desco = [searchedUser objectForKey:#"DescriptTitle"];
cell.DescriptTitle.text = desco;
cell.MainTitle.text = content;
NSString *image = [searchedUser objectForKey:#"ImaURL"];
[cell.FlagTitle setImageWithURL:[NSURL URLWithString:image]
placeholderImage:[UIImage imageNamed:#"placeholder.png"]];
cell.backgroundView = [[UIImageView alloc] initWithImage:[ [UIImage imageNamed:#"background.png"] stretchableImageWithLeftCapWidth:0.0 topCapHeight:5.0] ];
cell.selectedBackgroundView = [[UIImageView alloc] initWithImage:[ [UIImage imageNamed:#"background.png"] stretchableImageWithLeftCapWidth:0.0 topCapHeight:5.0] ];
}
return cell;
}
#end
For a way to delay the search, take a look at this SO question:
Delay UISearchbar parsing
A good idea could be to combine this with Logan's suggestion. A search should often not be performed until a minimum of characters have been entered, to avoid too broad searches (not much point performing a search for anything containing "s" in many cases, depending on what you are searching).
Perhaps instead of a timer, you could implement a search bar delegate to run a query after some custom logic, perhaps every 3 letters?
- (void) searchBar:(UISearchBar *)searchBar textDidChange:(NSString *)searchText {
if ((searchBar.text.length % 3) == 0) {
[self queryAsk];
}
}
Note: This logic isn't the best, and you might want to explore various parameters for when to search, but I think the concept improves over the timer because it would be more based on input. I think it would give you more control.
I am getting a very strange array issue with LogoURL. Sometimes it works and sometimes it errors when trying to display the URL's in the array as an image. This is an Mutable array problem and its driving me crazy.
import "ViewController.h"
#interface ViewController ()
#property (nonatomic, strong) MSTable *table;
#property (nonatomic, strong) NSMutableArray *items;
#property (weak, nonatomic) IBOutlet UITableView *MainTableView;
#end
#implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
// create the activity indicator in the main queue
self.MainTableView.hidden = YES;
UIActivityIndicatorView *ac = [[UIActivityIndicatorView alloc]
initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
[self.view addSubview:ac];
[ac startAnimating];
self.client = [MSClient clientWithApplicationURLString:#"https://mobile.net/" applicationKey:#""];
self.table = [self.client tableWithName:#"notifications"];
self.logoURL = [[NSMutableArray alloc] init];
self.rowitems = [[NSMutableArray alloc] init];
MSQuery *query = [self.table query];
query.fetchLimit = 3;
[query readWithCompletion:^(NSArray *items, NSInteger totalCount, NSError *error)
{
self.rowitems = [items mutableCopy];
//[self.MainTableView reloadData];
int a;
for (a = 0; a < 3; a++)
{
NSDictionary *apt = [self.rowitems objectAtIndex:a];
NSLog(#"%#", apt[#"barID"]);
NSDictionary *barIDDictionary = #{ #"myParam": apt[#"barID"]};
self.client = [MSClient clientWithApplicationURLString:#"https://outnight-mobile.azure-mobile.net/" applicationKey:#"okYeRGfBagYrsbkaqWIRObeDtktjkF10"];
[self.client invokeAPI:#"photos" body:barIDDictionary HTTPMethod:#"POST" parameters:nil headers:nil completion:^(id result, NSHTTPURLResponse *response, NSError *error) {
if (error) {
NSLog(#"Error %#", error );
}
else {
NSString *string = [NSString stringWithFormat:#"%#", [result objectForKey:#"rows"]];
NSString *stringWithoutbracketsend = [string stringByReplacingOccurrencesOfString:#")" withString:#""];
NSString *stringWithoutbracketsfront = [stringWithoutbracketsend stringByReplacingOccurrencesOfString:#"(" withString:#""];
NSString *completion = [stringWithoutbracketsfront stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
NSString *newStr = [completion substringFromIndex:1];
NSString *finalstring = [newStr substringToIndex:newStr.length-(newStr.length>0)];
[self.logoURL insertObject:finalstring atIndex:a];
[self.MainTableView reloadData];
}
}];
}
}];
self.MainTableView.hidden = NO;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [self.rowitems count];
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:#"cell"];
NSDictionary *stress = [self.rowitems objectAtIndex:indexPath.row];
cell.textLabel.text = stress[#"content"];
if (self.logoURL.count > indexPath.row) {
[cell.imageView setImageWithURL:[NSURL URLWithString:self.logoURL[indexPath.row]] placeholderImage:[UIImage imageNamed:#"greybox40.png"]];
NSLog(#"%#", self.logoURL[indexPath.row]);
}
else
cell.imageView.image = nil;
return cell;
}
#end
I need some fresh eyes on it, can anyone advice ?
thanks
I don’t know much about MSQuery, but if the completion block can be in a separate thread, this is going to mess you up.
The tableView can call -tableView:numberOfRowsInSection: when you have some number of rows, and then call -tableView:cellForRowAtIndexPath: when there’s a totally different number.
Also I don’t know what MSClient is, but if it’s running its completion block in a background thread you’re reloading your tableView in a background thread, so that’s gonna kill you, too.
Request my test webService for the data,
The tableView's last row is "More data..."
when click this row, send another request to get more data,
and I use [tableView reloaddata] many times, but there is nothing
happened, and I dont know why.So,please help me with this problem.
Thank you in advance.
and there is my tableViewController.h class:
#import <UIKit/UIKit.h>
#import "NoticeDetailViewController.h"
#interface NoticeViewController : UIViewController
<UITableViewDataSource,UITableViewDelegate>
{
NSMutableArray *allNoticeArray;
NSArray *addNoticeArray;
NSInteger totalNotice;
NSInteger pageIndex;
UITableView *tableView;
}
#property (nonatomic, retain) NSMutableArray *allNoticeArray;
#property (nonatomic, retain) NSArray *addNoticeArray;
#property NSInteger totalNotice;
#property NSInteger pageIndex;
#property (nonatomic, retain) UITableView *tableView;
- (NSMutableArray *)getNoticeList :(NSInteger)pageIndex;
#end
And tableViewController.m class:
#import "NoticeViewController.h"
#import "Notice.h"
#import "OAURLEncodingAdditions.h"
#interface NoticeViewController ()
#end
#implementation NoticeViewController
#synthesize allNoticeArray;
#synthesize addNoticeArray;
#synthesize pageIndex;
#synthesize tableView;
#synthesize totalNotice;
- (NSMutableArray *)getNoticeList :(NSInteger)pageIndex
{
AppDelegate *appDelegate = (AppDelegate *)[[UIApplication sharedApplication] delegate];
NSString *userId = appDelegate.user.userId;
NSString *departmentId = appDelegate.user.departmentId;
NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:#"https://xxx.xxx.xx.xx/FMS/Pages/Service/FMService.svc/GetAnnouncement?userId=%#&departmentId=%#&pageIndex=%d&pageSize=%d",userId,departmentId,self.pageIndex,1]];
ASIHTTPRequest *request = [ASIHTTPRequest requestWithURL:url];
[request setValidatesSecureCertificate:NO];
[request startSynchronous];
NSError *error = [request error];
if (!error)
{
NSString *responseString = [request responseString];
NSDictionary *responseDict = [responseString JSONValue];
NSArray *noticeArray = [responseDict objectForKey:#"d"];
NSMutableArray *arrayOfAllNotice = [[NSMutableArray alloc] init];
for (NSDictionary *noticeDic in noticeArray)
{
NSString *body = [noticeDic objectForKey:#"Body"];
NSString *departmentName = [noticeDic objectForKey:#"DepartmentName"];
NSString *noticeId = [noticeDic objectForKey:#"Id"];
NSString *isTop = [noticeDic objectForKey:#"IsTop"];
NSString *readState = [noticeDic objectForKey:#"ReadState"];
NSString *realName = [noticeDic objectForKey:#"RealName"];
NSString *title = [noticeDic objectForKey:#"Title"];
int noid = [noticeId intValue];
int isto = [isTop intValue];
int read = [readState intValue];
Notice *notice = [[Notice alloc] initWithBody:body
departmentName:departmentName
noticeId: noid
isTop:isto
readState:read
realName:realName
title:title];
[arrayOfAllNotice addObject:notice];
}
self.addNoticeArray = [[NSArray alloc] initWithArray:arrayOfAllNotice];
}
else
{
....
}
[allNoticeArray addObjectsFromArray:addNoticeArray];
NSLog(#"allNoticeArray count: %d",[allNoticeArray count]); //Here:When the last row clicked, the number changes:1->2
[self.tableView reloadData];
return allNoticeArray;
}
#pragma mark -
#pragma mark Table View Data Source Methods
- (NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
NSInteger theNumberOfRowsInSection;
if ( [allNoticeArray count] < (self.totalNotice))
{
theNumberOfRowsInSection = [allNoticeArray count]+1;
}
if ( [allNoticeArray count] == (self.totalNotice))
{
theNumberOfRowsInSection = [allNoticeArray count];
}
return theNumberOfRowsInSection;
}
- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
[self.tableView reloadData];
static NSString *NoticeListTableIdentifier = #"NoticeListTableIdentifier";
UITableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:NoticeListTableIdentifier];
if ( cell == nil )
{
cell = [[[UITableViewCell alloc]
initWithStyle:UITableViewCellStyleDefault reuseIdentifier:NoticeListTableIdentifier] autorelease];
}
if ( [allNoticeArray count] < (self.totalNotice) )
{
if ( [indexPath row] != [allNoticeArray count])
{
NSUInteger row = [indexPath row];
Notice *noticeOfTheRow = [allNoticeArray objectAtIndex:row];
NSString *title = noticeOfTheRow.title;
cell.textLabel.text = title;
}
else
{
cell.textLabel.text = #"More...";
}
}
if ( [allNoticeArray count] == (self.totalNotice) )
{
NSUInteger row = [indexPath row];
Notice *noticeOfTheRow = [allNoticeArray objectAtIndex:row];
NSString *title = noticeOfTheRow.title;
cell.textLabel.text = title;
}
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if ( [indexPath row] != [allNoticeArray count])
{
NSUInteger row = [indexPath row];
Notice *notice = [allNoticeArray objectAtIndex:row];
NSString *noticeDetailTitle = notice.title;
NoticeDetailViewController *noticeDetailViewController = [[[NoticeDetailViewController alloc] init] autorelease];
noticeDetailViewController.title = noticeDetailTitle;
ticeDetailViewController.noticeIdForGet = notice.noticeId;
[self.navigationController pushViewController:noticeDetailViewController animated:YES];
}
if ( [indexPath row] == [allNoticeArray count])
{
MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:self.view animated:YES];
hud.labelText = #"reload...";
self.pageIndex ++;
[self getNoticeList:self.pageIndex];
[self.tableView reloadData];
[MBProgressHUD hideHUDForView:self.view animated:YES];
}
}
- (void)pushBack
{
[self dismissModalViewControllerAnimated:YES];
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.allNoticeArray = [[NSMutableArray alloc] init];
self.pageIndex = 1;
MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:self.view animated:YES];
hud.labelText = #"reload...";
self.title = #"Notice";
UIBarButtonItem *leftButton = [[UIBarButtonItem alloc] initWithTitle:#"back"
style:UIBarButtonItemStyleBordered
target:self
action:#selector(pushBack)];
self.navigationItem.leftBarButtonItem = leftButton;
UIBarButtonItem *rightButton = [[UIBarButtonItem alloc] initWithTitle:#"reload"
style:UIBarButtonItemStyleBordered
target:self
action:#selector(reloadNotice)];
self.navigationItem.rightBarButtonItem = rightButton;
self.allNoticeArray = [self getNoticeList:self.pageIndex];
[MBProgressHUD hideHUDForView:self.view animated:YES];
}
#end
change:
if ( [indexPath row] == [allNoticeArray count])
to:
if ( [indexPath row] == [allNoticeArray count]-1)
The reason is that array (and row) indexing are base 0. So if an array has, say 3 objects, last object's index is 2
BTW,with the new language features, there's no need to declare the ivars in the interface. The compiler will take care of them if you have already declared the properties and synthesized them.
#interface NoticeViewController : UIViewController
<UITableViewDataSource,UITableViewDelegate>
{
NSMutableArray *allNoticeArray;
NSArray *addNoticeArray;
NSInteger totalNotice;
NSInteger pageIndex;
UITableView *tableView;
}
//...
#end