My first project stuck on OnActivityforResult - android

I tried to make a simple app which can keep scores on a game with four players. When I press the plus or minus button it opens a new activity (dialog theme) where the user should enter their score. That score should be stored into a text view.
Some part of code looks like this:
Here I opened new activities
buttonPlus1.setOnClickListener(this);
buttonPlus2.setOnClickListener(this);
buttonPlus3.setOnClickListener(this);
buttonPlus4.setOnClickListener(this);
buttonMinus1.setOnClickListener(this);
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.buttPlusPlayer1:
Intent i = new Intent(this, SecondActivity.class);
startActivityForResult(i, 1);
break;
case R.id.buttPlusPlayer2:
Intent i2 = new Intent(this, ThirdPlusActivity.class);
startActivityForResult(i2, 2);
break;
case R.id.buttPlusPlayer3:
Intent i3 = new Intent(this, FourthPlusActivity.class);
startActivityForResult(i3, 3);
break;
case R.id.buttPlusPlayer4:
Intent i4 = new Intent(this, FifthPlusActivity.class);
startActivityForResult(i4, 4);
break;
case R.id.buttMinusPlayer1:
Intent i5 = new Intent(this, FirstMinusActivity.class);
startActivityForResult(i5, 1);
}
}
That's an example how activities send data back to main activity
public class SecondActivity extends AppCompatActivity {
private EditText mEditText;
private ImageButton mBackSpace;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_second);
setTitle("ADD POINTS");
mEditText = findViewById(R.id.editTxtActivity);
//implementing backspace button
mBackSpace = findViewById(R.id.backSpaceButton);
mBackSpace.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String str = mEditText.getText().toString();
if (str.length() > 0) {
str = str.substring(0, str.length() - 1);
mEditText.setText(str);
}
}
});
}
#Override
public void onBackPressed() {
Intent i = new Intent();
i.putExtra("message", mEditText.getText().toString());
setResult(RESULT_OK, i);
Toast.makeText(this, "You added " + mEditText.getText().toString() + " points", Toast.LENGTH_LONG).show();
finish();
}
}
and "now" I receive the results from activities
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == 1 && resultCode == RESULT_OK) {
String a = data.getStringExtra("message");
int i =Integer.parseInt(a);
String b = data.getStringExtra ("message5");
int z = Integer.parseInt(b);
Integer fResult = i - z;
String firstResult = fResult.toString();
mFirstScore.setText(firstResult);
}
if (requestCode == 2 && resultCode == RESULT_OK) {
mSecondscore.setText(data.getStringExtra("message2"));
}
if (requestCode == 3 && resultCode == RESULT_OK) {
mThirdScore.setText(data.getStringExtra("message3"));
}
if (requestCode == 4 && resultCode == RESULT_OK) {
mFourthscore.setText(data.getStringExtra("message4"));
}
the problem is on the last part of the code because I don't know how to receive data from activities and to calculate the result. I want when the user hit the plus button to add numbers and when minusButton is clicked to substract and the result to be stored on a TextView which, for player1, in my case is mFirstScore.
Is this possible or I did everything wrong and it is not possible to manipulate data received from another activity how I image
PS: on case buttMinusPlayer1 and on first if with requestCode 1 I've tried something ;

On SecondActivity put your key message2
#Override
public void onBackPressed() {
Intent i = new Intent();
i.putExtra("message2", mEditText.getText().toString());
setResult(RESULT_OK, i);
finish();
}
and get the data from SecondActivity by the same key message2
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == 2 && resultCode == RESULT_OK) {
mSecondscore.setText(data.getStringExtra("message2"));
}
}
Hope this helps.

Related

Disable button in a Listview's row while getting response of a save?

