ListView動態加載數據

原文地址: http://hddev.blog.51cto.com/3365350/651517


 當listview需要加載的數據過多時,若一次性載入則速度會相當緩慢,影響用戶體驗,這時候就需要動態加載數據,即每次載入固定長度的數據,android market的listview就是採用這種方式,使得加載看起來很平滑,響應速度很快,有助於提高用戶體驗。
  首先,要實現動態加載首先需要在獲取數據時每次在上次獲取到的數據之後的位置開始取得固定長度的數據,可通過"select * from TableName LIMIT m OFFSET n"語句實現,其中m是要取得數據的長度,n是數據的偏移量。 
  然後,在Activity中需要重寫listview的onScroll方法,在onScroll中添加判斷條件,當上一次加載的數據顯示完並滑動到底部之後需要再次獲取數據,可以在UI Thread中在開啓一個線程去加載數據,加載數據時應彈出一個試圖提示用戶正在加載。

  最後,加載數據的線程處理完畢後,刷新ListView。

  以下是實現動態加載的主要步驟:

  1. //加載數據的方法 
  2.  
  3. private void fillAdapter(int count, int begin) { 
  4.         // TODO Auto-generated method stub 
  5.         SQLiteOpenHelper mSQLiteOpenHelper = new SQLiteOpenHelper ( 
  6.                 this); 
  7.         Cursor c= mSQLiteOpenHelper .getDynamicListViewData(count, offset); 
  8.  

 

  1. //監聽listview的onScroll方法 
  2.  
  3. OnScrollListener listScroll = new OnScrollListener() { 
  4.  
  5.         @Override 
  6.         public void onScrollStateChanged(AbsListView view, int scrollState) { 
  7.             // TODO Auto-generated method stub 
  8.         } 
  9.  
  10.         @Override 
  11.         public void onScroll(AbsListView view, int firstVisibleItem, 
  12.                 int visibleItemCount, int totalItemCount) { 
  13.             if(isLoading) //正在加載時就不要讓在執行活動觸發事件 
  14.                 return
  15.             if (firstVisibleItem + visibleItemCount == totalItemCount) { 
  16.                 // 開線程去獲取數據 
  17.                 if (totalItemCount <= totalItemsCount) { 
  18.                     Integer[] params = new Integer[] { 25, currentItemCount }; 
  19.  
  20.                     mAsynchTask = new AsynchTask(); 
  21.                     mAsynchTask.execute(params); 
  22.                 } else { 
  23.                     Toast.makeText(EventTracker.this"there is no data!"
  24.                             Toast.LENGTH_SHORT).show(); 
  25.                 } 
  26.             } 
  27.         } 
  28.     }; 

 

 

  1. //通過AsyncTask更方便的實現多線程管理,使得加載效果更平滑   
  2.  
  3. private class AsynchTask extends AsyncTask<Integer, Void, Void> { 
  4.         @Override 
  5.         /**將在onPreExecute 方法執行後馬上執行,該方法運行在後臺線程中。 
  6.          * 這裏將主要負責執行那些很耗時的後臺計算工作。可以調用 publishProgress方法 
  7.          * 來更新實時的任務進度。該方法是抽象方法,子類必須實現。 */ 
  8.         protected Void doInBackground(Integer... params) { 
  9.             fillAdapter(params[0], params[1]); 
  10.             return null
  11.         } 
  12.  
  13.   @Override 
  14.         /** 在doInBackground 執行完成後,onPostExecute 方法將被UI thread調用, 
  15.          * 後臺的計算結果將通過該方法傳遞到UI thread. 
  16.          * */ 
  17.         protected void onPreExecute() { 
  18.  
  19. //loadingView爲自定義的一個dialog,用於提示用戶正在加載 
  20.             mEventListView.addFooterView(loadingView); 
  21.             isLoading=true
  22.         } 
  23.  
  24.  
  25.         @Override 
  26.         /** 在doInBackground 執行完成後,onPostExecute 方法將被UI thread調用, 
  27.          * 後臺的計算結果將通過該方法傳遞到UI thread. 
  28.          * */ 
  29.         protected void onPostExecute(Void result) {      
  30.             bindAdapter(); 
  31.             mListView.removeFooterView(loadingView); 
  32.             mListView.setSelection(currentItemCount); 
  33.             currentItemCount += 25;//每次加載25列,偏移量也遞增25 
  34.             isLoading=false
  35.         } 
  36.     } 

 

  1. 數據庫中方法如下: 
  2. public Cursor getDynamicListViewData(int count, int offset) { 
  3.         return getReadableDatabase().rawQuery( 
  4.                 "select * from TableName limit " + count + "offset" + offset, 
  5.                 null); 
  6.     } 

 


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章