停止GPS并禁用GoogleApiClient

时间:2015-05-05 20:33:53

标签: android google-maps

我正在构建一个应用程序,以帮助您在外出时关注酒吧标签。我有一个功能,用户可以设置接近警报(地理围栏),以提醒他们关闭他们的标签,如果他们离开酒吧没有关闭。首先显示地图,然后将标记放在用户的位置,然后在标记周围显示100米的地理围栏。用户的位置定期更新,因此它在后台线程上运行。

我的问题是,当用户关闭其标签时,我想停止通过点击按钮禁用该应用正在使用的位置服务。此按钮单击发生在启动地图和地理定位服务的单独活动中。任何帮助将不胜感激!

PS - 我试图尽可能多地包含代码,所以请原谅我的混乱。

地图是从此活动中的addBtn启动的:

public class Alarm extends ActionBarActivity {
public static String TAG = "lstech.aos.debug";

static public boolean geofencesAlreadyRegistered = false;
Button addBtn, lobbyBtn, startTabBtn, settingsBtn;
boolean mapOpen = false;
double latitude, longitude = 0.0;
protected GoogleMap map;
ActionBar actionBar;
Fragment f;
FragmentManager fragmentManager;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.alarm_layout);

    actionBar = getSupportActionBar();
    actionBar.hide();

    addBtn = (Button) findViewById(R.id.add_geo_button);
    startTabBtn = (Button) findViewById(R.id.calculator_button);
    lobbyBtn = (Button) findViewById(R.id.lobby_button);
    settingsBtn = (Button) findViewById(R.id.settings_button);

    TinyDB tinydb = new TinyDB(this);
    mapOpen = tinydb.getBoolean("mapOpen");

    if (mapOpen)
        addBtn.setText(R.string.view_map_button);
    else
        addBtn.setText(R.string.set_gps_alert);

    fragmentManager = getSupportFragmentManager();
    f = fragmentManager.findFragmentByTag("uniqueTag");

    // SET MAP MARKER AND GEOFENCE
    addBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

            // create a map instance if one doesn't exist
            if (f == null) {
                fragmentManager
                        .beginTransaction()
                        .replace(android.R.id.content, new MapFragment(),
                                "uniqueTag").commit();

            } // keep instance of map if it's already showing
            else {
                fragmentManager.beginTransaction()
                        .replace(android.R.id.content, f, "uniqueTag")
                        .commit();
            }

            fragmentManager.executePendingTransactions();

            startService(new Intent(getApplicationContext(),
                    GeolocationService.class));
        }
    });

GeolocationService类设置位置和Geofence对象:

