【发布时间】:2019-03-14 20:51:14
【问题描述】:
我有cardsListLayout、titleLayout、cardMagazineLayout三种不同的布局,未来可能还会有更多,用作onCreateViewHolder方法的视图。
我想在onCreateViewHolder 方法中的视图之间切换,所以当用户从 AlertDialog 列表中选择时
这个 onOptionsItemSelected in MainActivity 哪里有菜单项“改变布局”,这样当用户按下它就会出现AlertDialog列表
@Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == R.id.change_layout) {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle(getString(R.string.choose_layout));
String[] layouts = {"Title Layout", "Cards List", "Card Magazine Layout"};
builder.setItems(layouts, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int index) {
switch (index) {
case 0: // Title layout
Toast.makeText(MainActivity.this,
"Title layout", Toast.LENGTH_LONG).show();
break;
case 1: // Cards List
Toast.makeText(MainActivity.this,
"Card list", Toast.LENGTH_LONG).show();
break;
case 2: // Cards Magazine Layout
Toast.makeText(MainActivity.this,
"Card Magazine Layout", Toast.LENGTH_LONG).show();
}
}
});
这是我的自定义适配器类PostAdapter
public class PostAdapter extends RecyclerView.Adapter<PostAdapter.PostViewHolder> {
private Context context;
private List<Item> items;
public PostAdapter(Context context, List<Item> items) {
this.context = context;
this.items = items;
}
@NonNull
@Override
public PostAdapter.PostViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(context);
// here's the three layouts that I can't switch between it
View cardsListLayout = inflater.inflate(R.layout.post_item_card_layout, parent, false);
View titleLayout = inflater.inflate(R.layout.post_item_grid_layout, parent, false);
View cardMagazineLayout = inflater.inflate(R.layout.card_magazine_layout,parent,false);
return new PostViewHolder(titleLayout);
}
@Override
public void onBindViewHolder(@NonNull PostViewHolder holder, int position) {
final Item item = items.get(position);
holder.postTitle.setText(item.getTitle());
final Document document = Jsoup.parse(item.getContent());
Elements elements = document.select("img");
Log.e("CODE", "Image: " + elements.get(0).attr("src"));
// Log.d("Text",document.text());
// holder.postDescription.setText(document.text());
Glide.with(context).load(elements.get(0).attr("src"))
.into(holder.postImage);
holder.itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent intent = new Intent(context, DetailsActivity.class);
intent.putExtra("url", item.getUrl());
intent.putExtra("title", item.getTitle());
intent.putExtra("content", item.getContent());
int youtubeThumbnailImagesetVisibility = 0;
Element element = document.body();
String youtubeThumbnailImageSrc = "";
String youTubeLink = "";
for (Element e : element.getElementsByClass
("YOUTUBE-iframe-video")) {
youtubeThumbnailImageSrc = e.attr("data-thumbnail-src");
youTubeLink = e.attr("src");
Log.e("YouTube thumbnail", youtubeThumbnailImageSrc);
Log.e("Youtube link", youTubeLink);
}
if (youtubeThumbnailImageSrc.isEmpty()) {
youtubeThumbnailImagesetVisibility = 8;
intent.putExtra("youtubeThumbnailImagesetVisibility",
youtubeThumbnailImagesetVisibility);
} else {
intent.putExtra("youtubeThumbnailImageSrc", youtubeThumbnailImageSrc);
intent.putExtra("youTubeLink", youTubeLink);
}
// String imageSrc = elements.get(0).attr("src");
// intent.putExtra("blogImage",imageSrc);
context.startActivity(intent);
}
});
}
@Override
public int getItemCount() {
return items.size();
}
public class PostViewHolder extends RecyclerView.ViewHolder {
ImageView postImage;
TextView postTitle;
TextView postDescription;
public PostViewHolder(View itemView) {
super(itemView);
postImage = itemView.findViewById(R.id.postImage);
postTitle = itemView.findViewById(R.id.postTitle);
postDescription = itemView.findViewById(R.id.postDescription);
}
}
}
我为每一个创建了两个不同的布局管理器,有一个 LinearLayoutManager 和一个 GridLayoutManager,目前我使用的是 GridLayout,所以我暂时评论了 LinearLayoutManger,直到我知道如何在它们之间切换
// linearLayoutManager = new LinearLayoutManager(this);
gridLayoutManager = new GridLayoutManager(this, 2, RecyclerView.VERTICAL, false);
// recyclerView.setLayoutManager(linearLayoutManager);
recyclerView.setLayoutManager(gridLayoutManager);
我渴望的结果
【问题讨论】:
-
适配器的想法是不要在不需要时重新创建视图。适配器只是检查特定位置的视图所需的视图类型。因此,如果您想创建另一个布局,那么您需要告诉适配器 notifyDataChanged 并通过 getItemViewType(position) 响应不同的视图类型,您希望重新生成单元格。
-
@peregreen 我想我们可以从 MainActivity 访问
adapter.onCreateViewHolder方法,还有recyclerView.addOnLayoutChangeListener我想说的是这个想法不是不可能的,有很多应用程序都有这个功能当用户选择另一个布局时,允许立即将布局更改为另一个布局 -
在我的情况下,当用户设置网格布局时,我将跨度计数设置为 2(或您想要的任何数字)并列出我将跨度计数设置为 1 的对象。
-
@sam 我明白了你的意思,但是如果有多种不同的布局,这个解决方案将不起作用,
post_item_grid_layout包含的内容不同于post_item_card_layout -
@DrMido 我不会说这是不可能的。我刚刚说过 viewType 是用于适配器的。所以经验法则:1)您想要不同的单元格 UI:然后创建不同的视图类型,2)您想要不同的单元格布局(列表或网格):然后只需更改布局管理器。 @Sam 的答案。
isViewWithCatalog提到的仅在与布局管理器存在 1 1 关系时才有效,因为它们不会使用彼此的缓存。但一般来说,这不是推荐的方法。
标签: android android-layout android-recyclerview android-viewholder recyclerview-layout