androidlistviewlistadapterfastscroll

FastScroll Behaves Strangely with a Custom ListAdapter which implements SectionIndexer


I am working on a ListActivity that has a inner class that is a child of SimpleAdapter that implements SectionIndexer.

class MySimpleAdapter extends SimpleAdapter implements SectionIndexer {

    HashMap<String, Integer> letters;
    Object[] sections;
    AlphabetIndexer alphaIndexer;
    public MySimpleAdapter(Context context, List<? extends Map<String, ?>> data,
            int resource, String[] from, int[] to, 
            HashMap<String, Integer> letters, Object[] sections) {
        super(context, data, resource, from, to);

        this.letters = letters;
        this.sections = sections;
    }

    @SuppressWarnings("unchecked")
    @Override
    public View getView(int position, View convertView, ViewGroup parent) {

        if (convertView == null) {
            convertView = getLayoutInflater().inflate(R.layout.common_image_row1, null);
        }

        HashMap<String, Object> data = (HashMap<String, Object>) getItem(position);
        Integer idArtist = Integer.parseInt((String) data.get("idArtist"));

        convertView.setTag(idArtist);

        ((TextView) convertView.findViewById(R.id.item_name))
            .setText((String) data.get("sName"));

        ImageView image = (ImageView) convertView.findViewById(R.id.item_image);
        image.setTag((String) data.get("sImageUrl"));           
        image.setImageResource(R.drawable.default_artwork);

        ((TextView) convertView.findViewById(R.id.item_count))
            .setText((String) data.get("iSongs") + " Songs");

        if (!bScrolling) {
            new API.DownloadImagesTask().execute(image);
        }
        return convertView;
    }

    public int getPositionForSection(int section) {
        String letter = (String) sections[section];

        return letters.get(letter);

    }

    public int getSectionForPosition(int position) {
        return 0;
    }

    public Object[] getSections() {
        return sections;
    }
}

The activity is receives a JSON object in a separate AysncTask. This object is made up of various JSONArrays whose keys are first letter of the item the items of the array. So, the array is made up of a bunch of items that begin with the letter "B". Therefore, that JSONArray's key is "B".

{
    B: ["ball", "buck", "bill"]
    C: ["charlie", "chuck", "chap"]
}

The object does not necessarily have all of the letters of the alphabet. I am also aware that order is not guaranteed with JSONObjects so I sort them.
List> maps = new ArrayList>(); ArrayList sections = new ArrayList(); HashMap letters = new HashMap();

        String[] alphabet = {"A","B","C","D","E","F","G","H","I","J","K","L","M","N"
                ,"O","P","Q","R","S","T","U","V","W","X","Y","Z"};
        int k = 0;
        for (int i = 0; i < alphabet.length; i++) {
            if (playlistArtists.optJSONArray(alphabet[i]) != null) {
                try {
                    JSONArray artists = playlistArtists.getJSONArray(alphabet[i]);
                    sections.add(alphabet[i]);

                    for (int j = 0; j < artists.length(); j++) {
                        JSONObject artist = (JSONObject) artists.get(j);
                        HashMap<String, String> map= new HashMap<String, String>();
                        map.put("idArtist", artist.getString("idArtist"));
                        map.put("sName", artist.getString("sName"));
                        map.put("sImageUrl", artist.getString("sImageUrl-thumb"));
                        map.put("iSongs", artist.getString("iSongs"));
                        maps.add(map);

                        letters.put(alphabet[i], k);
                        k++;
                    }
                } catch (JSONException e) {
                    Log.d(TAG,"JSONException in Music::GetMusicCatlog.doInBackground");
                    e.printStackTrace();
                }

            }
        }
        SimpleAdapter adapter = new MySimpleAdapter(Catalog.this, 
                maps,
                R.layout.common_image_row1,
                new String[] {"idArtist","sName", "sImageUrl", "iSongs" },
                new int[] {R.id.item_id, R.id.item_name, R.id.item_image, R.id.item_count }, 
                letters, 
                sections.toArray());
        setListAdapter(adapter);

The problem I am having is with FastScroll. I have everything working for the most part. The list is grouped by first letter and when using FastScroll the letter appears in the popup and goes to the correct group. The issue is when I let go of the FastScroll after going to the desired section the FastScroll "Jumps" to a random part of the list. It doesn't stay in the location where I let go of it. I think it is going to an arbitrary place in the section because I do not have the SectionIndexer implemented right. I think the problem is with this method.

public int getSectionForPosition(int position) {
        return 0;
    }

I am just not sure how to implement the SectionIndexer methods properly...


Solution

  • I saw many time getSectionForPosition implemented in the same way like getPositionForSection

        public int getPositionForSection(int section) {
            String letter = (String) sections[section];
    
            return letters.get(letter);
        }
    
        public int getSectionForPosition(int position) {
            String letter = (String) sections[position];
    
            return letters.get(letter);
        }