public class GeolocationService extends Service implements ConnectionCallbacks,
    OnConnectionFailedListener, LocationListener, ResultCallback<Status> {
// TinyDB saved value handles: (boolean)"mapReady"
LocationListener listener;
private static final long GEOFENCE_EXPIRATION_IN_HOURS = 12;
private static final long RADIUS = 100;
public static final long GEOFENCE_EXPIRATION_IN_MILLISECONDS = GEOFENCE_EXPIRATION_IN_HOURS
        * DateUtils.HOUR_IN_MILLIS;
public static final long UPDATE_INTERVAL_IN_MILLISECONDS = 10000;
public static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS = UPDATE_INTERVAL_IN_MILLISECONDS / 5;
protected GoogleApiClient mGoogleApiClient;
public static GoogleApiClient mGoogleApiClientStatic;
protected LocationRequest mLocationRequest;
private PendingIntent mPendingIntent;
List<Geofence> mGeofenceList;
static public List<Geofence> mGeofenceListPass;
SimpleGeofence simpleGeo;
static public SimpleGeofence geoFence;
Location mLocation, newLocation;
Intent intent;
public static LocationManager mlocManager;
public static LocationListener mlocListener;
public static android.location.LocationListener mlocListenerProvider;
public static PendingIntent pendingIntent;
public static ConnectionCallbacks connCallbacks;
public static OnConnectionFailedListener connFailedListener;

// ON START
// ***********
@Override
public void onStart(Intent intent, int startId) {
    buildGoogleApiClient();
    mGoogleApiClient.connect();
    mGoogleApiClientStatic = mGoogleApiClient;
    mlocManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
    mlocListener = this;
    mlocListenerProvider = new android.location.LocationListener() {

        @Override
        public void onLocationChanged(Location arg0) {
            // TODO Auto-generated method stub
        }

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

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

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

    mlocManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0L,
            0f, mlocListenerProvider);
}

// ON DESTROY
// *************
@Override
public void onDestroy() {
    super.onDestroy();

    if (mGoogleApiClient.isConnected())
        mGoogleApiClient.disconnect();
}

// REGISTER GEOFENCES
// *********************
protected void registerGeofences(Location location) {
    if (Alarm.geofencesAlreadyRegistered)
        return;

    Log.d(Alarm.TAG, "Registering Geofences");

    String geoId = "geoId";
    simpleGeo = new SimpleGeofence(geoId, location.getLatitude(),
            location.getLongitude(), RADIUS,
            GEOFENCE_EXPIRATION_IN_MILLISECONDS,
            Geofence.GEOFENCE_TRANSITION_ENTER
                    | Geofence.GEOFENCE_TRANSITION_DWELL
                    | Geofence.GEOFENCE_TRANSITION_EXIT);

    // mGeofenceList.add(new Geofence.Builder()

    HashMap<String, SimpleGeofence> geofences = SimpleGeofenceStore
            .getInstance().getSimpleGeofences();

    GeofencingRequest.Builder builder = new GeofencingRequest.Builder();

    for (Map.Entry<String, SimpleGeofence> item : geofences.entrySet()) {
        SimpleGeofence sg = item.getValue();
        sg.setLatitude(simpleGeo.getLatitude());
        sg.setLongitude(simpleGeo.getLongitude());
        builder.addGeofence(sg.toGeofence());

        SimpleGeofenceStore store = SimpleGeofenceStore.getInstance();
        store.setLatLong(simpleGeo.getLatitude(), simpleGeo.getLongitude());
        // Log.d(Alarm.TAG, sg.getLatitude() + " " + sg.getLongitude());
    }

    TinyDB tinydb = new TinyDB(getApplicationContext());
    tinydb.putBoolean("mapReady", false);

    GeofencingRequest geofencingRequest = builder.build();

    mPendingIntent = requestPendingIntent();
    pendingIntent = mPendingIntent;

    LocationServices.GeofencingApi.addGeofences(mGoogleApiClient,
            geofencingRequest, mPendingIntent).setResultCallback(this);

    Alarm.geofencesAlreadyRegistered = true;
} // end registerGeofences()

// REQUEST PENDING INTENT
// *************************
private PendingIntent requestPendingIntent() {

    if (null != mPendingIntent)
        return mPendingIntent;

    Intent intent = new Intent(this, GeofenceReceiver.class);
    return PendingIntent.getService(this, 0, intent,
            PendingIntent.FLAG_UPDATE_CURRENT);

} // end requestPendingIntent()

// START LOCATION UPDATES
// *************************
protected void startLocationUpdates() {
    LocationServices.FusedLocationApi.requestLocationUpdates(
            mGoogleApiClient, mLocationRequest, this);
} // end startLocationUpdates()

// STOP LOCATION UPDATES
// ************************
protected void stopLocationUpdates() {
    LocationServices.FusedLocationApi.removeLocationUpdates(
            mGoogleApiClient, this);
} // end stopLocationUpdates()

// ON CONNECTED
// ***************
@Override
public void onConnected(Bundle connectionHint) {
    Log.i(Alarm.TAG, "Connected to GoogleApiClient");
    startLocationUpdates();
} // end onConnected(Bundle connectionHint)

// ON LOCATION CHANGED
// **********************
@Override
public void onLocationChanged(Location location) {
    Log.d(Alarm.TAG, "new location : " + location.getLatitude() + ", "
            + location.getLongitude() + ". " + location.getAccuracy());
    broadcastLocationFound(location);

    if (!Alarm.geofencesAlreadyRegistered)
        registerGeofences(location);

} // end onLocationChanged(Location location)

// ON CONNECTION SUSPENDED
// **************************
@Override
public void onConnectionSuspended(int cause) {
    Log.i(Alarm.TAG, "Connection suspended");
    mGoogleApiClient.connect();
} // end onConnectionSuspended(int cause)

// ON CONNECTION FAILED
// ***********************
@Override
public void onConnectionFailed(ConnectionResult result) {
    Log.i(Alarm.TAG,
            "Connection failed: ConnectionResult.getErrorCode() = "
                    + result.getErrorCode());
} // end onConnectionFailed(ConnectionResult result)

// BUILD GOOGLE API CLIENT
// **************************
protected synchronized void buildGoogleApiClient() {
    Log.i(Alarm.TAG, "Building GoogleApiClient");

    mlocListener = this;
    connCallbacks = this;
    connFailedListener = this;

    mGoogleApiClient = new GoogleApiClient.Builder(this)
            .addConnectionCallbacks(this)
            .addOnConnectionFailedListener(this)
            .addApi(LocationServices.API).build();

    createLocationRequest();
} // end buildGoogleApiClient()

// CREATE LOCATION REQUEST
// **************************
protected void createLocationRequest() {
    mLocationRequest = new LocationRequest();
    mLocationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS);
    mLocationRequest
            .setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS);
    mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
} // end createLocationRequest()

