Recyclerview不会调用任何Adapter方法:onBindViewHolder,onCreateViewHolder

时间:2017-01-24 07:59:38

标签: android android-recyclerview android-adapter recycler-adapter

Recyclerview不会调用任何Adapter方法:onBindViewHolder,onCreateViewHolder因此适配器为空

这是我的代码:

public class PostsFragment extends Fragment {

public static final String TAG = "PostsFragment";
private static final String KEY_LAYOUT_POSITION = "layoutPosition";
private static final String KEY_TYPE = "type";
public static final int TYPE_HOME = 1001;
public static final int TYPE_FEED = 1002;
private int mRecyclerViewPosition = 0;
private OnPostSelectedListener mListener;


private RecyclerView mRecyclerView;
private RecyclerView.Adapter<PostViewHolder> mAdapter;

public PostsFragment() {
    // Required empty public constructor
}

public static PostsFragment newInstance(int type) {
    PostsFragment fragment = new PostsFragment();
    Bundle args = new Bundle();
    args.putInt(KEY_TYPE, type);
    fragment.setArguments(args);
    return fragment;
}

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    View rootView = inflater.inflate(R.layout.fragment_posts, container, false);
    rootView.setTag(TAG);

    mRecyclerView = (RecyclerView) rootView.findViewById(R.id.my_recycler_view);
    return rootView;
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);
    LinearLayoutManager linearLayoutManager = new LinearLayoutManager(getActivity());
    linearLayoutManager.setReverseLayout(true);
    linearLayoutManager.setStackFromEnd(true);
    mRecyclerView.setLayoutManager(linearLayoutManager);

    if (savedInstanceState != null) {
        // Restore saved layout manager type.
        mRecyclerViewPosition = (int) savedInstanceState
                .getSerializable(KEY_LAYOUT_POSITION);
        mRecyclerView.scrollToPosition(mRecyclerViewPosition);
        // TODO: RecyclerView only restores position properly for some tabs.
    }

    switch (getArguments().getInt(KEY_TYPE)) {

        case TYPE_HOME:
            Log.d(TAG, "Restoring recycler view position (following): " + mRecyclerViewPosition);

            FirebaseUtil.getCurrentUserRef().child("following").addChildEventListener(new ChildEventListener() {
                @Override
                public void onChildAdded(final DataSnapshot followedUserSnapshot, String s) {
                    String followedUserId = followedUserSnapshot.getKey();
                    String lastKey = "";
                    if (followedUserSnapshot.getValue() instanceof String) {
                        lastKey = followedUserSnapshot.getValue().toString();
                    }
                    Log.d(TAG, "followed user id: " + followedUserId);
                    Log.d(TAG, "last key: " + lastKey);
                    FirebaseUtil.getPeopleRef().child(followedUserId).child("posts")
                            .orderByKey().startAt(lastKey).addChildEventListener(new ChildEventListener() {
                        @Override
                        public void onChildAdded(final DataSnapshot postSnapshot, String s) {
                            HashMap<String, Object> addedPost = new HashMap<String, Object>();
                            addedPost.put(postSnapshot.getKey(), true);
                            FirebaseUtil.getFeedRef().child(FirebaseUtil.getCurrentUserId())
                                    .updateChildren(addedPost).addOnSuccessListener(new OnSuccessListener<Void>() {
                                @Override
                                public void onSuccess(Void aVoid) {
                                    FirebaseUtil.getCurrentUserRef().child("following")
                                            .child(followedUserSnapshot.getKey())
                                            .setValue(postSnapshot.getKey());
                                }
                            });
                        }

                        @Override
                        public void onChildChanged(DataSnapshot dataSnapshot, String s) {

                        }

                        @Override
                        public void onChildRemoved(DataSnapshot dataSnapshot) {

                        }

                        @Override
                        public void onChildMoved(DataSnapshot dataSnapshot, String s) {

                        }

                        @Override
                        public void onCancelled(DatabaseError databaseError) {

                        }
                    });
                }

                @Override
                public void onChildChanged(DataSnapshot dataSnapshot, String s) {

                }

                @Override
                public void onChildRemoved(DataSnapshot dataSnapshot) {

                }

                @Override
                public void onChildMoved(DataSnapshot dataSnapshot, String s) {

                }

                @Override
                public void onCancelled(DatabaseError databaseError) {

                }
            });

            FirebaseUtil.getFeedRef().child(FirebaseUtil.getCurrentUserId())
                    .addListenerForSingleValueEvent(new ValueEventListener() {
                        @Override
                        public void onDataChange(DataSnapshot dataSnapshot) {
                            final List<String> postPaths = new ArrayList<>();
                            for (DataSnapshot snapshot : dataSnapshot.getChildren()) {
                                Log.d(TAG, "adding post key: " + snapshot.getKey());
                                postPaths.add(snapshot.getKey());
                            }
                            mAdapter = new FirebasePostQueryAdapter(postPaths,
                                    new FirebasePostQueryAdapter.OnSetupViewListener() {
                                @Override
                                public void onSetupView(PostViewHolder holder, Post post, int position, String postKey) {
                                    setupPost(holder, post, position, postKey);
                                }
                            });
                        }
                        @Override
                        public void onCancelled(DatabaseError firebaseError) {

                        }
                    });
            break;
        default:
            throw new RuntimeException("Illegal post fragment type specified.");
    }
    mRecyclerView.setAdapter(mAdapter);
}