Issue:
I have a Listview in Mainactivity. Each row of listview has two buttons say SET and RUN.
Pressing SET will take you to SET activity and if the user clicks save button in SET Activity, I need to disable the SET button in the corresponding row position of the listview in mainactivity.
So Far Done:
For that I have a refresh function on a onclicklistener to requery the list with updated values. How to call that refresh function without keypress in the Mainactivity or is there any other way?
Activity MAIN :
viewHolder.ButtonSET.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String title = v.getTag().toString();
if (title.equals("SET")) {
if (Integer.parseInt((String) viewHolder.TDNQTY.getText()) > 0) {
if(scanoverornot(pos)<=0) {
Intent s = new Intent(DN.this, SETActivity.class);
s.putExtra("position", pos);
s.putExtra("mode", "SET");
try{
startActivityForResult(s, saverequestcode);
// getContext().startActivity(s);
}
catch(Exception e){
Toast.makeText(getContext(),""+e,Toast.LENGTH_LONG).show();
}
}
}
}
}
});
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (data == null)
return;
switch (requestCode) {
case saverequestcode:
if (resultCode == RESULT_OK) {
String SItem= data.getStringExtra("SItem");
int SPos= data.getIntExtra("SPos", 0);
saved = 700;
Toast.makeText(getApplicationContext(), ""+ SItem+ SPos, Toast.LENGTH_LONG).show();
//btnvalidate.performClick();
}
}
}
Activity SET :
Intent sav = new Intent();
sav.putExtra("SItem", String.valueOf(itemno));
sav.putExtra("SPos", String.valueOf(pos));
setResult(RESULT_OK, sav);
finish();
You can use startActivityForResult to nail this purpose:
startActivityForResult(new Intent(this, DestinationActivity.class), MY_RESULT);
And then in your MainActivity:
public int MY_RESULT = 10;
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == MY_RESULT) {
if (resultCode == Activity.RESULT_OK) {
//refresh the list according to your logic
}
}
}
Don't forget to call setResult(Activity.RESULT_OK); when user clicks save button.
saveButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
setResult(Activity.RESULT_OK);
}
});
Issue Lines:
Have to add super.onActivityResult(requestCode, resultCode, data);
Removed switch case and used if condition for requestCode check
Solution:
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (data == null)
return;
if (requestCode == saverequestcode) {
if (resultCode == Activity.RESULT_OK) {
String SItem = data.getStringExtra("SItem");
String SPos = data.getStringExtra("SPos");
Toast.makeText(getApplicationContext(), "Item :" + SItem + "Position :" + SPos, Toast.LENGTH_LONG).show();
}
if (resultCode == Activity.RESULT_CANCELED) {
//Any methods
}
}
else if (requestCode == importrequestcode){
}
}
Activity SET :
Intent sav = new Intent();
sav.putExtra("SItem", String.valueOf(itemno));
sav.putExtra("SPos", String.valueOf(pos));
setResult(Activity.RESULT_OK,sav);
finish();

onActivityResult - resultCode is always 0

I have problem with onActivityResult, whatever I'm doing I can't get resultCode right.
I know that there are similar questions but at the end they didn't help me and I couldn't fix it
MainActivity: method which will open new Activity Popup.class
public void openShopView(){
Intent intent = new Intent(this, Popup.class);
Bundle b = new Bundle();
b.putString("which", "ShopMain");
intent.putExtras(b);
startActivityForResult(intent, 1);
}
Second Activity: method which will open yet another Activity Popup.class just with different layout
shop_c1.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent intent = new Intent(getIntent());
Bundle b = new Bundle();
b.putString("which", "ShopBuildings");
intent.putExtras(b);
startActivity(intent);
finish();
}
});
Third Activity: and there is method which should setResult and close Activity
building2.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Log.i("LOG_NEW: ", "" + getCurrentBuildingTable(1) + ", " + checkSlotTable(1));
if(getCurrentBuildingTable(1) && checkSlotTable(1) == -1) {
Intent returnIntent = getIntent();
returnIntent.putExtra("result", 1);
setResult(RESULT_OK, returnIntent);
finish();
}else if (checkSlotTable(1) == -1){
Log.i("LOG_NEW: ", "Building already exist");
}
else{
Log.i("LOG_NEW: ", "Not enough resources");
}
}
});
At the end there is onActivityResult() from MainActivity
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
Log.i("LOG_RES: ", "Checking.. " + requestCode + ", " + resultCode);
if (requestCode == 1) {
if(resultCode == RESULT_OK){
String result = data.getStringExtra("result");
Log.i("LOG_RES: ", result);
}
}
}
Whatever I'm doing I can't start if(resultCode == RESULT_OK) loop and resultCode is always 0..
Thanks for help
setResult must be called in Second Activity, since intent of second activity was passed in startActivityForResult.
However, you can delegate the result code of Third Activity to Second Activity, then to third.
Change your Second Activity to something like this:
shop_c1.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent intent = new Intent(getIntent());
Bundle b = new Bundle();
b.putString("which", "ShopBuildings");
intent.putExtras(b);
startActivityForResult(intent,1);
//Remove finish from here
}
});
then also add this in Second Activity
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(requestCode==1){
setResult(resultCode,data);
}
finish();
}