// ON BIND
// **********
@Override
public IBinder onBind(Intent intent) {
    return null;
}

// BROADCAST LOCATION FOUND
// ***************************
public void broadcastLocationFound(Location location) {
    Intent intent = new Intent(
            "com.diligencedojo.tabsitter.geolocation.service");
    intent.putExtra("latitude", location.getLatitude());
    intent.putExtra("longitude", location.getLongitude());
    intent.putExtra("done", 1);
    // // 
    sendBroadcast(intent);
} // end broadcastLocationFound(Location location)

// ON RESULT
// ************
public void onResult(Status status) {
    if (status.isSuccess()) {
        Toast.makeText(getApplicationContext(),
                getString(R.string.geofences_added), Toast.LENGTH_SHORT)
                .show();

        TinyDB tinydb = new TinyDB(getApplicationContext());
        tinydb.putBoolean("mapReady", true);
    } else {
        Alarm.geofencesAlreadyRegistered = false;
        String errorMessage = getErrorString(this, status.getStatusCode());
        Toast.makeText(getApplicationContext(), errorMessage,
                Toast.LENGTH_SHORT).show();
    }
} // end onResult(Status status)

// GET ERROR STRING
// *******************
public static String getErrorString(Context context, int errorCode) {
    Resources mResources = context.getResources();

    switch (errorCode) {
    case GeofenceStatusCodes.GEOFENCE_NOT_AVAILABLE:
        return mResources.getString(R.string.geofence_not_available);
    case GeofenceStatusCodes.GEOFENCE_TOO_MANY_GEOFENCES:
        return mResources.getString(R.string.geofence_too_many_geofences);
    case GeofenceStatusCodes.GEOFENCE_TOO_MANY_PENDING_INTENTS:
        return mResources
                .getString(R.string.geofence_too_many_pending_intents);
    default:
        return mResources.getString(R.string.unknown_geofence_error);

    } // end switch (errorCode)
} // end getErrorString(Context context, int errorCode)

} // end GeolocationService Class

MapFragment是显示实际地图,标记和地理围栏的地方:

public class MapFragment extends Fragment {
protected SupportMapFragment mapFragment;
protected GoogleMap map;
protected Marker myPositionMarker;
Double latitude, longitude = 0.0;
Integer transition = 0;
float radius = 0;
long expiration = 0;
Handler handler;
HashMap<String, SimpleGeofence> geofences;
Button lobbyBtn, startTabBtn, settingsBtn;
private Bundle savedState = null;
Context mContext;
boolean mapOpen = false;
public static BroadcastReceiver mReceiver;
public static FragmentActivity fAct;

private BroadcastReceiver receiver = new BroadcastReceiver() {
    @Override
    public void onReceive(Context context, Intent intent) {
        Bundle bundle = intent.getExtras();

        if (bundle != null) {
            int resultCode = bundle.getInt("done");

            if (resultCode == 1) {
                latitude = bundle.getDouble("latitude");
                longitude = bundle.getDouble("longitude");

                updateMarker(latitude, longitude, context);
            } // end if (resultCode == 1)

        } // end if (bundle != null)
    } // end onReceive(Context context, Intent intent)
}; // end BroadcastReceiver receiver = new BroadcastReceiver()

@Override
public void onCreate(Bundle savedInstanceState) {
    setRetainInstance(true);
    setHasOptionsMenu(true);

    super.onCreate(savedInstanceState);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {
    View rootView = inflater.inflate(R.layout.fragment_map, container,
            false);

    mapFragment = SupportMapFragment.newInstance();

    FragmentTransaction fragmentTransaction = getChildFragmentManager()
            .beginTransaction();
    fragmentTransaction.add(R.id.map_container, mapFragment);
    fragmentTransaction.commit();

    startTabBtn = (Button) rootView.findViewById(R.id.calculator_button);
    lobbyBtn = (Button) rootView.findViewById(R.id.lobby_button);
    settingsBtn = (Button) rootView.findViewById(R.id.settings_button);

    lobbyBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Intent toLobby = new Intent(v.getContext(), Lobby.class);
            startActivity(toLobby);
        }
    });

    startTabBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Intent toCalc = new Intent(v.getContext(), CurrentTab.class);
            startActivity(toCalc);
        }
    });

    settingsBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Intent toCalc = new Intent(v.getContext(), StartTab.class);
            startActivity(toCalc);
        }
    });

    return rootView;
} // end onCreateView

