13

I am trying to pass an ArrayList of objects through an intent but cannot get it to work. Here is what I have:

public class QuestionView extends Activity {

    //variables and other methods...

    public void endQuiz() {
        Intent intent = new Intent(QuestionView.this, Results.class);
        intent.putExtra("correctAnswers", correctAnswers);
        intent.putExtra("wrongAnswers", wrongAnswers);
        intent.putParcelableArrayListExtra("queries", queries);
        startActivity(intent);
    }
}

Intents are being received here:

public class Results extends Activity {

    int cAnswers;
    int wAnswers;
    ArrayList<Question> qs;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.resultsmain);

        cAnswers = getIntent().getIntExtra("correctAnswers", -1);
        wAnswers = getIntent().getIntExtra("wrongAnswers", -1);

        qs = getIntent().getParcelableArrayListExtra("queries");

                    //more code...
    }
}

The two ints, correctAnswer and wrongAnswers, are being received and I can use them. The ArrrayList is not coming through. No errors on in the endQuiz() method but the 'qs = getIntent().getParcelableArrayListExtra("queries");' is throwing an error and saying "Bound Mismatch."

Any help on this is appreciated!

Question class:

public class Question {
    String a1;
    String a2;
    String a3;
    String a4;
    int correctAnswer;
    String query;
    int selectedAnswer;
    boolean correctness;

    public Question() {
    }

    public Question(String a1, String a2, String a3, String a4, int correctAnswer, String query, int selectedAnswer, boolean correctness) {
        this.a1 = a1;
        this.a2 = a2;
        this.a3 = a3;
        this.a4 = a4;
        this.correctAnswer = correctAnswer;
        this.query = query;
        this.selectedAnswer = selectedAnswer;
        this.correctness = correctness;
    }
    }
7
  • 1
    Does your Question class implement Parcelable? Commented Dec 4, 2012 at 18:22
  • 3
    no ... thats why he is casting it ... (ArrayList<? extends Parcelable>) queries); :) which certainly will not help Commented Dec 4, 2012 at 18:23
  • Can we see what the type of your queries ArrayList actually looks like? I mean the class... Commented Dec 4, 2012 at 18:25
  • @Selvin, but he's not getting class cast exception which is curious... Commented Dec 4, 2012 at 18:28
  • 1
    java generics ... similar code will not compile in C# but in java ... ArrayList<Object> a = null; ArrayList<? extends Parcelable> b = (ArrayList<? extends Parcelable>) a; works ... with only warrning Unchecked cast from ArrayList<Object> to ArrayList<? extends Parcelable> .... in java at runtime you don't know generic type Commented Dec 4, 2012 at 18:30

2 Answers 2

27

You must change your Question class to actually implement Parcelable. The Parcelable interface can be confusing at first... but hang in there.

There are two Parcelable methods that you should focus on:

  • writeToParcel() which converts your class into a Parcel object.
  • Question(Parcel in) which converts a Parcel object back into usable instance of your class.

You can safely cut & paste the other Parcelable information that I marked.

For the sake of simplicity I will only use part of your Question class:

public class Question implements Parcelable {
    String a1;
    String a2;
    ...

    public Question(String a1, String a1) {
        this.a1 = a1;
        this.a2 = a2;
    }

    // Your existing methods go here. (There is no need for me to re-write them.) 

    // The following methods that are required for using Parcelable
    private Question(Parcel in) {
        // This order must match the order in writeToParcel()
        a1 = in.readString();
        a2 = in.readString();
        // Continue doing this for the rest of your member data
    }

    public void writeToParcel(Parcel out, int flags) {
        // Again this order must match the Question(Parcel) constructor
        out.writeString(a1);
        out.writeString(a2);
        // Again continue doing this for the rest of your member data
    }

    // Just cut and paste this for now
    public int describeContents() {
        return 0;
    }

    // Just cut and paste this for now
    public static final Parcelable.Creator<Question> CREATOR = new Parcelable.Creator<Question>() {
        public Question createFromParcel(Parcel in) {
            return new Question(in);
        }

        public Question[] newArray(int size) {
            return new Question[size];
        }
    };
}

Now change how you put queries into your Intent extras.

intent.putParcelableArrayListExtra("queries", queries);

The way you read the Parcelable array is perfect as it is.

Sign up to request clarification or add additional context in comments.

4 Comments

Thank you for that detailed answer Sam! I did not give you all my code so I might have thrown you off course. I edited my opening post with all my classes. Now with that, should I implement Parcelable and add all those other methods in QuestionView or Question?
You only want to pass an ArrayList of Questions, so only the Question class should implement Parcelable
Oh man it works! This is the furthest I have been in the 2 months I have been working on this. Huge milestone today! Thank you again Sam. :)
@Sam how to parcel a bitmap?
7

In order to be able to deliver an ArrayList as part of an Intent, your type must implement Parcelable. Judging by the fact you had to cast your List to (ArrayList<? extends Parcelable>), you didn't do this. If you had, you could simply have:

class Foo implements Parcelable {
//implementation here
}
ArrayList<Foo> foos = new ArrayList<Foo>();
new Intent().putParcelableArrayListExtra("foos", foos); //no need to cast

1 Comment

It isn't necessary to implement Parcelable but using Serializable for this involves a performance penalty, so you actually should use Parcelable.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.