【问题标题】:Android ItemTouchHelper notifyItemChanged only works onceAndroid ItemTouchHelper notifyItemChanged 只工作一次
【发布时间】:2021-06-10 21:25:07
【问题描述】:

我目前正在学习android开发,但遇到了一个我没有找到解决方案的问题。

我有一个对产品进行分组的嵌套回收站视图。如果我向右滑动,项目会被移除,如果我向左滑动,它会弹回原始位置并打开带有编辑选项的叠加层。

问题是,如果我向左滑动两次,产品不会弹回。

我每次向左滑动时都使用notifyItemChanged方法重置产品。

当前行为:

PorductFragmant.java

View view = inflater.inflate(R.layout.fregment_products, container, false);
groups = view.findViewById(R.id.groups);

ArrayList<ProductGroup> productGroups = new ArrayList<>();
ArrayList<Product> products = new ArrayList<>();
products.add(new Product("Product #1", 500, 500));
products.add(new Product("Product #2", 400, 600));
products.add(new Product("Product #3", 500, 500));
products.add(new Product("Product #4", 500, 1000));
productGroups.add(new ProductGroup("Product Group #1", products));
productGroups.add(new ProductGroup("Product Group #1", new ArrayList<>()));

groups.setAdapter(new GroupAdapter(productGroups));
groups.setLayoutManager(new LinearLayoutManager(container.getContext()));

return view;

GroupAdapter.java

public class GroupAdapter extends RecyclerView.Adapter<GroupAdapter.ViewHolder> {
    private ArrayList<ProductGroup> groups = new ArrayList<>();

    public GroupAdapter(ArrayList<ProductGroup> groups) {
        setGroups(groups);
    }

    @NonNull
    @Override
    public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.product_group, parent, false);
        return new ViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
        holder.group = groups.get(position); // set the group model for the view holder
        holder.refresh(); // Refresh data in the view

        //Attach Touch Listener
        new ItemTouchHelper(new ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT) {
            @Override
            public boolean onMove(@NonNull RecyclerView recyclerView, @NonNull RecyclerView.ViewHolder viewHolder, @NonNull RecyclerView.ViewHolder target) {
                return false;
            }

            @Override
            public void onSwiped(@NonNull RecyclerView.ViewHolder viewHolder, int direction) {
                ProductAdapter.ViewHolder productHolder = (ProductAdapter.ViewHolder) viewHolder;
                productHolder.deleteBg.setVisibility(View.GONE);
                productHolder.editBg.setVisibility(View.GONE);

                switch (direction){
                    case ItemTouchHelper.RIGHT: {
                        //DELETE
                        holder.group.removeProduct(productHolder.getAdapterPosition()); //Remove the item
                        groups.set(holder.getAdapterPosition(), new ProductGroup((String) holder.title.getText(), holder.group.getProducts())); // update the group
                        notifyDataSetChanged(); // Notify Adapter
                        break;
                    }
                    case ItemTouchHelper.LEFT: {
                        //EDIT
                        holder.productAdapter.notifyItemChanged(productHolder.getAdapterPosition()); // Notify Item Changed

                        break;
                    }
                }
            }

            @Override
            public void onChildDraw(@NonNull Canvas c, @NonNull RecyclerView recyclerView, @NonNull RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, boolean isCurrentlyActive) {
                ProductAdapter.ViewHolder productHolder = (ProductAdapter.ViewHolder) viewHolder; // Cast view holder to product view holder

                // update visibility of the item's background
                if(isCurrentlyActive || dX != 0){
                    if(dX < 0){
                        productHolder.deleteBg.setVisibility(View.GONE);
                        productHolder.editBg.setVisibility(View.VISIBLE);
                    }else{
                        productHolder.editBg.setVisibility(View.GONE);
                        productHolder.deleteBg.setVisibility(View.VISIBLE);
                    }
                }else{
                    productHolder.deleteBg.setVisibility(View.GONE);
                    productHolder.editBg.setVisibility(View.GONE);
                }

                // update padding for the background
                // hide/show the opposite end of the background
                if(dX > 100)
                    productHolder.swipeBg.setPadding(0, 0, 0, 0);
                else if(dX > 0)
                    productHolder.swipeBg.setPadding(0, 0, 100, 0);
                else if(dX < -100)
                    productHolder.swipeBg.setPadding(0, 0, 0, 0);
                else if(dX < 0)
                    productHolder.swipeBg.setPadding(100, 0, 0, 0);


                getDefaultUIUtil().onDraw(c, recyclerView, productHolder.container, dX, dY, actionState, isCurrentlyActive);
            }
        }).attachToRecyclerView(holder.productsView);
    }

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

    public void setGroups(ArrayList<ProductGroup> groups){
        this.groups = groups;
        notifyDataSetChanged();
    }

    public static class ViewHolder extends RecyclerView.ViewHolder {
        public ProductAdapter productAdapter;
        public ProductGroup group;
        public ConstraintLayout header;
        public ConstraintLayout container;
        public TextView title;
        public ImageView closeBtn;
        public RecyclerView productsView;

        private boolean isOpen = false;
        public ViewHolder(@NonNull View itemView) {
            super(itemView);

            header = itemView.findViewById(R.id.header);
            container = itemView.findViewById(R.id.groupContainer);
            title = itemView.findViewById(R.id.title);
            closeBtn = itemView.findViewById(R.id.closeBtn);
            productsView = itemView.findViewById(R.id.products);

            //Hide products in group and set Layout Manager
            productsView.setVisibility(View.GONE);
            productsView.setLayoutManager(new LinearLayoutManager(itemView.getContext()));

            //Open / Close group
            header.setOnClickListener(v -> {
                isOpen = !isOpen;
                if(isOpen) {
                    productsView.setVisibility(View.VISIBLE);
                    closeBtn.setImageDrawable(ContextCompat.getDrawable(itemView.getContext(), R.drawable.ic_arrow_down));
                }
                else {
                    productsView.setVisibility(View.GONE);
                    closeBtn.setImageDrawable(ContextCompat.getDrawable(itemView.getContext(), R.drawable.ic_arrow_left));
                }
            });
        }

        public void refresh(){
            if(group == null) return;
            title.setText(group.getTitle()); // set group title
            productAdapter = new ProductAdapter(group.getProducts()); //set product adapter
            productsView.setAdapter(productAdapter); // assign the product adapter for the products recycle view
        }
    }
}