// ON PAUSE
// ***********
@Override
public void onPause() {
    super.onPause();
    fAct = getActivity();
    getActivity().unregisterReceiver(receiver);
}

// ON RESUME
// ************
@Override
public void onResume() {
    super.onResume();

    if (mapFragment != null) {

        if (map != null)
            map.animateCamera(CameraUpdateFactory.zoomTo(15));

        mapFragment.getMapAsync(new OnMapReadyCallback() {

            @Override
            public void onMapReady(GoogleMap googleMap) {
                map = googleMap;
                map.animateCamera(CameraUpdateFactory.zoomTo(15));

            } // end onMapReady(GoogleMap googleMap)

        }); // end mapFragment.getMapAsync(new OnMapReadyCallback()
    } // end if (mapFragment != null)

    mReceiver = receiver;

    getActivity().registerReceiver(
            receiver,
            new IntentFilter(
                    "com.diligencedojo.tabsitter.geolocation.service"));
} // end onResume()

// DISPLAY GEOFENCE
// *******************
protected void displayGeofences() {
    geofences = SimpleGeofenceStore.getInstance().getSimpleGeofences();

    // set circle around marker
    for (Map.Entry<String, SimpleGeofence> item : geofences.entrySet()) {
        SimpleGeofence sg = item.getValue();

        CircleOptions circleOptions1 = new CircleOptions()
                .center(new LatLng(sg.getLatitude(), sg.getLongitude()))
                .radius(sg.getRadius()).strokeColor(Color.BLACK)
                .strokeWidth(2).fillColor(0x500000ff);

        map.addCircle(circleOptions1);
    }

} // end displayGeofences()

// CREATE MARKER
// ****************
protected void createMarker(Double latitude, Double longitude,
        Context context) {
    LatLng latLng = new LatLng(latitude, longitude);

    myPositionMarker = map.addMarker(new MarkerOptions().position(latLng));
    map.moveCamera(CameraUpdateFactory.newLatLng(latLng));
    // display the geofence after the marker is placed to ensure that the
    // map is being displayed successfully
    displayGeofences();

    // save the state of the map (if it's open or not)
    TinyDB tinydb = new TinyDB(context);
    tinydb.putBoolean("mapOpen", true);
    tinydb.putDouble("latitude", latitude);
    tinydb.putDouble("longitude", longitude);
}

// UPDATE MARKER
// ****************
protected void updateMarker(Double latitude, Double longitude,
        Context context) {
    if (myPositionMarker == null)
        createMarker(latitude, longitude, context);

    LatLng latLng = new LatLng(latitude, longitude);
    myPositionMarker.setPosition(latLng);
    map.moveCamera(CameraUpdateFactory.newLatLng(latLng));
}

// ON CREATE OPTIONS MENU
// *************************
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
    super.onCreateOptionsMenu(menu, inflater);
    inflater.inflate(R.menu.menu_map, menu);
}

// ON OPTIONS SELECTED
// **********************
@Override
public boolean onOptionsItemSelected(MenuItem item) {

    return super.onOptionsItemSelected(item);
}

} // end MapFragment Class

CloseTab活动是我想停止应用正在使用的任何GPS服务的地方。我尝试了很多不同的方法,所以请耐心等待。

