【问题标题】:RecyclerView not showing lists yet data is being fed to adapterRecyclerView 未显示列表,但数据正在馈送到适配器
【发布时间】:2020-10-06 11:16:18
【问题描述】:

我正在将数据从FireStore 获取到自定义类对象中,当我在 for 循环期间使用Toast 时,我可以显示我想要的所有数据,但我传递给我的适配器的列表是空的.

我试图查明为什么它是空的,但没有任何效果。

这是我的主要课程:

products.whereEqualTo("IDliv","kITQ8wiPshsnWqHDlP5D").addSnapshotListener(new EventListener<QuerySnapshot>() {
        @Override
        public void onEvent(@Nullable QuerySnapshot documentSnapshots, @Nullable FirebaseFirestoreException e) {
            assert documentSnapshots != null;
            for (DocumentChange document : documentSnapshots.getDocumentChanges()) {
            generalObject obj=document.getDocument().toObject(generalObject.class);
            for(int i=0;i<obj.getproducts().size();i++){
                String[] body;
                  body=obj.getproducts().get(i).toString().split("\\+");
                ProductModel p = new ProductModel(body[0].toString(), body[1].toString(), body[2].toString());
                prod.add(p);

            }
            }

    }
    });
if(prod.size()>0) {
    adapter = new ProductAdapter(prod);
    RecyclerView recview = findViewById(R.id.items_recycler_view);
    recview.setHasFixedSize(true);
    recview.setLayoutManager(new LinearLayoutManager(this));
    recview.setAdapter(adapter);
}else{
    Toast.makeText(getApplicationContext(),"this list is empty",Toast.LENGTH_LONG).show();
}
    }

我的适配器类是这样的:

public class ProductAdapter  extends RecyclerView.Adapter<ProductAdapter.ViewHolder> {

    private ArrayList<ProductModel> products;

    public ProductAdapter(ArrayList<ProductModel> product) {
        this.products = product;
    }

    @NonNull
    @Override
    public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View v = (View) LayoutInflater.from(parent.getContext()).inflate(R.layout.adapter_product, parent, false);

        return new ViewHolder(v);
    }

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

        ProductModel prod = products.get(position);

        holder.name.setText(prod.getGetProductName());
        holder.description.setText(prod.getProductMarque());
        holder.qty.setText(prod.getProductQte());


    }

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

    public static class ViewHolder extends RecyclerView.ViewHolder {
        public final View view;
        public final TextView name;
        public final TextView description;
        public final TextView qty;

        public ViewHolder(View view) {
            super(view);
            this.view = view;
            name = view.findViewById(R.id.productsName);
            description = view.findViewById(R.id.marque);
            qty=view.findViewById(R.id.quantity);


        }
    }
}

知道有什么问题吗?

【问题讨论】:

    标签: android arraylist android-recyclerview google-cloud-firestore adapter


    【解决方案1】:

    需要在事件回调结束时添加notifyDataSetChanged()

        @Override
        public void onEvent(@Nullable QuerySnapshot documentSnapshots, @Nullable FirebaseFirestoreException e) {
            assert documentSnapshots != null;
            for (DocumentChange document : documentSnapshots.getDocumentChanges()) {
            generalObject obj=document.getDocument().toObject(generalObject.class);
            for(int i=0;i<obj.getproducts().size();i++){
                String[] body;
                  body=obj.getproducts().get(i).toString().split("\\+");
                ProductModel p = new ProductModel(body[0].toString(), body[1].toString(), body[2].toString());
                prod.add(p);
    
            }
            adapter.notifyDataSetChanged(); // <<<<<< here is the change
       }
    

    另一件事:if(prod.size()&gt;0) 条件太早了,因为它不会匹配,因为数据是在后台线程上接收的,所以这个条件永远不会满足。将此部分更改为:

    adapter = new ProductAdapter(prod);
    RecyclerView recview = findViewById(R.id.items_recycler_view);
    recview.setHasFixedSize(true);
    recview.setLayoutManager(new LinearLayoutManager(this));
    recview.setAdapter(adapter);
    
    if (prod.size()==0) {
        Toast.makeText(getApplicationContext(),"this list is empty",Toast.LENGTH_LONG).show();
    }
    

    【讨论】:

    • 非常感谢!
    【解决方案2】:

    您来自 Firebase 的查询是异步发生的,因此查询数据会在您实例化适配器后返回并添加到产品列表中。

    没有满足您的 if 语句,因为产品列表实际上是空的,因为该代码在查询返回之前被执行。

    // This is false here because this block is getting executed before 
    // the Firebase query returns the data. However your not seeing the 
    // toast, because you are passing the wrong context. Toast takes 
    // an activity context, not application context.
    
    if(prod.size()>0) {
        adapter = new ProductAdapter(prod);
        RecyclerView recview = findViewById(R.id.items_recycler_view);
        recview.setHasFixedSize(true);
        recview.setLayoutManager(new LinearLayoutManager(this));
        recview.setAdapter(adapter);
    }else{
        Toast.makeText(getApplicationContext(),"this list is empty",Toast.LENGTH_LONG).show();
    }
    

    尝试稍微更改代码以创建适配器,然后在查询返回后添加数据:

    adapter = new ProductAdapter();
        RecyclerView recview = findViewById(R.id.items_recycler_view);
        recview.setHasFixedSize(true);
        recview.setLayoutManager(new LinearLayoutManager(this));
        recview.setAdapter(adapter);
    
    
    products.whereEqualTo("IDliv","kITQ8wiPshsnWqHDlP5D").addSnapshotListener(new EventListener<QuerySnapshot>() {
            @Override
            public void onEvent(@Nullable QuerySnapshot documentSnapshots, @Nullable FirebaseFirestoreException e) {
                assert documentSnapshots != null;
                for (DocumentChange document : documentSnapshots.getDocumentChanges()) {
                generalObject obj=document.getDocument().toObject(generalObject.class);
    
                for(int i=0;i<obj.getproducts().size();i++){
                    String[] body;
                      body=obj.getproducts().get(i).toString().split("\\+");
                    ProductModel p = new ProductModel(body[0].toString(), body[1].toString(), body[2].toString());
                    prodList.add(p);
    
                }
    
                // Tell the adapter we have new data that we want to add
                adapter.addNewData(prodList)
    
                }
    
        }
        });
    

    然后稍微改变你的适配器:

    public class ProductAdapter  extends RecyclerView.Adapter<ProductAdapter.ViewHolder> {
    
        private ArrayList<ProductModel> products;
    
        public ProductAdapter() {
            this.products = new ArrayList<ProductModel>();
        }
    
        @NonNull
        @Override
        public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
            View v = (View) LayoutInflater.from(parent.getContext()).inflate(R.layout.adapter_product, parent, false);
    
            return new ViewHolder(v);
        }
    
        @Override
        public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
    
            ProductModel prod = products.get(position);
    
            holder.name.setText(prod.getGetProductName());
            holder.description.setText(prod.getProductMarque());
            holder.qty.setText(prod.getProductQte());
    
    
        }
    
        @Override
        public int getItemCount() {
            if (products != null) {
                return products.size();
            } else {
                return 0;
            }
        }
    
        public void addNewData(data: List<ProductModel>) {
            this.products.clear();
            this.products.addAll(data);
            notifyDatasetChanged(); //This will tell the adapter we have new data and to re-inflate the views
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2020-07-02
      • 2018-05-29
      • 1970-01-01
      • 2021-12-07
      • 2018-08-08
      • 2019-09-21
      • 2017-01-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多