Android-GridView 中带复选框的项目选择
Item-Selection with Checkbox in Android-GridView
我遇到了 Android GridView 的问题。我已经尝试了 Whosebug 的各种解决方案,但 none 确实有效。
我在 ArrayAdapter 的帮助下填充 GridView。适配器扩充仅包含图像和复选框的布局。我正在使用 "convertView" 来防止添加图像时出现闪烁(将近 500 张图像添加到 GridView)。
问题:当我选中复选框并滚动时,选中状态消失了。此外,例如,当我选中多个 GridView 项目的复选框时,选择模式会无休止地继续所有以下元素。
我的 GridView 是 RelativeLayout 的子元素。 RelativeLayout 用作 ViewPager 中使用的片段的根元素:
<GridView
android:id="@+id/MainGrid"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/appBackgroundColor"
android:drawSelectorOnTop="false"
android:listSelector="#00000000"
android:numColumns="2"
android:paddingLeft="6dp"
android:paddingTop="5dp"
android:paddingRight="6dp"
android:translationZ="2dp" />
我正在线程的帮助下填充 GridView,该线程正在从网站下载图像数据。我认为这应该没有问题,但为了完整起见,这里是代码:
//Declaring the Array
ArrayList<GridImage> ImageArray = new ArrayList<>();
//And the adapter
Adapter_GridAdapter GridViewAdapter = new Adapter_GridAdapter (getActivity().getApplicationContext(), ImageArray );
//The following is executed 500 times in a thread
ImageArray.add(new GridImage(URL));
getActivity().runOnUiThread(new Runnable() {
@Override
public void run() {
GridViewAdapter.notifyDataSetChanged();
}
});
GridView适配器的代码:
public class Adapter_GridAdapter extends ArrayAdapter<GridImage> {
Context context;
public Adapter_GridAdapter (Context context, ArrayList<GridImage> SearchResults) {
super(context, 0, SearchResults);
this.context = context;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = LayoutInflater.from(getContext());
View view = convertView;
if (convertView == null) {
view = inflater.inflate(R.layout.griditem_ig_post, null);
final ImageView ThisViewIMG = view.findViewById(R.id.GridImageView);
//Calculating Image Height (Square Image)
ThisViewIMG.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
ThisViewIMG.removeOnLayoutChangeListener(this);
ThisViewIMG.getLayoutParams().height = ThisViewIMG.getWidth();
ThisViewIMG.requestLayout();
}
});
}
final GridImage ThisImg = getItem(position);
final ImageView ThumbnailImage = view.findViewById(R.id.GridImageView);
//THIS IS THE CUSTOM CHECKBOX!
final CustomCheckBox scb = (CustomCheckBox) view.findViewById(R.id.MyCheckBox);
//I AM SAVING THE VALUE IN THE OBJECT (TRY #38181 THAT DIDN'T WORK)
scb.setChecked(ThisImg.IsChecked);
scb.setOnCheckedChangeListener(new CustomCheckBox.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CustomCheckBox checkBox, boolean isChecked) {
Log.d("CustomCheckBox", String.valueOf(isChecked));
ThisImg.setChecked(isChecked);
}
});
Glide.with(context).load(Post.IMG_ThumbnailURL).fitCenter().into(ThumbnailImage);
return view;
}
}
对象本身很简单,问题(我认为)也不应该隐藏在这里:
public class GridImage{
public String PostURL;
public Boolean IsChecked = false;
GridImage(String URL){
PostURL = URL;
}
public void setChecked(Boolean checked) {
IsChecked = checked;
}
}
我已经尝试过的:
- - 我的解决方案是使用标签而不是直接保存到对象中,对吗?
- - SparseBooleanArray,但我不是 100% 确定我这样做是正确的
在使用 ListView/GridView 适配器时,我总是避免使用 final 和 onCheckedChangeListener 因为有时两者都可能有问题逻辑似乎是正确的,所以试试下面的代码:
@Override
public View getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = LayoutInflater.from(getContext());
View view = convertView;
if (convertView == null) {
view = inflater.inflate(R.layout.griditem_ig_post, null);
ImageView ThisViewIMG = view.findViewById(R.id.GridImageView);
//Calculating Image Height (Square Image)
ThisViewIMG.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
v.removeOnLayoutChangeListener(this);
v.getLayoutParams().height = v.getWidth();
v.requestLayout();
}
});
}
GridImage ThisImg = getItem(position);
ImageView ThumbnailImage = view.findViewById(R.id.GridImageView);
//THIS IS THE CUSTOM CHECKBOX!
CustomCheckBox scb = (CustomCheckBox) view.findViewById(R.id.MyCheckBox);
scb.setChecked(ThisImg.IsChecked);
scb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
CustomCheckBox cb = (CustomCheckBox)view;
int position = (int)cb.getTag();
GridImage ThisImg = getItem(position);
Log.d("CustomCheckBox", String.valueOf(!ThisImg.IsChecked));
ThisImg.setChecked(!ThisImg.IsChecked);
cb.setChecked(ThisImg.IsChecked);
}
});
Glide.with(context).load(Post.IMG_ThumbnailURL).fitCenter().into(ThumbnailImage);
scb.setTag(position);
return view;
}
希望对您有所帮助!
我遇到了 Android GridView 的问题。我已经尝试了 Whosebug 的各种解决方案,但 none 确实有效。
我在 ArrayAdapter 的帮助下填充 GridView。适配器扩充仅包含图像和复选框的布局。我正在使用 "convertView" 来防止添加图像时出现闪烁(将近 500 张图像添加到 GridView)。
问题:当我选中复选框并滚动时,选中状态消失了。此外,例如,当我选中多个 GridView 项目的复选框时,选择模式会无休止地继续所有以下元素。
我的 GridView 是 RelativeLayout 的子元素。 RelativeLayout 用作 ViewPager 中使用的片段的根元素:
<GridView
android:id="@+id/MainGrid"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/appBackgroundColor"
android:drawSelectorOnTop="false"
android:listSelector="#00000000"
android:numColumns="2"
android:paddingLeft="6dp"
android:paddingTop="5dp"
android:paddingRight="6dp"
android:translationZ="2dp" />
我正在线程的帮助下填充 GridView,该线程正在从网站下载图像数据。我认为这应该没有问题,但为了完整起见,这里是代码:
//Declaring the Array
ArrayList<GridImage> ImageArray = new ArrayList<>();
//And the adapter
Adapter_GridAdapter GridViewAdapter = new Adapter_GridAdapter (getActivity().getApplicationContext(), ImageArray );
//The following is executed 500 times in a thread
ImageArray.add(new GridImage(URL));
getActivity().runOnUiThread(new Runnable() {
@Override
public void run() {
GridViewAdapter.notifyDataSetChanged();
}
});
GridView适配器的代码:
public class Adapter_GridAdapter extends ArrayAdapter<GridImage> {
Context context;
public Adapter_GridAdapter (Context context, ArrayList<GridImage> SearchResults) {
super(context, 0, SearchResults);
this.context = context;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = LayoutInflater.from(getContext());
View view = convertView;
if (convertView == null) {
view = inflater.inflate(R.layout.griditem_ig_post, null);
final ImageView ThisViewIMG = view.findViewById(R.id.GridImageView);
//Calculating Image Height (Square Image)
ThisViewIMG.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
ThisViewIMG.removeOnLayoutChangeListener(this);
ThisViewIMG.getLayoutParams().height = ThisViewIMG.getWidth();
ThisViewIMG.requestLayout();
}
});
}
final GridImage ThisImg = getItem(position);
final ImageView ThumbnailImage = view.findViewById(R.id.GridImageView);
//THIS IS THE CUSTOM CHECKBOX!
final CustomCheckBox scb = (CustomCheckBox) view.findViewById(R.id.MyCheckBox);
//I AM SAVING THE VALUE IN THE OBJECT (TRY #38181 THAT DIDN'T WORK)
scb.setChecked(ThisImg.IsChecked);
scb.setOnCheckedChangeListener(new CustomCheckBox.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CustomCheckBox checkBox, boolean isChecked) {
Log.d("CustomCheckBox", String.valueOf(isChecked));
ThisImg.setChecked(isChecked);
}
});
Glide.with(context).load(Post.IMG_ThumbnailURL).fitCenter().into(ThumbnailImage);
return view;
}
}
对象本身很简单,问题(我认为)也不应该隐藏在这里:
public class GridImage{
public String PostURL;
public Boolean IsChecked = false;
GridImage(String URL){
PostURL = URL;
}
public void setChecked(Boolean checked) {
IsChecked = checked;
}
}
我已经尝试过的:
- - 我的解决方案是使用标签而不是直接保存到对象中,对吗?
- - SparseBooleanArray,但我不是 100% 确定我这样做是正确的
在使用 ListView/GridView 适配器时,我总是避免使用 final 和 onCheckedChangeListener 因为有时两者都可能有问题逻辑似乎是正确的,所以试试下面的代码:
@Override
public View getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = LayoutInflater.from(getContext());
View view = convertView;
if (convertView == null) {
view = inflater.inflate(R.layout.griditem_ig_post, null);
ImageView ThisViewIMG = view.findViewById(R.id.GridImageView);
//Calculating Image Height (Square Image)
ThisViewIMG.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
v.removeOnLayoutChangeListener(this);
v.getLayoutParams().height = v.getWidth();
v.requestLayout();
}
});
}
GridImage ThisImg = getItem(position);
ImageView ThumbnailImage = view.findViewById(R.id.GridImageView);
//THIS IS THE CUSTOM CHECKBOX!
CustomCheckBox scb = (CustomCheckBox) view.findViewById(R.id.MyCheckBox);
scb.setChecked(ThisImg.IsChecked);
scb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
CustomCheckBox cb = (CustomCheckBox)view;
int position = (int)cb.getTag();
GridImage ThisImg = getItem(position);
Log.d("CustomCheckBox", String.valueOf(!ThisImg.IsChecked));
ThisImg.setChecked(!ThisImg.IsChecked);
cb.setChecked(ThisImg.IsChecked);
}
});
Glide.with(context).load(Post.IMG_ThumbnailURL).fitCenter().into(ThumbnailImage);
scb.setTag(position);
return view;
}
希望对您有所帮助!