public class CloseTab extends Activity {
Button numDrinksBtn, estBillBtn, avgCostBtn, tipAmtBtn, totBillBtn,
        dismissBtn;
TextView tipExpl;
int currDrinkTotal = 0;
double currTabTotal, currTipTotal, tipAmt = 0.0;
boolean isSobriety, isSaver, isCount = false;
GoogleApiClient mGoogleApiClient;
SimpleGeofence sg;
LocationListener mlocListener;
LocationManager locationManager;
android.location.LocationListener mlocListenerProvider;
PendingIntent mPendingIntent;
ConnectionCallbacks mConnCallbacks;
OnConnectionFailedListener mConnFailedListener;
BroadcastReceiver mReceiver;
FragmentActivity fAct;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.close_tab_layout);

    numDrinksBtn = (Button) findViewById(R.id.num_drinks_amout);
    estBillBtn = (Button) findViewById(R.id.est_bill_amout);
    avgCostBtn = (Button) findViewById(R.id.avg_cost_amout);
    tipExpl = (TextView) findViewById(R.id.tip_expl_text);
    tipAmtBtn = (Button) findViewById(R.id.total_tip_amount);
    totBillBtn = (Button) findViewById(R.id.total_bill_amout);
    dismissBtn = (Button) findViewById(R.id.dismiss_button);

    getSavedValues(); // populate view with saved values

    // DISMISS BUTTON
    dismissBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

            mGoogleApiClient = GeolocationService.mGoogleApiClientStatic;
            if (mGoogleApiClient.isConnected()) {
                mlocListener = GeolocationService.mlocListener;
                locationManager = GeolocationService.mlocManager;
                mlocListenerProvider =                        GeolocationService.mlocListenerProvider;
                mPendingIntent = GeolocationService.pendingIntent;
                mConnCallbacks = GeolocationService.connCallbacks;
                mConnFailedListener = GeolocationService.connFailedListener;
                LocationServices.FusedLocationApi.removeLocationUpdates(
                        mGoogleApiClient, mlocListener);
                LocationServices.GeofencingApi.removeGeofences(
                        mGoogleApiClient, mPendingIntent);
                locationManager.removeUpdates(mlocListenerProvider);
                mGoogleApiClient
                        .unregisterConnectionCallbacks(mConnCallbacks);
                mGoogleApiClient
                        .unregisterConnectionFailedListener(mConnFailedListener);
                // mGoogleApiClient.stopAutoManage(f);
                // mReceiver.abortBroadcast();
                // fAct = MapFragment.fAct;
                // mGoogleApiClient.stopAutoManage(fAct);
                // mReceiver = MapFragment.mReceiver;
                // fAct.unregisterReceiver(mReceiver);
                mGoogleApiClient.disconnect();
            }

            turnGPSOff();

            Intent intent = new Intent(
                    "android.location.GPS_ENABLED_CHANGE");
            intent.putExtra("enabled", false);
            sendBroadcast(intent);

            ActivityManager am = (ActivityManager) getSystemService(Activity.ACTIVITY_SERVICE);
            am.killBackgroundProcesses("com.diligencedojo.tabsitter");
            am.getRunningServices(100).clear();
            am.getRunningAppProcesses().clear();

            // clear all saved values
            TinyDB tinydb = new TinyDB(getApplicationContext());
            tinydb.clear();

            finish();
            startActivity(getIntent());

            Intent toLobby = new Intent(v.getContext(), Lobby.class);
            startActivity(toLobby);
        }
    });

} // end onCreate

// automatic turn off the gps
public void turnGPSOff() {
    Context ctx = getApplicationContext();
    // CloseTab.this
    String provider = Settings.Secure.getString(ctx.getContentResolver(),
            Settings.Secure.LOCATION_PROVIDERS_ALLOWED);

    if (provider.contains("gps")) { // if gps is enabled
        // Toast.makeText(getApplicationContext(),
        // "in->provider.contains(gps)", Toast.LENGTH_SHORT).show();

        final Intent poke = new Intent();
        poke.setClassName("com.android.settings",
                "com.android.settings.widget.SettingsAppWidgetProvider");
        poke.addCategory(Intent.CATEGORY_ALTERNATIVE);
        poke.setData(Uri.parse("3"));
        ctx.sendBroadcast(poke);
        // CloseTab.this.sendBroadcast(poke);
    }
}
..........

这些是我用于地理围栏的课程:

SimpleGeofence类

public class SimpleGeofence {
private final String id;
private double latitude;
private double longitude;
private final float radius;
private long expirationDuration;
private int transitionType;
private int loiteringDelay = 60000;

public SimpleGeofence(String geofenceId, double latitude, double longitude,
        float radius, long expiration, int transition) {
    this.id = geofenceId;
    this.latitude = latitude;
    this.longitude = longitude;
    this.radius = radius;
    this.expirationDuration = expiration;
    this.transitionType = transition;
}

public String getId() {
    return id;
}

public void setLatitude(Double mLat) {
    this.latitude = mLat;
}

public double getLatitude() {
    return latitude;
}

public void setLongitude(Double mLong) {
    this.longitude = mLong;
}

public double getLongitude() {
    return longitude;
}

public float getRadius() {
    return radius;
}

public void setExpirationDuration(long mExpirationDuration) {
    this.expirationDuration = mExpirationDuration;
}

public long getExpirationDuration() {
    return expirationDuration;
}

public int getTransitionType() {
    return transitionType;
}

public Geofence toGeofence() {
    Geofence g = new Geofence.Builder().setRequestId(getId())
            .setTransitionTypes(transitionType)
            .setCircularRegion(getLatitude(), getLongitude(), getRadius())
            .setExpirationDuration(expirationDuration)
            .setLoiteringDelay(loiteringDelay).build();
    return g;
}

} // end SimpleGefence Class

SimpleGeofenceStore类

