I have an Activity which uses several Fragments. One of my fragments have an ExpandableListView which uses an Adapter of self made. What is the good strategy to keep(or should I keep) and recreate/retain when screen orientation changes:
reference of the Fragment in Activity
ExpandableListView in the fragment
ExpandableListView's states (such as collapsed/opened groups)
What I am currently doing is: reCreating the Fragment,Adapter, ExpandableListView inside Fragment each and everytime. (Not keeping states yet, but I guess I will use SharedPreferences).
PS: to minus voters: please elaborate what I am doing wrong. Apparently I am missing some points.
If you don't have nested fragments, you can use setRetainInstance(true). Or you can override onSaveInstanceState(Bundle) and save all your data, that you'll repopulate in onCreate / onCreateView. Note that the data has to be Serializable or Parcelable (preferred).
I think the downvote is because this question has been asked 10000 times :)
Related
As the title suggests, I want to retain my fragments. I have enforced my app orientation to always be in landscape mode in the manifest file so that there will be no rotations.
I have read:
Understanding Fragment's setRetainInstance(boolean)
and
Why use Fragment#setRetainInstance(boolean)?
However, I am not sure if they apply to my situation.
My project consists of a ViewPager with swipe tabs. How can I ensure that the fragments used in the ViewPager are the same ones as created when the MainActivity first starts? Would I use the same tagging method and findfragment by tag?
Additionally, where would it be best to check for the tagged fragment, else create a new fragment?
Just a side question related to ViewPager: what can I do to immediately create all fragments used in the ViewPager when the mainactivity is started, rather than to wait for a swipe event to occur?
To answer your last question view pager will by default create the fragments around the current fragment so you don't need to worry about that part. What I would recommend is let the view pager manage your fragments for you rather changing the behaviour since you might face performance issues.
SetRetainInstance simply keeps the instance of your fragment when its detached so it's up to you to assess whether you need to use it or not.. is there anything you want to maintain about that fragment? if not then do not use it, free your memory as much as possible.
For the last question, why do you want the same fragments created from the first time to be retained ? all the time? if you NEED to do that then rethink your structuring. gracefully recreate your fragments and maybe have some caching of your data on another layer if that is what you are worried about.
I have implemented ViewPager and number of Fragment as child, here every child override own onAttach, onCreateView, onViewCreated and setUserVisibleHint.
In my app navigation behaviour is random, it not be in sequence every time. Since page viewer perform caching to load extra child, and this is what my problem is. I am not sure exactly when I should initialise/release member of child class.
Required suggestion from you guys, will it be preferable to use PageViwer in this case or I should go with traditional activity flow for each of component.
ViewPager is typically used for move efficient horizontal item to item navigation. Typical use cases would be
Swiping through the related items (e.g. emails, images, songs of an album, etc.)
Swiping between the tabs
Swiping back-and-forth in a wizard-like activity
For more details you can read a section about Swipe Views Android Design pattern.
Regarding the lifecycle, it basically uses the same lifecycle as any other Fragment. The only difference is, that lifecycle methods can be called a bit later or earlier than you expect, because of fragment's caching ViewPager implements.
I am not sure exactly when I should initialise/release member of child class.
You should basically rely on two methods: onStart() and onStop(). In onStart() you create class members and initialize everything you want to. In onStop() method you should deinitialize everything and remove all listeners you set in onStart().
Method setUserVisibleHint() is used independently of onStart() or onStop(). You shoud better not initialize or destroy anything in there. You must not consider it to the a lifecycle method, because it's not. It's there just to give you a hint, that your fragment is visible to the user. Here you can start or stop animation, or request data update or perform similar tasks. This is the only purpose of this method.
Required suggestion from you guys, will it be preferable to use
PageViwer in this case or I should go with traditional activity flow
for each of component.
If your activity fits into one of the points mentioned about, I would suggest you to use ViewPager. Otherwise you might consider other options.
Update: Most likely you won't override onCreate() and onDestroy() lifecycle methods of a fragment very often. You will use onCreateView() and onDestroyView() methods instead. There you can implement so called static initialization, the initialization which doesn't change while a fragment is still alive. This is layout initialization and similar tasks.
ViewPager Usages
Screen slides are transitions between one entire screen to another and are common with UIs like setup wizards or slideshows.
If you have good knowledge in Fragment than ViewPager is right component for implements.
Because viewpager provide a place which you can add fragment runtime.
For eg.
If you want to use TabBar in your project than viewpager is right component for using. Because it's provide a place which you can add Fragment runtime. Tabbar is common in android application. It's provide lot of functionality inbuild we can use to add fragment runtime.
Facebook app using ViewPager to manage tab. Viewpager provide smoothness of your application.
You can Download example from this url and check your requirement fulfill or not
You can download the Example here
ViewPager
It is an widget
Allows the user to swipe left or right to see an entirely new screen.
Easy to show the user multiple tabs
Dynamically add and remove pages (or tabs) at anytime.
To Read More: http://architects.dzone.com/articles/android-tutorial-using
I have an activity with a ViewPager with a variable number of fragments (tabs).
Upon start the activity checks if the associated (complex) data has been loaded. If it hasn't it shows a progress bar view and starts an AsyncTask which fetches the data. Depending on the data the activity creates a number of fragments (tabs) and gives each fragment a sub set of the data.
I currently hold references to the fragments (I know that it is discouraged) and I run into all sorts of problems when the fragments gets reused - I'm giving the data to the wrong instance of the fragment.
So, is there an "android way" of solving this problem?
I run into all sorts of problems when the fragments gets reused
Fragments usually don't get reused in a ViewPager. This is not like an AdapterView where rows get recycled. Using FragmentPagerAdapter or FragmentStatePagerAdapter, a fragment represents one and only one page.
I re-instantiate the ViewPager each time (but the fragments get reused?)
Ah. That's a slightly different problem.
The stock implementations of FragmentPagerAdapter and FragmentStatePagerAdapter make a couple of assumptions:
They are in complete control over the fragments, particularly in terms of running the transactions to add and remove them from the UI
That those fragments will only ever be used by one "logical" ViewPager (IOW, recreating that ViewPager for a configuration change is fine, but that' pretty much it)
Complicating matters is that these adapters store the fragments under certain tags, and therefore if those fragments still exist in those tags, those existing ones will get used, instead of new ones being created.
So, is there an "android way" of solving this problem?
It's unclear from your question why you even need to "re-instantiate the ViewPager". I'm assuming that this is tied to some sort of refresh operation, or something else that is forcing you to go through the process described in your second paragraph.
You could give my ArrayPagerAdpater a try, as it is friendlier about external agents mucking about with the fragments. Since you control the fragments' tags, you can always be certain that you are working with the right fragment -- rather than caching them yourself, just retrieve the right one and manipulate it.
I have fragments in a FragmentActivity, that has an ActionBar and Tab navigation. My problem is that I want to call a method on the Fragment. I cannot use findFragmentBy[Id|Tag], because the fragments are initiated and attached by the adapter, and it assigns a custom tag. I saw several solution based on keeping references to fragments, but I really want to avoid keeping any reference to my fragments, as they are handled by the FragmentPagerAdapter. Now I have everything in my Fragment (which is a workaround in my view), but the question still bothers me.
What is the best way to access a fragment instance from my activity, not added by my to FragmentManager, but the FragmentPagerAdapter?
I solved this problem by writing my own Adapter. Since they are pretty straightforward, they are easy to be implemented.
I am trying to make a sudoku application. It's a fragment based design, in which a fragment hosts a custom view which is a board. I am trying to learn how to build an effective communication within FragmentActivity, Fragment and View
Although a view is created using the FragmentActivity context and I can catch a reference to that context within the current view and then call methods inside FragmentActivity I don't want to tie views so directly to a fragment activity. Instead I want to tie the view to use methods inside a fragment. How can i do that, I can I capture a reference to a fragment and call methods inside that fragment from a view?
First of all, I strongly recommend that you read through the documentation on Fragments, as you clearly don't understand the whole concept/purpose of using Fragments in the first place (which is OK, because they are confusing the first time you learn them :P).
A lot of your question doesn't make very much sense to me, because I'm not sure what the View you are speaking of refers to. What I can tell you is that Fragments have their own UI/layout, along with their own separate lifecycle. So it sounds like you don't want your FragmentActivity to interact with the Fragments layouts/methods at all... instead, you should implement the UI's behavior and layout inside of the Fragment itself. That is, the Fragment will be in charge of updating the UI, receiving click/touch events, displaying information on the screen etc. The FragmentActivity will simply hold a reference to the current Fragment(s), and will be in charge of displaying/swapping in and out new Fragments as necessary (via the activity's FragmentManager).
Hope that answers the question somewhat... read through the documentation a couple times, it sounds like you are just misunderstanding the theory/purpose behind Fragments.