《第一行代码》第二版 学习总结34 Intent传递对象两种方式
最近利用下班时间,找了看什么书比较适合初学android的朋友,很多人推荐了这本书,于是就买了一本,感觉看书,思考,动手,再思考和总结这样过程还是很有必要的,于是就打算把自己学习的东西简单的总结一下;方便自己以后查找,也有利于学习的巩固。在这里首先要感谢一下书籍的作者——郭霖前辈。
这部分在书中都是比较靠后的位置了,也算是比较零散的知识点,我今天就先在这里简单总结一下;我们学过也是用过通过Intent的putExtra()方法实现传递String和int类型数据了,今天我们就来介绍一下如何通过Intent传递对象给其他组件。
1,实现方式
在使用Intent传递对象,我们这里有两种实现方式,一种是对象实现Serializable,另一种是实现Parcelable;其实序列化这个词在java语言学习中是不陌生的。关于两个接口的详细资料可点击查询(Serializable,Parcelable)。下面就来看看具体的实现步骤:
(1)Serializable方式
第一步:把要传递的对象类实现该接口
第二步:新建一个对象,通过Intent的putExtra()方法把对象添加到意图
第三步:在接受组件里面,使用getIntent().getSerializableExtra()获取该对象
(2)Parcelable方式
第一步:把要传递的对象类实现该接口
第二步:重写里面的几个方法(writeToParcel(),describeContents()),添加一个Parcelable.Creator<自定义类名>类型的常量CREATOR,重写里面的createFromParcel()和newArray()方法
第三步:新建一个对象,通过Intent的putExtra()方式吧对象添加到意图
第四步:在接受组件里面,使用getIntent().getParcelableExtra()获取该对象
分析:相较而言,第一种方式更加简单,但是常用的却是第二种,因为它更加的灵活,效率更高。很显然,第一种我们对对象的序列化是不可控的,也就是这种方式会把整个对象序列化;而第二种方式不一样,我们在方法实现的时候有一个对象到序列化数据(writeToParcel())和序列化数据到对象(createFromParcel())的可控过程。
2,代码示例
MainActivity.java代码:
package com.hfut.sendobjbyintent; import android.content.Intent; import android.support.v7.app.ActionBar; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.view.View; public class MainActivity extends AppCompatActivity { public static final int SERIALIZABLEFLAG = 1; public static final int PARCELABLEFLAG = 2; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //隐藏ActionBar ActionBar actionBar = getSupportActionBar(); if (actionBar != null) { actionBar.hide(); } } public void sendBySerializable(View view) { Intent intent = new Intent(this, SerializableActivity.class); intent.putExtra("ObjData", (MySerializable)getObject(SERIALIZABLEFLAG)); startActivity(intent); } public void sendByParcelable(View view) { Intent intent = new Intent(this, ParcelableActivity.class); intent.putExtra("ObjData", (MyParcelable)getObject(PARCELABLEFLAG)); startActivity(intent); } private Object getObject(int flag) { Object obj=null; String name="why"; int age=26; String sex="male"; if(flag==1){ MySerializable mySerializable = new MySerializable(); mySerializable.setAge(age); mySerializable.setName(name); mySerializable.setSex(sex); obj=mySerializable; } else if(flag==2){ MyParcelable myParcelable=new MyParcelable(); myParcelable.setAge(age); myParcelable.setName(name); myParcelable.setSex(sex); obj=myParcelable; } return obj; } }
MyParcelable.java代码:
package com.hfut.sendobjbyintent; import android.os.Parcel; import android.os.Parcelable; /** * author:why * created on: 2018/3/25 10:20 * description: */ public class MyParcelable implements Parcelable { private String name; private int age; private String sex; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getSex() { return sex; } public void setSex(String sex) { this.sex = sex; } @Override public int describeContents() { return 0; } @Override public void writeToParcel(Parcel dest, int flags) { //写入到Parcel dest.writeString(name); dest.writeInt(age); dest.writeString(sex); } public static final Parcelable.Creator<MyParcelable> CREATOR=new Parcelable.Creator<MyParcelable>(){ @Override public MyParcelable createFromParcel(Parcel source) { //从Parcel中读取生成对象;顺序和上面的dest的写入顺序要保持一致 MyParcelable myParcelable=new MyParcelable(); myParcelable.name=source.readString(); myParcelable.age=source.readInt(); myParcelable.sex=source.readString(); return myParcelable; } @Override public MyParcelable[] newArray(int size) { return new MyParcelable[size]; } }; }
MySerializable.java代码:
package com.hfut.sendobjbyintent; import java.io.Serializable; /** * author:why * created on: 2018/3/25 10:19 * description: */ public class MySerializable implements Serializable { private String name; private int age; private String sex; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getSex() { return sex; } public void setSex(String sex) { this.sex = sex; } }
ParcelableActivity.java代码:
package com.hfut.sendobjbyintent; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.widget.TextView; public class ParcelableActivity extends AppCompatActivity { TextView objContent; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_parcelable); objContent=findViewById(R.id.objContentParcel); } public void getDataParcel(View view){ MyParcelable myParcelable= (MyParcelable) getIntent().getParcelableExtra("ObjData"); StringBuilder stringBuilder=new StringBuilder(); stringBuilder.append("对象数据\n姓名: "+myParcelable.getName()+"\n"+ "年龄: "+myParcelable.getAge()+"\n性别: "+myParcelable.getSex()); objContent.setText(stringBuilder.toString()); } }
SerializableActivity.java代码:
package com.hfut.sendobjbyintent; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.widget.TextView; public class SerializableActivity extends AppCompatActivity { private TextView objContent; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_serializable); objContent=findViewById(R.id.objContentSerial); } public void getDataSerializable(View view){ MySerializable mySerializable= (MySerializable) getIntent().getSerializableExtra("ObjData"); StringBuilder stringBuilder=new StringBuilder(); stringBuilder.append("对象数据\n姓名: "+mySerializable.getName()+"\n"+ "年龄: "+mySerializable.getAge()+"\n性别: "+mySerializable.getSex()); objContent.setText(stringBuilder.toString()); } }
activity_main.xml代码:
<?xml version="1.0" encoding="utf-8"?> <LinearLayout 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" android:orientation="vertical" tools:context="com.hfut.sendobjbyintent.MainActivity"> <TextView android:textSize="20dp" android:textColor="@color/colorPrimary" android:layout_marginTop="30dp" android:gravity="center_horizontal" android:text="开启你的Intent传递对象数据之旅吧" android:layout_width="match_parent" android:layout_height="wrap_content" /> <Button android:layout_marginTop="30dp" android:textSize="20dp" android:text="Serializable方式传递对象" android:onClick="sendBySerializable" android:textAllCaps="false" android:layout_width="match_parent" android:layout_height="wrap_content" /> <Button android:textSize="20dp" android:layout_marginTop="10dp" android:text="Parcelable方式传递对象" android:onClick="sendByParcelable" android:textAllCaps="false" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout>
activity_parcelable.xml代码:
<?xml version="1.0" encoding="utf-8"?> <LinearLayout 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" android:orientation="vertical" tools:context="com.hfut.sendobjbyintent.ParcelableActivity"> <TextView android:textSize="20dp" android:id="@+id/objContentParcel" android:layout_marginTop="50dp" android:layout_width="match_parent" android:layout_height="150dp" /> <Button android:layout_marginTop="30dp" android:onClick="getDataParcel" android:layout_width="match_parent" android:layout_height="wrap_content" android:textSize="20dp" android:text="获取对象数据"/> </LinearLayout>
avtivity_serializable代码:
<?xml version="1.0" encoding="utf-8"?> <LinearLayout 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" android:orientation="vertical" tools:context="com.hfut.sendobjbyintent.SerializableActivity"> <TextView android:textSize="20dp" android:id="@+id/objContentSerial" android:layout_marginTop="30dp" android:layout_width="match_parent" android:layout_height="150dp" /> <Button android:layout_marginTop="10dp" android:onClick="getDataSerializable" android:layout_width="match_parent" android:layout_height="wrap_content" android:textSize="20dp" android:text="获取对象数据"/> </LinearLayout>
styles.xml代码:
<resources> <!-- Base application theme. --> <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> <!-- Customize your theme here. --> <item name="colorPrimary">@color/colorPrimary</item> <item name="colorPrimaryDark">@color/colorPrimaryDark</item> <item name="colorAccent">@color/colorAccent</item> </style> <style name="NoActionBarAppTheme" parent="Theme.AppCompat.Light.NoActionBar"> <!-- Customize your theme here. --> <item name="colorPrimary">@color/colorPrimary</item> <item name="colorPrimaryDark">@color/colorPrimaryDark</item> <item name="colorAccent">@color/colorAccent</item> </style> </resources>
主配置文件AndroidManifest.xml代码:
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.hfut.sendobjbyintent"> <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/AppTheme"> <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=".SerializableActivity" android:theme="@style/NoActionBarAppTheme"/> <activity android:name=".ParcelableActivity" android:theme="@style/NoActionBarAppTheme"></activity> </application> </manifest>
3,运行结果
第一步:运行程序
第二步:点击“Serializable方式传递对象”按钮
第三步:点击“获取对象数据”按钮
第四步:返回,点击“Parcelable方式传递对象”按钮
第五步:点击“获取对象数据”按钮
总结:这个示例里面就是简单的演示两种方式传递对象,其实很简单的,我处理的时候为了巩固其他的知识做的看起来累赘了一些;里面通过两种方式去除了ActionBar(具体查看);创建对象的时候,我是通过两个常量来定义获取不同的对象类型的。自己可以简单分析一下代码。好了,先写到这里吧,其实我也是刚刚加班回来,还没有吃饭了,先去做饭啦。。。