我正在ListView
通过 JSON 填充。我通过本教程完成了它。
我面临的唯一问题:我想在用户到达末尾时加载更多项目ListView
,我不想在开始时加载 100 个项目。我想显示 10 个项目,然后再显示 10 个项目。我怎样才能做到这一点?
我正在ListView
通过 JSON 填充。我通过本教程完成了它。
我面临的唯一问题:我想在用户到达末尾时加载更多项目ListView
,我不想在开始时加载 100 个项目。我想显示 10 个项目,然后再显示 10 个项目。我怎样才能做到这一点?
请按照以下步骤操作:-
大多数代码都有注释,因此您可以了解每个语句的作用。
页脚视图只不过是一段 XML,它定义了列表视图页脚的外观。
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="fill_parent"
android:gravity="center_horizontal"
android:padding="3dp"
android:layout_height="fill_parent">
<TextView
android:id="@id/android:empty"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:gravity="center"
android:padding="5dp"
android:text="Loading more days..."/>
</LinearLayout>
它只是一个简单的文本视图,带有用于演示目的的消息。但是你可以在这里放任何东西:-)
将视图添加到 ListView 并不难。您唯一需要注意的是,您将它放在将适配器添加到视图的行之上!我们将使用此代码将其添加到 ListView:addFooterView(View)
//add the footer before adding the adapter, else the footer will not load!
View footerView = ((LayoutInflater)this.getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.listfooter, null, false);
this.getListView().addFooterView(footerView);
现在是有趣的部分,检查我们是否一直向下并加载项目
实际加载是在单独的线程 (Runnable) 中完成的。这样我们就不会锁定主界面( GUI )。
//Here is where the magic happens
this.getListView().setOnScrollListener(new OnScrollListener(){
//useless here, skip!
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {}
//dumdumdum
@Override
public void onScroll(AbsListView view, int firstVisibleItem,
int visibleItemCount, int totalItemCount) {
//what is the bottom iten that is visible
int lastInScreen = firstVisibleItem + visibleItemCount;
//is the bottom item visible & not loading more already ? Load more !
if((lastInScreen == totalItemCount) && !(loadingMore)){
Thread thread = new Thread(null, loadMoreListItems);
thread.start();
}
}
});
加载由 2 完成Runnables
。调用第一个可运行loadMoreListItems
对象以获取数据,并returnRes
在主(UI)线程上调用第二个可运行对象以更新界面。要从第一个切换到第二个,我们使用一个名为:runOnUiThread的方法
这是实现 Runnables 的代码,我尽可能多地注释了代码以使其易于理解:
可运行以加载项目
private Runnable loadMoreListItems = new Runnable() {
@Override
public void run() {
//Set flag so we cant load new items 2 at the same time
loadingMore = true;
//Reset the array that holds the new items
myListItems = new ArrayList<String>();
//Simulate a delay, delete this on a production environment!
try { Thread.sleep(1000);
} catch (InterruptedException e) {}
//Get 15 new listitems
for (int i = 0; i < itemsPerPage; i++) {
//Fill the item with some bogus information
myListItems.add("Date: " + (d.get(Calendar.MONTH)+ 1) + "/" + d.get(Calendar.DATE) + "/" + d.get(Calendar.YEAR) );
// +1 day
d.add(Calendar.DATE, 1);
}
//Done! now continue on the UI thread
runOnUiThread(returnRes);
}
};
第二个 Runnable:由于我们不能从线程更新我们的 UI,这个 Runnable 负责处理!
private Runnable returnRes = new Runnable() {
@Override
public void run() {
//Loop thru the new items and add them to the adapter
if(myListItems != null && myListItems.size() > 0){
for(int i=0;i < myListItems.size();i++)
adapter.add(myListItems.get(i));
}
//Update the Application title
setTitle("Neverending List with " + String.valueOf(adapter.getCount()) + " items");
//Tell to the adapter that changes have been made, this will cause the list to refresh
adapter.notifyDataSetChanged();
//Done loading more.
loadingMore = false;
}
};
CommonsWare EndlessAdapter项目就是为此而设计的。它说它现在已经退役,没有列出任何解释或替换,但它工作得很好。