Proper data transfer between activities - android

I have few questions about passing data to another activity. Let's say I have three activities I called them
first activity
second activity
third activity
When app is enabled by user, the user is in the first activity. To go from the first activity to the third activity user must also go through the second activity. The workflow
first activity (user push button) ->
second activity (user push button) ->
third activity
Let's assume I need data from the first activity in the third activity, so I need to pass my HashMap with my data from first activity to the second activity and then to the third activity?, is there any way to pass data directly from first activity to third activity but like I said, user has to go also through second activity.
I'm doing this in that way...
Intent secondActivity = new Intent(this, secondActivity.class);
secondActivity.putExtra("myHashMap", dataHashMap);
this.startActivity(secondActivity);
then in the second activity I have this part of code
secondActivity = getIntent();
dataHashMap = (HashMap<String,
String>)secondActivity.getSerializableExtra("myHashMap");
and then I'm repeating this upper two steps for the third activity. Is this correct way? because looks a little bit confusing and time consuming. Also there is another problem, now if I am in the third activity and I want to go back to the second or first activity I have always pass some HashMap because activities expects this type of data. Is there a way to sometimes return to a previous activity but no longer pass any data (HashMap in my case) if it is not needed?.
secondActivity.putExtra("myHashMap", dataHashMap); //- I would like to sometimes skip this step
I tried to this code below to handle with this but it does not work, my app keep stopping/crashing because second activity expects hashMap data from the third activity.
secondActivity = getIntent();
if(secondActivity != null){
dataHashMap = (HashMap<String,
String>)secondActivity.getSerializableExtra("myHashMap");
}
Thanks for answers, regards.

You can use a variable that is placed inside Application class instance. This variable is shared for all activities and other elements of the application.

You have several options. Firstly, you said in a comment that you only need one element. In that case you can just pass the one element as an "extra" in the Intent, instead of passing the entire HashMap.
Secondly, I don't understand why you return from the third Activity to the second Activity by calling startActivity(). You should just call finish() and that will return you to the second Activity.
If you need to return some data from the third Activity to the second Activity, you should start third Activity using startActivityForResult() and set the data to return in third Activity using setResult() and the data will be returned to second Activity in onActivityResult().
Another option is to do it exactly as you have done it, but also copy the hashMap into the Intent as an "extra" each time you call startActivity(). If you only have a handfull of entries in the hashMap it won't make any noticeable difference in performance.

Related

regarding passing data through intent

I have an app with 3 Activities.
If the app runs for the first time, the flow is like this
Activity 1 ---> Activity 2 ---> Acitvity3
If its not the first Run, then it skip sholud Activity2
Activity 1 ---> Acitvity3
Activity 3 expects some data from Activity2.
Bundle b = getIntent().getExtras();
Integer mInt= b.getInt(filename);
Acitvity 1 doesnt send this data, which forces the app to crash if Activity 3 is started from Acitvity1 (i.e. for not first run). Is there any way by which I can skip checking for getExtras in Activity3 if its called by Activity1??
Whenever starting Activity3 from Activity1 ot Activity2 pass the one string variable like this..
if from ActivityA
intent.putExtra("from", "ActivityA");
if from ActivityB
intent.putExtra("from", "ActivityB");
and in the Activity3 get the value and check if it its from Activity2 perform the operation..
String stringExtra = getIntent().getStringExtra("from");
if (stringExtra.equals("ActivityA")) {
}else {
}
There is no way in Android to get the Activity which called your current Activity. Think about it, the calling "activity" might be the home page.
Instead, you could try passing another variable in the extras saying what activity is calling the new activity (a simple string, or even a Class object) and then according to which activity is being called, you could decide what to do with a simple "if" statement.
Hope this helps :)
Add a boolean extra as a flag to determine which activity started Activity3. Before trying to get mInt from extras, read the boolean first, which you would set to false in Activity 1's Intent launching Activity 3, and set to true in the Intent in Activity2.

Android: Update the contents of ListView even when another activity is active

The android app has two activities.
First: MainActivity
Second: AddNewDataActivity
The MainActivityhas a ListView. The user can create a new list view item by clicking on an "Add" button. When the user clicks on the Add button, a AddNewDataActivity is opened and the user fills in some details and saves the work done. Upon saving the work, the activity is finished and the MainActivity comes to front.
Now, before the MainActivity comes to front, I want to update the items in ListView.
For this From your MainActivity start the AddNewDataActivity Activity by calling StartActivityForResult() method not startActivity() and in your AddNewDataActivity activity when you finish call the method setResult() and pass the data in the Intent which will call the onActivityResult() method in your MainActivity here update your listview..
here check the example of startActivityForResult() example
Yous should serialize the Object you create in AddNewActivity and pass it to the main activity as result.
1) start second activity with startActivityForResult(Intent);
2) before calling finish on second activity serialize the object (as json) and put it as bundle extra to the result via setResult();
3) on MainActivity overriede onActivityResult and parse the data from result and add the object to your ArrayList or any data structure you use.
There is another way to do it. Using a singleton where u will have the ArrayList with data and before closing second activity add the object to that ArrayList, and int onActivityResult just refresh the ListView
Here is how to handle onActivityResult
Transfering data between Activities

