How to save selection of selected item in gridview when numColumns changes?

I have an ActionBarActivity with a GridView .

GridView has 2 columns in portrait and 3 columns in landscape.

When I select elements in a portrait (starting with an ActionMode ) and then rotate the device, highlighting the selected element shifts one element to the left. For example, if I select the second element and rotate, the first element will be highlighted. If I select the first element and rotate, the elements are not highlighted.

The actual choice in the code is correct, just the highlighting is wrong.

I noticed that this does not do if I keep numColumns the same for portrait and landscape orientation.

I believe that this problem arose after I changed my activity to ActionBarActivity , so this could be an error.

Does anyone know why and how to fix it?

+6
source share
2 answers

I had a similar scenario, and I decided that the problem was creating a custom mesh element with a boolean field to keep track of whether the element was selected or not, and then select the element accordingly through the user adapter. The following is an example of what I did:

(1) I created a custom mesh element with a boolean field, which we will call selectedStatus for simplicity. I also added the appropriate methods to the grid element class to get the selected status:

 public boolean getSelectedStatus () { return selectedStatus; } public void setSelectedStatus (boolean paramSelectedStatus) { this.selectedStatus = paramSelectedStatus; } 

(2) Then I created a custom Adapter that extends BaseAdapter process the created custom mesh object. In this Adapter I check whether the selected state of the mesh object is selected true or false and selects the element shown below accordingly:

 @Override public View getView (final int position, View convertView, ViewGroup parent) { // rest of getView() code... if (!yourGridObject.getSelectedStatus()) { convertView.setBackgroundColor(Color.TRANSPARENT); } else { convertView.setBackgroundColor(Color.LTGRAY); } // rest of getView() code... return convertView; } 

(3) Finally, you add onItemClickListener to set the selected state and background color of the grid elements when they are selected (click):

 yourGridView.setOnItemClickListener(new OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { YourGridObject yourGridObject = (YourGridObject) parent.getItemAtPosition(position); if (!yourGridObject.getSelected()) { view.setBackgroundColor(Color.LTGRAY); yourGridObject.setSelected(true); } else { view.setBackgroundColor(Color.TRANSPARENT); yourGridObject.setSelected(false); } } }); 

Implementing the selection in this way ensures that the selection (selection) of the grid elements does not change when the number of columns and rows changes, since the selection status is contained within the grid objects themselves.

+5
source

You do not need to manually process the selection of elements, as Willis suggests. Android fully supports what you ask. I assume that you are using an ArrayAdapter , however this answer applies to all adapters. Please note that some adapters (for example, CursorAdapter ) will not suffer from your published problem and do not require the following solution, since it already does this inside.

The problem is solved in two parts. First, the adapter must include stable identifiers. Two, your adapter should actually return stable identifiers. You will need to expand the ArrayAdapter or any adapter you are using. Then make sure that you define the following methods as shown below.

 private class MyAdapter extends ArrayAdapter<YourObjects> { @Override public boolean hasStableIds() { return true; } @Override public long getItemId(int position) { //Return a unique and stable id for the given position //While unique, Returning the position number does not count as stable. //For example: return getItem(position).methodThatReturnsUniqueValue(); } } 

Most adapters do not include hasStableIds . It is mainly used only when the selection mode is turned on. What I assume you are doing here. Returning to the truth, you essentially say that Android keeps track of activated (highlighted) elements based on their identification value instead of their position number.

Even with stable identifiers, you should actually return an identifier that is unique and stable in positional changes. Since most adapters do NOT allow stable identifiers, they usually return only the position number as a stable identifier. Technically, if a positionโ€™s position never changes with time, then the position number โ€œcanโ€ be used as a stable identifier. However, the safest way to return a stable / unique identifier is to assign a class object stored in the adapter and extract from it.

+3
source

Source: https://habr.com/ru/post/980500/


All Articles