How to handle getResults from multiple activities?

I am trying to get results back from intents in android studio.
In my main I start an activity and use startActivityForResult(intent, 1)
I then use get results in mainActivity from activity 2's setResults()
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 1) {
if(resultCode == RESULT_OK){
Bundle extras = data.getExtras();
if (extras != null) {
String name = extras.getString("FIRSTNAME");
String Lname = extras.getString("LASTNAME");
int ID = extras.getInt("ID");
//TODO: Get the list fragment to newinstance with out new arraylist
Person p = new Person(name, Lname, ID);
people.add(p);
getFragmentManager().beginTransaction().replace(R.id.content_main, FullList.newInstance(people)).commit();
}
In my fragment in activity 1 I am calling a new startActivityForResult(i, 2)
How do i get my main activity to grab the setResults()
from Activity 3?
Activity 3 is doing this:
Intent deleteIntent = new Intent();
deleteIntent.putExtra("FNAME", first);
deleteIntent.putExtra("LNAME", last);
deleteIntent.putExtra("ID", num);
setResult(RESULT_OK, deleteIntent);
finish();
I am trying to have my main activity call if (requestCode == 2)
But it works to no avail.
Here is the all the onActivityResult for reference:
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 1) {
if(resultCode == RESULT_OK){
Bundle extras = data.getExtras();
if (extras != null) {
String name = extras.getString("FIRSTNAME");
String Lname = extras.getString("LASTNAME");
int ID = extras.getInt("ID");
//TODO: Get the list fragment to newinstance with out new arraylist
Person p = new Person(name, Lname, ID);
people.add(p);
getFragmentManager().beginTransaction().replace(R.id.content_main, FullList.newInstance(people)).commit();
}
// NOW SEEING IF THE DETAILS SCREEN PASSED BACK RESULTS
} else if (requestCode == 2) {
if (resultCode == RESULT_OK) {
Bundle extras = data.getExtras();
if (extras != null) {
String name = extras.getString("FNAME");
String Lname = extras.getString("LNAME");
int ID = extras.getInt("ID");
Person p = new Person(name, Lname, ID);
// Delete happens here //
if (people.contains(p)) {
people.remove(p);
// If empty show blank frag, if not, update list //
if (people.isEmpty()) {
getFragmentManager().beginTransaction().replace(R.id.content_main, BlankList.newInstance());
} else {
getFragmentManager().beginTransaction().replace(R.id.content_main, FullList.newInstance(people)).commit();
}
} else {
Toast.makeText(this, "DIDNT RECEIVE SAME INFO", Toast.LENGTH_SHORT).show();
}
}
}
}
// END ELSE CHECK
}
}
Here is the code that is calling the startActivityForResult() in the Fragment on activity 1.
#Override
public void onListItemClick(ListView l, View v, int position, long id) {
//super.onListItemClick(l, v, position, id);
ArrayList<Person> people = (ArrayList<Person>) getArguments().getSerializable(ARG_People);
if (people != null && position != -1) {
Person listPerson = people.get(position);
Intent i = new Intent("OPENDETAILS");
i.putExtra("NAME", listPerson.name);
i.putExtra("LASTNAME", listPerson.lName);
i.putExtra("ID", listPerson.ID);
startActivityForResult(i, 2);
} else {
Toast.makeText(getActivity(), "EMPTY LIST ERROR", Toast.LENGTH_SHORT).show();
}
}
It's a little unclear what you're trying to do, but it sounds like:
Activity1 starts Activity2 for result
Activity2 starts Activity3 for result
Activity3 returns a result
Activity1 is expected receive Activity3's result.
If I got that right then the key element that seems to be missing here is that you are expecting Activity1 to get a result from Activity3 even though it was Activity2 that started it for result. In this case you should implement onActivityResult in Activity2, handle the results coming back from Activity3 and set them as Activity2's results to pass back to Activity1 and then finish; An activity will only receive results from activities it directly starts via startActivityForResult.
Use different code to launch different activities,
such as
startActivtityForResult(new Intent(this,Person1.class),1);
startActivtityForResult(new Intent(this,Person2.class),2);
startActivtityForResult(new Intent(this,Person3.class),3);
then on activityresult
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (resultCode) {
case 1:
//implement your code here
break;
case 2:
//implement your code here
break;
case 3:
//implement your code here
break;
}
}
then set Retrun result in these classes
Person1.class
return_intent.putExtra("result", 1);
setResult(1, return_intent);
Person2.class
Person1.class
return_intent.putExtra("result", 2);
setResult(2, return_intent);
Person3.class
Person1.class
return_intent.putExtra("result", 3);
setResult(3, return_intent);

