I'm trying to progressHUD in the Asynchronous request, but it does not seem to work probably. What i want is it to show the progessHUD until the Asynchronous request is done. at the moment it is not showing in the beginning, but after 3 sec it is showing for 0.1 second or something and after that the Asynchronous request is completed. What am i doing wrong, to achieve that the progessHUD is shown when the viewisloaded to the Asynchronous request is done?
As you can see below i've added progressHUD show and dismiss in the viewDidLoad and in the firstRequest method.
Viewdidload:
- (void)viewDidLoad
{
[super viewDidLoad];
[ProgressHUD show:#"Please Wait..."];
buttonLogin = [[UIBarButtonItem alloc] initWithTitle:#"Login" style:UIBarButtonItemStyleBordered target:self action:#selector(actionLogin)];
buttonLogout = [[UIBarButtonItem alloc] initWithTitle:#"Logout" style:UIBarButtonItemStyleBordered target:self action:#selector(actionLogout)];
CGRect screenRect = [[UIScreen mainScreen] bounds];
CGFloat screenWidth = screenRect.size.width;
CGFloat screenHeight = screenRect.size.height;
self.theTableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 0, screenWidth, screenHeight-160) style:UITableViewStylePlain];
self.theTableView.dataSource = self;
self.theTableView.delegate = self;
[self.view addSubview:self.theTableView];
self.navigationController.navigationBar.tintColor = [UIColor whiteColor];
self.navigationController.navigationBar.titleTextAttributes = #{NSForegroundColorAttributeName : [UIColor whiteColor]};
fixtures = [[NSMutableArray alloc] init];
sections = [[NSMutableArray alloc] init];
sortedArray = [[NSMutableArray alloc] init];
[self firstRequest];
self.bannerView = [[GADBannerView alloc] initWithFrame:CGRectMake(0.0, self.view.frame.size.height-100, GAD_SIZE_320x50.width, GAD_SIZE_320x50.height)];
self.theTableView.backgroundColor = [UIColor colorWithRed:243/255.0f green:243/255.0f blue:247/255.0f alpha:1.0f];
self.view.backgroundColor = [UIColor colorWithRed:243/255.0f green:243/255.0f blue:247/255.0f alpha:1.0f];
[self checkAuthStatus];
[ProgressHUD dismiss];
}
the request:
-(void)firstRequest
{
NSURL *url = [NSURL URLWithString:#"URL"];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
[NSURLConnection sendAsynchronousRequest:request
queue:[NSOperationQueue mainQueue]
completionHandler:^(NSURLResponse *response,
NSData *data, NSError *connectionError)
{
[ProgressHUD show:#"Please Wait..."];
jsonResult = [NSJSONSerialization JSONObjectWithData:data
options:0
error:NULL];
int subObjects = ((NSArray *)jsonResult[#"match"]).count;
for (int i = 0; i <= subObjects-1; i++) {
NSString *date = [NSString stringWithFormat:#"%# %#",[[[jsonResult valueForKey:#"match"] valueForKey:#"playdate"] objectAtIndex:i], [[[jsonResult valueForKey:#"match"] valueForKey:#"time"] objectAtIndex:i]];
NSString *identifier = [[NSLocale currentLocale] localeIdentifier];
NSDateFormatter *df = [[NSDateFormatter alloc] init];
[df setTimeZone: [NSTimeZone timeZoneWithName:#"US/Arizona"]];
[df setLocale:[NSLocale localeWithLocaleIdentifier:identifier]];
[df setDateFormat:#"yyyy-MM-dd HH:mm:ss"];
NSDate *myDate = [df dateFromString:[NSString stringWithFormat:#"%#", date]];
NSArray *items = [[NSString stringWithFormat:#"%#", myDate] componentsSeparatedByString:#" "];
NSString *home = [[[jsonResult valueForKey:#"match"] valueForKey:#"hometeam"] objectAtIndex:i];
NSString *away = [[[jsonResult valueForKey:#"match"] valueForKey:#"awayteam"] objectAtIndex:i];
NSString *league = [[[jsonResult valueForKey:#"match"] valueForKey:#"league"] objectAtIndex:i];
[fixtures addObject:
[[NSMutableDictionary alloc] initWithObjectsAndKeys:
items[0], #"date",
items[1], #"time",
home, #"home",
away, #"away",
league, #"league",
nil]];
[sections addObject:
[[NSMutableDictionary alloc] initWithObjectsAndKeys:
items[0], #"date",
nil]];
}
NSArray *copy = [sections copy];
NSInteger index = [copy count] - 1;
for (id object in [copy reverseObjectEnumerator]) {
if ([sections indexOfObject: object inRange: NSMakeRange(0, index)] != NSNotFound) {
[sections removeObjectAtIndex: index];
}
index--;
}
NSSortDescriptor *descriptor = [[NSSortDescriptor alloc] initWithKey:#"self" ascending:NO];
NSArray *descriptors = [NSArray arrayWithObject: descriptor];
NSArray* reverseTheArray = [[sections valueForKey:#"date"] sortedArrayUsingDescriptors:descriptors];
reversedArray = [[reverseTheArray reverseObjectEnumerator] allObjects];
[self.theTableView reloadData];
[ProgressHUD dismiss];
}
];
}
You should show ProgressHUD before sending a request.
Your code should look like this.
-(void)firstRequest
{
[ProgressHUD show:#"Please Wait..."];
NSURL *url = [NSURL URLWithString:#"URL"];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
[NSURLConnection sendAsynchronousRequest:request
queue:[NSOperationQueue mainQueue]
completionHandler:^(NSURLResponse *response,
NSData *data, NSError *connectionError)
{
// request processing stuff
...
[ProgressHUD dismiss];
}
];
Explanation. When you call sendAsynchronousRequest... the request itself performed somewhere in background thread. The network operation may take some time, 1-5-10 seconds. Your completionHandler will be executed once the request completes (after the delay). So you should show ProgressHUD before sending a request. Then start the request. And dismiss ProgressHUD at the end of your completionHandler block after everything is processed.
Update
There is one more issue I noticed in your code. viewDidLoad method is called only once on view controller when its view is loaded but at this point the view itself is not presented on screen. So you will not actually see ProgressHUD called from viewDidLoad. You may be interested in viewWillAppear and viewDidAppear methods if you want to handle when view is presented on screen.
I assume your view controller is designed to show data retrieved from web api. I believe the best option is to call your api in viewWillAppear.
- (void)viewDidLoad
{
[super viewDidLoad];
buttonLogin = [[UIBarButtonItem alloc] initWithTitle:#"Login" style:UIBarButtonItemStyleBordered target:self action:#selector(actionLogin)];
buttonLogout = [[UIBarButtonItem alloc] initWithTitle:#"Logout" style:UIBarButtonItemStyleBordered target:self action:#selector(actionLogout)];
CGRect screenRect = [[UIScreen mainScreen] bounds];
CGFloat screenWidth = screenRect.size.width;
CGFloat screenHeight = screenRect.size.height;
self.theTableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 0, screenWidth, screenHeight-160) style:UITableViewStylePlain];
self.theTableView.dataSource = self;
self.theTableView.delegate = self;
[self.view addSubview:self.theTableView];
self.navigationController.navigationBar.tintColor = [UIColor whiteColor];
self.navigationController.navigationBar.titleTextAttributes = #{NSForegroundColorAttributeName : [UIColor whiteColor]};
fixtures = [[NSMutableArray alloc] init];
sections = [[NSMutableArray alloc] init];
sortedArray = [[NSMutableArray alloc] init];
self.bannerView = [[GADBannerView alloc] initWithFrame:CGRectMake(0.0, self.view.frame.size.height-100, GAD_SIZE_320x50.width, GAD_SIZE_320x50.height)];
self.theTableView.backgroundColor = [UIColor colorWithRed:243/255.0f green:243/255.0f blue:247/255.0f alpha:1.0f];
self.view.backgroundColor = [UIColor colorWithRed:243/255.0f green:243/255.0f blue:247/255.0f alpha:1.0f];
[self checkAuthStatus];
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
[self firstRequest];
}
-(void)firstRequest
{
[ProgressHUD show:#"Please Wait..."];
NSURL *url = [NSURL URLWithString:#"URL"];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
[NSURLConnection sendAsynchronousRequest:request
queue:[NSOperationQueue mainQueue]
completionHandler:^(NSURLResponse *response,
NSData *data, NSError *connectionError)
{
// request processing stuff
...
[ProgressHUD dismiss];
}
];
}
Related
This is the code in my detail view it can delete event in when u come to detail view press the switch to add event and then press it again to delete it. However, when u come to detail view and then press back (using navigation) and then come o the same page again it cannot delete the event please help
there are more function but I delete just focus on Switch and EVENTKIT
//
// DetailScheduleViewController.m
// Register
//
// Created by junejubu on 3/10/2558 BE.
// Copyright (c) 2558 Thananont Aunsiripant. All rights reserved.
//
- (void)viewDidLoad {
[super viewDidLoad];
//NSLog(#"check show id sch ::%#",self.Show_ID);
self.Switch.on = NO;
self.lblNotification.text = #"Notification OFF";
[self getUserNotification];
[self getUserFollow];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (void)getUserNotification
{
NSString *urlStr2 = #"http://ptvshowthai.com/getNotification.php";
NSURL *url2 = [NSURL URLWithString:urlStr2];
self.getnoti = [ASIFormDataRequest requestWithURL:url2];
self.getnoti.requestMethod = #"POST"; //DELETE, PUT
self.getnoti.delegate = self;
self.getnoti.timeOutSeconds = 30;
[self.getnoti setPostValue: self.FK_User_ID forKey:#"sMemberID"];
[self.getnoti setValidatesSecureCertificate:NO];
[self.getnoti startAsynchronous];
}
- (void)requestFinished:(ASIHTTPRequest *)request
{
NSLog(#"requestFinished");
if (request == self.getnoti) {
self.dictnoti = [NSJSONSerialization JSONObjectWithData:[request responseData] options:NSJSONReadingAllowFragments error:nil];
self.NOTI = [[NSMutableArray alloc] init];
for (NSDictionary *dataDic in self.dictnoti )
{
// unsigned long count2 = [self.dict2 count];
NSString *ShowID2 = [dataDic objectForKey:#"Show_ID"];
self.str2 = [dataDic objectForKey:#"Event_Store"];
// NSLog(#"check str2 :: %#",self.str2);
[self.NOTI addObject:ShowID2];
}
NSLog(#"Show who noti ::%#",self.NOTI);
// NSLog(#"check str2 :: %#",self.str2);
}
if(request ==self.getFollow){
self.dict2 = [NSJSONSerialization JSONObjectWithData:[request responseData] options:NSJSONReadingAllowFragments error:nil];
NSLog(#"Dict getFollow :: %#",self.dict2);
//unsigned long count2 = [self.dict2 count];
//NSLog(#"show count ::%lu",count2);
_Show = [[NSMutableArray alloc] init];
// NSDictionary *dict;
for (NSDictionary *dataDic in self.dict2 )
{
// unsigned long count2 = [self.dict2 count];
NSString *ShowID = [dataDic objectForKey:#"Show_ID"];
[self.Show addObject:ShowID];
}
if ([self.Show containsObject: self.Show_ID]) {
_lblFollow.text = #"Following";
_lblFollow.textColor = [UIColor greenColor];
_i = #"0";
NSLog(#"check i green :: %#",_i);
self.Switch.hidden = NO;
NSLog(#"check self.noti : %#",self.NOTI);
if ([self.NOTI containsObject: self.Show_ID]){
self.Switch.on = YES;
}
self.lblNotification.hidden = NO;
[self.Switch addTarget:self action:#selector(Onoff) forControlEvents:UIControlEventValueChanged];
}
else{
_lblFollow.text = #"Follow";
_lblFollow.textColor = [UIColor redColor];
_i = #"1";
NSLog(#"check i red :: %#",_i);
self.Switch.hidden = YES;
self.Switch.on = NO;
self.lblNotification.hidden = YES;
[self.Switch addTarget:self action:#selector(Onoff) forControlEvents:UIControlEventValueChanged];
}
}
}
-(void)addevent{
_eventStore = [[EKEventStore alloc] init];
if ([_eventStore respondsToSelector:#selector(requestAccessToEntityType:completion:)])
{
[_eventStore requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) {
if (granted){
addEventgranted = 1;
EKEvent *event = [EKEvent eventWithEventStore:_eventStore];
[event setTitle:self.showNameTitle];
[event setStartDate: self.today];
[event setEndDate:[[NSDate alloc]initWithTimeInterval:self.duration sinceDate:event.startDate]];
NSTimeInterval alarmOffset = -300;
EKAlarm *alarm = [EKAlarm alarmWithRelativeOffset:alarmOffset];
[event addAlarm:alarm];
[event setCalendar:[_eventStore defaultCalendarForNewEvents]];
NSError *err;
[_eventStore saveEvent:event span:EKSpanThisEvent error:&err];
self.str = [[NSString alloc] initWithFormat:#"%#", event.eventIdentifier];
NSLog(#"check self.str :: %#",self.str);
NSString *url = #"http://ptvshowthai.com/insertNotification.php";
NSURL *urls = [NSURL URLWithString:url];
self.formData = [ASIFormDataRequest requestWithURL:urls];
self.formData.requestMethod = #"POST";
self.formData.delegate = self;
self.formData.timeOutSeconds = 30;
[self.formData setPostValue: self.FK_User_ID forKey:#"sMemberID"];
[self.formData setPostValue: self.Show_ID forKey:#"showID"];
NSLog(#"check str::: %#",self.str);
[self.formData setPostValue: self.str forKey:#"event"];
[self.formData setValidatesSecureCertificate:NO];
[self.formData startAsynchronous];
_lblFollow.text = #"Following";
_lblFollow.textColor = [UIColor greenColor];
NSLog(#"Follow");
[self getUserNotification];
}
}];
}
}
-(void)alert
{
if (addEventgranted == 1) {
UIAlertView *alert = [[UIAlertView alloc]initWithTitle:#"Success" message:#"Event Successfully added" delegate:self cancelButtonTitle:#"OK" otherButtonTitles: nil];
[alert show];
}
}
-(void)Onoff
{
if (self.Switch.on) {
[self addevent];
[self performSelector:#selector(alert) withObject:nil afterDelay:0.3];
self.lblNotification.text =#"Notification On";
}
else
{
NSLog(#"check str22::%#",self.str2);
EKEvent* event2 = [_eventStore eventWithIdentifier:self.str2];
if (event2 != nil) {
NSError* error = nil;
[_eventStore removeEvent:event2 span:EKSpanThisEvent error:&error];
}
self.lblNotification.text =#"Notification OFF";
NSString *url = #"http://ptvshowthai.com/deleteNotification.php";
NSURL *urls = [NSURL URLWithString:url];
self.formData = [ASIFormDataRequest requestWithURL:urls];
self.formData.requestMethod = #"POST";
self.formData.delegate = self;
self.formData.timeOutSeconds = 30;
[self.formData setPostValue: self.FK_User_ID forKey:#"sMemberID"];
[self.formData setPostValue: self.Show_ID forKey:#"showID"];
[self.formData setValidatesSecureCertificate:NO];
[self.formData startAsynchronous];
_lblFollow.text = #"Following";
_lblFollow.textColor = [UIColor greenColor];
NSLog(#"Follow");
[self getUserNotification];
}
}
Add below line of code at switch off condition also
Its better to add below line at ViewDidLoad instead of addEvent method..
_eventStore = [[EKEventStore alloc] init];
Hope it fixes..!
I'm stuck with an issue on how to best load a couple of UILabels asynchronously.
Here is my cellForRowAtIndexPath method:
UPDATE:
Based on the answer below, I've made changes:
Here is my new cellForRowAtIndexPath
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
// Retrieve cell
NSString *cellIdentifier = #"BuildingItem";
BuildingsTableViewCell *cell = [[tableView dequeueReusableCellWithIdentifier:cellIdentifier] initWithFrame:CGRectMake(10, 10,580, 100)];
// Get the area to be shown
Buildings *item = _feedItems[indexPath.row];
NSURL *MyURL = [NSURL URLWithString:item.buildingPointerImage];
UIImage *placeholder = [UIImage imageNamed:#"placeholder"];
NSString *path = [MyURL absoluteString];
NSString *key = [path MD5Hash];
[cell.buildingImageView loadImageFromURL:(NSURL*)MyURL placeholderImage:(UIImage*)placeholder cachingKey:(NSString*)key];
cell.buildingName.text = item.buildingPointerName;
cell.buildingYear.text = item.buildingPointerYear;
NSString *URL = #"http://rets.miamiresidential.com/ios/condos/buildings.php?action=get_range";
NSString *streetNumberURL = [NSString stringWithFormat:#"&street_number=%#",item.buildingStreetNumber];
NSString *streetNameURL = [NSString stringWithFormat:#"&street_name=%#",item.buildingStreetName];
NSString *ZipcodeURL = [NSString stringWithFormat:#"&zipcode=%#",item.buildingZipcode];
NSString *P1 = [URL stringByAppendingString:streetNumberURL];
NSString *P2 = [P1 stringByAppendingString:streetNameURL];
NSString *P3 = [P2 stringByAppendingString:ZipcodeURL];
NSURL *jsonFileUrl = [NSURL URLWithString:P3];
NSLog(#"%#",P3);
[cell.buildingSalesRange loadSalesRangeFromURL:(NSURL*)jsonFileUrl];
[cell.buildingRentalsRange loadRentalsRangeFromURL:(NSURL*)jsonFileUrl];
cell.layer.borderColor = [[UIColor whiteColor]CGColor];
cell.layer.backgroundColor = [[UIColor clearColor]CGColor];
cell.layer.borderWidth = 2;
return cell;
}
and here is my new .m file:
#import "PriceRanges.h"
#import <objc/runtime.h>
#implementation UILabel(Prices)
-(void) loadSalesRangeFromURL:(NSURL*)url {
NSLocale *locale = [[NSLocale alloc] initWithLocaleIdentifier:#"en_US"];
NSNumberFormatter *currencyStyle = [[NSNumberFormatter alloc] init];
[currencyStyle setNumberStyle:NSNumberFormatterCurrencyStyle];
[currencyStyle setLocale:locale];
[currencyStyle setMaximumFractionDigits:0];
NSURLRequest *urlRequest = [[NSURLRequest alloc] initWithURL:url];
[NSURLConnection sendAsynchronousRequest:urlRequest queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
{
if (error)
{
NSLog(#"Error,%#", [error localizedDescription]);
}
else
{
NSArray *priceArray = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingAllowFragments error:&error];
NSNumber *number = [priceArray valueForKeyPath:#"sales.number"];
NSString *lowest = [priceArray valueForKeyPath:#"sales.lowest"];
NSDecimalNumber *lowestDecimal = [NSDecimalNumber decimalNumberWithString:lowest];
NSString *lowestPrice = [currencyStyle stringFromNumber:lowestDecimal];
if (![number isEqualToNumber:[NSNumber numberWithInt:0]]) {
dispatch_async(dispatch_get_main_queue(), ^{
UILabel *labelFromData = [[UILabel alloc] init];
[labelFromData setText:[NSString stringWithFormat:#"%# for Sale from %#",number,lowestPrice]];
if (labelFromData) {
if ([self.text isEqualToString:labelFromData.text]) {
} else {
dispatch_async(dispatch_get_main_queue(), ^{
self.text = labelFromData.text;
});
}
}
self.text = [NSString stringWithFormat:#"%# for Sale from %#",number,lowestPrice];
});
}
};
}];
}
-(void) loadRentalsRangeFromURL:(NSURL*)url {
NSLocale *locale = [[NSLocale alloc] initWithLocaleIdentifier:#"en_US"];
NSNumberFormatter *currencyStyle = [[NSNumberFormatter alloc] init];
[currencyStyle setNumberStyle:NSNumberFormatterCurrencyStyle];
[currencyStyle setLocale:locale];
[currencyStyle setMaximumFractionDigits:0];
NSURLRequest *urlRequest = [[NSURLRequest alloc] initWithURL:url];
[NSURLConnection sendAsynchronousRequest:urlRequest queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
{
if (error)
{
NSLog(#"Error,%#", [error localizedDescription]);
}
else
{
NSArray *priceArray = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingAllowFragments error:&error];
NSNumber *number = [priceArray valueForKeyPath:#"rentals.number"];
NSString *lowest = [priceArray valueForKeyPath:#"rentals.lowest"];
NSDecimalNumber *lowestDecimal = [NSDecimalNumber decimalNumberWithString:lowest];
NSString *lowestPrice = [currencyStyle stringFromNumber:lowestDecimal];
if (![number isEqualToNumber:[NSNumber numberWithInt:0]]) {
dispatch_async(dispatch_get_main_queue(), ^{
[self setText:[NSString stringWithFormat:#"%# for Rent from %#",number,lowestPrice]];
});
}
}
}];
}
#end
As you might see, I have two different methods, but both still send the async request everytime the tables are scrolled.
I guess I am not clear on what to do now?
That's the problem with not having a data model independent of your UI, and a good example of when Model-View-Controller makes sense. You'll need another layer (preferably a separate class) responsible for keeping all the data you've fetched from the network, deciding when it's old enough to discard, etc. The cells should populate themselves from the cached data that the Model keeps, and if the data's not yet present, the model fetches it asynchronously and then notifies the View Controller when the new data arrive. If the cells are still visible, they get populated. If they've scrolled offscreen, been reused, etc, then the data updates don't result in any immediate UI change.
I've this piece of code that try to feed an array from a web-service. If it fails, an error message appears, with the possibility to tap on it to retry. But when I tap on it, the error message doesn't disappear, and the spinner doesn't re-appear.
-(void)Load_Commandes{
if(LIB_Error)
{
[LIB_Error removeFromSuperview];
LIB_Error = nil;
}
TABLE_Commandes.hidden = YES;
LIB_Chargement.hidden = NO;
spinner.hidden = NO;
[spinner startAnimating];
tab_Cdes = [self Init_Tableau];
spinner.hidden = YES;
LIB_Chargement.hidden = YES;
if(tab_Cdes != nil)
{
TABLE_Commandes.hidden = NO;
[TABLE_Commandes reloadData];
}
else
{
LIB_Error = [[UILabel alloc] initWithFrame:self.view.frame];
[LIB_Error setTextColor:[UIColor grayColor]];
[LIB_Error setBackgroundColor:[UIColor clearColor]];
[LIB_Error setTextAlignment:NSTextAlignmentCenter];
[LIB_Error setText:#"Erreur de chargement. \nToucher pour réessayer."];
[LIB_Error setNumberOfLines:2];
UITapGestureRecognizer* gesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:#selector(Load_Commandes)];
[LIB_Error addGestureRecognizer:gesture];
LIB_Error.userInteractionEnabled = YES;
[self.view addSubview:LIB_Error];
}
}
Here is the code I use to call the web-service, in [self Init_Tableau].
NSString *str=[NSString stringWithFormat:URL_ORDERS];
NSURL *url=[NSURL URLWithString:str];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:5.0];
NSData *returnData = [NSURLConnection sendSynchronousRequest: request returningResponse:&response error: &error];
Thanks you for your help, because I'll become crazy! ^^
UPDATE : I tried by a lot of different ways. But it seems to be impossible to do. Whatever I do, the visual changes are applied only when all treatments are done.
Here is the code of Init_Tableau.
-(NSArray*)Init_Tableau
{
NSMutableArray* a = [NSMutableArray array];
Reachability *networkReachability = [Reachability reachabilityForInternetConnection];
NetworkStatus networkStatus = [networkReachability currentReachabilityStatus];
if (networkStatus == NotReachable) {
NSLog(#"Erreur de chargement 1");
//return nil;
}
NSURLResponse* response;
NSError* error;
NSString *str=[NSString stringWithFormat:URL_ORDERS];
NSURL *url=[NSURL URLWithString:str];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:5.0];
NSData *returnData = [NSURLConnection sendSynchronousRequest: request returningResponse:&response error: &error];
NSString *responseBody = [[NSString alloc] initWithData:returnData encoding:NSUTF8StringEncoding];
if(error)
{
NSLog(#"Erreur de chargement 2");
return nil;
}
NSError *e = nil;
NSArray* resultList = [NSJSONSerialization JSONObjectWithData:returnData options:NSJSONReadingMutableContainers error:&e];
for(NSDictionary* dico in resultList){
Entete* cde = [[Entete alloc] init];
cde.ncde = [dico objectForKey:NCDE];
cde.nomf = [dico objectForKey:NOMF];
cde.noml = [dico objectForKey:NOML];
cde.prenomf = [dico objectForKey:PRENOMF];
cde.prenoml = [dico objectForKey:PRENOML];
cde.adresse1f = [dico objectForKey:ADRESSE1F];
cde.adresse1l = [dico objectForKey:ADRESSE1L];
cde.adresse2f = [dico objectForKey:ADRESSE2F];
cde.adresse2l = [dico objectForKey:ADRESSE2L];
cde.cpf = [dico objectForKey:CPF];
cde.cpl = [dico objectForKey:CPL];
cde.villef = [dico objectForKey:VILLEF];
cde.villel = [dico objectForKey:VILLEL];
cde.phonef = [dico objectForKey:PHONEF];
cde.phonel = [dico objectForKey:PHONEL];
cde.societef = [dico objectForKey:SOCIETEF];
cde.societel = [dico objectForKey:SOCIETEL];
cde.etatCde = [dico objectForKey:ETATCDE];
cde.moyenPaiement = [dico objectForKey:MOYENPAIEMENT];
cde.fdp = [dico objectForKey:FDP];
cde.mnt = [[dico objectForKey:MNTCDE] floatValue];
[a addObject:cde];
}
return [NSArray arrayWithArray:a];
}
I've put the code below in, and it looks close but I can't figure out why it's not doing the actual refresh. It has the "Pull to refresh" and the updated text displaying properly, but it's not updating the actual data. Am I missing something obvious, or do I have it misplaced or something?
I edited to add the self tableview call to reload the data. Still no luck.
FINAL EDIT___User below solved it with calling the data feed.
- (void)viewDidLoad
{
[super viewDidLoad];
UIRefreshControl *refresh = [[UIRefreshControl alloc] init];
refresh.attributedTitle = [[NSAttributedString alloc] initWithString:#"Pull to refresh"];
[refresh addTarget:self action:#selector(refreshmytable:) forControlEvents:UIControlEventValueChanged];
self.refreshControl = refresh;
NSURLSessionConfiguration *config =
[NSURLSessionConfiguration defaultSessionConfiguration];
_session = [NSURLSession sessionWithConfiguration:config
delegate:self
// delegate:nil
delegateQueue:nil];
[self fetchFeed];
}
- (void)refreshmytable:(UIRefreshControl *)refreshControl{
[self fetchFeed]; //Added 12:12 9.16.14
refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:#"Updating"];
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:#"MMM d, h:mm a"];
NSString *updated = [NSString stringWithFormat:#" Last Update: %#", [formatter stringFromDate:[NSDate date]]];
refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:updated];
[refreshControl endRefreshing];
[self.tableView reloadData]; //Added this 11:32 9.16.14
}
- (void)fetchFeed
{
NSString *userEID = MAP_getUsername();
//NSLog(userEID);
NSString *requestString1 = [#"URL" stringByAppendingString:userEID];
NSString *requestString2 = #"&status=pending";
NSString *requestString = [requestString1 stringByAppendingString:requestString2];
//NSLog(requestString);
/*NSString *requestString = #"http://URL";
*/
NSURL *url = [NSURL URLWithString:requestString];
NSURLRequest *req = [NSURLRequest requestWithURL:url];
NSURLSessionDataTask *dataTask =
[self.session dataTaskWithRequest:req
completionHandler:
^(NSData *data, NSURLResponse *response, NSError *error) {
NSDictionary *jsonObject = [NSJSONSerialization JSONObjectWithData:data
options:0
error:nil];
self.changeList = jsonObject[#"List"];
//self.changeList=nil; //tried to add here to remove duplicate data
NSLog(#"%#", self.changeList);
//- add code here to populate BNRItemStore with the change order list.
// - following code should be rewritten in fetchFeed that will load BNRItemStore.
if (self.changeList.count>0) {
for (int i = 0; i < self.changeList.count; i++) {
NSDictionary *coItem = self.changeList[i];
[[BNRItemStore sharedStore]
addItemWithApproverEid:coItem[#"approverEid"]
assignmentGroup:coItem[#"assignmentGroup"]
changeOrder:coItem[#"changeOrder"]
subcategory:coItem[#"subCatagory"]
title:coItem[#"title"]
];
}
}
//NSLog(#"sizeof(NSInteger) = %#", #(sizeof(NSInteger)));
//- end comment
dispatch_async(dispatch_get_main_queue(), ^{
[self.tableView reloadData];
});
//self.changeList=nil; //trying to null out list for refresh non duplicate data
// NSString *json = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
// NSLog(#"%#", json);
}];
[dataTask resume];
}
You are not fetching the new data. You have a method/message call fetchFeed that you call in the viewDidLoad but you never call it in the refresh method/message. I assume that if you refresh, then you need to fetch new data. Call `[self fetchFeed];' before reloading the table view. If you are fetch the data asynchronously, then you need to have the table view reload in the completion block when fetching the new data is complete.
You need to call to reloadData somewhere in refreshmytable method for the table view to update the data
- (void)refreshmytable:(UIRefreshControl *)refreshControl{
refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:#"Updating"];
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:#"MMM d, h:mm a"];
NSString *updated = [NSString stringWithFormat:#" Last Update: %#", [formatter stringFromDate:[NSDate date]]];
refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:updated];
[refreshControl endRefreshing];
[self.tableView reloadData]
}
I'm trying to create a simple rss reader. The code works okay, except the UI hangs when the feeds are being updated. I thought I cobbled together the code to get the feed and parse it on a background queue while updating the UI on the mainQueue, but the table hangs pretty badly. Code below:
-(void)refreshFeed2
{
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
for (NSString *feed in _feeds) {
// iterate over all feeds
NSLog(#"feed=%#", feed);
NSURL *url = [NSURL URLWithString:feed];
// Create url connection and fire request
NSURLConnection *conn = [[NSURLConnection alloc] init];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
(void)[conn initWithRequest:request delegate:self];
[NSURLConnection sendAsynchronousRequest:request queue:queue completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
{
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
if ([data length] == 0 && error == nil) {
// handle empty response
} else if (error != nil) {
// handle error
NSLog(#"Error %#", [error localizedDescription]);
} else if ([httpResponse statusCode] == 200) {
// data present and no errors
[queue addOperationWithBlock:^{
// parse feed on queue
RXMLElement *rss = [RXMLElement elementFromXMLData:data];
RXMLElement *rssChild = [rss child:#"channel"];
RXMLElement* title = [rssChild child:#"title"];
NSArray* items = [[rss child:#"channel"] children:#"item"];
NSMutableArray* result=[NSMutableArray array];
for (RXMLElement *e in items) {
// iterate over the articles
RSSArticle* article = [[RSSArticle alloc] init];
article.sourceTitle = [title text];
article.articleTitle = [[e child:#"title"] text];
article.articleDescription = [[e child:#"description"] text];
article.articleUrl = [NSURL URLWithString: [[e child:#"link"] text]];
NSString *articleDateString = [[e child:#"pubDate"] text];
article.articleDate = [NSDate dateFromInternetDateTimeString:articleDateString formatHint:DateFormatHintRFC822];
if (article.articleUrl != NULL) {
[result addObject:article];
}
}
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
// update table on mainQueue
for (RSSArticle *article in result) {
// iterate over articles
int insertIdx = [_allEntries indexForInsertingObject:article sortedUsingBlock:^(id a, id b) {
RSSArticle *entry1 = (RSSArticle *) a;
RSSArticle *entry2 = (RSSArticle *) b;
return [entry1.articleDate compare:entry2.articleDate];
}];
[_allEntries insertObject:article atIndex:insertIdx];
[self.LeftTableView insertRowsAtIndexPaths:[NSArray arrayWithObject:[NSIndexPath indexPathForRow:insertIdx inSection:0]]
withRowAnimation:UITableViewRowAnimationFade];
}
}];
}];
}
}];
// Stop refresh control
[refreshControl endRefreshing];
}
}
Code that calls refreshFeed2:
- (void)viewDidLoad {
[super viewDidLoad];
self.allEntries = [NSMutableArray array];
self.feeds = [NSArray arrayWithObjects:
#"http://feeds.washingtonpost.com/rss/politics",
#"http://rss.cnn.com/rss/cnn_allpolitics.rss",
#"http://www.npr.org/rss/rss.php?id=1012",
#"http://www.slatedigital.com/support/feeds/rss_kb.php?s=fd5aa35e773dc3177b85a2126583f002",
nil];
}
//add refresh control to the table view
refreshControl = [[UIRefreshControl alloc] init];
[refreshControl addTarget:self
action:#selector(refreshInvoked:forState:)
forControlEvents:UIControlEventValueChanged];
NSString* fetchMessage = [NSString stringWithFormat:#"Fetching Articles"];
refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:fetchMessage
attributes:#{NSFontAttributeName:[UIFont fontWithName:#"Helvetica" size:11.0]}];
[self.LeftTableView addSubview: refreshControl];
[self refreshInvoked:self forState:UIControlStateNormal];
}
-(void) refreshInvoked:(id)sender forState:(UIControlState)state {
NSOperationQueue *refreshQueue = [[NSOperationQueue alloc] init];
[refreshQueue addOperationWithBlock:^{
[self refreshFeed2];
}];
}
Any help?
Thanks!
Can you try this? replace
[self refreshInvoked:self forState:UIControlStateNormal];
by
[self performSelectorOnBackground:#selector(refreshFeed2) withObject:nil];
and replace the same instead of
-(void) refreshInvoked:(id)sender forState:(UIControlState)state {
[self performSelectorOnBackground:#selector(refreshFeed2) withObject:nil ];
}