public class SimpleGeofenceStore {
private static final long GEOFENCE_EXPIRATION_IN_HOURS = 12;
private static final long RADIUS = 100;
public static final long GEOFENCE_EXPIRATION_IN_MILLISECONDS =    GEOFENCE_EXPIRATION_IN_HOURS
        * DateUtils.HOUR_IN_MILLIS;
protected HashMap<String, SimpleGeofence> geofences = new HashMap<String, SimpleGeofence>();
private static SimpleGeofenceStore instance = new SimpleGeofenceStore();
private double latitude;
private double longitude;

public static SimpleGeofenceStore getInstance() {
    // mContext = context;
    return instance;
}

public void setLatLong(Double mLat, Double mLong) {
    this.latitude = mLat;
    this.longitude = mLong;
}

public Double getLatitude() {
    return latitude;
}

public Double getLongitude() {
    return longitude;
}

private SimpleGeofenceStore() {

    geofences.put("My House", new SimpleGeofence("My House", getLatitude(),
            getLongitude(), RADIUS, GEOFENCE_EXPIRATION_IN_MILLISECONDS,
            Geofence.GEOFENCE_TRANSITION_ENTER
                    | Geofence.GEOFENCE_TRANSITION_DWELL
                    | Geofence.GEOFENCE_TRANSITION_EXIT));

}

public HashMap<String, SimpleGeofence> getSimpleGeofences() {
    return this.geofences;
}

} // end SimpleGeofenceStore Class

1 个答案:

答案 0 :(得分:0)

要在按钮上单击其他活动时禁用位置服务和进程,我按照以下步骤操作。首先,我将GeolocationServices.java中的位置变量定义为public和static。这允许您在其他活动中访问它们。接下来,我把一个布尔变量&#34; tabClos​​ed&#34;在断开连接后可能重新连接GoogleApiClient的所有内容。我不完全确定我需要这个。

GeolocationServices.java

public class GeolocationService extends Service implements ConnectionCallbacks,
    OnConnectionFailedListener, LocationListener, ResultCallback<Status> {
// TinyDB saved value handles: (boolean)"mapReady"
LocationListener listener;
private static final long GEOFENCE_EXPIRATION_IN_HOURS = 12;
private static final long RADIUS = 100;
public static final long GEOFENCE_EXPIRATION_IN_MILLISECONDS = GEOFENCE_EXPIRATION_IN_HOURS
        * DateUtils.HOUR_IN_MILLIS;
public static final long UPDATE_INTERVAL_IN_MILLISECONDS = 10000;
public static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS = UPDATE_INTERVAL_IN_MILLISECONDS / 5;
// protected GoogleApiClient mGoogleApiClient;
public static GoogleApiClient mGoogleApiClient;
protected LocationRequest mLocationRequest;
// private PendingIntent mPendingIntent;
public static PendingIntent mPendingIntent;
List<Geofence> mGeofenceList;
SimpleGeofence simpleGeo;
Location mLocation, newLocation;
public static LocationManager mlocManager;
public static LocationListener mlocListener;
public static ConnectionCallbacks connCallbacks;
public static OnConnectionFailedListener connFailedListener;
public static ResultCallback<Status> mGeoCallback;

// ON START
// ***********
@Override
public void onStart(Intent intent, int startId) {
    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) {
        buildGoogleApiClient();
        mGoogleApiClient.connect();
    }
}

// ON DESTROY
// *************
@Override
public void onDestroy() {
    // super.onDestroy();

    if (mGoogleApiClient.isConnected()) {
        mGoogleApiClient.disconnect();
        mlocManager.removeUpdates(mPendingIntent);
        mlocManager.removeProximityAlert(mPendingIntent);
        mPendingIntent.cancel();
    }

    super.onDestroy();
}

// REGISTER GEOFENCES
// *********************
protected void registerGeofences(Location location) {
    if (Alarm.geofencesAlreadyRegistered)
        return;

    Log.d(Alarm.TAG, "Registering Geofences");

    String geoId = "geoId";
    simpleGeo = new SimpleGeofence(geoId, location.getLatitude(),
            location.getLongitude(), RADIUS,
            GEOFENCE_EXPIRATION_IN_MILLISECONDS,
            Geofence.GEOFENCE_TRANSITION_ENTER
                    | Geofence.GEOFENCE_TRANSITION_DWELL
                    | Geofence.GEOFENCE_TRANSITION_EXIT);

    // //
    HashMap<String, SimpleGeofence> geofences = SimpleGeofenceStore
            .getInstance().getSimpleGeofences();

    GeofencingRequest.Builder builder = new GeofencingRequest.Builder();

    for (Map.Entry<String, SimpleGeofence> item : geofences.entrySet()) {
        SimpleGeofence sg = item.getValue();
        sg.setLatitude(simpleGeo.getLatitude());
        sg.setLongitude(simpleGeo.getLongitude());
        builder.addGeofence(sg.toGeofence());

        SimpleGeofenceStore store = SimpleGeofenceStore.getInstance();
        store.setLatLong(simpleGeo.getLatitude(), simpleGeo.getLongitude());
        // Log.d(Alarm.TAG, sg.getLatitude() + " " + sg.getLongitude());
    }

    TinyDB tinydb = new TinyDB(getApplicationContext());
    tinydb.putBoolean("mapReady", false);

    GeofencingRequest geofencingRequest = builder.build();

    mPendingIntent = requestPendingIntent();

    mGeoCallback = this;

    LocationServices.GeofencingApi.addGeofences(mGoogleApiClient,
            geofencingRequest, mPendingIntent).setResultCallback(
            mGeoCallback);

    Alarm.geofencesAlreadyRegistered = true;
} // end registerGeofences()

