我希望模仿最新音乐应用程序中的功能,即弹出的漂亮小光标,可让人快速滚动到他们正在寻找的艺术家/专辑/曲目:
是否有方法可以在Android SDK的ListView
中启用此类功能?
答案 0 :(得分:16)
让列表适配器实现SectionIndexer。音乐应用程序还利用AlphabetIndexer来完成一些繁重的工作。还可以在实际setFastScrollEnabled(true)
上使用ListView
来启用此功能。
编辑:如果您没有使用CursorAdapter,则无法使用AlphabetIndexer。您可以尝试查看实现here,看看如何使其适应ArrayAdapter。
答案 1 :(得分:4)
这是我正在使用的ArrayAdapter的子类。请注意,我传入的objects
已按字母顺序排序,并Collections.sort(objects)
。
class SectionIndexingArrayAdapter<T> extends ArrayAdapter<T> implements
SectionIndexer {
HashMap<String, Integer> sectionsMap = new HashMap<String, Integer>();
ArrayList<String> sectionsList = new ArrayList<String>();
ArrayList<Integer> sectionForPosition = new ArrayList<Integer>();
ArrayList<Integer> positionForSection = new ArrayList<Integer>();
public SectionIndexingArrayAdapter(Context context, int textViewResourceId,
List<T> objects) {
super(context, textViewResourceId, objects);
// Note that List<T> objects has already been sorted alphabetically
// e.g. with Collections.sort(objects) **before** being passed to
// this constructor.
// Figure out what the sections should be (one section per unique
// initial letter, to accommodate letters that might be missing,
// or characters like ,)
for (int i = 0; i < objects.size(); i++) {
String objectString = objects.get(i).toString();
if (objectString.length() > 0) {
String firstLetter = objectString.substring(0, 1).toUpperCase();
if (!sectionsMap.containsKey(firstLetter)) {
sectionsMap.put(firstLetter, sectionsMap.size());
sectionsList.add(firstLetter);
}
}
}
// Calculate the section for each position in the list.
for (int i = 0; i < objects.size(); i++) {
String objectString = objects.get(i).toString();
if (objectString.length() > 0) {
String firstLetter = objectString.substring(0, 1).toUpperCase();
if (sectionsMap.containsKey(firstLetter)) {
sectionForPosition.add(sectionsMap.get(firstLetter));
} else
sectionForPosition.add(0);
} else
sectionForPosition.add(0);
}
// Calculate the first position where each section begins.
for (int i = 0; i < sectionsMap.size(); i++)
positionForSection.add(0);
for (int i = 0; i < sectionsMap.size(); i++) {
for (int j = 0; j < objects.size(); j++) {
Integer section = sectionForPosition.get(j);
if (section == i) {
positionForSection.set(i, j);
break;
}
}
}
}
// The interface methods.
public int getPositionForSection(int section) {
return positionForSection.get(section);
}
public int getSectionForPosition(int position) {
return sectionForPosition.get(position);
}
public Object[] getSections() {
return sectionsList.toArray();
}
}
答案 2 :(得分:3)
setFastScrollEnabled(真);
(http://developer.android.com/reference/android/widget/AbsListView.html)
答案 3 :(得分:2)
在anddev.org上我找到了这个教程:Alphabetic FastScroll ListView - similar to Contacts
它还包含一个简短的demo-video
希望它有所帮助!
答案 4 :(得分:2)
要收集列表视图中显示的项目的详细信息,您可以执行以下操作:
@Override
public void onScroll(AbsListView view, int firstVisibleItem,
int visibleItemCount, int totalItemCount) {
albumButton.setText(songs.get(firstVisibleItem).getAlbum());
}
这不是更简单吗?在这里,'songs'是Song对象的arraylist。您甚至可以通过添加firstVisibleItem + visibleItemCount来获取最后一个可见项。我发现这种技术非常有用。那么你会得到每首歌的第一个字母。我假设你发布的音乐应用中包含字母的灰色框是一个各种对话框?
无论如何,希望这会有所帮助。我意识到我迟到了,但这是为了未来的人
答案 5 :(得分:1)
我找到了一个很棒的解决方案here ...用一个巨大的列表做得很好......很好,很快......没有加载时间。
@Override
public int getPositionForSection(int section)
{
log.info("Get position for section");
for (int i = 0; i < this.getCount(); i++)
{
if (this.getItem(i).length() > 0)
{
String item = this.getItem(i).toUpperCase();
if (item.charAt(0) == sections.charAt(section))
{
return i;
}
}
}
return 0;
}
@Override
public int getSectionForPosition(int arg0)
{
log.info("Get section");
return 0;
}
@Override
public Object[] getSections()
{
log.info("Get sections");
String[] sectionsArr = new String[sections.length()];
for (int i = 0; i < sections.length(); i++)
{
sectionsArr[i] = "" + sections.charAt(i);
}
return sectionsArr;
}