【发布时间】:2013-03-13 16:57:39
【问题描述】:
有没有办法在谷歌地图 v2 的标记上设置longClickListsner?我想让用户长按标记并显示一个对话框,其中包含删除或查看信息的选项。这个可以吗?
【问题讨论】:
标签: android google-maps google-maps-android-api-2
有没有办法在谷歌地图 v2 的标记上设置longClickListsner?我想让用户长按标记并显示一个对话框,其中包含删除或查看信息的选项。这个可以吗?
【问题讨论】:
标签: android google-maps google-maps-android-api-2
我还有一个提议。
首先我使标记可拖动:
mapa.addMarker(new MarkerOptions() ...
.setDraggable(true);
之后你可以像这样设置监听器 setOnMarkerDragListener:
mapa.setOnMarkerDragListener(new OnMarkerDragListener() {
@Override
public void onMarkerDragStart(Marker marker) {
// TODO Auto-generated method stub
//Here your code
}
@Override
public void onMarkerDragEnd(Marker marker) {
// TODO Auto-generated method stub
}
@Override
public void onMarkerDrag(Marker marker) {
// TODO Auto-generated method stub
}
});
然后你可以覆盖你想要的(通常是 onMarkerDragStart 来模拟长按)
希望对你有帮助
【讨论】:
Marker 类没有 LongClickListener。虽然这种方法远非完美,但这里有一个关于您可以做什么的想法。
为您的 GoogleMap 对象设置长点击侦听器。长按时,检查单击的位置是否足够靠近您的任何标记。要确定此接近度阈值,您可以使用地图缩放级别。
这里是不太好的示例代码。我还没有尝试过,但它可能适合您的需求。
map.setOnMapLongClickListener(new OnMapLongClickListener() {
@Override
public void onMapLongClick(LatLng latLng) {
for(Marker marker : yourMarkerList) {
if(Math.abs(marker.getPosition().latitude - latLng.latitude) < 0.05 && Math.abs(marker.getPosition().longitude - latLng.longitude) < 0.05) {
Toast.makeText(MapActivity.this, "got clicked", Toast.LENGTH_SHORT).show(); //do some stuff
break;
}
}
}
});
【讨论】:
按照 ARP 的建议,您可以使用 OnMarkerDragListener 来模拟长按。就我而言,当 onMapLongClick() 发生时,我正在创建新标记,所以我想做一些与
类似(但不相等)的事情@Override
public void onMarkerDragStart(Marker marker) {
marker.remove();
MarkerOptions options = createBasedOnMarker(marker);
this.googleMap.addMarker(options);
}
这样,您将删除之前在地图中的标记,并在相同位置创建另一个具有相同内容的标记(您必须拥有地图或配对以保留您创建的标记中的信息)。
希望我的解决方法有所帮助。
【讨论】:
ARP 的答案很好,但它有一个丑陋的效果:当你开始拖动时,标记会向上移动,而当你完成时,标记仍处于比你用手指指向更高的位置。
【讨论】:
akaya's answer 不是一个坏方法,但如果你的项目有 com.google.maps.android:android-maps-utils:0.3+ library included 你可以确切的距离:
double distance = SphericalUtil.computeDistanceBetween(
marker.getPosition(),
latLng
);
if( distance < 50 ) { // closer than 50 meters?
//..do stuff..
}
【讨论】:
嘿,看看这段代码,我刚刚阻止了标记被拖动并使用了onMarkerDragStart 的长按检测。
public abstract class LinkMarkerLongClickListener implements GoogleMap.OnMarkerDragListener {
private int previousIndex = -1;
private Marker cachedMarker = null;
private LatLng cachedDefaultPostion = null;
private List<Marker> markerList;
private List<LatLng> defaultPostions;
public LinkMarkerLongClickListener(List<Marker> markerList){
this.markerList = new ArrayList<>(markerList);
defaultPostions = new ArrayList<>(markerList.size());
for (Marker marker : markerList) {
defaultPostions.add(marker.getPosition());
marker.setDraggable(true);
}
}
public abstract void onLongClickListener(Marker marker);
@Override
public void onMarkerDragStart(Marker marker) {
onLongClickListener(marker);
setDefaultPostion(markerList.indexOf(marker));
}
@Override
public void onMarkerDrag(Marker marker) {
setDefaultPostion(markerList.indexOf(marker));
}
@Override
public void onMarkerDragEnd(Marker marker) {
setDefaultPostion(markerList.indexOf(marker));
}
private void setDefaultPostion(int markerIndex) {
if(previousIndex == -1 || previousIndex != markerIndex){
cachedMarker = markerList.get(markerIndex);
cachedDefaultPostion = defaultPostions.get(markerIndex);
previousIndex = markerIndex;
}
cachedMarker.setPosition(cachedDefaultPostion);
}
}
你可以这样调用监听器!
map.setOnMarkerDragListener(new LinkMarkerLongClickListener(markers) {
@Override
public void onLongClickListener(Marker marker) {
ToastUtils.showToast(Mission1Activity.this, marker.getTitle());
}
});
【讨论】:
以防万一有人需要它,我调整了一个对数函数来计算@akaya 提到的接近度阈值,它适用于 5.0 到 18 之间的缩放。这是函数:
float zoom = mMap.getCameraPosition().zoom;
double maxDistance = 2000000 * Math.exp(-0.644*zoom);
【讨论】:
这是一个简单的工作解决方案。我们需要使用屏幕 xy 来检查距离。
googleMap.setOnMapLongClickListener{ loc ->
var distance = 10000
var nearestMarker: Marker? = null
allBcmMarkers.forEach { mrkr ->
googleMap?.projection?.let { prj ->
val tapXY = prj.toScreenLocation(loc)
val mrkrXY = prj.toScreenLocation(mrkr.position)
val THRESH = 50
val xDiff = abs(tapXY.x - mrkrXY.x)
val yDiff = abs(tapXY.y - mrkrXY.y)
if (xDiff < THRESH && yDiff < THRESH) {
val mrkrDist =
sqrt((xDiff * xDiff + yDiff * yDiff + xDiff * yDiff).toDouble())
if (mrkrDist < distance) {
distance = mrkrDist.toInt()
nearestMarker = mrkr
}
}
}
}
// you have nearestMarker
}
}
【讨论】: