Android Google Maps animating every location - java

I have an ArrayList of LatLng, and in a forloop of onMapReady(GoogleMap googleMap) I would like to animate moving from location to another in order.
I tried doing this in a for loop:
mMap.animateCamera(CameraUpdateFactory.newLatLngZoom(currLatLng,10), 1000, null);
and the animation happens only at the last location.
How would I go about doing so? Should I use the last parameter of animateCamera() method? (Cancellable Callback)

My instinct was correct.
The last parameter in animateCamera is a CancellableCallback() interface.
What I did is made a method called animateToLocationAtIndex(int index)
And then called:
mMap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng, 10), 2000, new GoogleMap.CancelableCallback() {
#Override
public void onFinish() {
// Placing a marker on the position after animated
Marker marker = mMap.addMarker(markerOptions);
animateLocationMovement(i+1);
}
This animates the locations as I wanted, although I ran into another issue where the map at the next location isn't loaded so it may seem like the animation is laggy.

Related

Want to know about google map pop ups or snippet upon exact location

I want to develop an app on google map that could notify me with some information set by the user when I am close to the exact location. So can I get a link for this that How can I get pop-ups when I am at the exact(user) location?
You'll first need to enable a location manager to start getting the user's current location. Then, every time the user's location updates, the location manager calls the onLocationChanged() method. Here, you would want to check the distance between the user's current location and the destination location. If they are within whatever distance you choose, then you can display your map marker. Here is a little example of how to do that:
#Override
public void onLocationChanged(Location location) {
float distanceInMeters = destLocation.distanceTo(location);
// Distance in miles
double distance_to_dest = (distanceInMeters/1609.344);
int distance_to_dest_int = (int)(distance_to_dest * 100);
distance_to_dest = ((double)distance_to_dest_int/100.00);
tvMilesToGo.setText(String.format("%.2f", distance_to_dest) + "mi");
// About 1/10th of a mile
if ((distanceInMeters > 149) && (distanceInMeters < 176)) {
// I played an alarm sound when close to the target destination
//if (alarmPlayer.isPlaying()) {
// alarmPlayer.stop();
//}
//alarmPlayer.start();
Marker marker = mMap.addMarker(new MarkerOptions()
.position(new LatLng(destLocation.getLatitude(), destLocation.getLongitude()))
.title(“Arrived”)
.snippet(“You have arrived at your destination!”)
.icon(red_descriptor));
Marker.showInfoWindow;
}
}
Note, in your case, you would probably only ever want to add a marker once, so, you would probably want to set a flag such as markerIsVisible = true once you add it to the map, and then check before adding the marker if (markerIsVisible == false) {add the marker, markerIsVisible = true}

lock map activity

In my application im trying to prevet the user to be able to scroll "free" around the map activity , i want the display content to be lock in some specific coordinates but the difficult part is to concatenate this with the ability of the camera geolocalization(GPS) to follow around the user .
i can for example try to add a move camera to the onLocationChanged and this will lock the camera in the region that i want evry time the user move , but this is not what i want , i just want to reset the camera if the user scroll in a zone that i dont want him to see , if you are browsing the map of Washington i want the camera to reset if the user goes for example on baltimora .
LatLng Washington = new LatLng(38.9150303, -77.1655794);
public void onLocationChanged(Location location) {
LatLng me = new LatLng(location.getLatitude(),location.getLongitude());
//LOCK CAMERA
mMap.moveCamera(CameraUpdateFactory.newLatLng(Washington));
//Marker Position
if (null != currentMarker) {
currentMarker.remove();
}
currentMarker = mMap.addMarker(new MarkerOptions().position(me).icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_GREEN)));
If you want the user to be able to move the map but restrict to a given area, the map offers you that option.
As mentioned here : Restricting the user's panning to a given area
private GoogleMap mMap;
// Create a LatLngBounds that includes the city of Adelaide in Australia.
private LatLngBounds ADELAIDE = new LatLngBounds(
new LatLng(-35.0, 138.58), new LatLng(-34.9, 138.61));
// Constrain the camera target to the Adelaide bounds.
mMap.setLatLngBoundsForCameraTarget(ADELAIDE);