private FirebaseRecyclerAdapter<Post, PostViewHolder> getFirebaseRecyclerAdapter(Query query) {
    return new FirebaseRecyclerAdapter<Post, PostViewHolder>(
            Post.class, R.layout.post_item, PostViewHolder.class, query) {
        @Override
        public void populateViewHolder(final PostViewHolder postViewHolder,
                                       final Post post, final int position) {
            setupPost(postViewHolder, post, position, null);
        }

        @Override
        public void onViewRecycled(PostViewHolder holder) {
            super.onViewRecycled(holder);

        }
    };
}

private void setupPost(final PostViewHolder postViewHolder, final Post post, final int position, final String inPostKey) {
    postViewHolder.setPhoto(post.getThumb_url());
    postViewHolder.setText(post.getText());
    postViewHolder.setTimestamp(DateUtils.getRelativeTimeSpanString(
            (long) post.getTimestamp()).toString());
    final String postKey;
    if (mAdapter instanceof FirebaseRecyclerAdapter) {
        postKey = ((FirebaseRecyclerAdapter) mAdapter).getRef(position).getKey();
    } else {
        postKey = inPostKey;
    }

    Author author = post.getAuthor();
    postViewHolder.setAuthor(author.getFull_name(), author.getUid());
    postViewHolder.setIcon(author.getProfile_picture(), author.getUid());

    ValueEventListener likeListener = new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            postViewHolder.setNumLikes(dataSnapshot.getChildrenCount());
            if (dataSnapshot.hasChild(FirebaseUtil.getCurrentUserId())) {
                postViewHolder.setLikeStatus(PostViewHolder.LikeStatus.LIKED, getActivity());
            } else {
                postViewHolder.setLikeStatus(PostViewHolder.LikeStatus.NOT_LIKED, getActivity());
            }
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    };
    FirebaseUtil.getLikesRef().child(postKey).addValueEventListener(likeListener);
    postViewHolder.mLikeListener = likeListener;

    postViewHolder.setPostClickListener(new PostViewHolder.PostClickListener() {
        @Override
        public void showComments() {
            Log.d(TAG, "Comment position: " + position);
            mListener.onPostComment(postKey);
        }

        @Override
        public void toggleLike() {
            Log.d(TAG, "Like position: " + position);
            mListener.onPostLike(postKey);
        }
    });
}

