banner
jzman

jzman

Coding、思考、自觉。
github

Add Overlay to Tian Di Map

Recently, there is still a bit of anxiety, and a large part of the reason is simply overthinking. By appropriately letting go of some things, everything will become clearer.

Continuing from the previous article, let's learn about the Tianditu Android SDK. In map development, in addition to common positioning needs, there is also the addition of overlays. For example, a recent project is related to risk management, which requires displaying corresponding risk points on the map. Below is today's content:

  1. Single Overlay
  2. Multiple Overlays
  3. Geometric Overlays
  4. Text Overlays
  5. Summary
  6. Test Effects

Single Overlay#

For adding a single overlay, we use images from the resource folder as specific overlays. Below is a custom Overlay, as follows:

/**
 * Powered by jzman.
 * Created on 2018/6/25 0025.
 */
public class MOverlay extends Overlay{
    private Drawable mDrawable;
    private DrawableOption mDrawableOption;
    private GeoPoint mGeoPoint;

    public MOverlay(Context context) {
        mDrawable = context.getResources().getDrawable(R.drawable.selected_marker);
        mDrawableOption = new DrawableOption();
        // Set anchor point position
        mDrawableOption.setAnchor(0.5f,1.0f);
        // Set rotation angle
        mDrawableOption.setRotate(0);
        // Set state
        mDrawableOption.setState(DrawableOption.STATE_NORMAL);
        // Set how many frames to refresh the image resource
        mDrawableOption.setPeriod(200);
    }

    @Override
    public boolean draw(GL10 gl, MapView mapView, boolean shadow, long when) {
        MapViewRender render = mapView.getMapViewRender();
        render.drawDrawable(gl,mDrawableOption,mDrawable,mGeoPoint);
        return true;
    }

    @Override
    public boolean onTap(GeoPoint p, MapView mapView) {
        // Specify the current clicked position to add the overlay, or specify it yourself
        mGeoPoint = p;
        return true;
    }
}

Then, add this Overlay to the MapView, as follows:

mapView.addOverlay(new MOverlay(this));

At this point, adding a single overlay is complete.

Multiple Overlays#

In development, it is often necessary to mark a group of related data locations on the map. At this point, multiple overlays need to be added to the map. To add a group of similar types of overlays, we use the abstract class ItemizedOverlay. Below is a custom Overlay for multiple overlays, as follows:

/**
 * Powered by jzman.
 * Created on 2018/6/25 0025.
 */
public class MItemOverlay2 extends ItemizedOverlay<OverlayItem> {

    private MapView mapView;
    private View view;
    private TextView tvItemOverlay;
    private ArrayList<OverlayItem> items;
    private ArrayList<DefaultGeoPoint<MarkerBean>> points;

    public MItemOverlay2(Drawable defaultMarker, ArrayList<DefaultGeoPoint<MarkerBean>> geoPoints, MapView mapView, View view) {
        super(defaultMarker);
        this.mapView = mapView;
        this.view = view;
        tvItemOverlay = view.findViewById(R.id.tvItemOverlayData);
        items = new ArrayList<>();
        points = geoPoints;
        for (int i = 0; i < points.size(); i++) {
            OverlayItem overlayItem = new OverlayItem(points.get(i),
                    points.get(i).getT().getTitle(),
                    points.get(i).getT().getSnippet());
            overlayItem.setMarker(defaultMarker);
            items.add(overlayItem);
        }
        populate();
    }

    /**
     * Total number of overlay items
     * @return
     */
    @Override
    public int size() {
        return items.size();
    }

    /**
     * Create overlay item
     * @param i
     * @return
     */
    @Override
    protected OverlayItem createItem(int i) {
        return items.get(i);
    }

    /**
     * Handle click events
     * @param index
     * @return
     */
    @Override
    protected boolean onTap(int index) {
        if (index == -1) return false;
        mapView.updateViewLayout(view, new MapView.LayoutParams(
                ViewGroup.LayoutParams.WRAP_CONTENT,
                ViewGroup.LayoutParams.WRAP_CONTENT,
                points.get(index),
                MapView.LayoutParams.BOTTOM_CENTER));
        tvItemOverlay.setText(points.get(index).getT().getTitle());
        view.setVisibility(View.VISIBLE);
        return true;
    }
}

Setting the View that pops up when clicking each overlay must have already been added to the MapView, as follows:

