RecyclerView:异构ViewType + NullPointer

时间:2019-05-12 11:03:27

标签: java android android-recyclerview

因此,基本上,NullPointer应该不是要解决的问题,但这使我发疯。 我正在解析具有以下结构的JSON “垂直”:[名称,图像,图片,时间戳,URL,状态] “水平”:[ ....一样 ]

使用GSON填充具有2个ViewType的RecyclerView,一个用于水平滚动,一个用于垂直滚动(就像Insta,FB的Newsfeed一样)。

问题如下:我的FeedAdapter中出现了一个NullPointer,我不知道为什么发生了NullPointer。让我们看看我的FeedAdapter:

FeedAdapter.java

public FeedAdapter(Context context, ArrayList<Object> items, List<Vertical> listVertical,List<Horizontal> listHorizontal) {
this.context = context;
this.items = items;
this.listVertical = listVertical;
this.listHorizontal = listHorizontal;

Vertical[] verticalList = listVertical.toArray(new Vertical[0]);
Horizontal [] horizontalList = listHorizontal.toArray(new Horizontal[0]);

@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup viewGroup, int viewType) {
    LayoutInflater inflater = LayoutInflater.from(context);
    View view;
    RecyclerView.ViewHolder holder = null;
    switch (viewType) {
        case VIEW_TYPE_VERTICAL:
            view = inflater.inflate(R.layout.news_timeline_item,viewGroup,false);
            holder = new VerticalViewHolder(view);
            break;
        case VIEW_TYPE_HORIZONTAL:
            view = inflater.inflate(R.layout.news_timeline_horizontal_single_row,viewGroup,false);
            holder = new HorizontalViewHolder(view);
            break;
        default:
            view = inflater.inflate(R.layout.news_timeline_horizontal_single_row, viewGroup, false);
            holder = new HorizontalViewHolder(view);
            break;
    }
    return holder; }

@Override
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int  position) {
    if (holder.getItemViewType() == VIEW_TYPE_VERTICAL)
        [1]verticalView((VerticalViewHolder) holder);
    else if (holder.getItemViewType() == VIEW_TYPE_HORIZONTAL)
        horizontalView((HorizontalViewHolder) holder);
}

public void verticalView (VerticalViewHolder holder ){

    VerticalScrollAdapter adapter_v = new VerticalScrollAdapter(listVertical);
    [2]holder.recyclerView.setLayoutManager(new LinearLayoutManager(context));
    holder.recyclerView.setAdapter(adapter_v);

}

public void horizontalView (HorizontalViewHolder holder) {
    HorizontalScrollAdapter adapter_h = new HorizontalScrollAdapter(listHorizontal);
    holder.recyclerView.setLayoutManager(new LinearLayoutManager(context,LinearLayoutManager.HORIZONTAL,false));
    holder.recyclerView.setAdapter(adapter_h);
}

@Override
public int getItemCount() {
    Log.e("items.size", String.valueOf(items.size()));
    return items.size();
}


@Override
public int getItemViewType(int position) {
    if (items.get(position) instanceof Vertical)
        return VIEW_TYPE_VERTICAL;
    if (items.get(position) instanceof Horizontal)
        return VIEW_TYPE_HORIZONTAL;
    return -1;
}


public class HorizontalViewHolder extends RecyclerView.ViewHolder {

    RecyclerView recyclerView;

    HorizontalViewHolder(View itemView) {
        super(itemView);
        recyclerView = itemView.findViewById(R.id.inner_recyclerView_horizontal);
    }
}


public class VerticalViewHolder extends RecyclerView.ViewHolder {
    RecyclerView recyclerView;

    VerticalViewHolder(View itemView) {
        super(itemView);
        recyclerView = itemView.findViewById(R.id.inner_recyclerView_vertical);

    }
}

Android Studio给我的错误是:

java.lang.NullPointerException: Attempt to invoke virtual method 'void androidx.recyclerview.widget.RecyclerView.setLayoutManager(androidx.recyclerview.widget.RecyclerView$LayoutManager)' on a null object reference
.FeedAdapter.verticalView(FeedAdapter.java:[2])
.FeedAdapter.onBindViewHolder(FeedAdapter.java[1])
[1] and [2] see code above

好吧,现在我检查了VerticalScrollAdapter:

public class VerticalScrollAdapter extends    RecyclerView.Adapter<VerticalScrollAdapter.mViewHolder> {
Vertical[] data;

public VerticalScrollAdapter(List<Vertical> data) {
    this.data = data.toArray(new Vertical[0]);
}

@NonNull
@Override
public mViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {

    View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.news_timeline_item,parent,false);
    return new mViewHolder(view);

}

@Override
public void onBindViewHolder(@NonNull mViewHolder h, int i) {
    Vertical feed = data[i];
    h.description.setText(feed.getStatus());
    h.title.setText(feed.getName());
    h.pubDate.setText(feed.getTimeStamp());
    Picasso.get().load(feed.getImage()).into(h.image);
}

@Override
public int getItemCount() {
    return data.length;
}


public class mViewHolder extends RecyclerView.ViewHolder {
    TextView title, description, pubDate;
    ImageView image;

    public mViewHolder(View itemView) {
        super(itemView);
        title = itemView.findViewById(R.id.title);
        description = itemView.findViewById(R.id.description);
        pubDate =  itemView.findViewById(R.id.published_date);
        image = itemView.findViewById(R.id.image_view);
    }
}
}

好吧,我从错误中了解的是,错误确实导致了错误的位置。这就是为什么我首先检查XML的原因:

    <androidx.recyclerview.widget.RecyclerView
    android:id="@+id/inner_recyclerView_horizontal"
    android:layout_width="match_parent"
    android:layout_height="match_parent" />

所以这个ID很好,让我们检查一下由我的适配器填充的单个项:

<?xml version="1.0" encoding="utf-8"?>
<androidx.cardview.widget.CardView  
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="250dp"
android:layout_height="270dp"
android:layout_margin="5dp"
android:background="#FFFFFF"
android:elevation="5dp"
android:orientation="vertical"
android:padding="5dp">

<LinearLayout
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

        <ImageView
            android:id="@+id/image_view"
            android:layout_width="match_parent"
            android:layout_height="150dp"
            android:scaleType="center" />

        <TextView
            android:id="@+id/title"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="bottom"
            android:layout_margin="8dp"
            android:textColor="#fff"
            android:text="Title"
            android:textSize="28sp" />

        <View
            android:layout_width="match_parent"
            android:layout_height="100dp"
            android:background="@drawable/bg_btn_ripple_dark"
            android:id="@+id/view" />

    </FrameLayout>

    <TextView
        android:id="@+id/description"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="8dp"
        android:text="this is the description" />

    <TextView
        android:id="@+id/published_date"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="8dp"
        android:text="2073/2/2" />
</LinearLayout>

因此,使用ID的一切都应该没问题-因此:此NullPointer在这里发生了什么事?

0 个答案:

没有答案