Android message between 2 activities problem - android

I have the following code in one activity:
in= new Intent(ThisActivity.this,AnotherActivity.class);
imgarr = new ImageView[55];
imgarr[0]=(ImageView) findViewById(R.id.species3);
imgarr[0].setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
b.putString("specno",Integer.toString(0)); in.putExtras(b);
in.setClassName("com.DuckHuntersJournal","com.DuckHuntersJournal._1_TagKillActivity");
startActivity(in);
}
});
And this code in another:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.menu1tagkill);
if ((savedInstanceState != null) && savedInstanceState.containsKey("specno")) {
Log.e(tag, "intent from species not null");
species.setText(savedInstanceState.getString("specno"));
}
However, savedInstanceState is null.
Why am I not getting any data back from the first activity?

You need to use :
getIntent().getExtras().getString("specno");
in order to get the passed string from the first activity.
EDIT: I'm not sure what you are trying to do... for getting data from another Activity that started the current one you need to use getIntent().getExtras().
For saving your current stat when the Activity goes to background you save the data in the onSaveInstanceState() method and then in the onCreate(Bundle savedInstance) method you get the saved data from the savedInstance parameter.

You'll need to do the following in your receiving Activity:
String species = getIntent().getStringExtra("specno");

Related

getSerializableExtra() is null randomly

There is a link in one activity, after I click on it it opens another activity. I add an enum parameter for the second activity.
#Override
protected void onCreate(Bundle savedInstanceState) {
binding.myLink.setOnClickListener(new View.OnClickListener() {
// ...
#Override
public void onClick(View view) {
Intent intent = new Intent(getActivityContext(), SecondActivity.class);
intent.putExtra(KEY, MyEnum.ENUM_VALUE);
startActivity(intent);
}
});
// ...
}
In onCreate of second activity I read this parameter
#Override
protected void onCreate(Bundle savedInstanceState) {
// ...
// get value
FirstActivity.MyEnum value = (FirstActivity.MyEnum ) getIntent()
.getSerializableExtra(AboutActivity.KEY);
// ...
}
Everything works but in Crashlytics I see that for some users value is null. Second activity is called only from first one and from nowhere else.
Can someone suggest me the scenario with this behavior? When can it happen like this?
I opened my app, opened the second activity and put app to background. After several hours I opened my app from the list of apps and everything is ok. No more ideas when it can happen.
use this :
#Override
public void onClick(View view) {
Intent intent = new Intent(getActivityContext(), SecondActivity.class);
Bundle bundle=new Bundle();
bundle.putSerializable(serializableKEY,yourSerializableClass);
intent.putExtras(KEY, bundle);
startActivity(intent);
}
});
and in second activity :
Bundle bundle=getIntent().getExtras();
yourSerializableClass clazz=(yourSerializableClass)bundle.getSerializable(serializableKEY);

Going back and forth between intents without losing user entered data

