Android Open Source - smartnavi Marker






From Project

Back to project page smartnavi.

License

The source code is released under:

Apache License

If you think the Android project smartnavi listed in this page is inappropriate, such as containing malicious code/tools or violating the copyright, please email info at java2s dot com, thanks.

Java Source Code

package org.osmdroid.bonuspack.overlays;
//from www  .j av  a 2s. c o m
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Point;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.util.Log;
import android.view.MotionEvent;

import org.osmdroid.DefaultResourceProxyImpl;
import org.osmdroid.ResourceProxy;
import org.osmdroid.ResourceProxy.bitmap;
import org.osmdroid.bonuspack.utils.BonusPackHelper;
import org.osmdroid.util.GeoPoint;
import org.osmdroid.views.MapView;
import org.osmdroid.views.Projection;
import org.osmdroid.views.overlay.Overlay;

/**
 * An icon placed at a particular point on the map's surface.
 * Mimics the Marker class from Google Maps Android API v2 as much as possible. Main differences:<br/>
 * - Doesn't support Z-Index: as other osmdroid overlays, Marker is drawn in the order of appearance. <br/>
 * - The icon can be any standard Android Drawable, instead of the BitmapDescriptor introduced in Google Maps API v2. <br/>
 * - The icon can be changed at any time. <br/>
 * - The InfoWindow hosts a standard Android View. It can handle Android widgets like buttons and so on. <br/>
 * - Supports a "sub-description", to be displayed in the InfoWindow, under the snippet, in a smaller text font. <br/>
 * - Supports an image, to be displayed in the InfoWindow. <br/>
 * - Supports "panning to view" on/off option (when touching a marker, center the map on marker position). <br/>
 * - Opening a Marker InfoWindow automatically close others only if it's the same InfoWindow shared between Markers. <br/>
 * - Events listeners are set per marker, not per map. <br/>
 * <p/>
 * TODO: <br/>
 * Impact of marker rotation on hitTest<br/>
 * When map is rotated, when panning the map, bug on the InfoWindow positioning (osmdroid issue #524)<br/>
 *
 * @author M.Kergall
 * @see MarkerInfoWindow
 * @see http://developer.android.com/reference/com/google/android/gms/maps/model/Marker.html
 */
public class Marker extends Overlay {

    /**
     * Usual values in the (U,V) coordinates system of the icon image
     */
    public static final float ANCHOR_CENTER = 0.5f, ANCHOR_LEFT = 0.0f, ANCHOR_TOP = 0.0f, ANCHOR_RIGHT = 1.0f, ANCHOR_BOTTOM = 1.0f;
    protected static MarkerInfoWindow mDefaultInfoWindow = null;
    protected static Drawable mDefaultIcon = null; //cache for default icon (resourceProxy.getDrawable being slow)
    /*attributes for standard features:*/
    protected Drawable mIcon;
    protected GeoPoint mPosition;
    protected float mBearing;
    protected float mAnchorU, mAnchorV;
    protected float mIWAnchorU, mIWAnchorV;
    protected float mAlpha;
    protected String mTitle, mSnippet;
    protected boolean mDraggable, mIsDragged;
    protected MarkerInfoWindow mInfoWindow;
    protected boolean mFlat;
    protected OnMarkerClickListener mOnMarkerClickListener;
    protected OnMarkerDragListener mOnMarkerDragListener;
    /*attributes for non-standard features:*/
    protected Drawable mImage;
    protected String mSubDescription;
    protected boolean mPanToView;
    protected Object mRelatedObject;
    /*internals*/
    protected Point mPositionPixels;

    public Marker(MapView mapView) {
        this(mapView, new DefaultResourceProxyImpl(mapView.getContext()));
    }

    public Marker(MapView mapView, final ResourceProxy resourceProxy) {
        super(resourceProxy);
        mBearing = 0.0f;
        mAlpha = 1.0f; //opaque
        mPosition = new GeoPoint(0.0, 0.0);
        mAnchorU = ANCHOR_CENTER;
        mAnchorV = ANCHOR_CENTER;
        mIWAnchorU = ANCHOR_CENTER;
        mIWAnchorV = ANCHOR_TOP;
        mDraggable = false;
        mIsDragged = false;
        mPositionPixels = new Point();
        mPanToView = true;
        mFlat = false; //billboard
        mOnMarkerClickListener = null;
        mOnMarkerDragListener = null;
        if (mDefaultIcon == null)
            mDefaultIcon = resourceProxy.getDrawable(bitmap.marker_default);
        mIcon = mDefaultIcon;
        if (mDefaultInfoWindow == null || mDefaultInfoWindow.mMapView != mapView) {
            //build default bubble, that will be shared between all markers using the default one:
            Context context = mapView.getContext();
            String packageName = context.getPackageName();
            int defaultLayoutResId = context.getResources().getIdentifier("bonuspack_bubble", "layout", packageName);
            if (defaultLayoutResId == 0)
                Log.e(BonusPackHelper.LOG_TAG, "Marker: layout/bonuspack_bubble not found in " + packageName);
            else
                mDefaultInfoWindow = new MarkerInfoWindow(defaultLayoutResId, mapView);
        }
        mInfoWindow = mDefaultInfoWindow;
    }

