UItableView is not refreshing data after loading for second time the View - objective-c

I'm having some trouble with a UITableView. It loads perfectly the first time I open it, but after the second try its not getting into the viewDidLoad method which causes the data not be refreshed on my tableview. I also made the proper release on my dealloc method. Any ideas about this? I've looked thru google but I didnt get anything useful. Thanks a lot for all the help you can provide me!
Here are my viewDidLoad and viewDidUnload methods
- (void)viewDidLoad
{
[super viewDidLoad];
saved_news.rowHeight =85;
addButton = [[UIBarButtonItem alloc] initWithTitle:#"Edit" style:UIBarButtonItemStyleBordered target:self action:#selector(edititems:)];
[self.navigationItem setLeftBarButtonItem:addButton];
[self setSaved:[CoreData sharedInstance].selectItems];
[saved_news reloadData];
}
- (void)viewDidUnload
{
[super viewDidUnload];
saved = nil;
saved_news = nil;
addButton =nil;
}

viewDidLoad and viewDidUnload are typically called only once during the lifetime of a controller (unless there's a low memory situation). I think what you are looking to use here are the viewDidAppear: and viewDidDisappear: methods.

Call
- (void)viewWillAppear:(BOOL)animated;
- (void)viewDidAppear:(BOOL)animated;
as you require load table here
[Yourtablename reloaddata];
Hope this helps..

Related

cant figure out how to change views using an NSTimer

I made a class called view2 which is a UIView Controller subclass and when i run the program the timer works fine but when it changes screens it just goes to black and not the picture I have on view2. This is the code I have on the .m of the opening view can anyone see where this is going wrong?
- (void)viewDidLoad
{
randomMain = [NSTimer scheduledTimerWithTimeInterval:(2) target:self selector:#selector(onTimer) userInfo:nil repeats:NO];
[super viewDidLoad];
}
-(void)onTimer{
view2 *second= [[view2 alloc] initWithNibName:nil bundle:nil];
[self presentViewController:second animated:YES completion:nil];
}
You have to specify the name of the xib file you want to load (without extension):
view2 *second = [[view2 alloc] initWithNibName:#"MyView2Xib" bundle:nil];
Or if you create the GUI programmatically, just use a simple init:
view2 *second = [[view2 alloc] init];
Some additional remarks:
Class names should always start with a capital letter, to distinguish them from variables.
It's a good idea to include part of the superclass' name in your subclass' name. If I saw a class called View2, I would assume it's a UIView subclass. I'd rather call it ViewController2.
There is no need to put the interval in parenthesis.
The action of an NSTimer should have a single argument (itself).
EDIT:
With a storyboard you have to manually perform the seque you set up between the 2 views:
- (void)onTimer {
[self performSegueWithIdentifier:#"YourSegueIdentifier" sender:self];
}
I would think viewDidLoad is not the appropriate place for your purposes. You should instead use viewDidAppear.
All of DrummerB's remarks are very valid and quite important.

Not calling [super dealloc] inside a static UIViewController subclass

In my app I have a UIViewController subclass (VC for short) that I only use in one place in the entire app. In that place, I have been creating and pushing it like this:
MyViewController* VC = [MyViewController new];
[self.navigationController pushViewController:VC animated:YES];
[VC release];
but I was thinking that since this is the only place I am using a view controller of this type, I could do something like this so the settings used won't be reset each time the view controller is pushed onto the stack:
static MapsToSendPicker* VC = nil;
if(!VC) {
VC = [MapsToSendPicker new];
}
[self.navigationController pushViewController:VC animated:YES];
[VC release];
The problem with that code is that in VC's dealloc method, I release all of my instance variables and set them to nil, and finally I call [super dealloc]. This deallocates the static view controller, but the test if(!VC) isn't evaluated to true after (this would defeat the purpose of the whole idea if it were; then I'd have to recreate the view controller each time anyway).
My solution is overriding the dealloc method in MyViewController and not calling [super dealloc] at the end. This works, but the compiler raises a warning. How can I get rid of that warning while maintaining the functionality I gain with this design? Thanks!
Edit:
After a quick Google search, I have found this solution:
- (void)dealloc {
if(NO) {
[super dealloc];
}
}
but I would like something a little bit... cleaner. Any thoughts?
Remove the [VC release]; line and add [super dealloc] back. Everything will work properly and dealloc will never get called. Generally you should consider using NSUserDefaults in order to restore the VC properties instead of keeping the controller in memory all the time.

self.tableView reloadData doesnt reload UITableView

I've been trying to reload my UITableView but to no avail. The code for my viewWillAppear looks like this:
-(void)viewWillAppear:(BOOL)animated {
self.navigationItem.rightBarButtonItem = [[[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemRefresh target:self action:#selector(refresh)] autorelease];
[super viewWillAppear:animated];
[self.tableView reloadData];
}
The code for my refresh method:
-(void)refresh{
NSLog(#"refreshing UITableView!");
[self.tableView reloadData];
}
Any help is very much appreciated!
Found it, to get an updated list, it was necessary to call the viewdidLoad method again, in addition to the self.tableView reloaddata.
Think the reason is you loosing pointer to your UITableView. Make sure that you UITableView #property is strong (retain) and check maybe you receiving memory warning and all your IBOutlets removing. Before you made reloadData try to:
NSLog(#"%#", self.tableView);
make sure that it's not nil.

Remove all settings from viewcontroller when dismissed

I got multiple viewcontrollers in my project. The first viewcontroller is called when the application starts and it presents a login screen. When the credentials are correct and the user logs in, the modalview is dismissed. and another viewcontroller is instantiated like this:
[self dismissModalViewControllerAnimated:NO];
Form *formcontroller = [[Form alloc] init];
[self presentModalViewController:formcontroller animated:YES];
When my other viewcontroller is presented the old one disappears. On the top of my secondviewcontroller i got an logout button, wich does exactly the same, so it dismisses the current viewcontroller and calls another like this:
-(IBAction)logOut:(id)sender{
[self dissmissModalViewControllerAnimated:NO];
}
And in my viewdiddisappear:
-(void)viewDidDisappear:(BOOL)animated{
Postform3ViewController *logincontroller = [[Postform3ViewController alloc] init];
[self presentModalViewController:logincontroller animated:YES];
}
The problem is:
When i push the logout button, and i return back to the logincontroller. The Credentials are still filled in. So my conclusion is that the first viewcontroller stays in memory. What am i doing wrong?
Edit:
I did find my own solution. I was profiling my application, and couldn't find any memory leaks. So i decided everything is released. Then i thought that i was able to set everything to empty myself. I did that in the viewDidAppear method like this:
-(void)viewDidAppear:(BOOL)animated {
gebruikersnaam.text = #"";
wachtwoord.text = #"";
[self.activeTextField resignFirstResponder];
[super viewDidAppear:animated];
}
Well first of all when you are using presentModalViewController and pushViewController the VC is retained so you should always release it after you have presented or pushed it.
Secondly in the third block of code it looks like you are creating a logincontroller but presenting a formcontroller. Perhaps you want to be presenting the VC you had just created:
[self presentModalViewController:logincontroller animated:animated];
Edit 0: For your code, in the first block, release like this:
Form *formcontroller = [[Form alloc] init];
[self presentModalViewController:formcontroller animated:YES];
...
[self dismissModalViewController:formcontroller animated:YES];
[formcontroller release];

Using Instruments to improve memory-management with modal view controllers

I feel like I don't understand something fundamental here. I've been working on memory management in my app while using Instruments to check out live allocations. I have a modal view controller (settingsViewController) that has an image for a background. One thing I noticed was that even after settingsViewController dealloc is called, there still is a live Malloc 520 KB, ImageIO is the responsible library. I'd expect live memory to drop back down after dismissing settingsViewController. Is the UIImageView still hanging around somewhere?
Here is how I load the image in viewDidLoad, as well as dismiss the view controller when I'm finished.
- (void)loadView {
[super loadView];
////// background ////////
UIImageView *background = [[UIImageView alloc] initWithImage:[UIImage imageNamed:#"settings_background.png"]];
[self.view addSubview:background];
[background release];
//////////////////////////
}
- (void)viewDidLoad {
[super viewDidLoad];
///////// done button //////////
UIBarButtonItem *done = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemDone target:self action:#selector(doneButtonPressed)];
self.navigationItem.leftBarButtonItem = done;
[done release];
////////////////////////////////
}
- (void) doneButtonPressed {
[self dismissModalViewControllerAnimated:YES];
}
- (void)dealloc {
NSLog(#"settingsViewController dealloc"];
[super dealloc];
}
At this point, this is all that is in the settingsViewController, so no need to do anything special in dealloc, right? Here is how I'm showing testViewController in the rootViewController.
- (void) loadSettingsView {
SettingsViewController *settingsViewController = [[SettingsViewController alloc] init];
UINavigationController *settingsNavigationController = [[UINavigationController alloc] initWithRootViewController:settingsViewController];
[self presentModalViewController:settingsNavigationController animated:YES];
[settingsViewController release];
[settingsNavigationController release];
}
I'd like to make sure I understand what is going on before moving forward. I have several different modal view controllers, each with a different image as a background. Since each one creates a Malloc 520 KB, I end up using 2-3 MB of precious memory for no good reason. What is holding on to that 520 KB?
When you use the +[UIImage imageNamed:] method, the framework caches the image data for you. That's why you see it hold onto some memory even after your view is released. If you're working in the simulator and you want to see it release that memory, send the simulator a memory warning after you've dismissed your view. The image framework should then release the cached image data.