2

I'm developing an application by using service to track user's locations and send the data to the server in the background. It's the GPS based app. When my program called requestLocationUpdates with GPS provider, the onLocationChanged is never called. However, the requestLocationUpdates works fine with network provider on my app. Please take a look at my code.

Android version: 4.1.2 Device: Galaxy nexus S

Tracker.java

private void init() {
    locationListener = new MyLocationListener();
    mNM = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
    NOTIFICATION = R.string.local_service_started;
    arrivedStatus = false;
    activity = TrackerActivity.getAppActivity();
}

@Override
public void onCreate() {
    super.onCreate();
    init();
    Log.i(tag, "Start Tracking");
    showStartNotification();
}

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
    Log.i("LocalService", "Received start id " + startId + ": " + intent);
    tripID = intent.getExtras().getInt("tripID") + "";
    locationInterval = intent.getExtras().getInt("locationInterval")
            * MILLISECONDS_PER_SECOND;
    //lm.requestLocationUpdates(LocationManager.NETWORK_PROVIDER,
    //      locationInterval, 0, locationListener);
    getLocation();
    return START_STICKY;
}

@Override
public void onDestroy() {
    super.onDestroy();
    Log.e("STOP_SERVICE", "Service has stopped");
    mNM.cancel(R.string.local_service_started);
    lm.removeUpdates(locationListener);
    stopSelf();
}

private void getLocation() {
    lm = (LocationManager) getApplicationContext().getSystemService(
            Context.LOCATION_SERVICE);

    // getting GPS status
    isGPSEnabled = lm.isProviderEnabled(LocationManager.GPS_PROVIDER);

    // getting network status
    isNetworkEnabled = lm
            .isProviderEnabled(LocationManager.NETWORK_PROVIDER);

    if (!isGPSEnabled && !isNetworkEnabled) {
        // no network provider is enabled
        Log.e(tag, "Non providers are enabled");
    } else {

        if (isGPSEnabled) {
            lm.requestLocationUpdates(LocationManager.GPS_PROVIDER,
                    locationInterval, 0, locationListener);
            Log.d(tag, "GPS Enabled");
        }

        if (isNetworkEnabled) {
            if (lm == null) {
                lm.requestLocationUpdates(LocationManager.NETWORK_PROVIDER,
                        locationInterval, 0, locationListener);
                Log.d(tag, "Network Enabled");
            }
        }
    }
}

@Override
public IBinder onBind(Intent intent) {
    // TODO Auto-generated method stub
    return null;
}

@SuppressWarnings("deprecation")
private void showStartNotification() {
    // In this sample, we'll use the same text for the ticker and the
    // expanded notification
    CharSequence text = getText(R.string.local_service_started);

    // Set the icon, scrolling text and timestamp
    Notification notification = new Notification(R.drawable.cameral, text,
            System.currentTimeMillis());

    // The PendingIntent to launch our activity if the user selects this
    // notification+
    PendingIntent contentIntent = PendingIntent.getActivity(this, 0,
            new Intent(this, TrackerActivity.class), 0);

    // Set the info for the views that show in the notification panel.
    notification.setLatestEventInfo(this,
            getText(R.string.local_service_label), text, contentIntent);

    // Send the notification.
    mNM.notify(NOTIFICATION, notification);
}

/**
 * private void showStopSpecification() { CharSequence text =
 * getText(R.string.local_service_cancel); Notification notification = new
 * Notification(R.drawable.btn_save_dialog, text,
 * System.currentTimeMillis()); mNM.notify(NOTIFICATION, notification); }
 */

private void checkResult(JSONObject json) {
    try {
        if (json.getString(KEY_SUCCESS) != null) {
            String res = json.getString(KEY_SUCCESS);
            if (Integer.parseInt(res) == 1) {
                Log.v(tag, "Store data successfully");
                activity.findViewById(R.id.tracker_info)
                        .setBackgroundResource(R.color.blue4);
                if (json.getInt(ARRIVED_STATUS) == 1) {
                    setArrivedStatus(true);
                } else {
                    setArrivedStatus(false);
                }
            } else if (json.getString(KEY_ERROR).equals("1")) {
                // Error in login
                String error_msg = json.getString(KEY_ERROR_MSG);
                Log.e(tag, error_msg);
                setArrivedStatus(false);
            } else {
                Log.e(tag, "Something is wrong");
                setArrivedStatus(false);
            }
        } else {
            Log.e(tag, "Something is wrong");
            setArrivedStatus(false);
        }
    } catch (JSONException e) {
        e.printStackTrace();
    }
}

public void setArrivedStatus(boolean status) {
    arrivedStatus = status;
}

public boolean getArrivedStatus() {
    return arrivedStatus;
}

private class MyLocationListener implements LocationListener {

    @Override
    public void onLocationChanged(Location location) {
        // TODO Auto-generated method stub
        currentLat = location.getLatitude() + "";
        currentLng = location.getLongitude() + "";
        Log.v(tag, LOCATION_CHANGED + " lat=" + currentLat + ", lon="
                + currentLng);
        try {
            JSONObject json = new LogInfo().execute(
                    new String[] { tripID, currentLat, currentLng }).get();
            checkResult(json);
            if (getArrivedStatus() == true) {
                Log.v(tag, "User has arrived safely");
                onDestroy();
            }
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (ExecutionException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }

    @Override
    public void onProviderDisabled(String provider) {
        // TODO Auto-generated method stub

    }

    @Override
    public void onProviderEnabled(String provider) {
        // TODO Auto-generated method stub

    }

    @Override
    public void onStatusChanged(String provider, int status, Bundle extras) {
        // TODO Auto-generated method stub

    }

}

}

I also already added the permission to my Manifest

<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />

Thank you

4

1 回答 1

0

调用此函数时,是否在设备的通知栏上看到 GPS 图标?如果是这样,这意味着它试图获取一个位置,而你只是在一个没有 GPS 接收的地方。

无论如何,您都可以使用谷歌的方式来获取位置,这里:https ://developers.google.com/events/io/sessions/324498944

另外,什么是“Tracker”类?是服务吗?如果是这样,你不应该让它引用一个活动,因为它会导致内存泄漏。而是使用正确的绑定。

您还应该避免调用 "onDestroy" ,因为调用它并不会真正关闭您的服务。而是调用“stopSelf”,并确保没有活动绑定到它。

如果您愿意,我很久以前就在这里问过这类问题(通过服务获取位置) 。

于 2013-09-07T18:39:01.330 回答