@Override
public void onDestroy() {
    super.onDestroy();
    if (mAdapter != null && mAdapter instanceof FirebaseRecyclerAdapter) {
        ((FirebaseRecyclerAdapter) mAdapter).cleanup();
    }
}


@Override
public void onSaveInstanceState(Bundle savedInstanceState) {
    // Save currently selected layout manager.
    int recyclerViewScrollPosition = getRecyclerViewScrollPosition();
    Log.d(TAG, "Recycler view scroll position: " + recyclerViewScrollPosition);
    savedInstanceState.putSerializable(KEY_LAYOUT_POSITION, recyclerViewScrollPosition);
    super.onSaveInstanceState(savedInstanceState);
}

private int getRecyclerViewScrollPosition() {
    int scrollPosition = 0;
    // TODO: Is null check necessary?
    if (mRecyclerView != null && mRecyclerView.getLayoutManager() != null) {
        scrollPosition = ((LinearLayoutManager) mRecyclerView.getLayoutManager())
                .findFirstCompletelyVisibleItemPosition();
    }
    return scrollPosition;
}
/**
 * This interface must be implemented by activities that contain this
 * fragment to allow an interaction in this fragment to be communicated
 * to the activity and potentially other fragments contained in that
 * activity.
 * <p/>
 */
public interface OnPostSelectedListener {
    void onPostComment(String postKey);
    void onPostLike(String postKey);
}

@Override
public void onAttach(Context context) {
    super.onAttach(context);
    if (context instanceof OnPostSelectedListener) {
        mListener = (OnPostSelectedListener) context;
    } else {
        throw new RuntimeException(context.toString()
                + " must implement OnPostSelectedListener");
    }
}

@Override
public void onDetach() {
    super.onDetach();
    mListener = null;
}

}

适配器类

public class FirebasePostQueryAdapter extends RecyclerView.Adapter<PostViewHolder> {
private final String TAG = "PostQueryAdapter";
private List<String> mPostPaths;
private OnSetupViewListener mOnSetupViewListener;

public FirebasePostQueryAdapter(List<String> paths, OnSetupViewListener onSetupViewListener) {
    if (paths == null || paths.isEmpty()) {
        mPostPaths = new ArrayList<>();
    } else {
        mPostPaths = paths;
    }
    mOnSetupViewListener = onSetupViewListener;
}

@Override
public PostViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    // create a new view
    View v = LayoutInflater.from(parent.getContext())
            .inflate(R.layout.post_item, parent, false);
    return new PostViewHolder(v);
}

public void setPaths(List<String> postPaths) {
    mPostPaths = postPaths;
    notifyDataSetChanged();
}

public void addItem(String path) {
    mPostPaths.add(path);
    notifyItemInserted(mPostPaths.size());
}

@Override
public void onBindViewHolder(final PostViewHolder holder, int position) {
    DatabaseReference ref = FirebaseUtil.getPostsRef().child(mPostPaths.get(position));
    // TODO: Fix this so async event won't bind the wrong view post recycle.
    ValueEventListener postListener = new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            Post post = dataSnapshot.getValue(Post.class);
            Log.d(TAG, "post key: " + dataSnapshot.getKey());
            mOnSetupViewListener.onSetupView(holder, post, holder.getAdapterPosition(),
                    dataSnapshot.getKey());
        }

        @Override
        public void onCancelled(DatabaseError firebaseError) {
            Log.e(TAG, "Error occurred: " + firebaseError.getMessage());
        }
    };
    ref.addValueEventListener(postListener);
    holder.mPostRef = ref;
    holder.mPostListener = postListener;
}

@Override
public void onViewRecycled(PostViewHolder holder) {
    super.onViewRecycled(holder);
    holder.mPostRef.removeEventListener(holder.mPostListener);
}

@Override
public int getItemCount() {
    return mPostPaths.size();
}

public interface OnSetupViewListener {
    void onSetupView(PostViewHolder holder, Post post, int position, String postKey);
}

}

