Activity 在使用 Intent 发送时没有收到 List<Object>

Activity does not receive List<Object> when sending it with Intent

我目前正在努力发送一个包含列表的对象的意图。 基本上我可以将正确的数据发送到另一个 activity,但我无法获取数据中的列表。对不起,我真的不知道怎么形容。

事实是,我可以通过调用例如recipes.get(0).getIngredients() 但在 RecipeDetailsActivity 中,由于列表为空,我收到错误消息。 (而且我也不知道如何在 DetailsActivity 中获取对象的正确索引)

提前致谢!

Recipe.java

public class Recipe implements Parcelable {

    @SerializedName("id")
    @Expose
    private Integer mId;
    @SerializedName("name")
    @Expose
    private String mName;
    @SerializedName("ingredients")
    @Expose
    private List < Ingredient > mIngredients = null;
    @SerializedName("steps")
    @Expose
    private List < Step > mSteps = null;
    @SerializedName("servings")
    @Expose
    private Integer mServings;
    @SerializedName("image")
    @Expose
    private String mImage;

    protected Recipe(Parcel in ) {
        if ( in .readByte() == 0) {
            mId = null;
        } else {
            mId = in .readInt();
        }
        mName = in .readString();
        if ( in .readByte() == 0) {
            mServings = null;
        } else {
            mServings = in .readInt();
        }
        mImage = in .readString();
    }

    public static final Creator < Recipe > CREATOR = new Creator < Recipe > () {
        @Override
        public Recipe createFromParcel(Parcel in ) {
            return new Recipe( in );
        }

        @Override
        public Recipe[] newArray(int size) {
            return new Recipe[size];
        }
    };

    public Integer getId() {
        return mId;
    }

    public void setId(Integer id) {
        mId = id;
    }

    public String getName() {
        return mName;
    }

    public void setName(String name) {
        mName = name;
    }

    public List < Ingredient > getIngredients() {
        return mIngredients;
    }

    public void setIngredients(List < Ingredient > ingredients) {
        mIngredients = ingredients;
    }

    public List < Step > getSteps() {
        return mSteps;
    }

    public void setSteps(List < Step > steps) {
        mSteps = steps;
    }

    public Integer getServings() {
        return mServings;
    }

    public void setServings(Integer servings) {
        mServings = servings;
    }

    public String getImage() {
        return mImage;
    }

    public void setImage(String image) {
        mImage = image;
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        if (mId == null) {
            dest.writeByte((byte) 0);
        } else {
            dest.writeByte((byte) 1);
            dest.writeInt(mId);
        }
        dest.writeString(mName);
        if (mServings == null) {
            dest.writeByte((byte) 0);
        } else {
            dest.writeByte((byte) 1);
            dest.writeInt(mServings);
        }
        dest.writeString(mImage);
    }
}

Ingredient.java

public class Ingredient {

    @SerializedName("quantity")
    @Expose
    private Double mQuantity;
    @SerializedName("measure")
    @Expose
    private String mMeasure;
    @SerializedName("ingredient")
    @Expose
    private String mIngredient;

    public Double getQuantity() {
        return mQuantity;
    }

    public void setQuantity(Double quantity) {
        mQuantity = quantity;
    }

    public String getMeasure() {
        return mMeasure;
    }

    public void setMeasure(String measure) {
        mMeasure = measure;
    }

    public String getIngredient() {
        return mIngredient;
    }

    public void setIngredient(String ingredient) {
        mIngredient = ingredient;
    }
}

RecipeActivity

public class RecipeActivity extends AppCompatActivity implements RecipeAdapter.RecipeAdapterOnClickHandler {
    private static final String TAG = RecipeActivity.class.getSimpleName();

    @BindView(R.id.recipe_recycler_view)
    RecyclerView mRecyclerView;

    private RecipeAdapter mRecipeAdapter;
    private List < Recipe > recipes;

    public static final String MY_RECIPE = "myRecipe";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_recipe);

        RecipeService service = RecipeClient.getRetrofit().create(RecipeService.class);

        Call < List < Recipe >> call = service.getAllRecipes();
        call.enqueue(new Callback < List < Recipe >> () {
            @Override
            public void onResponse(Call < List < Recipe >> call, Response < List < Recipe >> response) {
                if (response.isSuccessful()) {
                    recipes = response.body();
                    generateDataList(recipes);
                }
            }

            @Override
            public void onFailure(Call < List < Recipe >> call, Throwable t) {
                Toast.makeText(RecipeActivity.this, "Something went wrong...Please try later!", Toast.LENGTH_SHORT).show();
                Log.v(TAG, t.toString());
            }
        });
    }

    private void generateDataList(List < Recipe > recipeList) {
        ButterKnife.bind(this);
        mRecipeAdapter = new RecipeAdapter(this, recipeList, RecipeActivity.this);
        RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(RecipeActivity.this);
        mRecyclerView.setLayoutManager(layoutManager);
        mRecyclerView.setAdapter(mRecipeAdapter);
    }


    @Override
    public void onClick(int adapterPosition) {
        Context context = this;
        Class detailClass = RecipeDetailsActivity.class;

        Intent detailsIntent = new Intent(context, detailClass);
        detailsIntent.putExtra(MY_RECIPE, recipes.get(adapterPosition));
        startActivity(detailsIntent);
    }
}

RecipeDetailsActivity