ProductAdapter.java

public class ProductAdapter extends RecyclerView.Adapter<ProductAdapter.ViewHolder>{
    private ArrayList<Product> products = new ArrayList<>();

    public ProductAdapter(ArrayList<Product> products) {
        setProducts(products);
    }

    @NonNull
    @Override
    public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.product, parent, false);
        return new ViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
        holder.product = products.get(position); // set the product model for the view holder
        holder.refresh();
    }

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

    public void setProducts(ArrayList<Product> products){
        this.products = products;
        notifyDataSetChanged();
    }


    public static class ViewHolder extends RecyclerView.ViewHolder {
        public Product product;
        public MaterialCardView container;
        public ImageView icon;
        public TextView title;
        public TextView price;
        public RelativeLayout imageBox;
        public MaterialCardView editImage;
        public LinearLayout swipeBg;
        public RelativeLayout editBg;
        public RelativeLayout deleteBg;

        private boolean isOpen = false;
        public ViewHolder(@NonNull View itemView) {
            super(itemView);

            container = itemView.findViewById(R.id.productContainer);
            icon = itemView.findViewById(R.id.icon);
            title = itemView.findViewById(R.id.title);
            price = itemView.findViewById(R.id.price);
            imageBox = itemView.findViewById(R.id.imageBox);
            editImage = itemView.findViewById(R.id.editImage);
            swipeBg = itemView.findViewById(R.id.swipeBg);
            editBg = itemView.findViewById(R.id.editBg);
            deleteBg = itemView.findViewById(R.id.deleteBg);

            //hide things
            imageBox.setVisibility(View.GONE);
            editBg.setVisibility(View.GONE);
            deleteBg.setVisibility(View.GONE);

            //show/hide image
            container.setOnClickListener(v -> {
                isOpen = !isOpen;
                imageBox.setVisibility(isOpen ? View.VISIBLE : View.GONE);
            });

            //Image edit button
            editImage.setOnClickListener(v -> {
                Toast.makeText(itemView.getContext(), "Edit", Toast.LENGTH_SHORT).show();
            });
        }

        @SuppressLint("SetTextI18n")
        public void refresh(){
            if(product == null) return;
            icon.setImageDrawable(Product.getIconByID(container.getContext(), product.getIconID())); // set icon
            price.setText( String.format(Locale.ENGLISH, "%.0f", product.getPrice()) + " Ft"); // set price
            title.setText(product.getName()); // set title
            //TODO IMAGE
        }

    }
}

【问题讨论】:

    标签: java android android-recyclerview material-components-android


    【解决方案1】:

    我想通了。

    我必须在notifyItemChanged() 之后添加一个notifyDataSetChanged()

    ********
    
    case ItemTouchHelper.LEFT: {
        //EDIT
                        
        holder.productAdapter.notifyItemChanged(productHolder.getAdapterPosition()); // Notify Item Changed
        notifyDataSetChanged();
    
        break;
    }
    
    ********
    

    【讨论】:

      猜你喜欢
      • 2021-08-25
      • 2020-09-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-02-17
      • 1970-01-01
      • 1970-01-01
      • 2011-08-30
      相关资源
      最近更新 更多