I have a form. Here, the user fills in details like event name, description, location etc. To select the location, I have set a button. This is my button code:
btnMap.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent map = new Intent(getApplicationContext(), Map2.class);
startActivity(map);
}
});
I select the location from there, and the data is passed back to my main intent correctly. But the thing is, the data in the other fields like event, description etc. that users filled in are lost.
I tried startActivityForResult(map,1); too. Doesn't work. Is there a way to keep the data, without sending them in a bundle to the other intent and getting them back? like the select image button does? It goes to the gallery and comes back without resetting the other fields
contactImageImgView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent intent = new Intent();
intent.setType("image/*");
intent.setAction(Intent.ACTION_GET_CONTENT);
startActivityForResult(Intent.createChooser(intent, "Select Image"), 1);
}
});
You need to save your activity state.
Override the method onSaveInstanceState and persist all your data in the bundle
In onCreate, if savedInstanceState is not null, restore all your data and set all the fields.
#Override
public void onSaveInstanceState(Bundle savedInstanceState) {
savedInstanceState.putInt("MY_FIELD", 43);
// ... other fields
super.onSaveInstanceState(savedInstanceState);
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); // Always call the superclass first
if (savedInstanceState != null) {
int value = savedInstanceState.getInt("MY_FIELD");
// ... update your views
} else {
// no previous state, start fresh
}
}
Details here
Note: you have mentioned that rotation is blocked. This is generally bad for the user unless it's part of the feature of the app.
Explanation:
A screen rotation is a configuration change that causes the activity to restart with the appropriate resources. There are many more configuration changes such as screen unlock,device docked etc. Not all of them trigger an activity restart but some do. When your activity restarts due to a configuration change, onSaveInstanceState gets called and savedInstanceState will be not-null when onCreate is called.
When you start a new activity Android may destroy the previous one to recover some of the resources it was consuming. In that case, when you return to that previous activity, it is actually a new instance of the Activity subclass and the internal state has been lost. It's up to you to save and restore any state necessary within the onSaveInstanceState and onCreate callback methods, respectively.
Have a look at this page for more information and examples: Recreating an Activity | Android Developers
public class FormActivity extends Activity {
private static final String NAME = "NAME";
private EditText nameEdit;
// Declare other view references here...
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_form);
nameEdit = (EditText) findViewById(R.id.name_edit);
// Find other views...
if (savedInstanceState != null) {
final String nameValue = savedInstanceState.getString(NAME, "");
nameEdit.setText(nameValue);
// Restore other saved values...
} else {
// No saved values to restore
}
}
#Override
public void onSaveInstanceState(Bundle outState, PersistableBundle outPersistentState) {
final String nameValue = nameEdit.getText().toString()
outState.putString(NAME, nameValue);
// Put (save) other values into the outState bundle...
super.onSaveInstanceState(outState, outPersistentState);
}
// Other FormActivity code...
}

edit text saving status in android

i did a lot of trials before coming here, i need that user find the same values entered in
an activity when he returns to , i did this code but it is not working :
public class ActivityUn extends Activity {
#Override
public void onSaveInstanceState(Bundle savedInstanceState) {
savedInstanceState.putString("arm_1", rm_1ts);
savedInstanceState.putString("arm_2", rm_2ts);
super.onSaveInstanceState(savedInstanceState);
}
public void ajouter(View v) {
db.open();
long id = db.insertMENAGE(rm_1ts,rm_2ts); }
EditText rm_1;
EditText rm_2;
String rm_1ts = "";
String rm_2ts = "";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_un);
rm_1 = (EditText)findViewById(R.id.rm_1);
rm_2 = (EditText)findViewById(R.id.rm_2);
if (savedInstanceState != null) {
// Restore value of members from saved state
rm_1ts = savedInstanceState.getString("arm_1");
rm_2ts = savedInstanceState.getString("arm_2");
rm_1.setText(rm_1ts);
rm_2.setText(rm_2ts);
}
Button bton = (Button)findViewById(R.id.ajoutUn);
bton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
rm_1ts = rm_1.getText().toString();
rm_2ts = rm_2.getText().toString();
ajouter(v);
}
});
The problem is that onSaveInstanceState is only called when your Activity is killed via System to free memory or a 3rd party app. But when you press a back button in an Activity it simply is equivalent to finish(). In this case onSaveInstanceState is not called. So if you want to store data every time your Activity is created just store the values in a SharedPreference. You can store the values either in onStop or onPause method depending on your needs.
Here you can learn more about SharedPrefence and other types of storage options.
For the sake of simplicity, you could store the value in the SharedPreferences.
getSharedPreferences().edit().putString("myEditText", yourValue).commit();
That's it.
Try restoring the state in onStart or onResume instead of onCreate. onCreate is only called if the activity needs to be recreated after it is destroyed. Often the activity will be retained in the background in a stopped state, and won't call onCreate when it comes back.
Anywhere in your file, put:
#Override
public void onResume() {
super.onResume();
//Your code here
}

How to save multiple values to a single variable through an activity.

