Drag and drop marker on google map

I have markers. I would like to move the marker with a drag and drop-function, and then check the location where we drop that marker.
1.) In this show google map tiles show on screen and zoom at given level.

MainActivity.java


@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);


MapView map = (MapView) findViewById(R.id.map);

map.getController().setCenter(
getPoint(40.70686417491799, -74.01572942733765));
map.getController().setZoom(17);
map.setBuiltInZoomControls(true);
}

2.) I was doing some precise measurements with markers on my map, and I wanted my marker to be exactly on the spot I touched and lifted my finger so the measurement was exactly precise.

MainActivity.java


ImageView dragImage=(ImageView) findViewById(R.id.drag);
Drawable marker = getResources().getDrawable(R.drawable.marker);

marker.setBounds(0, 0, marker.getIntrinsicWidth(),
marker.getIntrinsicHeight());

map.getOverlays().add(new SitesOverlay(marker, dragImage, map));

3.) If you touch "near" the marker, the marker does not go to that exact point, but moves along with your finger's movement. I needed the marker to appear just below my finger on the ACTION_DOWN, ACTION_MOVE and ACTION_UP.

SiteOverLay.java


package com.example.draganddropbasic;
import java.util.ArrayList;
import java.util.List;
import android.graphics.Canvas;
import android.graphics.Point;
import android.graphics.drawable.Drawable;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import com.google.android.maps.GeoPoint;
import com.google.android.maps.ItemizedOverlay;
import com.google.android.maps.MapView;
import com.google.android.maps.OverlayItem;

public class SitesOverlay extends ItemizedOverlay {
private List items = new ArrayList();
private Drawable marker = null;
private OverlayItem inDrag = null;
private ImageView dragImage = null;
private int xDragImageOffset = 0;
private int yDragImageOffset = 0;
private int xDragTouchOffset = 0;
private int yDragTouchOffset = 0;
MapView map;

public SitesOverlay(Drawable marker, ImageView dragImage, MapView map) {
super(marker);
this.marker = marker;
this.map = map;
this.dragImage = dragImage;

xDragImageOffset = dragImage.getDrawable().getIntrinsicWidth() / 2;
yDragImageOffset = dragImage.getDrawable().getIntrinsicHeight();

items.add(new OverlayItem(getPoint(40.748963847316034,
-73.96807193756104), "UN", "United Nations"));
items.add(new OverlayItem(getPoint(40.76866299974387,
-73.98268461227417), "Lincoln Center",
"Home of Jazz at Lincoln Center"));
items.add(new OverlayItem(getPoint(40.765136435316755,
-73.97989511489868), "Carnegie Hall",
"Where you go with practice, practice, practice"));
items.add(new OverlayItem(getPoint(40.70686417491799,
-74.01572942733765), "The Downtown Club",
"Original home of the Heisman Trophy"));

populate();
}

private GeoPoint getPoint(double lat, double lon) {
return (new GeoPoint((int) (lat * 1000000.0), (int) (lon * 1000000.0)));
}

@Override
protected OverlayItem createItem(int i) {
return (items.get(i));
}

@Override
public void draw(Canvas canvas, MapView mapView, boolean shadow) {
super.draw(canvas, mapView, shadow);

boundCenterBottom(marker);
}

@Override
public int size() {
return (items.size());
}

@Override
public boolean onTouchEvent(MotionEvent event, MapView mapView) {
final int action = event.getAction();
final int x = (int) event.getX();
final int y = (int) event.getY();
boolean result = false;

if (action == MotionEvent.ACTION_DOWN) {
for (OverlayItem item : items) {
Point p = new Point(0, 0);

map.getProjection().toPixels(item.getPoint(), p);

if (hitTest(item, marker, x - p.x, y - p.y)) {
result = true;
inDrag = item;
items.remove(inDrag);
populate();

xDragTouchOffset = 0;
yDragTouchOffset = 0;

setDragImagePosition(p.x, p.y);
dragImage.setVisibility(View.VISIBLE);

xDragTouchOffset = x - p.x;
yDragTouchOffset = y - p.y;

break;
}
}
} else if (action == MotionEvent.ACTION_MOVE && inDrag != null) {
setDragImagePosition(x, y);
result = true;
} else if (action == MotionEvent.ACTION_UP && inDrag != null) {
dragImage.setVisibility(View.GONE);

GeoPoint pt = map.getProjection().fromPixels(x - xDragTouchOffset,
y - yDragTouchOffset);
OverlayItem toDrop = new OverlayItem(pt, inDrag.getTitle(),
inDrag.getSnippet());
Log.i("info",
"get lat:" + pt.getLatitudeE6() + " lang:"
+ pt.getLongitudeE6());
items.add(toDrop);
populate();

inDrag = null;
result = true;
}

return (result || super.onTouchEvent(event, mapView));
}

private void setDragImagePosition(int x, int y) {
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) dragImage
.getLayoutParams();

lp.setMargins(x - xDragImageOffset - xDragTouchOffset, y
- yDragImageOffset - yDragTouchOffset, 0, 0);
dragImage.setLayoutParams(lp);
}
}

4.) MainActivity.java


package com.example.draganddropbasic;

import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.view.KeyEvent;
import android.widget.ImageView;
import com.google.android.maps.GeoPoint;
import com.google.android.maps.MapActivity;
import com.google.android.maps.MapView;
import com.google.android.maps.MyLocationOverlay;

public class MainActivity extends MapActivity {
private MapView map = null;
private MyLocationOverlay me = null;

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);


map = (MapView) findViewById(R.id.map);

map.getController().setCenter(
getPoint(40.70686417491799, -74.01572942733765));
map.getController().setZoom(17);
map.setBuiltInZoomControls(true);

ImageView dragImage = (ImageView) findViewById(R.id.drag);
Drawable marker = getResources().getDrawable(R.drawable.marker);

marker.setBounds(0, 0, marker.getIntrinsicWidth(),
marker.getIntrinsicHeight());

map.getOverlays().add(new SitesOverlay(marker, dragImage, map));

me = new MyLocationOverlay(this, map);
map.getOverlays().add(me);
}

@Override
public void onResume() {
super.onResume();

me.enableCompass();
}

@Override
public void onPause() {
super.onPause();

me.disableCompass();
}

@Override
protected boolean isRouteDisplayed() {
return (false);
}

@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_S) {
map.setSatellite(!map.isSatellite());
return (true);
} else if (keyCode == KeyEvent.KEYCODE_Z) {
map.displayZoomControls(true);
return (true);
}

return (super.onKeyDown(keyCode, event));
}

private GeoPoint getPoint(double lat, double lon) {
return (new GeoPoint((int) (lat * 1000000.0), (int) (lon * 1000000.0)));
}

}

5.) activity_main.xml


< ?xml version="1.0" encoding="utf-8"?>
< RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent" >

< com.google.android.maps.MapView
android:id="@+id/map"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:apiKey="0mjl6OufrY-tHs6WFurtL7rsYyEMpdEqBCbyjXg"
android:clickable="true" />

< ImageView
android:id="@+id/drag"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/marker"
android:visibility="gone" />

< /RelativeLayout>

6.) Now run this and you get the desired result.

0 comments:

Post a Comment