0

我想模拟地图上标记的位置。我有存储在 ArrayList 中的 LatLng 值列表。我使用此值每秒更新地图。我需要这个函数在 AsyncTask 中工作,这样我的 UI 线程仍然可以响应。

最初,我尝试使用Thread.sleep()但使应用程序没有响应。

protected String doInBackground(Void... voids) {
    new Handler(Looper.getMainLooper()).postDelayed(new Runnable() {
        @Override
        public void run() {
            for (int i = 0; i < waypoint.size(); i++) {
                marker = googleMap.addMarker(new MarkerOptions().position(waypoint.get(0)));
                marker.setPosition(waypoint.get(i));
                try {
                    Thread.sleep(1000); // Thread sleep made application not responsive.
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }, 500);
    return null;
}

我也尝试过使用.postDelayed,但整数i需要声明为 final,这是一个问题,因为我需要整数来改变值。

protected String doInBackground(Void... voids) {
    for (int i = 0; i < waypoint.size(); i++) {
        new Handler(Looper.getMainLooper()).postDelayed(new Runnable() {
            @Override
            public void run() {
                marker = googleMap.addMarker(new MarkerOptions().position(waypoint.get(0)));
                marker.setPosition(waypoint.get(i)); // Integer i needs to declare final.
            }
        }, 1000);
    }
    return null;
}

有没有办法做到这一点?谢谢你。

4

3 回答 3

0

Thread.sleep()如果您可以腾出一个工作线程,则该方法是可以的。您的代码中的问题是您正在暂停的线程是 UI 线程,这就是您的应用程序冻结的原因。您必须了解,您在那里所做的只是使用 Handler 构造向 UI 线程发布一个可运行文件,仅此而已。

在您的第二种方法中,您可以在基于 AsyncTask 的类中覆盖(在 UI 线程中交付)之后转储处理程序部分并使用publishProgress(从后台调用) 。onProgressUpdate它的效果相同,但样板更少。查看https://developer.android.com/reference/android/os/AsyncTask了解详情。

最后,为了规避匿名类中的最终要求,您可以声明一个包含一个元素的最终数组并使用位置 0 来读取/写入该值。希望您不需要经常这样做。

于 2018-12-09T22:09:17.867 回答
0

最快(但在使用多线程时不是最正确的)方式是:

protected String doInBackground(Void... voids) {
for (final TYPE_OF_WAYPOINT cWaypoint : waypoint) {
    new Handler(Looper.getMainLooper()).postDelayed(new Runnable() {
        @Override
        public void run() {
            marker = googleMap.addMarker(new MarkerOptions().position(waypoint.get(0)));
            marker.setPosition(cWaypoint);
        }
    }, 1000);
}
return null;

}

我不知道“航点”列表的类型是什么,所以我写了“TYPE_OF_WAYPOINTS”作为占位符。

于 2018-12-10T09:09:03.697 回答
0

@emandt 答案不起作用,但他给出的想法可以工作。因此,我尝试了,并且对他的回答进行了一些修改,它可以完美地工作:

protected String doInBackground(Void... voids) {
for (final TYPE_OF_WAYPOINT cWaypoint : waypoint) {
    new Handler(Looper.getMainLooper()).post(new Runnable() {
        @Override
        public void run() {
            marker = googleMap.addMarker(new MarkerOptions().position(waypoint.get(0)));
            marker.setPosition(cWaypoint);
        }
    });
    try {
        Thread.sleep(1000);
    } catch (Exception e) {
        // catch exception here
    }
}
return null;
}

.postDelayed首先,我已将.post. 然后,为了将操作延迟一秒钟,我添加了Thread.sleep(1000)inside for (...)but outside new Handler(Looper.getMainLooper()).post(...));

现在,应用程序可以在后台执行该过程,用户仍然可以与 UI 交互。谢谢。

于 2018-12-14T03:32:46.737 回答