Greetings. I've got a nav-bar application that's misbehaving. I've got two buttons, one that shows all results from my database and another that shows a subset of my database. Of course, each button has its own action method. Both of these methods instantiate a view controller object of the same class.
If I start the app and only click the "all results" button, I do see all results. The goofy thing is that when I click the button for the subset of results (and see the subset of results), click Back on the nav bar, and then click the first button for the entire set, I see the subset again.
While debugging with break points all over the place, I noticed that the dealloc method of my results view controller doesn't get called. However, when I click Back and then click the all-results button, the alloc/init methods are indeed called again for my results view controller.
So even if I have a blatant memory leak, how is it possible that my freshly allocated/initialized view controller object has the same data as that of the previously instantiated view? Stepping through the code made this problem seem even more bizarre, as it appeared to be behaving properly...just yielding old data.
Any advice at all would be great. Thanks!
Calling "reloadTableData" on the table view should ensure the data is refreshed. Call that in the action methods.
Why do your buttons repeatedly instantiate the view controller? Why not have pointers to the view controllers as instance variables that you only have to set once and then can use at will?
This is just a wild guess, but it could be related to the reuse of tableViewCells. Try always creating a UITableViewCell, avoiding the reuse-identifier to see if the old data persists.
I figured out what was wrong a while ago and thought I would answer my own stupid question. :)
I had forgotten that I made my Database class a singleton and put a master pointer to "allResults" in the app delegate class.
Thanks anyway for your input. Every little bit helps me understand this new environment better.
Related
In my iOS 5 project, using ARC and Storyboards, I feel that I have run into a strange behavior. I would like to confirm if what I am experiencing is in fact the default behavior AND if it can be modified.
I have a NavigationController with a RootViewController in story board. Neither of these is tied to a specific subclass. On RootViewController I have a button that is connected to a segue for a ListingViewController, which makes a static call to a web service (does not vary by user input). What I have noticed - at least in the simulator - is that when I press the button, go back, and press it again, the second time it loads unrealistically quickly! It seems as though the ListingViewController is being cached.
Is this supposed to be happening? What can I do to fix it?
Is this supposed to be happening? What can I do to fix it?
Why do you think it's broken? I haven't looked into whether the storyboard holds onto its view controllers, but it wouldn't be surprising if it does.
If you're doing something like making your web service request in -viewDidLoad, but you want it to happen every time the view appears, you should move that to -viewWillAppear or -viewDidAppear.
I'm kind of new to iPhone development so bear with me.
I have an application wherein I display a lot of data in a tableviews, edit it in a detailview etc. However, I also have a login-system.
The problem I have is that I can't figure out how to reload the subviews of the NavigationController when I've logged out, or how to dealloc it completely and reinitialize it upon a succesful login.
This means that data from the last user who logged out is still present in my tableview when I log in as another user, as the data is set to reload only when the view loads for the first time.
Thankful for any and all contributions.
There are probably several ways you could go about this; it's up to you (and without more information about your app, I can't suggest a particular solution). You might consider:
-viewWillAppear: — this method is called on any UIViewController subclass when it's about to (re)appear as part of a UINavigationController stack (or tab bar controller, etc.). You can clear out fields, etc. This is mostly useful when a view controller reappears (being uncovered or switched to), because you usually create a new view controller instance each time you display one.
Notifications and delegates — your view controllers (and other objects) can communicate with each other about when a logout occurs, and reconfigure themselves as necessary.
I'm using core data for a tab bar + navigation controller prototype app, with one entity: Event.
So I have two tabs, the past and the present. I'm using nsfetchedresultscontroller and nspredicate to filter the data into their respective table views.
now here is where i'm having a problem, when i create a new date, it shows up in the present table view like i expect, but as time goes by the event stays there past the date, and never moves to the past table view. The only way i can achieve this is just launching the app from scratch, killing the background view.
I've tried to install reloadData call to table view in view will appear. That doesn't work.
I tried to use [tableview reloadData] when the app launches from background too. but that doesn't work too.
I can't think of anything else, hoping you guys could help.
[Edit]
I just figured out how to do it! I tried to download the sample code i thought i uploaded to github, but looks like there is no file there. I cant figure out how to upload the project up there.
anyway, the thing to do to achieve this is in the view did appear, just place in the entire fetch request that's in the fetched results controller (without the fetched results controller variables) with the predicate. now if the moment you switch views, the entire data is updated and filtered!
Hope this helps anyone else looking for a solution to this problem.
Uhm, if you have already tried reload data, these others could be possible problems:
be sure the cache is consistent with the predicate. If in table
controller you use a cache, and the table is populated with something
like entityDate = myCalculatedDate then the predicate could be different,
and you need to delete cache first. I think you could try to set
cache:nil to see if this is the problem.
for updating table, especially with new inserted rows, or moved rows
to different index you need to implement the fetched controller
delegate
[EDIT] also if I remember well, I am not sure if standard
mechanism of viewWillAppear/dissappear works as expected with Tab Bar,
probably there's some delegate to implements, but it's just a
guessing !
this what I can guess without seeing the code.
could anyone help me with the next question. I am working on an app with the navigation similar to Notes app has. The problem I faced i how to implement navigation within one level and keep root view as the previous screen. So the scenario I need to achieve:
1. Drill down from the top level list to the detailed view.
2. From this detailed view navigate to the detailed view of the next/previous item.
3. Back button should lead to the root view.
I've tried several approaches and no-one worked fine for me. The most right solution from my point of view is to create a middle controller between the root and detailed controllers to handle this next/prev redirects. But the main problem here is that switching from one detailed view to another the navigation pane stays the same, so it's not involved in the animation, whether Notes app work right in this case.
Could you point me how it' better to arrange controllers interaction in this case?
Thanks in advance. Sorry for quite big post, was trying to be as informative as possible.
Best regards,
Roman
I think the best implementation is this way:
Say you have a Note class where the data is stored.
You could have two view controllers, one with the list of notes and one with the details.
Both of these can be added to a navigation controller.
Then, when you want to switch to the next note, you retrieve that object somehow and assign it to your detail controller with a -setNote: call. That method will be responsible for changing what the outlets are displaying.
I've resolved this question - it's enough to pop current view and push new one, created for the next object in the list. The only think to remember is to save the reference to the navigation controller before the pop call, because after it self.navigationController becomes nil.
Yeah, it's misbehaving badly. Jongsma's reply is the best. In case you wanted to re-create controllers, I've found this to work:
[parent performSelectorOnMainThread:#selector(showMyItem:)
withObject:myNextItem
waitUntilDone:NO];
[self.navigationController popViewControllerAnimated:NO];
performSelectorOnMainThread delays execution of the method until the next run of the main loop, and by then the previous controller is removed already and navigation controller is in a stable state.
I'm starting out in iPhone development, and I'm trying to do a Contacts-style controller to add items to a table. I've got the two controllers designed, but I can't seem to figure out how to pass data between them. How can I get data from the modal controller to its parent?
Just trying to call methods on parentViewController won't work (and results in compiler warnings and crashes). I've considered moving the data out of the controller itself (which is going to happen anyway, I'm just trying to keep things as simple as possible for now), but even then I still have to somehow tell the parent view to refresh its data. Again, how can I do this?
I've considered moving the data out of the controller itself (which is going to happen anyway
I think now may be the time to follow that consideration and create a separate "ContactList" model object to store your data.
Your modal view controller just adds new "Contacts" into the "ContactList".
Your TableViewController should observe the same "ContactList". As items are added/removed to/from the "ContactList" your TableViewController will simply add and remove rows from its tableView.
In this way you will keep each ViewController independent, your code will be more flexible and adding/removing single rows will be much more efficient than reloading an entire tableView.
You either keep a link to the sub view you create and ask it for data that has changed on return, or else ad yourself as a delegate of a subview and have it call you back directly (which does work if you have a valid reference).
I had the same question and found this sample code: http://developer.apple.com/iphone/library/samplecode/LocateMe/Introduction/Intro.html
Helped me a ton and was pretty easy to figure out from the code.
In short, use delegate.
I would suggest you have a look at Lecture 11: Text input, Presenting content modally (May 6) - iPhone App Programming course offered by Stanford. Search for it on iTunes U.
Download this sample app if you want to know how to implement delegate: http://www.stanford.edu/class/cs193p/downloads/11-Pickers.zip