// REQUEST PENDING INTENT
// *************************
private PendingIntent requestPendingIntent() {
    PendingIntent tempPendingIntent = null;

    if (null != mPendingIntent)
        return mPendingIntent;

    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) {
        Intent intent = new Intent(this, GeofenceReceiver.class);
        tempPendingIntent = PendingIntent.getService(this, 0, intent,
                PendingIntent.FLAG_UPDATE_CURRENT);
    }

    return tempPendingIntent;

} // end requestPendingIntent()

// BROADCAST LOCATION FOUND
// ***************************
public void broadcastLocationFound(Location location) {
    Intent intent = new Intent(
            "com.diligencedojo.tabsitter.geolocation.service");
    intent.putExtra("latitude", location.getLatitude());
    intent.putExtra("longitude", location.getLongitude());
    intent.putExtra("done", 1);

    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed)
        sendBroadcast(intent);

} // end broadcastLocationFound(Location location)

// START LOCATION UPDATES
// *************************
protected void startLocationUpdates() {
    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) { //
        LocationServices.FusedLocationApi.requestLocationUpdates(
                mGoogleApiClient, mLocationRequest, this);
    }
} // end startLocationUpdates()

// STOP LOCATION UPDATES
// ************************
protected void stopLocationUpdates() {
    LocationServices.FusedLocationApi.removeLocationUpdates(
            mGoogleApiClient, this);
} // end stopLocationUpdates()

// ON CONNECTED
// ***************
@Override
public void onConnected(Bundle connectionHint) {
    Log.i(Alarm.TAG, "Connected to GoogleApiClient");
    startLocationUpdates();
} // end onConnected(Bundle connectionHint)

// ON LOCATION CHANGED
// **********************
@Override
public void onLocationChanged(Location location) {
    Log.d(Alarm.TAG, "new location : " + location.getLatitude() + ", "
            + location.getLongitude() + ". " + location.getAccuracy());

    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed)
        broadcastLocationFound(location);

    if (!Alarm.geofencesAlreadyRegistered)
        registerGeofences(location);

} // end onLocationChanged(Location location)

// ON CONNECTION SUSPENDED
// **************************
@Override
public void onConnectionSuspended(int cause) {
    Log.i(Alarm.TAG, "Connection suspended");

    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed)
        mGoogleApiClient.connect();

} // end onConnectionSuspended(int cause)

// ON CONNECTION FAILED
// ***********************
@Override
public void onConnectionFailed(ConnectionResult result) {
    Log.i(Alarm.TAG,
            "Connection failed: ConnectionResult.getErrorCode() = "
                    + result.getErrorCode());
} // end onConnectionFailed(ConnectionResult result)

// BUILD GOOGLE API CLIENT
// **************************
protected synchronized void buildGoogleApiClient() {
    Log.i(Alarm.TAG, "Building GoogleApiClient");

    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) {
        mlocListener = this;
        connCallbacks = this;
        connFailedListener = this;

        mGoogleApiClient = new GoogleApiClient.Builder(this)
                .addConnectionCallbacks(connCallbacks)
                .addOnConnectionFailedListener(connFailedListener)
                .addApi(LocationServices.API).build();

        createLocationRequest();
    }

} // end buildGoogleApiClient()

// CREATE LOCATION REQUEST
// **************************
protected void createLocationRequest() {
    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) {
        mLocationRequest = new LocationRequest();
        mLocationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS);
        mLocationRequest
                .setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS);
        mLocationRequest
                .setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
    }

} // end createLocationRequest()

// ON BIND
// **********
@Override
public IBinder onBind(Intent intent) {
    return null;
}

