首页 > 解决方案 > 我可以有一个加载不同数据集的回收视图吗

问题描述

我正在开发用于书籍的移动应用程序。

我有所有类别的 recyclerview - 浪漫,历史等。这辆 RV 正在从 Firebase 获取数据。

我想要做的是:

例如,当用户单击 Romance 时,需要打开一个新活动。在那个活动中,我想让一个 RV 加载包含该类型所有书籍的数据集。

然后,如果用户打开历史记录,我希望将该数据集加载到同一个 RV 中。

我想避免代码重复,我要问的是 - 我是否可以有 1 个带有 If 语句的类来处理用户选择并将数据集加载到一个 RV 中?

如果可能的话,你能告诉我怎么做吗?

谢谢 !

编辑:这是我的代码。到目前为止我所做的是适配器、GetAndSet 类、2 个活动。为了在一个 RV 中显示类别,我使用了 1 个适配器和 1 个 GetAndSet 类,1 个 XML 文件。我为浪漫和喜剧创建了 2 个单独的类,并在其中连接到 firebase。适配器:

公共类 CategoriesAdapter 扩展 RecyclerView.Adapter {

Context mContext;
List<Categories> mData;

public CategoriesAdapter(Context mContext, List<Categories> mData) {
    this.mContext = mContext;
    this.mData = mData;
}


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

    View row = LayoutInflater.from( mContext ).inflate( R.layout.row_attractions, parent, false );

    return new MyViewHolder( row );
}

@Override
public void onBindViewHolder(@NonNull MyViewHolder holder, int position) {

    holder.DesName.setText( mData.get( position ).getName() );
    Glide.with( mContext ).load( mData.get( position ).getImage() ).into( holder.DesImage );
}

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

public class MyViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {

    TextView DesName;
    ImageView DesImage;

    public MyViewHolder(@NonNull View itemView) {
        super( itemView );

        itemView.setClickable( true );
        mContext = itemView.getContext();

        DesName = itemView.findViewById( R.id.DesName );
        DesImage = itemView.findViewById( R.id.DesImage );
        DesImage.setOnClickListener( this );
    }


    @Override
    public void onClick(View v) {

        final Intent intent;
        Toast.makeText(itemView.getContext(),"Test",Toast.LENGTH_LONG ).show();
        switch (getAdapterPosition()) {
            case 0:
                intent = new Intent( mContext, Romance.class );
                break;

             case 1:
                intent = new Intent( mContext, Comedy.class );
              break;

            // case 2:
            //     intent = new Intent( mContext, RegentsPark.class );
            //  break;

            default:
                intent = new Intent( mContext, Home.class );
                break;
        }
        mContext.startActivity( intent );
    }

}

}

Romance 类(与 Comedy 类相同,但在 Firebase 中我引用数据集的行除外:

public class Romance extends AppCompatActivity {


RecyclerView categoriesRecyclerView ;
CategoriesAdapter categoriesAdapter  ;
FirebaseDatabase firebaseDatabase;
DatabaseReference databaseReference ;
List<Categories> categoriesList;

private EditText mSearchField;
private ImageButton mSearchBtn;

private RecyclerView mResultList;

private DatabaseReference mUserDatabase;

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


    categoriesRecyclerView  = findViewById(R.id.BookRV);
    categoriesRecyclerView.setLayoutManager(new LinearLayoutManager(Romance.this));
    categoriesRecyclerView.setHasFixedSize(true);
    firebaseDatabase = FirebaseDatabase.getInstance();
    databaseReference = firebaseDatabase.getReference("ListParks");

   // mUserDatabase = FirebaseDatabase.getInstance().getReference("Categories");


    mSearchField = (EditText) findViewById(R.id.search_field);
    mSearchBtn = (ImageButton) findViewById(R.id.search_btn);

    mResultList = (RecyclerView) findViewById(R.id.result_list);
    mResultList.setHasFixedSize(true);
    mResultList.setLayoutManager(new LinearLayoutManager(this));

    mSearchBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {

            String searchText = mSearchField.getText().toString();

            firebaseUserSearch(searchText);

        }
    });

}

