Android学习笔记之传递数据
在 Android 开发中,可以使用 Intent
来在两个 Activity 之间传递数据。通过在 Intent
中添加键值对,然后在下一个 Activity 中使用 getIntent()
方法获取 Intent
对象 ,再使用 getXXXExtra()
方法获取数据。可以使用 putExtra()
传值,使用 getXXXExtra()
取值。
让然其他办法也很多:全局变量啦、单例啦、依赖注入感觉更好用,但不在本文讨论范围内。
Intent
类
Intent
类封装了下面6种信息:
- 组件名称(
ComponentName
) - 动作(
Action
) - 种类(
Category
) - 数据(
Data
) - 附件信息(
Extra
) - 标志(
Flag
)
Data
可以传递数据,但涉及到 Intent
的筛选机制比较复杂(还没学到),这里,我使用 Extra
传递数据。
让我们声明一个 Intent
并写入数据:
Intent intent = new Intent(this, GetMessage.class); // GetMessage.class 表示数据接收者
intent.putExtra("key", value); // 键值对,key是字符串,value是任意Java内置数据类型
设置上下文
上面的代码第一行用于设置上下文( context
)。第一个参数引用自身,用 this
;第二个参数引用目标类 (数据接收者),注意,是对类的引用,不是对象。
你可以这样设置上下文:
- 方法一
Intent intent = new Intent(this, GetMessage.class);
- 方法二
Intent intent = new Intent();
intent.setClass(this, GetMessage.class);
- 方法三
Intent intent = new Intent();
intent.setClassName(this, "host.skyone.intent.GetMessage");
- 方法四
Intent intent = new Intent();
intent.setClassName("host.skyone.intent.MainActivity", "host.skyone.intent.GetMessage");
设置数据
设置数据使用 intent.putExtra(String key, value)
方法,value
可以说任意 Java内置数据类型及其数组
。
intent.putExtra("name", "skyone");
intent.putExtra("age", 19);
当然,你也可以使用 intent.putExtras(Bundle data)
方法并传入 Bundle
对象设置数据。
Bundle bundle = new Bundle();
bundle.putString("name", "skyone");
bundle.putInt("age", 19);
intent.putExtras(bundle);
传出数据
想要打开一个 activity
并写入数据,只需要调用:
satrtActivity(intent);
是不是很简单?
接收数据
从打开的新 activity
中接收数据:
Intent intent = getIntent();
String name = intent.getStringExtra("name"); // name = "skyone"
int age = intent.getIntExtra("age"); // age = 19
当然,使用 bundle
也是可以滴:
Intent intent = getIntent();
Bundle bundle = intent.getExtras();
String name = bundle.getString("name"); // name = "skyone"
int age = bundle.getInt("age"); // name = 19
返回数据
从子Activity中返回数据,可以在子Activity中声明一个 Intent
,并传给 setResult(int resultCode, Intent intent)
。
例如,在 ReturnMessage
中返回数据到 MainActivity
。在 ReturnMessage.java
中:
Intent intent = new Intent(this, MainActivity.class);
intent.putExtra("message", "Hello world!");
setResult(52021, intent);
finish();
在 MainActivity
中调用 ReturnMessage
startActivityForResult(new Intent(this, ReturnMessage.class), 2021); // 2021 是RequestCode
在 MainActivity
中接收数据通过重写 onActivityResult(int requestCode, int resultCode, Intent data)
实现,而 requestCode
和 resultCode
则用于判断是谁返回的数据
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 2021 && resultCode == 52021) {
Toast.makeText(this,
"接收到消息:" + data.getStringExtra("message"),
Toast.LENGTH_LONG).show();
}
}
使用 Bundle
还可以使用 Bundle
来在两个 Activity 之间传递数据。
在第一个 Activity 中,使用 Bundle
传递数据:
Intent intent = new Intent(this, SecondActivity.class);
Bundle bundle = new Bundle();
bundle.putString("name", "John");
bundle.putInt("age", 25);
intent.putExtra("user", bundle);
startActivity(intent);
在第二个 Activity 中,获取传递过来的数据:
Bundle bundle = getIntent().getBundleExtra("user");
String name = bundle.getString("name");
int age = bundle.getInt("age");
示例
传出数据
创建一个 Empty Activity
,包名我取名为 host.skyone.intent
;
先画一个简单的页面,用到了两个按钮 Button
,一个输入框 EditText
,一个label TextView
。
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<TextView
android:id="@+id/tips2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="40dp"
android:text="@string/TextView"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<EditText
android:id="@+id/edit_msg"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:autofillHints=""
android:hint="@string/hint"
android:inputType="text"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/tips2"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/send_message"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onSendMessage"
android:text="@string/send_message"
app:layout_constraintBottom_toTopOf="@+id/button"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_msg" />
<Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/return_test"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_msg" />
</androidx.constraintlayout.widget.ConstraintLayout>
再看 MainActivity.java
。onCreate
方法保存原样就好:
onCreate
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
新建一个按钮事件,用来读取文本框的值并传递给子Activity
onSendMessage
public void onSendMessage(View view) {
String message = ((EditText) findViewById(R.id.edit_msg)).getText().toString();
Intent intent = new Intent(this, GetMessage.class);
intent.putExtra("message", message);
startActivity(intent);
}
这里我们用需要创建新Empty Activity: GetMessage
。
好,MainActivity.java
完成了,来到 GetMessage
。首先,依然先画个简单的界面:
activity_get_message.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".GetMessage">
<TextView
android:id="@+id/tips"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/tips"
app:layout_constraintBottom_toTopOf="@+id/showMessage"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/showMessage"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
GetMessage.java
部分也没什么好说的,就是读取数据嘛,在第一节已经讲过了
GetMessage.java
package host.skyone.intent;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.widget.TextView;
public class GetMessage extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_get_message);
Intent intent = getIntent();
String message = intent.getStringExtra("message");
((TextView)findViewById(R.id.showMessage)).setText(message); // 找到View并显示数据
}
}
再次提醒,
Strings.xml
在最下面
返回数据
创建新Empty Activity: ReturnMessage
在 MainActivity
中加入onReturnMessageTest
public void onReturnMessageTest(View view) {
startActivityForResult(new Intent(this, ReturnMessage.class), 2021);
}
记得在 activity_main.xml
中第二个按钮中加入 android:onClick="onReturnMessage"
然后开始写 ReturnMessage
,同样,界面如下:
activity_return_message.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".ReturnMessage">
<EditText
android:id="@+id/edit_query"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:autofillHints="Hello world!"
android:hint="@string/hint"
android:inputType="text"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/textView"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/return_message"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onReturnMessage"
android:text="@string/return_message"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_query" />
<TextView
android:id="@+id/textView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="40dp"
android:text="@string/TextView"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
按钮的事件函数如下:
public void onReturnMessage(View view) {
String message = ((EditText)findViewById(R.id.edit_query)).getText().toString();
Intent intent = new Intent(this, MainActivity.class);
intent.putExtra("message", message);
setResult(52021, intent);
finish();
}
OK,快编译安装试试吧~~~
例图
代码
MainActivity.java
package host.skyone.intent;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
public void onSendMessage(View view) {
String message = ((EditText) findViewById(R.id.edit_msg)).getText().toString();
Intent intent = new Intent(this, GetMessage.class);
intent.putExtra("message", message);
startActivity(intent);
}
public void onReturnMessageTest(View view) {
startActivityForResult(new Intent(this, ReturnMessage.class), 2021);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 2021 && resultCode == 52021) {
Toast.makeText(this, "接收到消息:" + data.getStringExtra("message"), Toast.LENGTH_LONG).show();
}
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<TextView
android:id="@+id/tips2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="40dp"
android:text="@string/TextView"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<EditText
android:id="@+id/edit_msg"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:autofillHints=""
android:hint="@string/hint"
android:inputType="text"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/tips2"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/send_message"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onSendMessage"
android:text="@string/send_message"
app:layout_constraintBottom_toTopOf="@+id/button"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_msg" />
<Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onReturnMessageTest"
android:text="@string/return_test"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_msg" />
</androidx.constraintlayout.widget.ConstraintLayout>
GetMessage.java
package host.skyone.intent;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.widget.TextView;
public class GetMessage extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_get_message);
Intent intent = getIntent();
String message = intent.getStringExtra("message");
((TextView)findViewById(R.id.showMessage)).setText(message);
}
}
activity_get_message.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".GetMessage">
<TextView
android:id="@+id/tips"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/tips"
app:layout_constraintBottom_toTopOf="@+id/showMessage"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/showMessage"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
ReturnMessage.java
package host.skyone.intent;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
public class ReturnMessage extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_return_message);
}
public void onReturnMessage(View view) {
String message = ((EditText)findViewById(R.id.edit_query)).getText().toString();
Intent intent = new Intent(this, MainActivity.class);
intent.putExtra("message", message);
setResult(52021, intent);
finish();
}
}
activity_return_message.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".ReturnMessage">
<EditText
android:id="@+id/edit_query"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:autofillHints="Hello world!"
android:hint="@string/hint"
android:inputType="text"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/textView"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/return_message"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onReturnMessage"
android:text="@string/return_message"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/edit_query" />
<TextView
android:id="@+id/textView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="40dp"
android:text="@string/TextView"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="host.skyone.intent">
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.Intent">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".GetMessage"
android:parentActivityName=".MainActivity">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".MainActivity" />
</activity>
<activity
android:name=".ReturnMessage"
android:parentActivityName=".MainActivity">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".MainActivity" />
</activity>
</application>
</manifest>
strings.xml
<resources>
<string name="app_name">intent</string>
<string name="TextView">输入一些东西</string>
<string name="return_message">返回消息</string>
<string name="return_test">测试返回消息</string>
<string name="send_message">发送消息</string>
<string name="hint">message</string>
<string name="tips">接收 到了以下信息:</string>
</resources>