views:

66

answers:

4

Hi,

this is my first iPhone application and I'm using JSON framework to decode JSON sent from a server.

I insert the data in a NSMutableArray from an AppDelegate file.

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {    

   responseData = [[NSMutableData data] retain];
   museums = [[NSMutableArray alloc] init];
   viewController = [[RootViewController alloc] init];
   NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:@"http://my_json_link"]];
   [[NSURLConnection alloc] initWithRequest:request delegate:self];

   [window addSubview:navigationController.view];
   [window makeKeyAndVisible];

   return YES;
}


- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
    [responseData setLength:0];
}

- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
    [responseData appendData:data];
}

- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {
    NSLog(@"Connection failed: %@", [error description]);
}


- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
    [connection release];

    NSString *responseString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];
    [responseData release];

    NSError *error;
    SBJSON *json = [[SBJSON new] autorelease];
    NSDictionary *data = (NSDictionary *)[json objectWithString:responseString error:&error];
    [responseString release];   

    if (data == nil)
        NSLog(@"JSON parsing failed: %@", [error localizedDescription]);
    else {
        for (NSDictionary *item in data) {

            // Read the data 
            NSString *aName = [item objectForKey:@"name"];
            NSString *aDescription = [item objectForKey:@"description"];

            // Create a new museum object with the data from json 
            Museum *museum = [[Museum alloc] initWithName:aName description:aDescription];

            // Add the museum object to the Array
            [museums addObject:museum];
            [museum release];
        }       
    }   
    viewController.museums = museums;  
}

The museums array is not empty inside connectionDidFinishLoading function, but I can't see it when I try to print it in RootViewController. I tried to set the array in the line

viewController.museums = museums; 

but I didn't understand what is wrong.

I can fix the problem only if I move these lines:

[window addSubview:viewController.view];  
[window makeKeyAndVisible]; 

from the first function to connectionDidFinishLoading function. But in this case doesn't work the other view when I click one record of the table.

Thanks for any help.

A: 

try using

viewController.museums = [museums retain];
Satyam svv
Yes, I have same problem
Katie
No need (will create a memory leak) if your viewController's 'museums' is declared as a 'retain' property, which is the normal way it'd be declared.
Graham Perks
Not necessarily. When you use retain, you have to release and there won't be any momory leak.
Satyam svv
A: 

Try to put a NSLog inside the for loop and check if it is executed.

Paolo Sangregorio
+1  A: 
viewController = [[RootViewController alloc] init];

First, I need you to make sure that the viewController you create in didFinishLaunching... is actually the correct viewController. Have you actually wired up that instance to be what you think it is or do you two instance os RootViewController?

Second if you are actually setting museums on the right instance of RootViewController you need to make sure that your timing is correct. This means that are you setting museums BEFORE you trying to print it out in viewController

--Edit--

OK since we established that things are happening in the wrong order you should try and reload the table. The UITableView has a method called reloadData that will take care of this for you and you need to call this everytime you change the data source after the table has been created.

So in RootViewController add a method called reload which in turn calls reloadData on your UITableView and modify your code:

viewController.museums = museums; 
[viewController reload];
willcodejavaforfood
Thanks for your replay. You are right, if I debug the code RootViewController is called before the delegate and this is why I can't see nothing in the table. Sorry but I'm new in iphone application and I don't know how wire up the two instance. Do I need to do it in MainWindow.xib?
Katie
So it is happening in the wrong order? Does the viewController have a table that is supposed to display the data?
willcodejavaforfood
+1  A: 

You could add to your view controller, temporarily just for debugging:

-(void) setMuseums:(NSMutableArray*)m {
   self->_museums = [m retain];
}

and then add a breakpoint in there. Make sure it's getting hit, or maybe there's something later coming along and setting it to nil.

The Museums property is declared as @property (nonatomic, retain) NSMutableArray *museums; right?

Graham Perks
Thanks. Yes, the property is (nonatomic, retain). Now I tried to insert setMuseums and that I can see is the museums array is set but after numberOfRowsInSection function. So there is something wrong but I don't understand where.
Katie
Great! Then you probably just need to have the table reload its data after you set the museums property. After you set museums, do something like [viewController.tableView reloadData]
Graham Perks