我正在尝试从一个“活动”发送客户类的对象,并在另一个“”中显示它。
客户类别的代码:
public class Customer {
private String firstName, lastName, address;
int age;
public Customer(String fname, String lname, int age, String address) {
firstName = fname;
lastName = lname;
age = age;
address = address;
}
public String printValues() {
String data = null;
data = "First Name :" + firstName + " Last Name :" + lastName
+ " Age : " + age + " Address : " + address;
return data;
}
}
我想将其对象从一个“活动”发送到另一个“,然后在另一个活动”上显示数据。
我怎样才能做到这一点?
你可以尝试使用该类。限制是它不能在一个过程之外使用。
一项活动:
final Object obj1 = new Object();
final Intent in = new Intent();
in.putExtra(EXTRA_TEST, new Sharable(obj1));
其他活动:
final Sharable s = in.getExtras().getParcelable(EXTRA_TEST);
final Object obj2 = s.obj();
public final class Sharable implements Parcelable {
private Object mObject;
public static final Parcelable.Creator < Sharable > CREATOR = new Parcelable.Creator < Sharable > () {
public Sharable createFromParcel(Parcel in ) {
return new Sharable( in );
}
@Override
public Sharable[] newArray(int size) {
return new Sharable[size];
}
};
public Sharable(final Object obj) {
mObject = obj;
}
public Sharable(Parcel in ) {
readFromParcel( in );
}
Object obj() {
return mObject;
}
@Override
public int describeContents() {
return 0;
}
@Override
public void writeToParcel(final Parcel out, int flags) {
final long val = SystemClock.elapsedRealtime();
out.writeLong(val);
put(val, mObject);
}
private void readFromParcel(final Parcel in ) {
final long val = in .readLong();
mObject = get(val);
}
/////
private static final HashMap < Long, Object > sSharableMap = new HashMap < Long, Object > (3);
synchronized private static void put(long key, final Object obj) {
sSharableMap.put(key, obj);
}
synchronized private static Object get(long key) {
return sSharableMap.remove(key);
}
}
你可以尝试使用该类。限制是它不能在一个过程之外使用。
一项活动:
final Object obj1 = new Object();
final Intent in = new Intent();
in.putExtra(EXTRA_TEST, new Sharable(obj1));
其他活动:
final Sharable s = in.getExtras().getParcelable(EXTRA_TEST);
final Object obj2 = s.obj();
public final class Sharable implements Parcelable {
private Object mObject;
public static final Parcelable.Creator < Sharable > CREATOR = new Parcelable.Creator < Sharable > () {
public Sharable createFromParcel(Parcel in ) {
return new Sharable( in );
}
@Override
public Sharable[] newArray(int size) {
return new Sharable[size];
}
};
public Sharable(final Object obj) {
mObject = obj;
}
public Sharable(Parcel in ) {
readFromParcel( in );
}
Object obj() {
return mObject;
}
@Override
public int describeContents() {
return 0;
}
@Override
public void writeToParcel(final Parcel out, int flags) {
final long val = SystemClock.elapsedRealtime();
out.writeLong(val);
put(val, mObject);
}
private void readFromParcel(final Parcel in ) {
final long val = in .readLong();
mObject = get(val);
}
/////
private static final HashMap < Long, Object > sSharableMap = new HashMap < Long, Object > (3);
synchronized private static void put(long key, final Object obj) {
sSharableMap.put(key, obj);
}
synchronized private static Object get(long key) {
return sSharableMap.remove(key);
}
}
根据我的经验,有三种主要的解决方案,各有其缺点和优点:
实施Parcelable实现可串行化使用某种轻量级事件总线库(例如,Greenrobot的EventBus或Square的Otto)
Parcelable-快速且符合Android标准,但它有很多样板代码,并且需要硬编码字符串以供在提取意图值(非强类型)时参考。
可序列化-接近于零样板,但这是最慢的方法,并且在从意图中提取值(非强类型)时还需要硬编码字符串。
事件总线-零样板,最快的方法,不需要硬编码字符串,但它需要额外的依赖项(虽然通常很轻,约40 KB)
我发布了这三种方法的非常详细的比较,包括效率基准。
我一直想知道为什么这不能像调用其他活动的方法一样简单。我最近写了一个实用程序库,使它几乎如此简单。你可以在这里查看(https://github.com/noxiouswinter/gnlib_android/wiki/gnlauncher).
GNLauncher使从另一个“活动”等向“活动”发送对象/数据变得简单,就像调用该“活动”中的一个函数并将所需数据作为参数一样。它引入了类型安全性,并消除了所有必须串行化、使用字符串键附加到意图以及在另一端撤消的麻烦。
用法
使用要在要启动的“活动”上调用的方法定义接口。
public interface IPayload {
public void sayHello(String name, int age);
}
在要启动的“活动”上实现上述界面。当活动准备就绪时,也通知GNLauncher。
public class Activity_1 extends Activity implements IPayload {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//Notify GNLauncher when the Activity is ready.
GNLauncher.get().ping(this);
}
@Override
public void sayHello(String name, int age) {
Log.d("gnlib_test", "Hello " + name + "! \nYour age is: " + age);
}
}
在另一个“活动”中,获取上述“活动”的代理,并使用所需参数调用任何方法。
public class Activity_2 extends Activity {
public void onClick(View v) {
((IPayload)GNLauncher.get().getProxy(this, IPayload.class, Activity_1.class)).sayHello(name, age);
}
}
将启动第一个活动,并使用所需参数调用方法。
先决条件
请参阅https://github.com/noxiouswinter/gnlib_android/wiki#prerequisites有关如何添加依赖项的信息。
我创建了一个保存临时对象的单例助手类。
public class IntentHelper {
private static IntentHelper _instance;
private Hashtable<String, Object> _hash;
private IntentHelper() {
_hash = new Hashtable<String, Object>();
}
private static IntentHelper getInstance() {
if(_instance==null) {
_instance = new IntentHelper();
}
return _instance;
}
public static void addObjectForKey(Object object, String key) {
getInstance()._hash.put(key, object);
}
public static Object getObjectForKey(String key) {
IntentHelper helper = getInstance();
Object data = helper._hash.get(key);
helper._hash.remove(key);
helper = null;
return data;
}
}
不要将对象放在Intent中,而是使用IntentHelper:
IntentHelper.addObjectForKey(obj, "key");
在新的“活动”中,您可以获取对象:
Object obj = (Object) IntentHelper.getObjectForKey("key");
请记住,一旦加载,对象将被删除,以避免不必要的引用。