    /**
     * Sets the icon for the marker. Can be changed at any time.
     *
     * @param icon if null, the default osmdroid marker is used.
     */
    public void setIcon(Drawable icon) {
        if (icon != null)
            mIcon = icon;
        else
            mIcon = mDefaultIcon;
    }

    public GeoPoint getPosition() {
        return mPosition;
    }

    public void setPosition(GeoPoint position) {
        mPosition = position.clone();
    }

    public float getRotation() {
        return mBearing;
    }

    public void setRotation(float rotation) {
        mBearing = rotation;
    }

    public void setAnchor(float anchorU, float anchorV) {
        mAnchorU = anchorU;
        mAnchorV = anchorV;
    }

    public void setInfoWindowAnchor(float anchorU, float anchorV) {
        mIWAnchorU = anchorU;
        mIWAnchorV = anchorV;
    }

    public float getAlpha() {
        return mAlpha;
    }

    public void setAlpha(float alpha) {
        mAlpha = alpha;
    }

    public String getTitle() {
        return mTitle;
    }

    public void setTitle(String title) {
        mTitle = title;
    }

    public String getSnippet() {
        return mSnippet;
    }

    public void setSnippet(String snippet) {
        mSnippet = snippet;
    }

    public boolean isDraggable() {
        return mDraggable;
    }

    public void setDraggable(boolean draggable) {
        mDraggable = draggable;
    }

    public boolean isFlat() {
        return mFlat;
    }

    public void setFlat(boolean flat) {
        mFlat = flat;
    }

    /**
     * Removes this Marker from the MapView.
     * Note that this method will operate only if the Marker is in the MapView overlays
     * (it should not be included in a container like a FolderOverlay).
     *
     * @param mapView
     */
    public void remove(MapView mapView) {
        mapView.getOverlays().remove(this);
    }

    public void setOnMarkerClickListener(OnMarkerClickListener listener) {
        mOnMarkerClickListener = listener;
    }

    public void setOnMarkerDragListener(OnMarkerDragListener listener) {
        mOnMarkerDragListener = listener;
    }

    public String getSubDescription() {
        return mSubDescription;
    }

    /**
     * set the "sub-description", an optional text to be shown in the InfoWindow, below the snippet, in a smaller text size
     */
    public void setSubDescription(String subDescription) {
        mSubDescription = subDescription;
    }

    /**
     * get the image to be shown in the InfoWindow - this is not the marker icon
     */
    public Drawable getImage() {
        return mImage;
    }

    /**
     * set an image to be shown in the InfoWindow  - this is not the marker icon
     */
    public void setImage(Drawable image) {
        mImage = image;
    }

    /**
     * Set the InfoWindow to be used.
     * Default is a MarkerInfoWindow, with the layout named "bonuspack_bubble".
     * You can use this method either to use your own layout, or to use your own sub-class of InfoWindow.
     * Note that this InfoWindow will receive the Marker object as an input, so it MUST be able to handle Marker attributes.
     * If you don't want any InfoWindow to open, you can set it to null.
     */
    public void setInfoWindow(MarkerInfoWindow infoWindow) {
        mInfoWindow = infoWindow;
    }

    /**
     * If set to true, when clicking the marker, the map will be centered on the marker position.
     * Default is true.
     */
    public void setPanToView(boolean panToView) {
        mPanToView = panToView;
    }

    /**
     * @return the related object.
     */
    public Object getRelatedObject() {
        return mRelatedObject;
    }

    /**
     * Allows to link an Object (any Object) to this marker.
     * This is particularly useful to handle custom InfoWindow.
     */
    public void setRelatedObject(Object relatedObject) {
        mRelatedObject = relatedObject;
    }

    public void showInfoWindow() {
        if (mInfoWindow == null)
            return;
        int markerWidth = 0, markerHeight = 0;
        markerWidth = mIcon.getIntrinsicWidth();
        markerHeight = mIcon.getIntrinsicHeight();

        int offsetX = (int) (mIWAnchorU * markerWidth) - (int) (mAnchorU * markerWidth);
        int offsetY = (int) (mIWAnchorV * markerHeight) - (int) (mAnchorV * markerHeight);

        mInfoWindow.open(this, mPosition, offsetX, offsetY);
    }

