startActivityForResult详解

Demo链接:http://download.csdn.net/detail/l_lhc/9395394

startActivityForResult与startActivity的不同之处在于:

1. startActivity

仅仅是跳转到目标页面,若是想跳回当前页面进行数据刷新或其他处理,则必须再使用一次startActivity( )

A跳转到B:         A-->B
B执行finish操作:  B-->finish(B)-->A

2. startActivityForResult( )

可以一次性完成这项任务,当程序执行到这段代码的时候,假若从A跳转到下一个B,而当这个B调用了finish()方法以后,程序会自动跳转回A,并调用前一个A中的onActivityResult( )方法。

A跳转到B:         A-->B 
B执行finish操作: B-->finish(B)-->onActivityResult(A)-->A

相关函数:

  • startActivityForResult(Intent intent, Int requestCode) :设置请求码(请求码必须大于等于0,否则将不会回调onActivityResult方法),并实现跳转
  • setResult(int resultCode, Intent intent) :设置结果码,和回调给onActivityResult的intent
  • onActivityResult(int requestCode, int resultCode, Intent intent):根据接收到的请求码和结果码,进行相应的逻辑处理

相关参数:(假定A为原始Activity,B为跳转后的Activity;A–>B)

  • Intent :意图,用户可以在intent中设置将要跳转的目标Activity,和将要传递的数据等。
  • resultCode:结果码,在B中setResult中设置,在A中的onActivityResult中进行判断,处理。
  • requestCode:请求码,在A中startActivityForResult中设置,A跳转到B,B再返回A后,在A的onActivityResult中对requestCode处理。

SetResult的使用示例(resultCode结果码的使用):

1 . 在A中设置跳转:

Intent intent=new Intent();
intent.setClass(A.this, B.class);
Bundle bundle=new Bundle();
String str1="aaaaaa";
bundle.putString("str1", str1);
intent.putExtras(bundle);
startActivityForResult(intent, 0);//这里采用startActivityForResult来做跳转,此处的0为一个依据,可以写其他的值,但一定要>=0

2 . 修改A中的onActivityResult()方法:

protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    switch (resultCode) { //resultCode为回传的标记,我在B中回传的是RESULT_OK
       case RESULT_OK:
            Bundle b=data.getExtras(); //data为B中回传的Intent
            String str=b.getString("str1");//str即为回传的值
            break;
        default:
            break;
    }
}

3 . 在B中设置setResult()方法:

setResult(RESULT_OK, intent); //intent为A传来的带有Bundle的intent,当然也可以自己定义新的Bundle
finish();//此处一定要调用finish()方法

Android activity的setResult()在什么时候调用(重点也是难点)

如果在startActivityForResult起来的Activity里面设置setResult,结果并不会马上返回给parent的Activity,只有当前Activity被finish,结果才会被发送给parent的onActivityResult去处理!

如果一个activity要返回数据到启动它的那个activity,可以调用setResult()方法。那什么时候去调用setResult()方法返回数据呢?
看一下源码就明白了:

public final void setResult(int resultCode, Intent data) {
        synchronized (this) {
            mResultCode = resultCode;
            mResultData = data;
        }
    }

    public void finish() {
        if (mParent == null) {
            int resultCode;
            Intent resultData;
            synchronized (this) {
                resultCode = mResultCode;
                resultData = mResultData;
            }
            if (Config.LOGV) Log.v(TAG, "Finishing self: token=" + mToken);
            try {
                if (ActivityManagerNative.getDefault()
                    .finishActivity(mToken, resultCode, resultData)) {
                    mFinished = true;
                }
            } catch (RemoteException e) {
                // Empty
            }
        } else {
            mParent.finishFromChild(this);
        }
    }

这段代码可以看出activity返回result是在被finish的时候,也就是说调用setResult()方法必须在finish()之前。
那么如果在如下方法中调用setResult()也有可能不会返回成功: onPause(), onStop(), onDestroy(),
因为这些方法调用不一定是在finish之前的,当然在onCreate()就调用setResult肯定是在finish之前的

按BACK键从一个Activity退出来的,一按BACK,android就会自动调用Activity的finish()方法,然后设置resultCode为RESULT_CANCELED,也就不会返回任何数据了 .
解决方法就是在Activity里面捕获按BACK的事件,捕获到之后先setResult,然后自己来调用finish,就搞定了……把BACK事件直接自己给吞了

@Override
    public void onBackPressed() {
        Log.i(TAG, "onBackPressed");
        setResult(Const.LIVE_OK);
        super.onBackPressed();
    }

当然还可以在onCreate()就调用setResult,不过我觉得这种方法没有重写onBackPressed()方法好。

注意:

  • 在finish之前调用setResult()方法
  • Activity的启动模式会对setResult方法有影响,建议Activity启动模式使用默认(standard)启动模式。

requestCode(请求码)的使用:

1.在A中Button_1的点击事件中,设置A–>B的跳转,请求码为 REQUEST_1

Intent intent = new Intent(this,B.class);
startActivityForResult(intent, Config.REQUEST_1);

2.在A中Button_2的点击事件中,设置A–>B的跳转,请求码为 REQUEST_2

Intent intent = new Intent(this,B.class);
startActivityForResult(intent, Config.REQUEST_2);

3.修改A中onActivityResult()方法

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) { 
        if(requestCode == Config.REQUEST_1){//如果是通过A中的 Button_1 跳转到B.class后,又由B.class 返回A
            //进行逻辑处理
        }else if(requestCode == Config.REQUEST_2){//如果是通过A中的 Button_2 跳转到B.class后,又由B.class 返回A
            //进行逻辑处理
        }
        super.onActivityResult(requestCode, resultCode, data);
    }

参考:http://www.cnblogs.com/lijunamneg/archive/2013/02/05/2892616.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值