主要班级

public class FeedsActivity extends AppCompatActivity implements PostsFragment.OnPostSelectedListener {
private static final String TAG = "FeedsActivity";
private FloatingActionButton mFab;

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

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    ViewPager viewPager = (ViewPager) findViewById(R.id.feeds_view_pager);
    FeedsPagerAdapter adapter = new FeedsPagerAdapter(getSupportFragmentManager());
    adapter.addFragment(PostsFragment.newInstance(PostsFragment.TYPE_HOME), "HOME");
    adapter.addFragment(PostsFragment.newInstance(PostsFragment.TYPE_FEED), "FEED");
    viewPager.setAdapter(adapter);
    viewPager.setCurrentItem(1);
    TabLayout tabLayout = (TabLayout) findViewById(R.id.feeds_tab_layout);
    tabLayout.setupWithViewPager(viewPager);

    mFab = (FloatingActionButton) findViewById(R.id.fab);
    mFab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            FirebaseUser user = FirebaseAuth.getInstance().getCurrentUser();
            if (user == null || user.isAnonymous()) {
                Toast.makeText(FeedsActivity.this, "You must sign-in to post.", Toast.LENGTH_SHORT).show();
                return;
            }
            Intent newPostIntent = new Intent(FeedsActivity.this, NewPostActivity.class);
            startActivity(newPostIntent);
        }
    });
}

@Override
public void onPostComment(String postKey) {
    Intent intent = new Intent(this, CommentsActivity.class);
    intent.putExtra(CommentsActivity.POST_KEY_EXTRA, postKey);
    startActivity(intent);
}

@Override
public void onPostLike(final String postKey) {
    final String userKey = FirebaseUtil.getCurrentUserId();
    final DatabaseReference postLikesRef = FirebaseUtil.getLikesRef();
    postLikesRef.child(postKey).child(userKey).addListenerForSingleValueEvent(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            if (dataSnapshot.exists()) {
                // User already liked this post, so we toggle like off.
                postLikesRef.child(postKey).child(userKey).removeValue();
            } else {
                postLikesRef.child(postKey).child(userKey).setValue(ServerValue.TIMESTAMP);
            }
        }

        @Override
        public void onCancelled(DatabaseError firebaseError) {

        }
    });
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.menu_feeds, menu);
    return true;
}

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    // Handle action bar item clicks here. The action bar will
    // automatically handle clicks on the Home/Up button, so long
    // as you specify a parent activity in AndroidManifest.xml.
    int id = item.getItemId();

    //noinspection SimplifiableIfStatement
    if (id == R.id.action_settings) {
        // TODO: Add settings screen.
        return true;
    } else if (id == R.id.action_profile) {
        startActivity(new Intent(this, ProfileActivity.class));
        return true;
    }

    return super.onOptionsItemSelected(item);
}

class FeedsPagerAdapter extends FragmentPagerAdapter {
    private final List<Fragment> mFragmentList = new ArrayList<>();
    private final List<String> mFragmentTitleList = new ArrayList<>();

    public FeedsPagerAdapter(FragmentManager manager) {
        super(manager);
    }

    @Override
    public Fragment getItem(int position) {
        return mFragmentList.get(position);
    }

    @Override
    public int getCount() {
        return mFragmentList.size();
    }

    public void addFragment(Fragment fragment, String title) {
        mFragmentList.add(fragment);
        mFragmentTitleList.add(title);
    }

    @Override
    public CharSequence getPageTitle(int position) {
        return mFragmentTitleList.get(position);
    }
}

}

activity_feeds.xml

<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/main_content"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
>

<android.support.design.widget.AppBarLayout
    android:id="@+id/appbar"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">

    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        app:layout_scrollFlags="scroll|enterAlways|snap"
        app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
        app:layout_behavior="@string/appbar_scrolling_view_behavior" />

    <android.support.design.widget.TabLayout
        android:id="@+id/feeds_tab_layout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"/>

