15

我有一个ListView附加到一个ArrayAdapter. 当用户单击下载中某个项目的下载按钮时,ListView下载开始使用DownloadManager.

我想要做的是使用进度条(放置在项目布局中)跟踪下载进度。如何做到这一点?

Pocket Cast 的方式正是我所追求的:

Pocket Cast 示例 http://www.mrcrab.net/images/thumb_big/9982-Pocket_Casts_Apk_v4.3.2_Android-0.jpg

注意:我知道如何使用DownloadManager,这是棘手的进度条的即时更新。

4

2 回答 2

17

这就是我最终解决它的方式(经过多次迭代和不同的实现)。这有点棘手,但基本上你需要三件事:

  1. 收集元数据的 AsyncTask
  2. 一个滚动监听器,告诉我们用户何时停止滚动/滚动
  3. 一种巧妙的算法,可以找到任何需要更新的可见行并要求适配器仅更新该特定行

这是我设计和实现它的方式:

截屏

我在这里写了更详细的内容,完整的实现请参见github 代码

    private class UpdaterAsyncTask extends AsyncTask<Void, Void, Void> {

    boolean isRunning = true;

    public void stop() {
        isRunning = false;
    }

    @Override
    protected Void doInBackground(Void... params) {

        while (isRunning) {

            // Gather data about your adapter objects
            // If an object has changed, mark it as dirty                

            publishProgress();

            try {
                Thread.sleep(200);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }

        return null;
    }

    @Override
    protected void onProgressUpdate(Void... params) {
        super.onProgressUpdate();

        // Update only when we're not scrolling, and only for visible views
        if (mScrollState == OnScrollListener.SCROLL_STATE_IDLE) {
            int start = mListview.getFirstVisiblePosition();
            for(int i = start, j = mListview.getLastVisiblePosition(); i<=j; i++) {
                View view = mListview.getChildAt(i-start);
                if (((Content)mListview.getItemAtPosition(i)).dirty) {
                    mListview.getAdapter().getView(i, view, mListview); // Tell the adapter to update this view
                }

            }
        }

      }
    }
于 2013-11-25T16:47:15.663 回答
0

对于特定的视图项,您可以使用getChildAt(int index)检索并更新它。

并且可以借助getFirstVisiblePosition()getLastVisiblePosition()遍历所有可见项目

于 2013-10-30T17:29:21.273 回答