使用Monodroid / Xamarin在地图上绘制叠加

时间:2014-10-24 06:53:44

标签: android google-maps xamarin xamarin.android

我正在尝试将图像叠加层添加到我的Xamarin / Android地图中,该地图位于自定义渲染器中。

我无法让它出现在地图上。此配方似乎已过时http://developer.xamarin.com/recipes/android/controls/mapview/add_an_overlay_to_a_map/或者我错过了Android.GoogleMaps.Overlay类。

public class MapContentPageRenderer: PageRenderer
    {
        Android.Views.View _view;
        private GoogleMap _map;
        private MapFragment _mapFragment;
        private LatLng _initLatLng;

        protected override void OnElementChanged(ElementChangedEventArgs<Page> e)
        {
            base.OnElementChanged(e);

            var page = e.NewElement as MapContentPage;
            var activity = this.Context as Activity;

            if (activity != null)
            {
                _view = activity.LayoutInflater.Inflate(Resource.Layout.MapLayout, this, false);
                AddView(_view);
                if (page != null) _initLatLng = new LatLng(page.InitLat, page.InitLng);
                InitMapFragment(activity);
            }
            SetupMapIfNeeded();
        }

        protected override void OnLayout(bool changed, int l, int t, int r, int b)
        {
            base.OnLayout(changed, l, t, r, b);
            var msw = MeasureSpec.MakeMeasureSpec(r - l, MeasureSpecMode.Exactly);
            var msh = MeasureSpec.MakeMeasureSpec(b - t, MeasureSpecMode.Exactly);
            if (_view == null) return;
            _view.Measure(msw, msh);
            _view.Layout(0, 0, r - l, b - t);
        }

        private void InitMapFragment(Activity activity)
        {
            var cameraPosition = new CameraPosition.Builder().Target(_initLatLng).Zoom(14.0f).Build();
            _mapFragment = activity.FragmentManager.FindFragmentByTag("mapWithOverlay") as MapFragment;
            if (_mapFragment != null) return;
            var mapOptions = new GoogleMapOptions()
                .InvokeMapType(GoogleMap.MapTypeNormal)
                .InvokeRotateGesturesEnabled(false)
                .InvokeZoomControlsEnabled(false)
                .InvokeCamera(cameraPosition)
                .InvokeCompassEnabled(true);

            var fragTx = activity.FragmentManager.BeginTransaction();
            _mapFragment = MapFragment.NewInstance(mapOptions);

            fragTx.Add(Resource.Id.mapWithOverlay, _mapFragment, "mapWithOverlay");
            fragTx.Commit();
        }

        private void SetupMapIfNeeded()
        {
            if (_map != null) return;
            _map = _mapFragment.Map;
            if (_map == null) return;
            ZoomToPosition();

            var mapOverlay = new GroundOverlayOptions()
                .Position(_initLatLng, 150, 200)
                .InvokeImage(BitmapDescriptorFactory.FromResource(Resource.Drawable.Icon));
            _map.AddGroundOverlay(mapOverlay);
        }

        private void ZoomToPosition()
        {
            var cameraUpdate = CameraUpdateFactory.NewLatLngZoom(_initLatLng, 15);

            _map.MoveCamera(cameraUpdate);
        }
    }

1 个答案:

答案 0 :(得分:0)

Android.GoogleMaps.Overlay 已弃用

这样你不应该尝试使用此功能,因为您发布的link中的示例已过时

相反,您应该为 Android GoogleMaps 使用 GroundOverlay TileOverlay ,或者使用其他<强>覆盖,取决于您要实现的目标。

更新1 : -

以下是创建自定义 GroundOverlay 的示例: -

  • 100 x 100像素
  • 绘制一个红色的半透明圆圈
  • 然后在其中显示“18”的黄色文字

cobjGoogleMap将是您之前已定义和引用的 GoogleMap 类型的地图引用。

与您所拥有的参考link一样,它会创建一个画布,并展示如何在将此添加到地图之前在此画布上绘制一些内容。希望这会让您走上创建自定义绘制叠加层的正确道路吗?

private GroundOverlay cobjGroundOverlay = null;

private void AddMyCustomDrawnOverlayToMap()
{
    LatLng objMapPosition = new LatLng(51, -1.1);
    int intWidth = 100;
    int intHeight = 100;
    //
    using (Bitmap objBitmap = GenerateMyCustomDrawnOverlay(intWidth, intHeight))
    {
        using (Android.Gms.Maps.Model.BitmapDescriptor objBitmapDescriptor = Android.Gms.Maps.Model.BitmapDescriptorFactory.FromBitmap(objBitmap))
        {
            GroundOverlayOptions objGroundOverlayOptions = new GroundOverlayOptions()
                .Position(objMapPosition, intWidth, intHeight)
                .InvokeImage(objBitmapDescriptor);
            //
            cobjGroundOverlay = cobjGoogleMap.AddGroundOverlay(objGroundOverlayOptions);
        }
    }
    //
    // Move the camera to the position where we added the new ground overlay:-
    CameraUpdate objCameraUpdate = CameraUpdateFactory.NewLatLngZoom(objMapPosition, 17);
    cobjGoogleMap.MoveCamera(objCameraUpdate);
}


private Bitmap GenerateMyCustomDrawnOverlay(int pintWidth, int pintHeight)
{
    // Create your custom overlay Bitmap using a Canvas object:-
    //
    var objPaint = new global::Android.Graphics.Paint();
    objPaint.AntiAlias = true;
    objPaint.Color = global::Android.Graphics.Color.Red;
    objPaint.Alpha = 150;
    //
    var objPaint2 = new global::Android.Graphics.Paint();
    objPaint2.AntiAlias = true;
    objPaint2.Color = global::Android.Graphics.Color.Yellow;
    objPaint2.TextSize = 90;
    objPaint2.Alpha = 255;
    //
    Bitmap objBitmap = Bitmap.CreateBitmap(pintWidth, pintHeight, Bitmap.Config.Argb8888);
    Canvas objCanvas = new Canvas(objBitmap);
    //
    int intHalfWidth = pintWidth / 2;
    int intHalfHeight = pintHeight / 2;
    //
    // Draw a circle (red / semi-transparent):-
    objCanvas.DrawRoundRect(new global::Android.Graphics.RectF(0, 0, (float)pintWidth, (float)pintHeight), intHalfWidth, intHalfHeight, objPaint);
    //
    // Draw some text, although your probably want to do MeasureText etc in order to center things properly:-
    objCanvas.DrawText("18", 0, 80, objPaint2);
    //
    // Return the bitmap that will be used:-
    return objBitmap;
}