onActivityResult error when I press "cancel" button on my second Activity

I have the next activities:
Activity1
//declare
private static final int SAVE_DATA_FROM_ACTIVITY = 203;
//........... not important code
//button to open second Activity
public void btn_openSecondActivity(View view)
{
Intent intent = new Intent(Activity2.this, Activity1.class);
startActivityForResult(intent, SAVE_DATA_FROM_ACTIVITY);
}
}
protected void onActivityResult (int requestCode, int resultCode, Intent data)
{
if (requestCode == SAVE_DATA_FROM_activity)
{
name= data.getStringExtra("Name");
}
}
//....... not important code
Activity2
On Second Activity I have two buttons:
Cancel
Save
//............
//declare
private static final int OK_RESULT_CODE = 1;
//Cancel button
public void btn_cancel(View view)
{
finish();
}
//Save button
public void btn_save (View view)
{
Intent intent = new Intent();
intent.putExtra("Name",et_name.getText().toString());
setResult(OK_RESULT_CODE, intent);
finish();
}
PROBLEM
When I click Save button all works perfect, but the problem it's when I click Cancel button, then it's reports an error:
Failure delivering result ResultInfo{who=null, request=203, result=0, data=null} to activity {com.example.alvaro.project/com.alvaro.project.Activity1}: java.lang.NullPointerException
I understand the problem, when I cancel is not the same result code but i don't know how I can solve it
Any suggestions?
You have issue in onActivityResult method. You don't check result.
Change your condition from :
if (requestCode == SAVE_DATA_FROM_activity)
to:
if (resultCode == OK_RESULT_CODE && requestCode == SAVE_DATA_FROM_activity)
Change this
if (requestCode == SAVE_DATA_FROM_activity)
{
name= data.getStringExtra("Name");
}
into
if (requestCode == SAVE_DATA_FROM_activity&&resultCode==RESULT_OK)
{
name= data.getStringExtra("Name");
}
and
Your cancel method is like
public void btn_cancel(View view)
{
setResult(RESULT_CANCELED);
finish();
}
And instead of OK_RESULT_CODE use Android default ok like Activity.RESULT_OK
Check if you manage to set the result
protected void onActivityResult (int requestCode, int resultCode, Intent data)
{
if (requestCode == SAVE_DATA_FROM_activity && resultCode = Activity2.OK_RESULT_CODE)
{
name= data.getStringExtra("Name");
} else {
//probably btn_cancel pressed
}
}
check resultCode in onActivityResult
protected void onActivityResult (int requestCode, int resultCode, Intent data)
{
if (resultCode == 1/*OK_RESULT_CODE from Second Activity */ && requestCode == SAVE_DATA_FROM_activity)
{
name= data.getStringExtra("Name");
}
}
Activity1
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == SAVE_DATA_FROM_activity) {
if (resultCode == Activity.RESULT_OK) {
name = data.getStringExtra("Name");
} else if (resultCode == Activity.RESULT_CANCELED){
// TODO something
}
}
}
Activity2
delete field OK_RESULT_CODE
//Cancel button
public void btn_cancel(View view) {
setResult(Activity.RESULT_CANCELED, new Intent());
finish();
}
//Save button
public void btn_save(View view) {
Intent intent = new Intent();
intent.putExtra("Name", et_name.getText().toString());
setResult(Activity.RESULT_OK, intent);
finish();
}

Multiple onActivityResult for 1 Activity