How to updatecamera only once

I'm working on a project with google maps and I want to update the camera and camera zoom to the location of the user but only once (when the app is running) why only once? because I want the user to be able to move and drag around the map without updating the camera every 5 or "n" seconds.
I get the users position in the method onLocationChanged() and then I update the camera, but this is updating the camera every 5 seconds (my interval) and i is not what I want. I just want to update it the first time when the map is opened.
#Override
public void onLocationChanged(Location location) {
Log.d(TAG, "OnLocationChanged"+String.valueOf(location.getLatitude())
+ "longitude" + String.valueOf(location.getLongitude()));
eraseMarkers();
if (mMap != null) {
LatLng newLatLng = new LatLng(location.getLatitude(), location.getLongitude());
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom(newLatLng,CAMARA_ZOOM));
I appreciate your help

libGDX textured disappearing when tapping home button

I am developing a mobile game for Android with libGDX. I have noticed that when I click the home button and then go back to the game, the player has disappeared. All other actors attached to the stage exist, and when I remove the code that moves the player it is also drawn. It only disappears when it is moving. I have done so much debugging, and sometimes the position seems to update corretly but the player is invisible, but sometimes it is just NaN. I have for example tried to save position and velocity in pause function and provide the player with them in the resume function, but nothing helps.
This is what I am doing in the player update function:
// When these lines are removed, the app works perfectly
velocity.add(0.0f, GRAVITY);
velocity.scl(deltaTime);
position.add(velocity);
velocity.scl(1/deltaTime);
It doesn't even help if I re-create the player in resume function
player2 = new Player(resourceManager.getRegion("player"), new Vector2(320.0f, 350.0f), 300.0f);
Finally I tried to create completely distinct player object that is drawn after the home button is clicked. It is visible, but is does not move:
player2 = new Player(resourceManager.getRegion("player"), new Vector2(320.0f, 350.0f), 300.0f);
Intrestingly enough I was dealing with the same issue today , every texture (actors) remains in screen after resume but not the main actor which was the one who was moving (main actor in my case). After hours debuging I found that when the game state changes between pause and resume the render method (mine looks like this) will get 0 for deltaTime:
#Override public void render(float deltaTime) {
update(delta);
spriteBatch.setProjectionMatrix(cam.combined);
spriteBatch.begin();
spriteBatch.draw(background, cam.position.x - (WIDTH / 2), 0, WIDTH, HEIGHT);
....
spriteBatch.end();}
deltaTime is time elapsed from last render.
apparently there is no time elapsed from pause to resume hence 0.
down the chain of actor updates I was updating my main actor like this
velocity.scl(deltaTime);
position.add(MOVEMENT * deltaTime, velocity.y);
which was passed 0 at very next render after resume hence the NaN (Not a Number).
anyway not sure if there is a better way to go about this or not but this is how I did, a simple check for zero deltaTime in my main actor update method and replace with a very small amount .001f : (please note in subsequent update deltaTime wont be zero and this if statment only get called once and exactly after resume)
public void update(float deltaTime) {
if (deltaTime <= 0) {
deltaTime=.001f;
}
velocity.scl(deltaTime);
position.add(MOVEMENT * deltaTime, velocity.y);
...
}
Oh yeah, I had the same issue before.
What I did was in onPause(), which is called when you press home button, I destroyed all assets references.
Then in onResume(), which is called when you're back, I reassigned the assets again.
render() method continue called when you press home button on Android so it's seems that you player position continue updating with gravity so when you resume your game you not able to see you player on screen so use a flag on position update code and change flag in pause() and resume() method of ApplicationListener interface.
enum GameState{
PAUSED, RESUMED
}
GameState gameState;
#Override
public void create() {
gameState=GameState.RESUMED;
...
}
#Override
public void render() {
Gdx.gl.glClearColor(1,1,1,1);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
if(gameState==GameState.RESUMED) {
velocity.add(0.0f, GRAVITY);
velocity.scl(deltaTime);
position.add(velocity);
velocity.scl(1/deltaTime);
}
}
#Override
public void pause() {
gameState=GameState.PAUSED;
}
#Override
public void resume() {
gameState=GameState.RESUMED;
}

