我正在尝试使用Firebase实时数据库实现多视图或所谓的异构recyclerview。我在github上找到了一个异构recyclerview实现的示例。
我遵循此步骤在Firebase上实现。但是我的代码无效。
fragment_search.java(我的选项卡式视图中的片段之一)这是我的片段文件,其中包含将包含多个视图的主recyclerview
public class fragment_search extends Fragment {
RecyclerView recyclerViewSearch;
private static SingleSearchBannerModel singleSearchBannerModel;
private static SingleSearchType1Model singleSearchType1Model;
private static DatabaseReference databaseReference;
private List<Object> objects = new ArrayList<>();
private static SearchMainAdapter searchMainAdapter;
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_search,null);
//Recycler view initialized and Properties Set.
recyclerViewSearch = view.findViewById(R.id.recyclerview_search);
recyclerViewSearch.setHasFixedSize(true);
recyclerViewSearch.setLayoutManager(new LinearLayoutManager(getContext()));
databaseReference = FirebaseDatabase.getInstance().getReference();
return view;
}
private List<Object> getObjects(){
objects.addAll(getBannerData());
objects.addAll(getType1Data());
return objects;
}
public static List<SingleSearchBannerModel> getBannerData(){
final List<SingleSearchBannerModel> singleSearchBannerModelList = new ArrayList<>();
databaseReference.child("Featured").addChildEventListener(new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
singleSearchBannerModel = dataSnapshot.getValue(SingleSearchBannerModel.class);
singleSearchBannerModelList.add(singleSearchBannerModel);
searchMainAdapter.notifyDataSetChanged();
System.out.println("this is image in getBanner == "+singleSearchBannerModel.getImage());
}
@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) {
}
});
return singleSearchBannerModelList;
}
public static List<SingleSearchType1Model> getType1Data(){
final List<SingleSearchType1Model> singleSearchType1ModelList = new ArrayList<>();
databaseReference.child("Featured").addChildEventListener(new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
singleSearchType1Model = dataSnapshot.getValue(SingleSearchType1Model.class);
singleSearchType1ModelList.add(singleSearchType1Model);
searchMainAdapter.notifyDataSetChanged();
}
@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) {
}
});
return singleSearchType1ModelList;
}
@Override
public void onStart() {
super.onStart();
searchMainAdapter = new SearchMainAdapter(getContext(),getObjects());
System.out.println("this is getObject == "+getObjects());
System.out.println("this is getBanner == "+getBannerData());
System.out.println("this is getType1 == "+getType1Data());
recyclerViewSearch.setAdapter(searchMainAdapter);
}
}
fragment_home.xml这是片段的xml文件,其中包含一个recyclerview(我的主recyclerview)。
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<android.support.v7.widget.RecyclerView
android:id="@+id/recyclerview_search"
android:layout_width="match_parent"
android:layout_height="match_parent">
</android.support.v7.widget.RecyclerView>
模型文件
*我有两个模型文件。基本上是getter和setters *
SingleSearchBannerModel.java我的第一个模型文件。
public class SingleSearchBannerModel {
String Image;
public SingleSearchBannerModel() {
}
public SingleSearchBannerModel(String image) {
Image = image;
}
public String getImage() {
return Image;
}
public void setImage(String image) {
Image = image;
}
}
SingleSearchType1Model.java这是我的第二个模型文件。
public class SingleSearchType1Model {
String Image;
public SingleSearchType1Model() {
}
public SingleSearchType1Model(String image) {
Image = image;
}
public String getImage() {
return Image;
}
public void setImage(String image) {
Image = image;
}
}
RecyclerView适配器
适配器是用于将值设置为recyclerView的适配器。我正在尝试在一个recyclerview中插入两个视图,所以有三个适配器。一个是MainAdapter,它结合了其他两个适配器。 MainAdapter设置为fragment_search.java(我的主要片段)的recyclerview。
SearchBannerAdapter.java此适配器用于生成所需的布局文件并填充膨胀的布局文件。
public class SearchBannerAdapter extends RecyclerView.Adapter<SearchBannerAdapter.TaskViewHolder>{
List<SingleSearchBannerModel> data;
public SearchBannerAdapter(List<SingleSearchBannerModel> data) {
this.data = data;
}
@NonNull
@Override
public TaskViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.search_single_banners,parent,false);
return new TaskViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull TaskViewHolder holder, int position) {
SingleSearchBannerModel singleSearchBannerModel = data.get(position);
Picasso.get().load(singleSearchBannerModel.getImage()).fit().into(holder.imageView);
}
@Override
public int getItemCount() {
return data.size();
}
public static class TaskViewHolder extends RecyclerView.ViewHolder{
View mView;
ImageView imageView;
public TaskViewHolder(View itemView) {
super(itemView);
mView = itemView;
imageView = mView.findViewById(R.id.search_banner_imgView);
}
}
}
search_single_banners.xml在SearchBannerAdapter.java中膨胀的xml文件>
<android.support.constraint.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto">
<android.support.v7.widget.CardView
android:layout_width="290dp"
android:layout_height="160dp"
android:id="@+id/longCard"
android:layout_marginTop="50dp"
android:layout_marginEnd="20dp"
app:cardCornerRadius="20sp"
app:cardElevation="@dimen/ten"
app:cardPreventCornerOverlap="false"
android:layout_centerHorizontal="true">
<ImageView
android:id="@+id/search_banner_imgView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@drawable/test1"/>
</android.support.v7.widget.CardView>
SearchType1Adapter.java
这是第二个使search_type_1.xml膨胀的适配器。public class SearchType1Adapter extends RecyclerView.Adapter<SearchType1Adapter.TaskViewHolder>{ List<SingleSearchType1Model> data; public SearchType1Adapter(List<SingleSearchType1Model> data) { this.data = data; } @NonNull @Override public TaskViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.search_type_1,parent,false); return new TaskViewHolder(view); } @Override public void onBindViewHolder(@NonNull TaskViewHolder holder, int position) { SingleSearchType1Model singleSearchType1Model = data.get(position); Picasso.get().load(singleSearchType1Model.getImage()).fit().into(holder.imageView); } @Override public int getItemCount() { return data.size(); } public static class TaskViewHolder extends RecyclerView.ViewHolder{ View mView; ImageView imageView; public TaskViewHolder(View itemView) { super(itemView); mView = itemView; imageView = mView.findViewById(R.id.search_single_type_1_imgView); } } }
search_type_1.xml
SearchType1Adapter.java中膨胀的文件
这是在fragment_search中用于填充主recyclerview的主适配器。<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" xmlns:app="http://schemas.android.com/apk/res-auto"> <android.support.v7.widget.CardView android:layout_width="290dp" android:layout_height="160dp" android:id="@+id/longCard" android:layout_marginTop="50dp" android:layout_marginEnd="20dp" app:cardCornerRadius="20sp" app:cardElevation="@dimen/ten" app:cardPreventCornerOverlap="false" android:layout_centerHorizontal="true"> <ImageView android:id="@+id/search_single_type_1_imgView" android:layout_width="match_parent" android:layout_height="match_parent" android:background="@drawable/test1"/> </android.support.v7.widget.CardView>
SearchMainAdapter.java
public class SearchMainAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> { private Context context; private List<Object> items; private final int BANNER = 1; private final int TYPE1 = 2; public SearchMainAdapter(Context context, List<Object> items) { this.context = context; this.items = items; } @NonNull @Override public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { LayoutInflater inflater = LayoutInflater.from(parent.getContext()); View view; RecyclerView.ViewHolder holder; switch (viewType){ case BANNER: view = inflater.inflate(R.layout.search_banners,parent,false); holder = new BannerViewHolder(view); break; case TYPE1: view = inflater.inflate(R.layout.search_type_1,parent,false); holder = new Type1ViewHolder(view); break; default: view = inflater.inflate(R.layout.search_banners,parent,false); holder = new Type1ViewHolder(view); break; } return holder; } @Override public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) { if(holder.getItemViewType() == BANNER) BannerView((BannerViewHolder) holder); else if (holder.getItemViewType() == TYPE1) Type1View((Type1ViewHolder) holder); } private void BannerView(BannerViewHolder holder){ SearchBannerAdapter searchBannerAdapter = new SearchBannerAdapter(getBannerData()); holder.recyclerView.setLayoutManager(new LinearLayoutManager(context,LinearLayoutManager.HORIZONTAL,false)); holder.recyclerView.setAdapter(searchBannerAdapter); } private void Type1View(Type1ViewHolder holder){ SearchType1Adapter searchType1Adapter = new SearchType1Adapter(getType1Data()); holder.recyclerView.setLayoutManager(new LinearLayoutManager(context,LinearLayoutManager.HORIZONTAL,false)); holder.recyclerView.setAdapter(searchType1Adapter); } @Override public int getItemCount() { return items.size(); } @Override public int getItemViewType(int position) { if (items.get(position) instanceof SingleSearchBannerModel) return BANNER; if (items.get(position) instanceof SingleSearchType1Model) return TYPE1; return -1; } public static class BannerViewHolder extends RecyclerView.ViewHolder{ RecyclerView recyclerView; public BannerViewHolder(View itemView) { super(itemView); recyclerView = itemView.findViewById(R.id.recyclerview_banners); } } public static class Type1ViewHolder extends RecyclerView.ViewHolder{ RecyclerView recyclerView; public Type1ViewHolder(View itemView) { super(itemView); recyclerView = itemView.findViewById(R.id.recyclerview_search_type_1); } } }
search_banners.xml和search_type_1.xml具有相同的代码
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> <android.support.v7.widget.RecyclerView android:id="@+id/recyclerview_banners" android:layout_width="match_parent" android:layout_height="match_parent"> </android.support.v7.widget.RecyclerView>
上面的代码不起作用。我想知道我哪里做错了。我的主要目标是制作类似于Google Play商店或hotstar(在UI方面)的应用。因此,我假设他们正在使用单个recyclerview和其中的多个视图。
感谢您的帮助。
我正在尝试使用Firebase实时数据库实现多视图或所谓的异构recyclerview。我在github上找到了一个异构recyclerview实现的示例。我关注了...
我知道这个答案有点晚了,但将来可能仍然会对某人有所帮助。这是我实现目标的方式
public class HeteroActivity extends AppCompatActivity {
private ArrayList<Object> objects = new ArrayList<>();
private static final String TAG = HeteroActivity.class.getSimpleName();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_hetero);
RecyclerView recyclerView = findViewById(R.id.recycler_View);
MainAdapter adapter = new MainAdapter(this, getObject());
recyclerView.setAdapter(adapter);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
}
private ArrayList<Object> getObject() {
DatabaseReference reference = FirebaseDatabase.getInstance().getReference().child("Data");
reference.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
objects.add(getVerticalData(dataSnapshot).get(0));
objects.add(getHorizontalData(dataSnapshot).get(0));
}
@Override
public void onCancelled(@NonNull DatabaseError databaseError) {
}
});
return objects;
}
public static ArrayList<SingleVertical> getVerticalData(DataSnapshot dataSnapshot) {
ArrayList<SingleVertical> singleVerticals = new ArrayList<>();
for (DataSnapshot snapshot : dataSnapshot.getChildren()){
singleVerticals.add(new SingleVertical(
snapshot.child("price").getValue(String.class),
snapshot.child("location").getValue(String.class),
snapshot.child("image").getValue(String.class)
));
Log.e(TAG,"Text loaded");
}
return singleVerticals;
}
public static ArrayList<SingleHorizontal> getHorizontalData(DataSnapshot dataSnapshot) {
ArrayList<SingleHorizontal> singleHorizontals = new ArrayList<>();
for (DataSnapshot snapshot : dataSnapshot.getChildren()){
singleHorizontals.add(new SingleHorizontal(
snapshot.child("price").getValue(String.class),
snapshot.child("location").getValue(String.class),
snapshot.child("image").getValue(String.class)
));
Log.e(TAG,"Horizontal data loaded");
}
return singleHorizontals;
}