    public void hideInfoWindow() {
        if (mInfoWindow != null)
            mInfoWindow.close();
    }

    public boolean isInfoWindowShown() {
        return (mInfoWindow != null) && mInfoWindow.isOpen() && (mInfoWindow.mMarkerRef == this);
    }

    @Override
    public void draw(Canvas canvas, MapView mapView, boolean shadow) {
        if (shadow)
            return;
        if (mIcon == null)
            return;

        final Projection pj = mapView.getProjection();

        pj.toPixels(mPosition, mPositionPixels);
        int width = mIcon.getIntrinsicWidth();
        int height = mIcon.getIntrinsicHeight();
        Rect rect = new Rect(0, 0, width, height);
        rect.offset(-(int) (mAnchorU * width), -(int) (mAnchorV * height));
        mIcon.setBounds(rect);

        mIcon.setAlpha((int) (mAlpha * 255));

        float rotationOnScreen = (mFlat ? -mBearing : mapView.getMapOrientation() - mBearing);
        drawAt(canvas, mIcon, mPositionPixels.x, mPositionPixels.y, false, rotationOnScreen);
    }

    public boolean hitTest(final MotionEvent event, final MapView mapView) {
        final Projection pj = mapView.getProjection();
        pj.toPixels(mPosition, mPositionPixels);
        final Rect screenRect = pj.getIntrinsicScreenRect();
        int x = -mPositionPixels.x + screenRect.left + (int) event.getX();
        int y = -mPositionPixels.y + screenRect.top + (int) event.getY();
        boolean hit = mIcon.getBounds().contains(x, y);
        return hit;
    }

    @Override
    public boolean onSingleTapConfirmed(final MotionEvent event, final MapView mapView) {
        boolean touched = hitTest(event, mapView);
        if (touched) {
            if (mOnMarkerClickListener == null) {
                return onMarkerClickDefault(this, mapView);
            } else {
                return mOnMarkerClickListener.onMarkerClick(this, mapView);
            }
        } else
            return touched;
    }

    public void moveToEventPosition(final MotionEvent event, final MapView mapView) {
        final Projection pj = mapView.getProjection();
        mPosition = (GeoPoint) pj.fromPixels((int) event.getX(), (int) event.getY());
        mapView.invalidate();
    }

    @Override
    public boolean onLongPress(final MotionEvent event, final MapView mapView) {
        boolean touched = hitTest(event, mapView);
        if (touched) {
            if (mDraggable) {
                //starts dragging mode:
                mIsDragged = true;
                hideInfoWindow();
                if (mOnMarkerDragListener != null)
                    mOnMarkerDragListener.onMarkerDragStart(this);
                moveToEventPosition(event, mapView);
            }
        }
        return touched;
    }

    @Override
    public boolean onTouchEvent(final MotionEvent event, final MapView mapView) {
        if (mDraggable && mIsDragged) {
            if (event.getAction() == MotionEvent.ACTION_UP) {
                mIsDragged = false;
                if (mOnMarkerDragListener != null)
                    mOnMarkerDragListener.onMarkerDragEnd(this);
                return true;
            } else if (event.getAction() == MotionEvent.ACTION_MOVE) {
                moveToEventPosition(event, mapView);
                if (mOnMarkerDragListener != null)
                    mOnMarkerDragListener.onMarkerDrag(this);
                return true;
            } else
                return false;
        } else
            return false;
    }

    //-- Marker events listener interfaces ------------------------------------

    /**
     * default behaviour when no click listener is set
     */
    protected boolean onMarkerClickDefault(Marker marker, MapView mapView) {
        marker.showInfoWindow();
        if (marker.mPanToView)
            mapView.getController().animateTo(marker.getPosition());
        return true;
    }

    public interface OnMarkerClickListener {
        abstract boolean onMarkerClick(Marker marker, MapView mapView);
    }

    public interface OnMarkerDragListener {
        abstract void onMarkerDrag(Marker marker);

        abstract void onMarkerDragEnd(Marker marker);

        abstract void onMarkerDragStart(Marker marker);
    }

}




Java Source Code List