</android.support.design.widget.AppBarLayout>

<android.support.v4.view.ViewPager
    android:id="@+id/feeds_view_pager"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
     />

<android.support.design.widget.FloatingActionButton
    android:id="@+id/fab"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="end|bottom"
    android:layout_margin="@dimen/fab_margin"
    android:src="@android:drawable/ic_input_add"
    android:tint="@android:color/white"/>

post_item.xml

<android.support.v7.widget.CardView
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_margin="8dp"
android:layout_height="wrap_content" >


<LinearLayout
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
<RelativeLayout
    android:layout_width="match_parent"
    android:layout_height="50dp"
    android:padding="10dp">
    <de.hdodenhof.circleimageview.CircleImageView
        android:id="@+id/post_author_icon"
        android:layout_width="@dimen/post_author_icon_size"
        android:layout_height="@dimen/post_author_icon_size"
        android:layout_centerVertical="true"
        android:layout_alignParentLeft="true"
        android:layout_alignParentStart="true"/>
    <TextView
        android:id="@+id/post_author_name"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerVertical="true"
        android:layout_toRightOf="@id/post_author_icon"
        android:layout_marginLeft="4dp"
        style="@style/Base.TextAppearance.AppCompat.Title"
        android:textColor="@android:color/primary_text_light_nodisable"
        android:text="Unknown"/>
    <TextView
        android:id="@+id/post_timestamp"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerVertical="true"
        android:layout_alignParentRight="true"
        android:layout_alignParentEnd="true"
        android:layout_gravity="end"
        android:textColor="@android:color/primary_text_light"
        android:textSize="18sp" />
</RelativeLayout>
<ImageView
    android:id="@+id/post_photo"
    android:layout_width="match_parent"
    android:layout_height="200dp"
    android:layout_alignParentLeft="true"
    android:layout_alignParentTop="true"
    android:scaleType="centerCrop" />
    <TextView
        android:id="@+id/post_text"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:singleLine="false"
        android:layout_marginLeft="6dp"
        android:layout_marginRight="6dp"
        android:layout_marginTop="6dp"
        android:layout_marginBottom="6dp"
        android:textColor="@android:color/primary_text_light"
        android:textSize="16sp"
        android:ellipsize="end" />
    <TextView
        android:id="@+id/post_num_likes"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginLeft="6dp"
        android:layout_marginRight="6dp"
        android:layout_marginTop="6dp"
        android:layout_marginBottom="6dp"
        android:textColor="@android:color/secondary_text_light"
        android:textSize="14sp" />
    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:padding="6dp">
        <ImageView
            android:id="@+id/post_like_icon"
            android:layout_width="30dp"
            android:layout_height="30dp"
            android:src="@drawable/heart_full"/>
        <ImageView
            android:id="@+id/post_comment_icon"
            android:layout_width="30dp"
            android:layout_height="30dp"
            android:layout_marginLeft="6dp"
            android:layout_toRightOf="@id/post_like_icon"
            android:src="@drawable/ic_chat_24dp"
            android:tint="@color/blue_grey_500"/>
    </RelativeLayout>

</LinearLayout>

fragment_posts.xml

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".PostsFragment">

    <android.support.v7.widget.RecyclerView
        android:id="@+id/my_recycler_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:scrollbars="vertical" />

1 个答案:

答案 0 :(得分:1)

您正在初始化适配器之前在recyclerview上设置适配器。尝试:

public static String myReverse(String str) {
    byte[] bytes = str.getBytes("ASCII");
    // memory at full capacity
    str = null;
    // memory at 1/3 capacity
    for (int i = 0; i < bytes.length / 2; i++) {
        byte tmp = bytes[i];
        bytes[i] = bytes[bytes.length - i - 1];
        bytes[bytes.length - i - 1] = tmp;
    }
    return new String(bytes, "ASCII");
}