Элемент строки в представлении Android-ресайклера дублируется при прокрутке, а представление расширяется относительно макета

1

В представлении Recycler есть два текстовых поля в каждой строке. Когда мы нажимаем на один текстовый просмотр, он расширяет расширяемый макет. Этот расширяемый макет дублирует при прокрутке.

Вот мой класс адаптера

public class AlbumsAdapter extends RecyclerView.Adapter<AlbumsAdapter.MyViewHolder> {

private Context mContext;
private List<Album> albumList;

RecyclerView rv;
public class MyViewHolder extends RecyclerView.ViewHolder {
    public TextView title, count;
    public ImageView thumbnail, overflow;
    ExpandableRelativeLayout expandableLayout11;


    public MyViewHolder(final View view) {
        super(view);
        title = (TextView) view.findViewById(R.id.title);
        count = (TextView) view.findViewById(R.id.count);
        thumbnail = (ImageView) view.findViewById(R.id.thumbnail);
        expandableLayout11 = (ExpandableRelativeLayout)view. findViewById(R.id.expandableLayout11);


    }
}



public AlbumsAdapter(Context mContext, List<Album> albumList ) {
    this.mContext = mContext;
    this.albumList = albumList;

}

@Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    View itemView = LayoutInflater.from(parent.getContext())
            .inflate(R.layout.album_card, parent, false);

    return new MyViewHolder(itemView);
}

@Override
public void onBindViewHolder(final MyViewHolder holder, final int position) {
    final Album album = albumList.get(position);
    holder.title.setText(album.getName());
    holder.count.setText(album.getNumOfSongs() + " songs");

holder.title.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
          holder.expandableLayout11.toggle();

    }

});


   }

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

}

Моя основная деятельность

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main2);

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);
    getSupportActionBar().setHomeButtonEnabled(true);
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);

    initCollapsingToolbar();

    recyclerView = (RecyclerView) findViewById(R.id.recycler_view);

    albumList = new ArrayList<>();
    adapter = new AlbumsAdapter(this, albumList );

    RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(this);
    recyclerView.setLayoutManager(mLayoutManager);
    recyclerView.addItemDecoration(new GridSpacingItemDecoration(1, dpToPx(10), true));
    recyclerView.setItemAnimator(new DefaultItemAnimator());
    recyclerView.setAdapter(adapter);

    prepareAlbums();

    try {
        Glide.with(this).load(R.drawable.cover).into((ImageView) findViewById(R.id.backdrop));
    } catch (Exception e) {
        e.printStackTrace();
    }
}

/**
 * Initializing collapsing toolbar
 * Will show and hide the toolbar title on scroll
 */
private void initCollapsingToolbar() {
    final CollapsingToolbarLayout collapsingToolbar =
            (CollapsingToolbarLayout) findViewById(R.id.collapsing_toolbar);
    collapsingToolbar.setTitle("Developer List");
    AppBarLayout appBarLayout = (AppBarLayout) findViewById(R.id.appbar);
    appBarLayout.setExpanded(true);

    // hiding & showing the title when toolbar expanded & collapsed
    appBarLayout.addOnOffsetChangedListener(new AppBarLayout.OnOffsetChangedListener() {
        boolean isShow = false;
        int scrollRange = -1;

        @Override
        public void onOffsetChanged(AppBarLayout appBarLayout, int verticalOffset) {
            if (scrollRange == -1) {
                scrollRange = appBarLayout.getTotalScrollRange();
            }
            if (scrollRange + verticalOffset == 0) {
                collapsingToolbar.setTitle("Developer List");
                isShow = true;
            } else if (isShow) {
                collapsingToolbar.setTitle("Developer List");
                isShow = false;
            }
        }
    });
}


private void prepareAlbums() {
    int[] covers = new int[]{
            R.drawable.album1,
            R.drawable.album2,
            R.drawable.album3,
            R.drawable.album4,
            R.drawable.album5,
            R.drawable.album6,
            R.drawable.album7,
            R.drawable.album8,
            R.drawable.album9,
            R.drawable.album10,
            R.drawable.album11};

    Album a = new Album("True Romance", 13, covers[0]);
    albumList.add(a);

    a = new Album("Xscpae", 8, covers[1]);
    albumList.add(a);

    a = new Album("Maroon 5", 11, covers[2]);
    albumList.add(a);

    a = new Album("Born to Die", 12, covers[3]);
    albumList.add(a);

    a = new Album("Honeymoon", 14, covers[4]);
    albumList.add(a);

    a = new Album("I Need a Doctor", 1, covers[5]);
    albumList.add(a);

    a = new Album("Loud", 11, covers[6]);
    albumList.add(a);

    a = new Album("Legend", 14, covers[7]);
    albumList.add(a);

    a = new Album("Hello", 11, covers[8]);
    albumList.add(a);

    a = new Album("Greatest Hits", 17, covers[9]);
    albumList.add(a);

    adapter.notifyDataSetChanged();
}
}
Теги:
android-recyclerview
expandablerecyclerview

2 ответа

2

В вашем классе модели Album добавьте флаг boolean, скажем: isExpanded и добавьте установщик геттера для того же самого, предположим, что они:

// Getter for isExpanded flag
public boolean isExpanded() {
 return isExpanded;
}

// setter for isExpanded flag
public void setIsExpanded(boolean flag) {
 isExpanded = flag;
}

Затем выполните следующие действия в методе onBindViewHolder:

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

 final Album album = albumList.get(position);
 holder.title.setText(album.getName());
 holder.count.setText(album.getNumOfSongs() + " songs");

 if(album.isExpanded()) {

   holder.expandableLayout11.expand();

   } else {

   holder.expandableLayout11.collapse();
   }

 holder.title.setOnClickListener(new View.OnClickListener() {
   @Override
   public void onClick(View view) {
      // toggle view
      holder.expandableLayout11.toggle();
      // toggle isExpanded flag
      album.setIsExpanded( ! album.isExpanded() )
  }
}
  • 0
    Спасибо за ваш комментарий, как вы думаете, мой обходной путь, ваш работает на тех же принципах, что и мой.
  • 0
    @Abbas вы устанавливаете длительность на 0, что означает время, до которого анимация просмотра должна длиться. Но мое решение - в соответствии с документацией по представлению переработчика, в которой говорится, что нам нужно указывать каждое состояние просмотра, независимо от того, связано ли оно с содержимым в каждой строке или с видимостью.
Показать ещё 2 комментария
0

Элементы в RecyclerView повторно используются. Поэтому вы должны сохранить положение расширяемых элементов.
Затем измените состояние expandableLayout при загрузке строки

int[] expandablePositionArray; // define int array for save all position of expandable items

public AlbumsAdapter(Context mContext, List<Album> albumList ) {
    this.mContext = mContext;
    this.albumList = albumList;
    // init int array
    expandablePositionList = new int[albumList.size()];
}

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

   // expand or collapse expandableLayout11 when row load base on expandable position 
   if(expandablePositionList[position] == 1){
       holder.expandableLayout11.expand();
   }else{
       holder.expandableLayout11.collapse();
   }

    holder.title.setOnClickListener(new View.OnClickListener() {
       @Override
       public void onClick(View view) {
          holder.expandableLayout11.toggle();

          // save the position of expandable row
          if(expandablePositionList[position] == 1){
               expandablePositionList[position] = 0;
          }else{
               expandablePositionList[position] = 1;
          }
    }
}

Ещё вопросы

Сообщество Overcoder
Наверх
Меню