So the question is simple: When is it best to use a ViewModel and getting data from that versus using the newInstance function on a fragment and passing the data through the creation.
I've tried googling it, but there doesn't seem to be much out there. Not anything I can easily seem to find.
ViewModel together with LiveData will store the values throughout the life cycle of the Fragment/Activity. It can also observe the underlying data so when the ViewModel changes your views will be automatically notified and updated. Read more about MVVM.
Related
I had an observer for LiveData LD but the observer's onChange(Data pData) method was not being called when I made modified data like LD.getValue().modify().
I'm answering this cuz I was unable to find a solution to my specific situation.
The observer's onChanged(data) is not called when the wrapped data is modified. It's called when the wrapped data is replaced with some other data. For example
LD.getValue().modify();
Won't work but
newData = LD.getValue();
newData.modify();
LD.setValue(newData);
will call the observer.
I think you can use postValue(newData) also. Haven't tried it cuz setValue worked.
Here is the guide from where I understood this
https://developer.android.com/topic/libraries/architecture/livedata#java
Is there a way preserve my fragments instances so that they don't get recreates when coming back from another Fragment through navigation component?
I thought of saving the fragment's instance in a variable and using it if it's not null in onCreateView(), but it seems this is not advised can generate memory leaks.
It's my only option to refactor my app and use ViewModels in all my fragments?
When Fragment is recreated from back stack, first method which gets called is onCreateView while when Fragment is being created for first time, onAttach followed by onCreate is called.
So you can avoid reinitialization of variables using these one time invoked methods in order to preserve their previous states. But this is advisable for small use cases only. To preserve larger data sets, you should consider using ViewModels which are bound to fragment lifecycle and retains the data until fragment is detached & destroyed.
You can post your exact use case here if you need more help.
I'm a beginner Android developer. I'm still learning new things every day, and while learning I have heard this question quite frequently: What will happen if we send View object as parameter within OnCreate Method? I have searched about it but didn't find anything helpful. I just want to know is it really possible and if so then please explain the scenario.
oncreate() called when the activity is first created. This is where you should do all of your normal static set up: create views, bind data to lists, etc. This method also provides you with a Bundle containing the activity's previously frozen state.
I have an android app with one "home" or "main" activity that relies on fragments to accomplish several tasks. This data relies on information retrieved from a server (mine, and presumably a substantial amount by google maps).
I would like to structure my code such that several other activities (ie. preferences) can temporarily take focus before returning to the main activity.
Currently android destroys and recreates the main activity, which means bandwidth is wasted every time.
There are several notable intent flags which 'solve' this problem (Intent.FLAG_ACTIVITY_REORDER_TO_FRONT and Intent.FLAG_ACTIVITY_CLEAR_TOP), however they only appear to be useful when transitioning back to the main activity, which means I have to #override the system behaviour for both onKeyDown() and onBackPressed(). I would really prefer not to do this in case it causes other issues or eventually becomes deprecated.
Is this safe? Or is the better solution to force my application to create a serialization (savedInstanceState) of the main activity and all fragments anytime another activity temporarily takes the foreground?
Using saved instance state is the proper approach here. That will let you persist the information retrieved from the server when the activity gets re-created.
You only need to implement code to save / restore the instance state in the fragment or activity that holds the data. If you want to share that data across all your fragments, you can place it in the activity and add code to save the instance state of the activity. Then you can access the data that's stored in the activity from your fragments with ((MainActivity)getActivity()).getData().
For code to save and restore instance state, take a look at:
http://developer.android.com/training/basics/activity-lifecycle/recreating.html#SaveState
http://developer.android.com/training/basics/activity-lifecycle/recreating.html#RestoreState
If the data you need to persist is really large, you can use a retained fragment instead, as explained here:
http://developer.android.com/guide/topics/resources/runtime-changes.html#RetainingAnObject
Another trick for large data objects is to use a singleton class to store the data while the orientation change takes place.
I am working with Android Fragments pretty extensively and one of the problems I am having is the lack of proper mechanism to pass complex objects to it.
In the android developers documentation for Fragments, they have a static method called newInstance called with some simple arguments which will be packaged into a Bundle and used inside the Fragment. However this method cannot be employed for passing complex objects.
Because I have been using the Fragments api a lot, it is becoming more and more important to have complex objects passed to it. One way to do this is by implementing the Parcelable interface, which I don't want to do for all the classes.
So, I thought I could do this :
Define an interface like this in the Fragment:
// Container Activity must implement this interface
public interface ReceiveDataInterface {
public MyClass getData(uniqueFragmentID);
}
Force the Activities using this fragment to implement the interface and call ReceiveDataInterface.getData(getArgument.getString(UNIQUEID))
In the Activity instantiate fragment using the newInstance method by passing a uniqueFragmentID and implement the ReceiveDataInterface which gives data based on uniqueFragmentID.
Is it a good idea to do this? if not, why? and how should I go about doing this?
Note:This is done in the same lines as OnArticleSelectedListener described in the documentation.
Any help is much appreciated.
We use this approach for any app we build for android. It works well. I havent tested every method of doing this, but i think this is among the best way.
Another approach would be to make the Fragment themselves independent. Why not write the code that fetches data from network/database in the Fragment itself?