Próbuję rozszerzyć HashMap jako Parcelable i mam składnię do kompilacji, jednak w czasie wykonywania wyrzuca wyjątek i zwraca wskaźnik zerowy próbujący un-marszałka danych.Czy jest możliwe utworzenie mapy HashMap na Androidzie?
Nadawca musi przesłać do (Parcelable), aby rozwiązać niejednoznaczność, jednak odbiorca skarży się, że oczekuje się, że będzie Parcelable, ale odnalazł HashMap.
Czy ktoś odniósł sukces? Czy moja składnia jest nieprawidłowa? Czy istnieje lepsze rozwiązanie?
Poniżej znajduje się kod:
- HomeActivity.java - nadawca
- ContentViewActivity.java - odbiornik
- ContentItemSimple.java - jak sugeruje jego nazwa (okłady String i Integer)
- ContentItemCollection.java - to HashMap
HomeActivity.java
package com.mobibob.android.studyparceable;
import java.util.HashMap;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.os.Parcel;
import android.os.Parcelable;
import android.text.format.Time;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
public class HomeActivity extends Activity implements OnClickListener {
private static final String TAG = "HomeActivity";
private ContentItemSimple mContentItemSimple = null;
private ContentItemContainer mContentItemContainer = null;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.home);
Button click = (Button) findViewById(R.id.button_clickit);
click.setOnClickListener(this);
mContentItemSimple = new ContentItemSimple();
mContentItemSimple.name = "mobibob";
mContentItemSimple.year = 2010;
String value = "value";
Time nowTime = new Time();
nowTime.setToNow();
mContentItemContainer = new ContentItemContainer();
mContentItemContainer.put("string", new String("baseball is great!"));
mContentItemContainer.put("integer", new Integer(1234));
// mContentItemContainer.put("boolean", new Boolean(true));
// mContentItemContainer.put("date", nowTime);
// mContentItemContainer.put("parcel", new Bundle());
Log.d(TAG, "..... " + mContentItemContainer.toString());
}
@Override
public void onClick(View v) {
Intent i = new Intent(getBaseContext(), ContentViewActivity.class);
i.putExtra(ContentItemSimple.EXTRA_CONTENT_DETAIL, mContentItemSimple);
i.putExtra(ContentItemContainer.EXTRA_CONTENT_CONTAINER, (Parcelable) mContentItemContainer);
startActivityForResult(i, 0);
}
}
ContentViewActivity
package com.mobibob.android.studyparceable;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
import com.mobibob.android.studyparceable.ContentItemSimple;
public class ContentViewActivity extends Activity implements OnClickListener {
private static final String TAG = "ContentViewActivity";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.content_view);
Button gohome = (Button) findViewById(R.id.button_gohome);
gohome.setOnClickListener(this);
ContentItemSimple ci = null;
ContentItemContainer cx = null;
try {
ci = getIntent().getParcelableExtra(ContentItemSimple.EXTRA_CONTENT_DETAIL);
Log.i(TAG, "ci = " + ci.toString());
cx = getIntent().getParcelableExtra(ContentItemContainer.EXTRA_CONTENT_CONTAINER);
Log.i(TAG, "cx = " + cx.toString());
TextView tvName = (TextView) findViewById(R.id.ci_name);
tvName.setText(ci.name);
TextView tvYear = (TextView) findViewById(R.id.ci_year);
tvYear.setText(String.format("%d", ci.year));
} catch (Exception e) {
Log.e(TAG, e.toString());
e.printStackTrace();
}
}
@Override
public void onClick(View v) {
finish();
}
}
ContentItemSimple.java
package com.mobibob.android.studyparceable;
import android.os.Parcel;
import android.os.Parcelable;
import android.util.Log;
public class ContentItemSimple implements Parcelable {
public static final String TAG = "ContentItem";
public static final String EXTRA_CONTENT_DETAIL = "contentDetail";
public String name = "name";
public Integer year = Integer.MIN_VALUE;
ContentItemSimple() {
name = new String("");
year = new Integer(Integer.MIN_VALUE);
}
ContentItemSimple(Parcel in) {
try {
name = in.readString();
year = in.readInt();
} catch (Exception e) {
Log.e(TAG, e.toString());
e.printStackTrace();
}
}
@Override
public String toString() {
return String.format("name=%s age=%d", name, year);
}
@Override
public int describeContents() {
return 0;
}
@Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeString(name);
dest.writeInt(year);
}
public static final Parcelable.Creator<ContentItemSimple> CREATOR = new Parcelable.Creator<ContentItemSimple>() {
public ContentItemSimple createFromParcel(Parcel in) {
return new ContentItemSimple(in);
}
public ContentItemSimple[] newArray(int size) {
return new ContentItemSimple[size];
}
};
}
ContentItemContainer.java
package com.mobibob.android.studyparceable;
import java.util.HashMap;
import java.util.Iterator;
import android.os.Parcel;
import android.os.Parcelable;
public class ContentItemContainer extends HashMap<String, Object> implements Parcelable {
/**
* Container for wddx 'struct' elements.
*/
private static final long serialVersionUID = 1L;
// public String name = "?";
// public String value = "?";
public static final String EXTRA_CONTENT_DETAIL = "contentDetail";
public static final String EXTRA_CONTENT_CONTAINER = "contentContainer";
public static final String EXTRA_CONTENTDETAIL_NAME = "name";
public static final String EXTRA_CONTENTDETAIL_VALUE = "value";
// private static HashMap<String, Object> map = new HashMap<String, Object>();
ContentItemContainer() {
super();
}
ContentItemContainer(Parcel in) {
in.readMap(this, ContentItemContainer.class.getClassLoader());
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder("");
Integer x = 0;
Iterator<HashMap.Entry<String, Object>> it = this.entrySet().iterator();
while (it.hasNext()) {
HashMap.Entry<String, Object> pairs = (HashMap.Entry<String, Object>) it.next();
x++;
sb.append("\n"+x.toString()+": ").append("name=").append(pairs.getKey()).append(" value=").append(pairs.getValue().toString());
}
return sb.toString();
}
@Override
public int describeContents() {
return 0;
}
@Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeMap(this);
}
public static final Parcelable.Creator<ContentItemContainer> CREATOR = new Parcelable.Creator<ContentItemContainer>() {
public ContentItemContainer createFromParcel(Parcel in) {
return new ContentItemContainer(in);
}
public ContentItemContainer[] newArray(int size) {
return new ContentItemContainer[size];
}
};
}
Dlaczego nie użyć 'Bundle' zamiast' HashMap'? – CommonsWare
Pomyślałem o tym, więc pozwól mi zmienić i zobaczyć, czy dostaję to, czego potrzebuję. Tymczasem czy to może działać? Wiem, że dokumentacja stwierdza, że Parcelable nie ma być serializerem "ogólnego przeznaczenia", ale myślałem, że jest to nadal w rozsądnym zakresie. – mobibob
Przełączanie na zestaw wygląda tak, jak będzie działać w przypadku mojego projektu. Tymczasem chciałbym znać odpowiedź na to pytanie w obecnej formie. (Wierzę, że odpowiedź będzie oświecająca w odniesieniu do systemu operacyjnego Android i jego SDK.) – mobibob