高德地图SDK Android版开发 9 覆盖物示例3批量点、海量点
前言
前文介绍了如何在地图上添加一个Marker,本文重点介绍如何批量添加和删除 ,海量点 的功能。
批量操作:一次性向地图上大批量添加 Marker的接口。 海量点:应用于移动端的海量点图层用于批量展现具有相似属性的坐标点数据。海量点图层支持处理的点数量级跨度较大,从几十个点至十万个点(建议不超过100000个点数据)都可以应用海量点图层进行处理。该功能自 Android 地图 SDK 5.1.0版本起支持。
相关的类和接口
批量添加
高德地图SDKBaiduMap
地图类除了提供添加一个Marker的接口外,还提供了批量添加的接口:
addMarker
接口可以在地图上添一个图片标记对象。addMarkers
接口可以在地图上添一组图片标记对象。setOnMarkerClickListener
和removeMarkerClickListener
接口可以添加和移除Marker单击事件。
类型 方法 说明 Marker addMarker(MarkerOptions options) 在地图上添一个图片标记(marker)对象。 ArrayList< Marker > addMarkers(ArrayList< MarkerOptions > options, boolean moveToCenter) 在地图上添一组图片标记(marker)对象,并设置是否改变地图状态以至于所有的marker对象都在当前地图可视区域范围内显示。 void setOnMarkerClickListener(AMap.OnMarkerClickListener listener) 设置marker点击事件监听接口。
海量点
MultiPointOverlay
海量点管理对象,可以将大量点展示在地图上,通过MultiPointOverlayOptions
类来设置海量点的选项。
Marker
Text
BasePointOverlay
BaseOverlay
MultiPointOverlay
Polyline
Polygon
Arc
Circle
TextOptions
MarkerOptions
BaseOptions
MultiPointOverlayOptions
PolylineOptions
PolygonOptions
ArcOptions
CircleOptions
AMap类
高德地图AMap
地图类与海量点相关的接口:
类型 方法 说明 MultiPointOverlay addMultiPointOverlay
(MultiPointOverlayOptions options)在地图上添加一个海量点覆盖物(MultiPointOverlay)对象 void setOnMultiPointClickListener
(AMap.OnMultiPointClickListener listener)设置海量点单击事件监听
AMap.OnMultiPointClickListener接口
public interface OnMultiPointClickListener {
boolean onPointClick ( MultiPointItem item) ;
}
MultiPointOverlayOptions 海量点选项
类型 方法 说明 MultiPointOverlayOptions icon
(BitmapDescriptor bitmapDescriptor)设置海量点的显示图标 MultiPointOverlayOptions anchor
(float u, float v)设置海量点的锚点比例。 float getAnchorU
()获取海量点锚点在水平范围的比例。 float getAnchorV
()获取海量点锚点垂直范围的比例。 BitmapDescriptor getIcon
()获取海量点的显示图标
MultiPointOverlay
类型 方法 说明 void setItems
(List< MultiPointItem > items)设置海量点,初始化或者更新海量点时可以调用此方法。 同步方法,如果点很多时,会消耗一定的时间,建议放在子线程中处理。 void setAnchor
(float anchorX, float anchorY)统一设置海量点图标锚点比例。 void setEnable
(boolean enable)设置海量点是否显示,默认为显示 List< MultiPointItem > getItems
()获取海量点,初始化或者更新海量点时可以调用此方法 void remove
()从地图上移除海量点图层 void destroy
()海量点图层销毁
MultiPointItem 海量点中单个点的属性
类型 方法 说明 String getCustomerId
()LatLng getLatLng
()Object getObject
()String getSnippet
()String getTitle
()
类型 方法 说明 void setLatLng
(LatLng latLng)void setCustomerId
(String customerId)为海量点设置一个唯一标识,可以用来判断,默认为null void setObject
(Object object)设置附加信息对象。 void setSnippet
(String snippet)void setTitle
(String title)
示例
界面布局
<?xml version="1.0" encoding="utf-8"?>
< androidx.constraintlayout.widget.ConstraintLayout xmlns: android= " http://schemas.android.com/apk/res/android"
xmlns: app= " http://schemas.android.com/apk/res-auto"
xmlns: tools= " http://schemas.android.com/tools"
android: layout_width= " match_parent"
android: layout_height= " match_parent"
tools: context= " .MapMarkersActivity" >
< com.amap.api.maps.MapView
android: id= " @+id/map"
android: layout_width= " match_parent"
android: layout_height= " 0dp"
app: layout_constraintBottom_toTopOf= " @id/bottomView"
app: layout_constraintTop_toTopOf= " parent" />
< androidx.appcompat.widget.LinearLayoutCompat
android: id= " @+id/bottomView"
android: layout_width= " match_parent"
android: layout_height= " wrap_content"
android: orientation= " vertical"
app: layout_constraintBottom_toBottomOf= " parent"
app: layout_constraintTop_toBottomOf= " @id/map" >
< RadioGroup
android: id= " @+id/RadioGroup"
android: layout_width= " match_parent"
android: layout_height= " wrap_content"
android: background= " @android:color/background_dark"
android: gravity= " center_horizontal"
android: orientation= " horizontal"
android: paddingHorizontal= " 10dp" >
< RadioButton
android: id= " @+id/bulk"
android: layout_width= " 0dp"
android: layout_height= " wrap_content"
android: layout_weight= " 1"
android: checked= " true"
android: onClick= " setMarkerFlag"
android: text= " 批量点"
android: textColor= " @color/white"
android: textStyle= " bold" />
< RadioButton
android: id= " @+id/multiPoint"
android: layout_width= " 0dp"
android: layout_height= " wrap_content"
android: layout_weight= " 1"
android: onClick= " setMarkerFlag"
android: text= " 海量点"
android: textColor= " @color/white"
android: textStyle= " bold" />
< RadioButton
android: id= " @+id/clear"
android: layout_width= " 0dp"
android: layout_height= " wrap_content"
android: layout_weight= " 1"
android: onClick= " setMarkerFlag"
android: text= " 清除"
android: textColor= " @color/white"
android: textStyle= " bold" />
</ RadioGroup>
</ androidx.appcompat.widget.LinearLayoutCompat>
</ androidx.constraintlayout.widget.ConstraintLayout>
MapMarks类
常量
public static final String BULK = "Bulk" ;
public static final String MULTI_POINT = "MultiPoint" ;
成员变量
List < BaseOverlay > overlays = new ArrayList < > ( ) ;
Marker selectedMarker;
List < String > selectedFlags = new ArrayList < > ( ) ;
ArrayList < BitmapDescriptor > bitmaps = new ArrayList < > ( ) ;
BitmapDescriptor dotBitmap;
AMap. OnMarkerClickListener bulkMarkerClickListener;
AMap. OnMultiPointClickListener multiPointClickListener;
初始化
selectedFlags. add ( BULK ) ;
int [ ] drawableIds = BubbleIcons. Number ;
for ( int drawableId : drawableIds) {
BitmapDescriptor bitmap = BitmapDescriptorFactory . fromResource ( drawableId) ;
bitmaps. add ( bitmap) ;
}
dotBitmap = BitmapDescriptorFactory . fromResource ( CircleIcons. BLueDot [ 0 ] ) ;
创建覆盖物
public void addMarkers ( ) {
if ( selectedFlags. isEmpty ( ) )
return ;
for ( String flag : selectedFlags) {
switch ( flag) {
case BULK :
addBulk ( ) ;
break ;
case MULTI_POINT :
loadLocations ( new LoadCallBack ( ) {
@Override
public void onLoaded ( List < MultiPointItem > points) {
addMultiPoint ( points) ;
}
} ) ;
break ;
}
}
}
批量点
创建MarkerOptions的集合 在地图上批量添加覆盖物 设置Marker单击事件
private void addBulk ( ) {
List < LatLng > points = new ArrayList < > ( ) ;
points. add ( new LatLng ( 39.97923 , 116.357428 ) ) ;
points. add ( new LatLng ( 39.94923 , 116.397428 ) ) ;
points. add ( new LatLng ( 39.97923 , 116.437428 ) ) ;
points. add ( new LatLng ( 39.92353 , 116.490705 ) ) ;
points. add ( new LatLng ( 40.023537 , 116.289429 ) ) ;
points. add ( new LatLng ( 40.022211 , 116.406137 ) ) ;
ArrayList < MarkerOptions > optionsList = new ArrayList < > ( ) ;
for ( int i = 0 ; i < points. size ( ) ; ++ i) {
MarkerOptions option = new MarkerOptions ( )
. position ( points. get ( i) )
. icon ( bitmaps. get ( i) ) ;
optionsList. add ( option) ;
}
boolean moveToCenter = true ;
ArrayList < Marker > newOverlays = map. addMarkers ( optionsList, moveToCenter) ;
overlays. addAll ( newOverlays) ;
if ( bulkMarkerClickListener == null ) {
bulkMarkerClickListener = new AMap. OnMarkerClickListener ( ) {
@Override
public boolean onMarkerClick ( Marker marker) {
showToast ( "点击 marker" ) ;
return true ;
}
} ;
map. setOnMarkerClickListener ( bulkMarkerClickListener) ;
}
}
海量点
private void addMultiPoint ( ) {
MultiPointOverlayOptions overlayOptions = new MultiPointOverlayOptions ( )
. icon ( dotBitmap)
. anchor ( 0.5f , 0.5f ) ;
MultiPointOverlay multiPointOverlay = map. addMultiPointOverlay ( overlayOptions) ;
overlays. add ( multiPointOverlay) ;
if ( multiPointClickListener == null ) {
multiPointClickListener = new AMap. OnMultiPointClickListener ( ) {
@Override
public boolean onPointClick ( MultiPointItem item) {
if ( selectedMarker != null )
selectedMarker. remove ( ) ;
MarkerOptions markerOptions = new MarkerOptions ( ) ;
markerOptions. position ( item. getLatLng ( ) ) ;
markerOptions. icon ( bitmaps. get ( 0 ) ) ;
selectedMarker = ( Marker ) map. addMarker ( markerOptions) ;
return true ;
}
} ;
map. setOnMultiPointClickListener ( multiPointClickListener) ;
}
}
加载大量点数据(参考自官网示例Demo)
List < MultiPointItem > multiPointItems = new ArrayList < > ( ) ;
while ( . . . ) {
MultiPointItem multiPointItem = new MultiPointItem ( latLng) ;
multiPointItems. add ( multiPointItem) ;
}
multiPointOverlay. setItems ( multiPointItems) ;
移除覆盖物
public void removeOverlay ( ) {
for ( BaseOverlay overlay : overlays) {
if ( overlay instanceof Marker ) {
Marker marker = ( Marker ) overlay;
marker. remove ( ) ;
} else if ( overlay instanceof MultiPointOverlay ) {
MultiPointOverlay multiPointOverlay = ( MultiPointOverlay ) overlay;
multiPointOverlay. remove ( ) ;
}
}
overlays. clear ( ) ;
if ( selectedMarker != null )
selectedMarker. remove ( ) ;
selectedMarker = null ;
}
设置属性
public void setFlags ( String flag) {
selectedFlags. clear ( ) ;
if ( flag != null )
selectedFlags. add ( flag) ;
removeOverlay ( ) ;
addMarkers ( ) ;
}
加载地图和移除地图
public void onMapLoaded ( ) {
addMarkers ( ) ;
}
public void onMapDestroy ( ) {
isDestroy = true ;
removeOverlay ( ) ;
for ( BitmapDescriptor bitmap : bitmaps) {
bitmap. recycle ( ) ;
}
bitmaps = null ;
if ( dotBitmap != null )
dotBitmap. recycle ( ) ;
}
MapMarkersActivity类
以下是MapMarkersActivity
类部分代码
控件响应事件
public void setMarkerFlag ( View view) {
boolean checked = ( ( RadioButton ) view) . isChecked ( ) ;
if ( ! checked)
return ;
int id = view. getId ( ) ;
String flag;
if ( id == R . id. bulk)
flag = MapMarkers . BULK ;
else if ( id == R . id. multiPoint)
flag = MapMarkers . MULTI_POINT ;
else if ( id == R . id. clear)
flag = null ;
else
return ;
mapMarkers. setFlags ( flag) ;
}
运行效果图