mapView.addView(view, new MapView.LayoutParams(
        ViewGroup.LayoutParams.WRAP_CONTENT,
        ViewGroup.LayoutParams.WRAP_CONTENT,
        null,
        MapView.LayoutParams.TOP_LEFT));

If it does not appear added, an error will occur, with the error message as follows:

>  java.lang.IllegalArgumentException: Given view not a child of com.tianditu.android.maps.MapView{ac3dbd7 V.E...... ........ 0,192-1080,1692 #7f070050 app:id/mapView}

Then, add this Overlay to the MapView, as follows:

Drawable drawable1 = getResources().getDrawable(R.drawable.selected_marker);
MItemOverlay2 mItemOverlay2 = new MItemOverlay2(drawable1, markers, mapView, view);
mapView.getOverlays().add(mItemOverlay2);

At this point, adding multiple overlays is complete.

Geometric Overlays#

Geometric overlays mainly use geometric shapes to mark related location points. Below is a custom Overlay that adds geometric overlays by clicking on the map location. The effect can be referenced in the test effect image at the end, as follows:

/**
 * Powered by jzman.
 * Created on 2018/6/25 0025.
 */
public class GeometricOverlay extends Overlay{
    private CircleArcOption mCircleArcOption;
    private GeoPoint mGeoPoint;

    public GeometricOverlay() {
        mCircleArcOption = new CircleArcOption();
        // Set whether the overlay is a dashed line
        mCircleArcOption.setDottedLine(true);
        // Set fill color
        mCircleArcOption.setFillColor(Color.GRAY);
        // Set border color
        mCircleArcOption.setStrokeColor(Color.BLACK);
        // Set border width
        mCircleArcOption.setStrokeWidth(5);
        // Whether to use the center point, setting true draws a sector, otherwise a circular arc
        mCircleArcOption.setUseCenter(true);
        // Set starting angle and scanning angle
        mCircleArcOption.setAngle(0,100);
    }

    @Override
    public boolean draw(GL10 gl, MapView mapView, boolean shadow, long when) {
        MapViewRender render = mapView.getMapViewRender();
        render.drawCircleArc(gl,mCircleArcOption,mGeoPoint,1000);
        return true;
    }

    @Override
    public boolean onTap(GeoPoint p, MapView mapView) {
        // Specify the current clicked position to add the overlay, or specify it yourself
        mGeoPoint = p;
        return true;
    }
}

Then, add this Overlay to the MapView, as follows:

mapView.addOverlay(new GeometricOverlay());

At this point, adding multiple overlays is complete.

Text Overlays#

Text overlays are used to add text at corresponding location points. Below is a custom Overlay that adds text overlays by clicking on the map location. The effect can be referenced in the test effect image at the end, as follows:

/**
 * Powered by jzman.
 * Created on 2018/6/25 0025.
 */
public class TextOverlay extends Overlay{
    private FontOption mFontOption;
    private GeoPoint mGeoPoint;

    public TextOverlay(Context context) {
        mFontOption = new FontOption();
        // Set fill color
        mFontOption.setFillColor(Color.RED);
        // Set font color and size
        mFontOption.setFontColor(Color.BLACK);
        mFontOption.setFontSize(60);
        // Set text border width and color
        mFontOption.setStrokeWidth(4);
        mFontOption.setStrokeColor(Color.GRAY);
        // Set text rotation angle
        mFontOption.setTextRotate(60);
        // Set font
        Typeface typeface = Typeface.createFromAsset(context.getAssets(), "font/font.ttf");
        mFontOption.setFontTypeface(typeface);
    }

    @Override
    public boolean draw(GL10 gl, MapView mapView, boolean shadow, long when) {
        MapViewRender render = mapView.getMapViewRender();
        if (mGeoPoint!=null){
            render.drawText(gl,mFontOption,"This is a text overlay",mGeoPoint);
        }
        return true;
    }

    @Override
    public boolean onTap(GeoPoint p, MapView mapView) {
        // Specify the current clicked position to add the overlay, or specify it yourself
        mGeoPoint = p;
        return true;
    }
}

Then, add this Overlay to the MapView, as follows:

mapView.addOverlay(new TextOverlay(this));

At this point, adding multiple overlays is complete.

Summary#

In summary, the general steps for adding overlays using Tianditu are as follows:

  1. Create the specific overlay
  2. Initialize specific parameters for the overlay
  3. Override the draw() method
  4. Add this Overlay to the MapView

Test Effects#

image

The addition of overlays to Tianditu is now complete.

Loading...
Ownership of this post data is guaranteed by blockchain and smart contracts to the creator alone.