I am creating an application in which I scan a number of bar codes and keep extracting their values and clubbing them in a single place. As simple as this sounds I have been unable to create either an array in which I keep storing new values or a string where I keep concatenating them.
Please comment in case someone needs more code or explanation, I understand the question might not be very rich in either.
EDIT :
public class example
{
String val;
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
try
{
String list_id=ToolList3.ID;
String list_qty=ToolScanDet3.qty;
// val is returned from the barcode scanning app.
val=val+issue_id+"~"+issue_qty+";";
Log.d("Tools issued till yet...", val);
/* Club all the tool IDs together and fire a single query to issue
them all against one name. */
Intent i=new Intent(Issue.this,Issue1.class);
startActivity(i);
//Issue1 again returns a pair of id and qty which needs to be saved along with the previous set of values.
}
I am basically having trouble trying to save the returned set of values along with the previous ones, the new ones that are returned wipe out the previous values. I tried putting them in an array too but that requires a counter which again defeats the purpose because the counter will be initialized to zero and start over again.
Unless the number of elements is known and constant, it is preferred to use ArrayList instead of array. In the case when you want to keep the data when the activity is destroyed caused by orientation change, you can save them in onSavedInstanceState :
#Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putString("temp", tempString);
}
Then retrieve it back in onCreate:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if(savedInstanceState != null) {
your_arraylist = savedInstanceState.getString("temp");
}
EDIT:
According to what you want, the Scan activity should not initialize any string. It should obtain the string value which is passed to it by the main instead:
public class ScanActivity extends Activity {
String tempString;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if(savedInstanceState == null) {
tempString = getIntent().getStringExtra("temp");
} else {
// orientation change
tempString = saveInstanceState.getString("temp");
}
}
Once you have finished the scan, do
Intent output = new Intent();
output.putExtra("temp", tempString);
setResult(RESULT_OK, output);
finish();
to send back the string to your Main activity.
I could not find any solution that was feasible to my situation and thats why I had to create a local database using SQL Lite. Pushing values to the database each time needed and then retrieving the values after my work flow was over.
Comment in case anyone needs help with the creation of a local database using SQL Lite. Happy to help :)

onResume causing problems on start up

I have an activity that allows the user to start a second activity. The second activity has a list of items which I add to an array list. When I return to the previous activity I want to display the size of the array list.
However I am having a problem with onResume(). It is called when my first activity is created and as a result generates an error as the array list does not exist when it is first launched!
onResume():
#Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
getIntentData();
calcSubTotal(orderData);
}
getIntentData():
public void getIntentData(){
b = new Bundle();
b = getIntent().getExtras();
orderData = b.getParcelable("order");
Toast.makeText(this.getApplicationContext(), orderData.size(), Toast.LENGTH_LONG).show();
}
onCreate() of second activity:
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_starters);
createTestData();
b = new Bundle();
orderData = new MenuItemList();
adapter = new MenuItemArrayAdapter(this, starters);
this.setListAdapter(adapter);
}
#Override
protected void onListItemClick(ListView l, View v, int position, long id) {
Toast.makeText(this.getApplicationContext(), l.getItemAtPosition(position).toString() + " clicked", Toast.LENGTH_LONG).show();
//add clicked item to orderData....
MenuItem m = (MenuItem)l.getItemAtPosition(position);
//create new item
orderData.add(m);
}
Any idea how I might be able to control this?
ERROR:
java.lang.RuntimeException: Unable to resume activity {com.example.waitronproto3/com.example.waitronproto3.SectionsActivity}: java.lang.NullPointerException
I think you may want to have a look at startActivityForResult instead, when you're starting your second Activity. It'll allow your second activity to return a result back to your first activity. You can read up on it at the Activity documentation, specifically the "Starting Activities and Getting Results" section of the document.
Edit: By the looks of your code - nothing you're doing is either storing a bundle from the second activity and sending it back to the first. So you'll never get the proper Bundle data in your first activity. As suggested, look into startActivityForResult to launch your second activity with. This will allow you to return data back into your first activity with ease.
However I am having a problem with onResume(). It is called when my first activity is created and as a result generates an error as the array list does not exist when it is first launched!
I recommend changing getIntentData() to check if the appropriate data exists first:
public void getIntentData(){
Intent intent = getIntent();
if(intent != null && intent.hasExtra("order")) {
orderData = b.getParcelable("order");
Toast.makeText(this.getApplicationContext(), orderData.size(), Toast.LENGTH_LONG).show();
calculateSubTotal(order);
}
}
And update onResume():
#Override
protected void onResume() {
super.onResume();
getIntentData();
}
(Though you could simply put getIntentData() in onResume() now.)
Your onResume() will be called after onCreate() according to the Android Lifecycle so you will want to check that the data is not null before trying to use it.
`if(intentData != null)
//do something`

Categories

Resources