public class RecipeDetailsActivity extends AppCompatActivity implements IngredientAdapter.IngredientAdapterOnClickHandler {
    private static final String TAG = RecipeDetailsActivity.class.getSimpleName();

    private Recipe recipes;
    private List < Recipe > recipeList;

    private String recipeName;
    private String ingredient;
    private Double quantity;
    private String measure;
    private List < Ingredient > ingredientList = new ArrayList < > ();
    IngredientAdapter mAdapter;

    @Nullable
    @BindView(R.id.ingredients)
    TextView ingredientsTV;
    @Nullable
    @BindView(R.id.quantity)
    TextView quantityTV;
    @BindView(R.id.recipe_details_rv)
    RecyclerView mRecyclerView;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_recipe_details);

        Intent intentToCatch = getIntent();
        recipes = intentToCatch.getParcelableExtra(RecipeActivity.MY_RECIPE);

        recipeName = recipes.getName();
        ingredientList = recipes.getIngredients();
        if (ingredientList != null) {
            ingredient = ingredientList.get(0).getIngredient();
            quantity = ingredientList.get(0).getQuantity();
            measure = ingredientList.get(0).getMeasure();
        } else {
            Log.v(TAG, "FAILING LOADING INGREDIENTSLIST");
        }
        setTitle(recipeName);

        ButterKnife.bind(this);

        mAdapter = new IngredientAdapter(this, ingredientList, RecipeDetailsActivity.this);
        RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(RecipeDetailsActivity.this);
        mRecyclerView.setLayoutManager(layoutManager);
        mRecyclerView.setAdapter(mAdapter);

    }

    @Override
    public void onClick(int adapterPosition) {

    }
}

RecipeAdapter

public class RecipeAdapter extends RecyclerView.Adapter < RecipeAdapter.RecipeAdapterViewHolder > {

    private List < Recipe > mRecipeList;
    private Context mContext;
    private RecipeAdapterOnClickHandler mOnClickHandler;

    public RecipeAdapter(Context context, List < Recipe > recipeList, RecipeAdapterOnClickHandler onClickHandler) {
        mContext = context;
        mRecipeList = recipeList;
        mOnClickHandler = onClickHandler;
    }

    public interface RecipeAdapterOnClickHandler {
        void onClick(int adapterPosition);
    }

    public class RecipeAdapterViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
        @BindView(R.id.recipe_name)
        TextView mRecipeName;

        public RecipeAdapterViewHolder(@NonNull View itemView) {
            super(itemView);
            itemView.setOnClickListener(this);
            ButterKnife.bind(this, itemView);
        }

        @Override
        public void onClick(View v) {
            int adapterPosition = getAdapterPosition();
            mOnClickHandler.onClick(adapterPosition);
        }

    }

    @NonNull
    @Override
    public RecipeAdapterViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        LayoutInflater layoutInflater = LayoutInflater.from(parent.getContext());
        View view = layoutInflater.inflate(R.layout.recipe_list_item, parent, false);
        return new RecipeAdapterViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull RecipeAdapterViewHolder holder, int position) {
        holder.mRecipeName.setText(mRecipeList.get(position).getName());
    }

    @Override
    public int getItemCount() {
        if (mRecipeList == null) {
            return 0;
        }
        return mRecipeList.size();
    }
}

成分适配器

public class IngredientAdapter extends RecyclerView.Adapter < IngredientAdapter.IngredientAdapterViewHolder > {

    private List < Ingredient > mIngredient;
    private Context mContext;
    private IngredientAdapterOnClickHandler mOnClickHandler;

    public IngredientAdapter(Context context, List < Ingredient > ingredientList, IngredientAdapterOnClickHandler onClickHandler) {
        mContext = context;
        mIngredient = ingredientList;
        mOnClickHandler = onClickHandler;
    }

    public interface IngredientAdapterOnClickHandler {
        void onClick(int adapterPosition);
    }

    public class IngredientAdapterViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
        @BindView(R.id.ingredients)
        TextView ingredientTextView;
        @BindView(R.id.step_description)
        TextView stepsDescriptionTextView;
        @BindView(R.id.quantity)
        TextView quantityDescriptionTextView;

        public IngredientAdapterViewHolder(@NonNull View itemView) {
            super(itemView);
            ButterKnife.bind(this, itemView);
        }

        @Override
        public void onClick(View v) {
            int adapterPosition = getAdapterPosition();
            mOnClickHandler.onClick(adapterPosition);
        }
    }

    @NonNull
    @Override
    public IngredientAdapterViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        LayoutInflater layoutInflater = LayoutInflater.from(parent.getContext());
        View view = layoutInflater.inflate(R.layout.recipe_details_list_item, parent, false);
        return new IngredientAdapterViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull IngredientAdapterViewHolder holder, int position) {
        holder.ingredientTextView.setText(mIngredient.get(position).getIngredient());
        holder.stepsDescriptionTextView.setText(mIngredient.get(position).getQuantity().toString());
        holder.quantityDescriptionTextView.setText(mIngredient.get(position).getMeasure());

    }

    @Override
    public int getItemCount() {
        if (mIngredient == null) {
            return 0;
        }
        return mIngredient.size();
    }
}

我建议您在 RecipeDetailsActivity public 静态变量中创建 Recipe recipes 变量。喜欢public static Recipe recipes。当您打开详细 activity 时,就像这样:RecipeDetailsActivity.recipes = recipes.get(adapterPosition); 在这种情况下,这将是一个更简单的解决方案。