// ON RESULT
// ************
public void onResult(Status status) {
    TinyDB tinydb = new TinyDB(getApplicationContext());
    boolean tabClosed = tinydb.getBoolean("tabClosed");

    if (!tabClosed) {

        if (status.isSuccess()) {
            Toast.makeText(getApplicationContext(),
                    getString(R.string.geofences_added), Toast.LENGTH_SHORT)
                    .show();

            tinydb.putBoolean("mapReady", true);
        } else {
            Alarm.geofencesAlreadyRegistered = false;
            String errorMessage = getErrorString(this,
                    status.getStatusCode());
            Toast.makeText(getApplicationContext(), errorMessage,
                    Toast.LENGTH_SHORT).show();
        }
    } else {
        Toast.makeText(getApplicationContext(),
                "Tab closed, do not add geofence.", Toast.LENGTH_SHORT)
                .show();
    }

} // end onResult(Status status)

// GET ERROR STRING
// *******************
public static String getErrorString(Context context, int errorCode) {
    Resources mResources = context.getResources();

    switch (errorCode) {
    case GeofenceStatusCodes.GEOFENCE_NOT_AVAILABLE:
        return mResources.getString(R.string.geofence_not_available);
    case GeofenceStatusCodes.GEOFENCE_TOO_MANY_GEOFENCES:
        return mResources.getString(R.string.geofence_too_many_geofences);
    case GeofenceStatusCodes.GEOFENCE_TOO_MANY_PENDING_INTENTS:
        return mResources
                .getString(R.string.geofence_too_many_pending_intents);
    default:
        return mResources.getString(R.string.unknown_geofence_error);

    } // end switch (errorCode)
} // end getErrorString(Context context, int errorCode)

} // end GeolocationService Class

现在在CloseTab.java中,我检索了我在GeolocationService.java中声明了public static的变量。禁用位置服务时,使用相同的待处理意图作为参数非常重要。首先,我删除了地理围栏,然后更新了位置,然后我将google api客户端全部断开连接。最后,我使用stopService(intent)删除任何延迟服务(例如在我的MapFragment.java中启动的服务)。

public class CloseTab extends Activity {
Button numDrinksBtn, estBillBtn, avgCostBtn, tipAmtBtn, totBillBtn,
        dismissBtn;
TextView tipExpl;
int currDrinkTotal = 0;
double currTabTotal, currTipTotal, tipAmt = 0.0;
boolean isSobriety, isSaver, isCount = false;
GoogleApiClient mGoogleApiClient;
PendingIntent mPendingIntent;
ResultCallback<Status> mGeoCallback;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.close_tab_layout);

    numDrinksBtn = (Button) findViewById(R.id.num_drinks_amout);
    estBillBtn = (Button) findViewById(R.id.est_bill_amout);
    avgCostBtn = (Button) findViewById(R.id.avg_cost_amout);
    tipExpl = (TextView) findViewById(R.id.tip_expl_text);
    tipAmtBtn = (Button) findViewById(R.id.total_tip_amount);
    totBillBtn = (Button) findViewById(R.id.total_bill_amout);
    dismissBtn = (Button) findViewById(R.id.dismiss_button);

    getSavedValues(); // populate view with saved values

    // DISMISS BUTTON
    dismissBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

            mGoogleApiClient = GeolocationService.mGoogleApiClient;
            if (mGoogleApiClient.isConnected()) {
                // Log.d("DBG", "mGoogleApiClient.isConnected()");

                mPendingIntent = GeolocationService.mPendingIntent;
                mGeoCallback = GeolocationService.mGeoCallback;

                try { // Log.d("DBG", "try hit in CloseTab");

                    // use the same pending intent set in GeolocationService
                    // to identify the right things to disable

                    // Remove geofence
                    LocationServices.GeofencingApi.removeGeofences(
                            mGoogleApiClient, mPendingIntent)
                            .setResultCallback(mGeoCallback);
                    // Remove location updates
                    LocationServices.FusedLocationApi
                            .removeLocationUpdates(mGoogleApiClient,
                                    mPendingIntent);
                    // Disconnect google client
                    mGoogleApiClient.disconnect();

                    // Remove any lingering services
                    Intent intent = new Intent(getApplicationContext(),
                            GeolocationService.class);
                    stopService(intent);

                } catch (SecurityException securityException) {
                    // Catch exception generated if the app does not use
                    // ACCESS_FINE_LOCATION permission.
                    Log.d("DBG", "catch hit in CloseTab");
                }
            }

            // clear all saved values
            TinyDB tinydb = new TinyDB(getApplicationContext());
            tinydb.clear();
            // tab has been closed. this is used as a condition to determine
            // if gps should be allowed to reconnect on it's own
            tinydb.putBoolean("tabClosed", true);

            Intent toLobby = new Intent(v.getContext(), Lobby.class);
            startActivity(toLobby);
        }
    });

}// end onCreate

希望这会帮助别人。