Going back to activity with EditTexts populated. - Android

I have Activity A which has editTexts and from activity A, a user can go to activity B and fill out more information. Once the user is done on activity B, they press a button and come back to A. I would like to come back to A with the information that the user had filled in to be already there and not have to fill in the information again.
Currently, this is my code for coming back from B to A.
Intent intent = new Intent(NewAddressActivity.this, CreditCardActivity.class);
intent.putExtra("newAddressEntered", true);
intent.putExtra("newAddress", (Serializable) newAddress);
startActivity(intent);
With this code, when the user comes back, the fields on activity A are empty.
*Note - I need to pass data from B to A when going back.
Any tips on how to do this properly would be greatly appreciated.
Thanks
You are on the right track. You can do that using .putExtra
You can pass extra data via the intent using intent.putExtra("key",
text_field.getText().toString()) on the intent before you send it (in
the first activity) and getIntent().getExtras().getString("key") in
the second activity.
This is assuming text_field is your EditText you want to pass the
value from. You can change "key" to whatever you want, too.
You're actually not "coming back", but starting a new empty intent, thats why the fields are blank again. Instead, you should just call:
finish()
Regarding filling related fields from different Activities, I wouldn't recommend that, but if you need to keep it that way, you may have a singleton class to store all field values for instance.
Also, you could send B fields to A as activity results.-
http://developer.android.com/training/basics/intents/result.html
But still, I would recommend keeping all related fields in one Activity.
Change the launchmode of your Activity A (CreditCardActivity) to singleTop in manifest file and try. The documentation says
If an instance of the activity already exists at the top of the target task, the system routes the intent to that instance through a call to its onNewIntent() method, rather than creating a new instance of the activity.
So your activity should retain old values.

How to get back to the first activity when opening multiple activities

I have an app which have HomeActivity and 4 activities A,B,C,D.
I want when clicking on button start_activity_A_btn in HomeActivity to star activity A, and A starts B, B starts C, C starts D, then done button which takes me to HomeActivity.
NOTICE : in every activity (A,B,C,D) I have some data to save and get back to the HomeActivity after pressing done button.
What you need to do use the following flag in your intent (please check the link, it explains a similar situation to the one you are facing): FLAG_ACTIVITY_REORDER_TO_FRONT. So, in your activity D, in the onClickListener for the done button, here's the code you'd have to use:
Intent intent = new Intent(this, ActivityAname.class);
intent.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
intent.putExtra("data", dataYouReceiveFromABCD);
startActivity(intent);
This will get your A Activity to resume.
Now, regarding the "data" you will just have to keep accumulating this data in a String using some separator if that's possible (since you haven't told us what this data is exactly), so if it was a username and a password you could separate the two using a random combination of characters that will possibly never occur ("246#$^") and then just keep creating a string that you keep building in A, B, C and D and then finally in D you put that String as an extra in the intent (check the code I've posted above). If it's some other sort of data then you could perhaps serialize it if that helps. However, if you do use a String with a predetermined separator then all you will have to do is in Activity A you will have to use the following code in the onResume() method of Activity A.
if(this.getIntent().getExtras().getString("data") != null)
{
String data = this.getIntent().getExtras().getString("data");
//do some stuff here with that data
}
If you need data returning an Activity, you should use startActivityForResult to start ABCD. This works very much like your HomeActivity is opening up some dialog, and once the Activity finished (by pressing done or cancel, depends), you get onActivityResult in your HomeActivity.

Basic Android code flow

Lets say you have one main activity called "main", and other sub-activities that do some work and then return some data. Each time main gets called it starts up the sub-activities one at a time.
Main:
onCreate...{
Intent i1 = new Intent("com.bla.bla.activity1");
startActivity(i1);
//Get bundles from activity1 and save some variables..
Intent i2 = new Intent("com.bla.bla.activity2");
startActivity(i2);
//Get bundles from activity2 and save some variables..
Intent i3 = new Intent("com.bla.bla.activity3");
startActivity(i2);
//Get bundles from activity1 and save some variables..
}
If I understand correctly, activity1 will be created at first, and then destroyed. Will the code resume and start activity2 or will it just start activity1 again because the main activity was paused and then resumed (assuming we don't add an onResume/onPause etc..)?
Edit:
Lets say these sub-activities return one string each, and each string should be saved in one individual column of an SQL entry at the end of the main activity. The main activity should collect the three strings, save it as en entry and the destroy itself.
For this to work, the main activity has to resume for example at intent "i2" after intent "i1" has done some work and returned the string.
How is this result best achieved?
Like Alex said, you wouldn't want to do that. You want to use the different Intents to call different Activities to create a flow to your program. Main might lead to Activity 1, Activity 1 leads to 2, 3, or 4. If you have several activities, you can use a switch statement to determine which activity you want to launch, based on conditions that are, or are not, met.
Hope this helps.
EDIT Answer:
If you want to save variables from different Activities, the you would want to start the second Activity from the first, the third, from the second, and so on. To create the data for the database, you can simply create an object, and then pass that object from Activity to Activity, using the Parcelable interface. Within each of your Activities you would want to use methods to save the returned data to the database, as you see fit.

Categories

Resources