private void firebaseUserSearch(String searchText) {

    Toast.makeText(Romance.this, "Started Search", Toast.LENGTH_LONG).show();

    Query firebaseSearchQuery = mUserDatabase.orderByChild("name").startAt(searchText).endAt(searchText + "\uf8ff");

    FirebaseRecyclerAdapter<Users, UsersViewHolder> firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<Users, UsersViewHolder>(

            Users.class,
            R.layout.list_layout,
            UsersViewHolder.class,
            firebaseSearchQuery

    ) {
        @Override
        protected void populateViewHolder(UsersViewHolder viewHolder, Users model, int position) {


            viewHolder.setDetails(getApplicationContext(), model.getName(), model.getImage());

        }
    };

    mResultList.setAdapter(firebaseRecyclerAdapter);

}


// View Holder Class

public static class UsersViewHolder extends RecyclerView.ViewHolder {

    View mView;

    public UsersViewHolder(View itemView) {
        super(itemView);

        mView = itemView;

    }

    public void setDetails(Context ctx, String userName, String userImage){

        TextView user_name = (TextView) mView.findViewById(R.id.name_text);
        ImageView user_image = (ImageView) mView.findViewById(R.id.profile_image);


        user_name.setText(userName);

        Glide.with(ctx).load(userImage).into(user_image);


    }




}

@Override
protected void onStart() {
    super.onStart();


    databaseReference.addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(@NonNull DataSnapshot dataSnapshot) {

            categoriesList = new ArrayList<>();
            for (DataSnapshot catsnap: dataSnapshot.getChildren()) {

                Categories post = catsnap.getValue(Categories.class);
                categoriesList.add(post) ;
            }
            //set Adapter
            categoriesAdapter = new CategoriesAdapter(Romance.this,categoriesList);
            categoriesRecyclerView.setAdapter(categoriesAdapter);
        }

        @Override
        public void onCancelled(@NonNull DatabaseError databaseError) {

        }
    });
}
}

我可以避免为每种类型的书籍创建不同的类吗?

标签: javaandroid

解决方案


如果你想知道用户在第一个 RecyclerView 上选择了什么类别:

当用户单击 RecyclerView 项目时,将类别名称/标识符传递给您要打开的活动。然后从第二个活动中根据您从前一个活动中获得的类别获取您的数据集对象并将其传递给适配器。

您可以制作自定义 RecyclerView.Adapter。这是一个很好的例子:

Android 开发者文档示例

启动适配器时,您传递数据集。这是您的自定义 RecyclerView.Adapter 类的构造函数:

public MyAdapter(String[] myDataset) {
    mDataset = myDataset;
}

因此,每次您创建列出书籍的活动时,您都可以创建新的 RecyclerView.Adapter 实例来传递您的数据集。

将其放在活动的 onCreate 方法中的某个位置:

MyAdapter myAdapter = new MyAdapter(myDataset);
recyclerView.setAdapter(myAdapter);

创建活动时,您的 RecyclerView 将加载您提供给 RecyclerView.Adapter 的新数据集。

PS 如果您实际上正在恢复活动并且从未销毁它并且想要更改已经存在的 RecyclerView 的适配器并刷新新项目,您可以在您的 onResume 方法中执行此操作

MyAdapter myAdapter = new MyAdapter(myDataset);
recyclerView.setAdapter(myAdapter);
myAdapter.notifyDataSetChanged();

另一种方法是,再次,如果您正在恢复(而不是创建)活动并且真的不想创建新的适配器并在每次活动恢复时设置它,那么您将不得不手动编辑您传递的数据集对象早于您的自定义适配器并调用:

myAdapter.notifyDataSetChanged();

通过说编辑我并不是说重新分配变量!如果您使用另一个对象重新分配变量,适配器将失去对该对象的引用并且它将无法工作。


推荐阅读