我想编制一个GPS定位器,它每15秒更新一次位置。但是要更新的方法(onLocationChanged)不被称为... 按下按钮时,它只在TextView中设置一次位置,显示的时间有时也是几分钟......
什么时候调用onLocationChanged?强制每10秒(或更快)或仅在位置发生变化时?
我的代码(仅限GPS代码,还有用于检查Google Play服务是否已激活的代码):
/* IMPORT FILES */
public class MainActivity extends ActionBarActivity implements
GooglePlayServicesClient.ConnectionCallbacks,
GooglePlayServicesClient.OnConnectionFailedListener,
LocationListener {
///////////////////////////////////////////////////////////////////
/*
* Attributes
*/
private static LocationClient mLocationClient;
private static boolean LocEnabled = false;
private static boolean LocConnected = false;
private static LocationRequest LocRequest;
///////////////////////////////////////////////////////////////////
/*
* Location Update Settings
*/
// Milliseconds per second
private static final int MILLISECONDS_PER_SECOND = 1000;
// Update frequency in seconds
public static final int UPDATE_INTERVAL_IN_SECONDS = 15;
// Update frequency in milliseconds
private static final long UPDATE_INTERVAL = MILLISECONDS_PER_SECOND * UPDATE_INTERVAL_IN_SECONDS;
// The fastest update frequency, in seconds
private static final int FASTEST_INTERVAL_IN_SECONDS = 1;
// A fast frequency ceiling in milliseconds
private static final long FASTEST_INTERVAL = MILLISECONDS_PER_SECOND * FASTEST_INTERVAL_IN_SECONDS;
///////////////////////////////////////////////////////////////////
/*
* Local Vars
*/
SharedPreferences Prefs;
Editor Editor;
boolean UpdatesRequested;
//VIEW Elements
static Button btn_refresh_loc;
static TextView txt_position;
static View rootView;
//Position elements
static Position myPosition = new Position("Meine Position");
static Location lastLocation;
///////////////////////////////////////////////////////////////////
/*
* METHODS TO CHECK FOR GOOGLE PLAY SERVICES */
///////////////////////////////////////////////////////////////////
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction()
.add(R.id.container, new MainFragment())
.commit();
}
//check for G-Play Services
if(servicesConnected())
{
Toast.makeText(getApplicationContext(), "Google Play Services available", Toast.LENGTH_SHORT).show();
Log.i("G Play Services", "Google Play Services available");
}
else
{
Toast.makeText(getApplicationContext(), "Google Play Services not available", Toast.LENGTH_SHORT).show();
Log.e("G Play Services", "Google Play Services NOT AVAILABLE");
finish();
}
//check for Location Service activated
if(checkLocEnabled())
{
Toast.makeText(getApplicationContext(), "Location Service enabled", Toast.LENGTH_SHORT).show();
Log.i("LOC", "Location Service enabled");
LocEnabled = true;
}
else
{
Toast.makeText(getApplicationContext(), "Location Service disabled", Toast.LENGTH_SHORT).show();
Log.e("LOC", "Location Service DISABLED");
showGPSsettings();
}
// Open the shared preferences
Prefs = getSharedPreferences("SharedPreferences", Context.MODE_PRIVATE);
// Get a SharedPreferences editor
Editor = Prefs.edit();
mLocationClient = new LocationClient(this,this,this);
UpdatesRequested = true; //start loc client without updates
//set loc update parameter
LocRequest = LocationRequest.create();
LocRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
LocRequest.setInterval(UPDATE_INTERVAL);
LocRequest.setFastestInterval(FASTEST_INTERVAL);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
public static class MainFragment extends Fragment {
public MainFragment() {
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
rootView = inflater.inflate(R.layout.fragment_main, container, false);
//View inits
btn_refresh_loc = (Button) rootView.findViewById(R.id.btn_refresh_loc);
txt_position = (TextView) rootView.findViewById(R.id.txt_location);
//ClickListeners
btn_refresh_loc.setOnClickListener(new OnClickListener()
{
@SuppressLint("SimpleDateFormat")
public void onClick(View v)
{
Log.i("BTN","Get Location");
if(!LocEnabled)
{
// Reconnect the client.
mLocationClient.disconnect();
mLocationClient.connect();
}
if(LocConnected)
{
lastLocation = mLocationClient.getLastLocation();
myPosition.setPos(lastLocation);
String date = new java.text.SimpleDateFormat("dd.MM.yyyy HH:mm:ss").format(new java.util.Date (lastLocation.getTime()));
// Report to the UI that the location was updated
txt_position.setText("Lat: " + myPosition.getLat() + " Lng: " + myPosition.getLng() + "\n" + date);
Log.i("LOC","Lat: " + myPosition.getLat() + " Lng: " + myPosition.getLng() + "\n" + date);
}
}
});
return rootView;
}
}
@Override
protected void onStart() {
super.onStart();
// Connect the client.
mLocationClient.connect();
}
@Override
protected void onPause() {
// Save the current setting for updates
Editor.putBoolean("KEY_UPDATES_ON", UpdatesRequested);
Editor.commit();
super.onPause();
}
@Override
protected void onResume() {
/*
* Get any previous setting for location updates
* Gets "false" if an error occurs
*/
if (Prefs.contains("KEY_UPDATES_ON")) {
UpdatesRequested =
Prefs.getBoolean("KEY_UPDATES_ON", false);
// Otherwise, turn off location updates
} else {
Editor.putBoolean("KEY_UPDATES_ON", false);
Editor.commit();
}
super.onResume();
}
@Override
protected void onStop() {
/*if (mLocationClient.isConnected()) {
removeLocationUpdates(this);
}*/
// Disconnecting the client invalidates it.
mLocationClient.disconnect();
LocConnected = false;
super.onStop();
}
///////////////////////////////////////////////////////////////////
/*
* Location Services
*/
/*
* Called by Location Services when the request to connect the
* client finishes successfully. At this point, you can
* request the current location or start periodic updates
*/
@Override
public void onConnected(Bundle dataBundle) {
// Display the connection status
Toast.makeText(this, "Connected", Toast.LENGTH_SHORT).show();
LocConnected = true;
if (UpdatesRequested) {
mLocationClient.requestLocationUpdates(LocRequest, this);
}
}
/*
* Called by Location Services if the connection to the
* location client drops because of an error.
*/
@Override
public void onDisconnected() {
// Display the connection status
Toast.makeText(this, "Disconnected. Please re-connect.",
Toast.LENGTH_SHORT).show();
LocConnected = false;
}
/*
* Called by Location Services if the attempt to
* Location Services fails.
*/
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {
/*
* Google Play services can resolve some errors it detects.
* If the error has a resolution, try sending an Intent to
* start a Google Play services activity that can resolve
* error.
*/
if (connectionResult.hasResolution()) {
try {
// Start an Activity that tries to resolve the error
connectionResult.startResolutionForResult(
this,
CONNECTION_FAILURE_RESOLUTION_REQUEST);
/*
* Thrown if Google Play services canceled the original
* PendingIntent
*/
} catch (IntentSender.SendIntentException e) {
// Log the error
e.printStackTrace();
}
} else {
/*
* If no resolution is available, display a dialog to the
* user with the error.
*/
Toast.makeText(getApplicationContext(), "ERROR: Location Connection failed", Toast.LENGTH_SHORT).show();
Log.e("Location", "Connection failed - " + connectionResult.getErrorCode());
}
LocConnected = false;
}
/*
* Define the callback method that receives location updates(non-Javadoc)
* @see com.google.android.gms.location.LocationListener#onLocationChanged(android.location.Location)
*/
@SuppressLint("SimpleDateFormat")
@Override
public void onLocationChanged(Location location) {
String date = new java.text.SimpleDateFormat("dd.MM.yyyy HH:mm:ss").format(new java.util.Date (location.getTime()));
// Report to the UI that the location was updated
txt_position.setText("# Lat: " + location.getLatitude() + " Lng: " + location.getLongitude() + "\n" + date);
Log.i("LOC","# Lat: " + location.getLatitude() + " Lng: " + location.getLongitude() + "\n" + date);
}
}
代码部分复制自Google Developer Training网站
答案 0 :(得分:0)
尝试以下代码: -
public class GPSTracker extends Service implements LocationListener
{
private final Context mContext;
// flag for GPS status
boolean isGPSEnabled = false;
// flag for network status
boolean isNetworkEnabled = false;
boolean canGetLocation = false;
Location location; // location
public static double latitude; // latitude
public static double longitude; // longitude
// The minimum distance to change Updates in meters
private static final long MIN_DISTANCE_CHANGE_FOR_UPDATES = 10; // 10 meters
// The minimum time between updates in milliseconds
private static final long MIN_TIME_BW_UPDATES = 1000 * 60 * 1; // 1 minute
// Declaring a Location Manager
protected LocationManager locationManager;
public GPSTracker(Context context)
{
this.mContext = context;
getLocation();
}
public Location getLocation()
{
try
{
locationManager = (LocationManager) mContext.getSystemService(LOCATION_SERVICE);
// getting GPS status
isGPSEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
// getting network status
isNetworkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
if (!isGPSEnabled && !isNetworkEnabled)
{
// no network provider is enabled
}
else
{
this.canGetLocation = true;
// First get location from Network Provider
if (isNetworkEnabled)
{
locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER,
MIN_TIME_BW_UPDATES,MIN_DISTANCE_CHANGE_FOR_UPDATES, this);
// Log.d("Network", "Network");
if (locationManager != null)
{
location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
if (location != null)
{
latitude = location.getLatitude();
longitude = location.getLongitude();
// System.out.println("latitude if (isNetworkEnabled) => "+latitude);
// System.out.println("longitude if (isNetworkEnabled) => "+longitude);
}
}
}
// if GPS Enabled get lat/long using GPS Services
if (isGPSEnabled)
{
if (location == null)
{
locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER,
MIN_TIME_BW_UPDATES,MIN_DISTANCE_CHANGE_FOR_UPDATES, this);
// Log.d("GPS Enabled", "GPS Enabled");
if (locationManager != null)
{
location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
if (location != null)
{
latitude = location.getLatitude();
longitude = location.getLongitude();
// System.out.println("latitude if (isGPSEnabled) => "+latitude);
// System.out.println("longitude if (isGPSEnabled) => "+longitude);
}
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
return location;
}
@Override
public void onLocationChanged(Location location)
{
}
@Override
public void onProviderDisabled(String provider)
{
}
@Override
public void onProviderEnabled(String provider)
{
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras)
{
}
@Override
public IBinder onBind(Intent arg0)
{
return null;
}
}
当你需要lat和long时,请按以下方式调用: -
new GPSTracker();
System.out.println(GPSTracker.latitude + GPSTracker.longitude);