我试图找出Heterogeneous Recyclerview的工作原理,并根据我的需要进行调整。我有3个layouts
。第一个是带有BottomBar
的标题(在这种情况下不在底部),并且始终显示。其他2个layouts
会根据BottomBar
中的哪个标签进行切换。 BottomBar
中的第一个标签会显示grid layout
,第二个标签会显示list layout
。我已经成功实现了它,但是有轻微的轻弹和更改列表并不是很顺利。此外,单击第二个选项卡时,仍然会选择第一个选项卡。在第二个选项卡上单击,然后选中它。如何使其更顺畅,并在第一次单击时选择特定选项卡?
Adapter
public class ProfileAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private final int HEADER_TYPE = 0;
private final int IMAGE_GRID_TYPE = 1;
private final int IMAGE_LIST_TYPE = 2;
private final int cellSize;
private Context mContext;
private List<Home> mHomeList;
private boolean onBind;
private OnHeaderItemClickedListener mListener;
int selectedPosition;
public ProfileAdapter(Context context, List<Home> homeList) {
this.mContext = context;
this.mHomeList = homeList;
this.cellSize = Utils.getScreenWidth(context) / 3;
}
public interface OnHeaderItemClickedListener {
void onTabGridClicked();
void onTabListClicked();
}
@Override
public void onDetachedFromRecyclerView(RecyclerView recyclerView) {
super.onDetachedFromRecyclerView(recyclerView);
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(mContext);
switch (viewType) {
case HEADER_TYPE:
View viewHeader = inflater.inflate(R.layout.item_profile_header, parent, false);
StaggeredGridLayoutManager.LayoutParams lp1 = (StaggeredGridLayoutManager.LayoutParams) viewHeader.getLayoutParams();
lp1.setFullSpan(true);
viewHeader.setLayoutParams(lp1);
return new ProfileAdapter.HeaderHolder(viewHeader);
case IMAGE_GRID_TYPE:
View viewGridImage = inflater.inflate(R.layout.item_profile_grid_image, parent, false);
StaggeredGridLayoutManager.LayoutParams layoutParams = (StaggeredGridLayoutManager.LayoutParams) viewGridImage.getLayoutParams();
layoutParams.height = cellSize;
layoutParams.width = cellSize;
layoutParams.setFullSpan(false);
viewGridImage.setLayoutParams(layoutParams);
return new ImageGridHolder(viewGridImage);
case IMAGE_LIST_TYPE:
View viewListImage = inflater.inflate(R.layout.item_profile_list_image, parent, false);
StaggeredGridLayoutManager.LayoutParams lp3 = (StaggeredGridLayoutManager.LayoutParams) viewListImage.getLayoutParams();
lp3.setFullSpan(true);
viewListImage.setLayoutParams(lp3);
return new ImageListHolder(viewListImage);
}
return null;
}
@Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
switch (holder.getItemViewType()) {
case HEADER_TYPE:
onBind = true;
bindHeader((HeaderHolder) holder, mHomeList.get(position));
onBind = false;
break;
case IMAGE_GRID_TYPE:
onBind = true;
bindGridImage((ImageGridHolder) holder, mHomeList.get(position));
onBind = false;
break;
case IMAGE_LIST_TYPE:
onBind = true;
bindListImage((ImageListHolder) holder, mHomeList.get(position));
onBind = false;
break;
}
}
private void bindHeader(final HeaderHolder holder, Home home) {
holder.getItemProfileHeaderBinding().setHome(home);
holder.getItemProfileHeaderBinding().bottomBar.setOnTabSelectListener(new OnTabSelectListener() {
@Override
public void onTabSelected(@IdRes int tabId) {
switch (tabId) {
case R.id.tab_grid:
if (!onBind) {
mListener.onTabGridClicked();
selectedPosition = holder.getLayoutPosition();
notifyItemChanged(selectedPosition);
}
break;
case R.id.tab_list:
if (!onBind) {
mListener.onTabListClicked();
selectedPosition = holder.getLayoutPosition();
notifyItemChanged(selectedPosition);
}
break;
}
}
});
adjustTabs(holder);
}
private void bindGridImage(ImageGridHolder holder, Home home) {
holder.getItemProfileGridImageBinding().setHome(home);
Uri uri = new Uri.Builder()
.scheme(UriUtil.LOCAL_RESOURCE_SCHEME)
.path(String.valueOf(R.drawable.ap_android_icon))
.build();
holder.getItemProfileGridImageBinding().ivImage.setImageURI(uri);
}
private void bindListImage(ImageListHolder holder, Home home) {
holder.getItemProfileListImageBinding().setHome(home);
}
@Override
public int getItemViewType(int position) {
if (isPositionHeader(position)) {
return HEADER_TYPE;
}
if (mHomeList.get(position).getGridListType() == 2) {
return IMAGE_LIST_TYPE;
} else {
return IMAGE_GRID_TYPE;
}
}
private boolean isPositionHeader(int position) {
return position == 0;
}
@Override
public int getItemCount() {
return mHomeList.size();
}
private void adjustTabs(HeaderHolder holder) {
holder.getItemProfileHeaderBinding().bottomBar.getTabWithId(R.id.tab_grid).setPadding(0, 30, 0, 0);
holder.getItemProfileHeaderBinding().bottomBar.getTabWithId(R.id.tab_list).setPadding(0, 30, 0, 0);
holder.getItemProfileHeaderBinding().bottomBar.getTabWithId(R.id.tab_group).setPadding(0, 30, 0, 0);
holder.getItemProfileHeaderBinding().bottomBar.getTabWithId(R.id.tab_bookmark).setPadding(0, 30, 0, 0);
}
private static class HeaderHolder extends RecyclerView.ViewHolder {
ItemProfileHeaderBinding mItemProfileHeaderBinding;
HeaderHolder(View itemView) {
super(itemView);
mItemProfileHeaderBinding = DataBindingUtil.bind(itemView);
}
ItemProfileHeaderBinding getItemProfileHeaderBinding() {
return mItemProfileHeaderBinding;
}
}
private static class ImageGridHolder extends RecyclerView.ViewHolder {
ItemProfileGridImageBinding mItemProfileGridImageBinding;
ImageGridHolder(View itemView) {
super(itemView);
mItemProfileGridImageBinding = DataBindingUtil.bind(itemView);
}
ItemProfileGridImageBinding getItemProfileGridImageBinding() {
return mItemProfileGridImageBinding;
}
}
private static class ImageListHolder extends RecyclerView.ViewHolder {
ItemProfileListImageBinding mItemProfileListImageBinding;
ImageListHolder(View itemView) {
super(itemView);
mItemProfileListImageBinding = DataBindingUtil.bind(itemView);
}
ItemProfileListImageBinding getItemProfileListImageBinding() {
return mItemProfileListImageBinding;
}
}
public void addOnHeaderItemClickListener(OnHeaderItemClickedListener listener) {
this.mListener = listener;
}
}
选项卡点击发生的 Fragment
public class ProfileFragment extends BaseFragment implements ProfileAdapter.OnHeaderItemClickedListener {
private static final String ARG_PARAM1 = "param1";
FragmentProfileMultipleBinding mBinder;
FragmentManager mFragmentManager;
Home mHome;
ProfileAdapter mAdapter;
List<Home> mHomeList;
StaggeredGridLayoutManager mManager;
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
mBinder = DataBindingUtil.inflate(inflater, R.layout.fragment_profile_multiple, container, false);
mFragmentManager = getChildFragmentManager();
mHome = new Home();
populateList();
mManager = new StaggeredGridLayoutManager(3, StaggeredGridLayoutManager.VERTICAL);
mAdapter = new ProfileAdapter(getContext(), mHomeList);
mBinder.rvGrid.setLayoutManager(mManager);
mBinder.rvGrid.setAdapter(mAdapter);
mAdapter.addOnHeaderItemClickListener(this);
setUIListeners();
return mBinder.getRoot();
}
private void populateList() {
for (int i = 0; i < 20; i++) {
mHomeList.add(i, mHome);
}
}
private void populateUpdatedList() {
for (Home home : mHomeList) {
home.setGridListType(2);
}
}
private void populateGridList() {
for (Home home : mHomeList) {
home.setGridListType(5);
}
}
@Override
public void onTabGridClicked() {
populateGridList();
mManager = new StaggeredGridLayoutManager(3, StaggeredGridLayoutManager.VERTICAL);
}
@Override
public void onTabListClicked() {
populateUpdatedList();
mManager = new StaggeredGridLayoutManager(1, StaggeredGridLayoutManager.VERTICAL);
}
}
修改
我添加了notifyDataSetChanged();
而不是notifyItemChanged(selectedPosition);
,并且更改是即时的,但第二个标签永远不会被选中,我无法在第一个和第二个之间切换。我必须点击第三个才能回到第一个。好像标签位置卡住了。