我已经实现了一个简单的GPS程序,可以获取坐标并在屏幕上显示它们。当我试图改进这种设计并实现异步任务时,GPS似乎不会出于某种原因而起作用。关于在GPS上使用异步任务是否存在问题?这是我的代码:
private class DownloadTask extends AsyncTask<String, Void, Object> {
protected Object doInBackground(String... args) {
Log.i("MyApp", "Background thread starting");
LocationManager mLocationManager;
Gpslistener Gpslistener;
Gpslistener = new Gpslistener();
try{
mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
mLocationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0,Gpslistener);
}catch (Exception e) {
test_gps = true;
}
return null;
}
protected void onPostExecute(Object result) {
if(test_gps == true){
if (ParkingActivity.this.progressDialog != null) {
ParkingActivity.this.progressDialog.dismiss();
}
AlertMessage("GPS Error", "Unable to get location");
}
public class Gpslistener implements LocationListener
{
@Override
public void onLocationChanged(Location loc)
{
loc.getLatitude();
loc.getLongitude();
}
@Override
public void onProviderDisabled(String provider)
{
}
@Override
public void onProviderEnabled(String provider)
{
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras)
{
}
}
每次运行它时,它总会捕获异常。 GPS权限在清单中设置,我总是使用不同的应用程序来确保GPS连接在线,因此我将其作为潜在错误消除。老实说,我不能想到任何其他东西,没有异步任务它完美的工作!非常感谢任何帮助,谢谢!
被修改 我的异常logcat:
05-09 22:56:20.199: E/EXCEPTION:(8874): java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare()
05-09 22:56:20.199: E/EXCEPTION:(8874): java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare()
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.os.Handler.<init>(Handler.java:121)
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.location.LocationManager$ListenerTransport$1.<init>(LocationManager.java:173)
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.location.LocationManager$ListenerTransport.<init>(LocationManager.java:173)
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.location.LocationManager._requestLocationUpdates(LocationManager.java:579)
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.location.LocationManager.requestLocationUpdates(LocationManager.java:446)
05-09 22:56:20.199: E/EXCEPTION:(8874): at stefan.testservice.ParkingActivity$DownloadTask.doInBackground(ParkingActivity.java:163)
05-09 22:56:20.199: E/EXCEPTION:(8874): at stefan.testservice.ParkingActivity$DownloadTask.doInBackground(ParkingActivity.java:1)
05-09 22:56:20.199: E/EXCEPTION:(8874): at android.os.AsyncTask$2.call(AsyncTask.java:185)
05-09 22:56:20.199: E/EXCEPTION:(8874): at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:306)
05-09 22:56:20.199: E/EXCEPTION:(8874): at java.util.concurrent.FutureTask.run(FutureTask.java:138)
05-09 22:56:20.199: E/EXCEPTION:(8874): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1088)
05-09 22:56:20.199: E/EXCEPTION:(8874): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:581)
05-09 22:56:20.199: E/EXCEPTION:(8874): at java.lang.Thread.run(Thread.java:1019)
答案 0 :(得分:4)
你不能这样做。一旦doInBackground()
返回,线程就会死亡。 GPS监听器是一个处理程序,需要Looper
线程才能运行。在doInBackground()
开始时,您需要拨打Looper.prepare()
,然后拨打电话Looper.loop()
。它将永远循环,直到您在线程的quit()
对象上调用Looper
。
AsyncTask
实际上是为一次性临时线程设计的,所以我使用普通线程。虽然,我没有理由认为你没有理由。你必须100%确定你结束循环,否则即使在用户关闭应用程序后它也会永远运行。
Java Can't create handler inside thread that has not called Looper.prepare()
答案 1 :(得分:1)
另外,gps监听器没有任何理由不这样命名。只有当它获得一个位置(并且可能需要时间)时,它才会调用方法“onLocationChanged”。 你不需要为此设置asyncTask,因为所有对“requestLocationUpdates”的调用都是异步的......
答案 2 :(得分:0)
如果你想要一种肮脏而不太感性的方式:
mLocationManager = (LocationManager)getActivity().getSystemService(Context.LOCATION_SERVICE);
Looper.prepare();
Looper.loop();
if(mLocationManager.isProviderEnabled(LocationManager.GPS_PROVIDER)){
mLocationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, GPS_MINIMUM_TIME, GPS_MINIMUM_DISTANCE, MyFragment.this);
}
Looper.myLooper().quit();
基本上,它会使当前线程成为执行消息的主线程,很快你就会放弃这个线程作为主线程。我不确定这会带来什么后果。