How do I go about using a users location when they are in a certain place? The place would trigger an action based on location

I'm trying to create an app for android with little experience programming. I want to use a phones gps to determine a place on google maps then cause an action to happen. The action would be based on the location and I'd also like to have the user designate locations to cause an action.
If there are any resources or websites you can point me to I would really appreciate it.
I'm currently only using android studio, is there anything else I need?
first, you need the current user location. You can follow the steps offered here to obtain it. The locationmanager provides a method onLocationChanged(Location loc) which then is triggered automatically when the location changes. You can implement your "actions" here. Im not quite sure if I have understood what the designation of locations by the user would have to trigger.
If you want to trigger a specific "action", you can implement the method onMapClicked(Location loc) by setting an onMapClickListener to your map.
Depending on how your "predefined places" are built, you have different possibilities.
1) Are those places points? --> you can calculate the euclidian (or spherical) distances, and related to that distance decide if you want to trigger something or not.
2) are those places 2d rectangles? --> use LatLngBounds and its contains(LatLng point) method to decide if the userlocation or user-designated-location is inside
3) are those places any polygons? here is a good example on how to create such a place. there is also a contains() method.
4) Are your places not predefined? We need more information on what you want to do in this case.
edit based upon ur comment :
so you there are 2 things your app should do:
1) do some action (just like popping up a message), when the user is entering a "place" or comming near to a "place"
2) give the user the possibily to create such a place by himself.
secondary can be done by adding a onMapClickListener to your map.
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
mMap.setOnMapClickListener(new GoogleMap.OnMapClickListener() {
#Override
public void onMapClick(LatLng latLng) {
// latLng is the lcoation, tapped by the user on the map. lets save it
chosen_location = new LatLng(latLng.latitude, latLng.longitude);
}
});
}
This will save the single points, tabbed by a user on a map. If you wanna go further later for polygons, you can add this point to an ArrayList of points. However, you probably want the user to add more information about that point. Make use of EditText to let the user e.g. enter a description of that point (or later polygon), and finally, when clicking a button to "save that entered place", you can add it to an ArrayList. You probably also gonna have a server-backend in order to update and retrieve a list of places created by multiple people from anywhere.
but for now, lets go on and check if the user came nearTo such a point or entered such a polygon:
LocationManager lm = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
lm.requestLocationUpdates(LocationManager.GPS_PROVIDER, 35000, 10, new LocationListener() {
#Override
public void onLocationChanged(Location location) {
// the users location changed (e.g. he moved some meters)
current_location = new LatLng(location.getLatitude(), location.getLongitude());
// somehow get all the places ( i guess a server backend is recommended )
// for now, lets say all the places are already obtained into an Arraylist called places:
ArrayList<LatLng> places = new ArrayList<LatLng>;
// Go check for each of the places, if the users current location is near to such a point
for (LatLng place : places) {
if (distance(place,current_location)<100) {
LatLng near_place = place;
// here we are! near_place is near the users current location, lets do some action
Log.d("app","Users location (" + current_location.latitude +","+current_location.longitude+") is near to a place with coordinates "+near_place.latitude+","+near_place.longitude+").");
}
}
}
#Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
#Override
public void onProviderEnabled(String provider) {
}
#Override
public void onProviderDisabled(String provider) {
}
});
}
and here is a method to calculate (spherical) distance in meters between to LatLng objects:
/**
* method calculate distance between two LatLng points in meter
*/
public float distance(double lat_a, double lng_a, double lat_b, double lng_b) {
double earthRadius = 3958.75;
double latDiff = Math.toRadians(lat_b - lat_a);
double lngDiff = Math.toRadians(lng_b - lng_a);
double a = Math.sin(latDiff / 2) * Math.sin(latDiff / 2) +
Math.cos(Math.toRadians(lat_a)) * Math.cos(Math.toRadians(lat_b)) *
Math.sin(lngDiff / 2) * Math.sin(lngDiff / 2);
double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
double distance = earthRadius * c;
int meterConversion = 1609;
return new Double(distance * meterConversion).floatValue();
}

Categories

Resources