com.ilm.sandwich.BackgroundService.java
com.ilm.sandwich.BuildConfig.java
com.ilm.sandwich.Config.java
com.ilm.sandwich.GoogleMapActivity.java
com.ilm.sandwich.Info.java
com.ilm.sandwich.MySupportMapFragment.java
com.ilm.sandwich.OsmMapActivity.java
com.ilm.sandwich.Settings.java
com.ilm.sandwich.StartChooser.java
com.ilm.sandwich.TouchableWrapper.java
com.ilm.sandwich.tools.Core.java
com.ilm.sandwich.tools.HttpRequests.java
com.ilm.sandwich.tools.Locationer.java
com.ilm.sandwich.tools.MapDownload.java
com.ilm.sandwich.tools.MyItemizedOverlay.java
com.ilm.sandwich.tools.PlacesAutoComplete.java
com.ilm.sandwich.tools.PlacesTextSearch.java
com.ilm.sandwich.tools.Statistics.java
com.ilm.sandwich.tools.SuggestionsAdapter.java
org.osmdroid.bonuspack.BuildConfig.java
org.osmdroid.bonuspack.BuildConfig.java
org.osmdroid.bonuspack.cachemanager.CacheManager.java
org.osmdroid.bonuspack.clustering.GridMarkerClusterer.java
org.osmdroid.bonuspack.clustering.MarkerClusterer.java
org.osmdroid.bonuspack.clustering.StaticCluster.java
org.osmdroid.bonuspack.kml.ColorStyle.java
org.osmdroid.bonuspack.kml.IconStyle.java
org.osmdroid.bonuspack.kml.KmlDocument.java
org.osmdroid.bonuspack.kml.KmlFeature.java
org.osmdroid.bonuspack.kml.KmlFolder.java
org.osmdroid.bonuspack.kml.KmlGeometry.java
org.osmdroid.bonuspack.kml.KmlGroundOverlay.java
org.osmdroid.bonuspack.kml.KmlLineString.java
org.osmdroid.bonuspack.kml.KmlMultiGeometry.java
org.osmdroid.bonuspack.kml.KmlPlacemark.java
org.osmdroid.bonuspack.kml.KmlPoint.java
org.osmdroid.bonuspack.kml.KmlPolygon.java
org.osmdroid.bonuspack.kml.LineStyle.java
org.osmdroid.bonuspack.kml.Style.java
org.osmdroid.bonuspack.location.FlickrPOIProvider.java
org.osmdroid.bonuspack.location.GeoNamesPOIProvider.java
org.osmdroid.bonuspack.location.GeocoderGisgraphy.java
org.osmdroid.bonuspack.location.GeocoderNominatimOld.java
org.osmdroid.bonuspack.location.GeocoderNominatim.java
org.osmdroid.bonuspack.location.NominatimPOIProvider.java
org.osmdroid.bonuspack.location.POI.java
org.osmdroid.bonuspack.location.PicasaPOIProvider.java
org.osmdroid.bonuspack.mapsforge.GenericMapView.java
org.osmdroid.bonuspack.mapsforge.MapsForgeTileModuleProvider.java
org.osmdroid.bonuspack.mapsforge.MapsForgeTileProvider.java
org.osmdroid.bonuspack.mapsforge.MapsForgeTileSource.java
org.osmdroid.bonuspack.overlays.DefaultInfoWindow.java
org.osmdroid.bonuspack.overlays.ExtendedOverlayItem.java
org.osmdroid.bonuspack.overlays.FolderOverlay.java
org.osmdroid.bonuspack.overlays.GroundOverlay.java
org.osmdroid.bonuspack.overlays.InfoWindow.java
org.osmdroid.bonuspack.overlays.ItemizedOverlayWithBubble.java
org.osmdroid.bonuspack.overlays.MapEventsOverlay.java
org.osmdroid.bonuspack.overlays.MapEventsReceiver.java
org.osmdroid.bonuspack.overlays.MarkerInfoWindow.java
org.osmdroid.bonuspack.overlays.Marker.java
org.osmdroid.bonuspack.overlays.Polygon.java
org.osmdroid.bonuspack.overlays.Polyline.java
org.osmdroid.bonuspack.routing.GoogleRoadManager.java
org.osmdroid.bonuspack.routing.MapQuestRoadManager.java
org.osmdroid.bonuspack.routing.OSRMRoadManager.java
org.osmdroid.bonuspack.routing.RoadLeg.java
org.osmdroid.bonuspack.routing.RoadManager.java
org.osmdroid.bonuspack.routing.RoadNode.java
org.osmdroid.bonuspack.routing.Road.java
org.osmdroid.bonuspack.utils.BonusPackHelper.java
org.osmdroid.bonuspack.utils.DouglasPeuckerReducer.java
org.osmdroid.bonuspack.utils.HttpConnection.java
org.osmdroid.bonuspack.utils.PolylineEncoder.java
org.osmdroid.bonuspack.utils.WebImageCache.java