So I have a very simple app I am working on. It's purpose is to collect asset data from 1 pc, and 1 or 2 monitors.
My form contains 3 edittext views, and 3 buttons (one for each asset I am collecting data for). The buttons invoke startActivityForResult for the barcode scanner, then I want to pass the result to the associated edittext view based on which button was pressed (example: press "scan" button to the right of "Asset - PC" edittext, scan and return data to it's associated edittext. Then if you press the button "scan" thats next to the "Asset - Mon1" edittext, return data to "Asset - Mon1" edittext.... and so on...)
With the code I have here, all the items work, just not as intended. Pressing any of the "scan" buttons always returns the result to the first edittext view "Asset - PC".
public class TestShit extends Activity {
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
}
public void assetPcClick(View view) {
Intent intent1 = new Intent("com.google.zxing.client.android.SCAN");
intent1.setPackage("com.google.zxing.client.android");
intent1.putExtra("SCAN_MODE", "ONE_D_MODE");
startActivityForResult(intent1, 0);
}
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
if (requestCode == 0) {
if (resultCode == RESULT_OK) {
String contents1 = intent.getStringExtra("SCAN_RESULT");
String format1 = intent.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetPC = (EditText) findViewById(R.id.assetPC);
assetPC.setText(contents1);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
}
public void assetMon1Click(View view) {
Intent intent2 = new Intent("com.google.zxing.client.android.SCAN");
intent2.setPackage("com.google.zxing.client.android");
intent2.putExtra("SCAN_MODE", "ONE_D_MODE");
startActivityForResult(intent2, 0);
}
public void onActivityResult2(int requestCode, int resultCode, Intent intent2) {
if (requestCode == 0) {
if (resultCode == RESULT_OK) {
String contents2 = intent2.getStringExtra("SCAN_RESULT");
String format2 = intent2.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetMon1 = (EditText) findViewById(R.id.assetMon1);
assetMon1.setText(contents2);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
}
public void assetMon2Click(View view) {
Intent intent3 = new Intent("com.google.zxing.client.android.SCAN");
intent3.setPackage("com.google.zxing.client.android");
intent3.putExtra("SCAN_MODE", "ONE_D_MODE");
startActivityForResult(intent3, 0);
}
public void onActivityResult3(int requestCode, int resultCode, Intent intent3) {
if (requestCode == 0) {
if (resultCode == RESULT_OK) {
String contents3 = intent3.getStringExtra("SCAN_RESULT");
String format3 = intent3.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetMon2 = (EditText) findViewById(R.id.assetMon2);
assetMon2.setText(contents3);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
}
}
Any suggestions on how I can better manage my multiple "ActivityForResult" and "onActivityResult" 's ?
My fix, thank you for all your help!
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
if (requestCode == 0) {
if (resultCode == RESULT_OK) {
String contents1 = intent.getStringExtra("SCAN_RESULT");
String format1 = intent.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetPC = (EditText) findViewById(R.id.assetPC);
assetPC.setText(contents1);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
if (requestCode == 1) {
if (resultCode == RESULT_OK) {
String contents1 = intent.getStringExtra("SCAN_RESULT");
String format1 = intent.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetMon1 = (EditText) findViewById(R.id.assetMon1);
assetMon1.setText(contents1);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
if (requestCode == 2) {
if (resultCode == RESULT_OK) {
String contents1 = intent.getStringExtra("SCAN_RESULT");
String format1 = intent.getStringExtra("SCAN_RESULT_FORMAT");
EditText assetMon2 = (EditText) findViewById(R.id.assetMon2);
assetMon2.setText(contents1);
} else if (resultCode == RESULT_CANCELED) {
// Handle cancel
}
}
}
In your startActivityForResult, don't use 0's on both calls... use different numbers like 0 & 1... then you can implement a switch in your onActivityResult method with the requestCode. If the requestCode = 0 then the first method has returned, if it is 1, then the second has returned. This should be the same for more calls.
public void onActivityResult(int requestCode, int resultCode, Intent intent){
switch(requestCode){
case 0: // Do your stuff here...
break;
case 1: // Do your other stuff here...
break;
case etc:
break;
}
}
The calls should be something like this then:
(For the first time)
startActivityForResult(intent1, 0);
(For the second time)
startActivityForResult(intent2, 1);
(for the third time)
startActivityForResult(intent3, 2);
(for the nth time)
startActivityForResult(intentn, n - 1);
Or, you could declare static int values to use, instead of the more unrecognisable int values.
While you startActivityForResult you send a requestcode with it,
this should be different(unique) for your every activity you are starting from your button, say button 1 starts activity request code 1, button 2 requestcode = 2, and button 3 request code =3, then for your parent activity you must have only one onActivityResult()
in this function take a switch case , scan requestcodes, requestcode = 1 will give result from first activity and request code =2 gives for activity 2 and so on...
There's nothing in Android that is ever going to recognize and call methods named onActivityResult2 or onActivityResult3. Those are just method names you made up that are going to be ignored by the system.
You need to change your code such that you pass a different request code when you call startActivityForResult(). (requestCode is the 2nd parameter to that method)
Then in onActivityResult check the requestCode to see which activity you are getting the result from, and handle accordingly.

Categories

Resources