Android Google地图自定义InfoWindow

时间:2018-01-06 04:03:16

标签: android google-maps google-maps-android-api-2

我想自己设计一个不同的信息窗口,但无法找到正确的方法。

如图所示:

enter image description here

当我点击标记时,我想在底部显示一个条形图。我会在那里提供有关标记的详细信息。 (它将包括姓名,地址,图标)以及这些名称,地址,必须是可点击的。

有哪些可行的方法(方法)?

2 个答案:

答案 0 :(得分:1)

用于设置自定义标记

 googleMap.addMarker(iconGenerator.createMarker(latitude, longitude, your_string to display))

您可以使用com.google.maps.android.ui.IconGenerator类生成Google Map utils的自定义标记。

要包含的Gradle行是

compile 'com.google.maps.android:android-maps-utils:0.3+

在我的情况下,我并不想再添加一个库,因此需要从here中提取所需的类和数据。

public class IconGenerator {


    private static final int STYLE_DEFAULT = 1;
    private static final int STYLE_WHITE = 2;
    private static final int STYLE_RED = 3;
    private static final int STYLE_BLUE = 4;
    private static final int STYLE_GREEN = 5;
    private static final int STYLE_PURPLE = 6;
    private static final int STYLE_ORANGE = 7;
    private final Context mContext;
    private BubbleDrawable mBackground;
    private ViewGroup mContainer;
    private TextView mTextView;

    public IconGenerator(Context context) {
        mContext = context;
        mBackground = new BubbleDrawable(mContext.getResources());
        mContainer = (ViewGroup) LayoutInflater.from(mContext).inflate(R.layout.amu_text_bubble, null);
        RotationLayout mRotationLayout = (RotationLayout) mContainer.getChildAt(0);
        mTextView = mRotationLayout.findViewById(R.id.amu_text);
        setStyle();
    }

    private static int getStyleColor(int style) {
        switch (style) {

            case STYLE_RED:
                return 0xffcc0000;
            case STYLE_BLUE:
                return 0xff0099cc;
            case STYLE_GREEN:
                return 0xff669900;
            case STYLE_PURPLE:
                return 0xff9933cc;
            case STYLE_ORANGE:
                return 0xffff8800;
            case STYLE_DEFAULT:
            case STYLE_WHITE:
            default:
                return 0xffffffff;
        }
    }

    private static int getTextStyle(int style) {
        switch (style) {
            case STYLE_RED:
            case STYLE_BLUE:
            case STYLE_GREEN:
            case STYLE_PURPLE:
            case STYLE_ORANGE:
                return R.style.amu_Bubble_TextAppearance_Light;
            case STYLE_DEFAULT:
            case STYLE_WHITE:
            default:
                return R.style.amu_Bubble_TextAppearance_Dark;
        }
    }

    public MarkerOptions createMarker(double latitude, double longitude, String text) {
        LatLng latLng = new LatLng(latitude, longitude);
        float mAnchorV = 1F;
        float mAnchorU = 0.5F;
        return new MarkerOptions().
                icon(BitmapDescriptorFactory.fromBitmap(makeIcon(text))).
                position(latLng).
                anchor(mAnchorU, mAnchorV);
    }

    private Bitmap makeIcon(CharSequence text) {
        if (mTextView != null) {
            mTextView.setText(text);
        }

        return makeIcon();
    }

    private Bitmap makeIcon() {
        int measureSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
        mContainer.measure(measureSpec, measureSpec);
        int measuredWidth = mContainer.getMeasuredWidth();
        int measuredHeight = mContainer.getMeasuredHeight();
        mContainer.layout(0, 0, measuredWidth, measuredHeight);
        Bitmap r = Bitmap.createBitmap(measuredWidth, measuredHeight, Bitmap.Config.ARGB_8888);
        r.eraseColor(Color.TRANSPARENT);
        Canvas canvas = new Canvas(r);
        mContainer.draw(canvas);
        return r;
    }

    private void setStyle() {
        setColor(getStyleColor(IconGenerator.STYLE_RED));
        setTextAppearance(mContext, getTextStyle(IconGenerator.STYLE_RED));
    }

    private void setColor(int color) {
        mBackground.setColor(color);
        setBackground(mBackground);
    }

    @SuppressWarnings("deprecation")
    // View#setBackgroundDrawable is compatible with pre-API level 16 (Jelly Bean).
    private void setBackground(Drawable background) {
        mContainer.setBackgroundDrawable(background);

        // Force setting of padding.
        // setBackgroundDrawable does not call setPadding if the background has 0 padding.
        if (background != null) {
            Rect rect = new Rect();
            background.getPadding(rect);
            mContainer.setPadding(rect.left, rect.top, rect.right, rect.bottom);
        } else {
            mContainer.setPadding(0, 0, 0, 0);
        }
    }

    private void setTextAppearance(Context context, int resid) {
        if (mTextView != null) {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                mTextView.setTextAppearance(resid);
            } else
                mTextView.setTextAppearance(context, resid);
        }
    }

}

对于自定义窗口

创建标记集详细信息以标记并访问getInfoContents googleMap.setInfoWindowAdapter方法上的详细信息时,还会为您的自定义视图设置详细信息。

 googleMap.setInfoWindowAdapter(new GoogleMap.InfoWindowAdapter() {
            @Override
            public View getInfoWindow(Marker marker) {
                return null;
            }

            @Override
            public View getInfoContents(Marker marker) {
                YourModelClassName detailDto = (YourModelClassName ) marker.getTag();
                View v = View.inflate(MapViewActivity.this, R.layout.custom_info_window, null);
               // set widget of your custom_layout like below
                CustomFTextView txtResourceName = v.findViewById(R.id.txt_resource_name);
                CustomFTextView txtResourceAddress = v.findViewById(R.id.txt_resource_address);
                ImageView imageViewPic = v.findViewById(R.id.img_event);
                if (detailDto != null) {
                    txtResourceName.setText(detailDto.getResourceName());
                    txtResourceAddress.setText(detailDto.getAddress());
                    String mUrl = base_Url + detailDto.getImageUrl();
                    Picasso.with(MapViewActivity.this).load(mUrl).resize(TARGET_WIDTH, TARGET_HEIGHT).centerInside().into(imageViewPic);
                }
                return v;
            }
        });

将数据设置为这样的标记。

this.googleMap.addMarker(new MarkerOptions().position(sydney)).setTag(detailDto);

答案 1 :(得分:1)

GoogleMap.InfoWindowAdapter将显示附加标记的自定义窗口,如果要在屏幕底部显示标记详细信息,请隐藏自定义窗口并在MapView上显示自定义视图

main.xml中

 <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <fragment xmlns:android="http://schemas.android.com/apk/res/android"
            xmlns:tools="http://schemas.android.com/tools"
            android:id="@+id/map"
            android:name="com.google.android.gms.maps.SupportMapFragment"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            tools:context="com.iphonealsham.speedli.activitys.MapsActivity" />

        <LinearLayout
            android:id="@+id/linearLayoutCustomView"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="bottom|center_horizontal"
            android:orientation="vertical">

            <TextView
                android:id="@+id/textViewTitle"
                android:layout_width="match_parent"
                android:layout_height="wrap_content" />

            <TextView
                android:id="@+id/textViewOtherDetails"
                android:layout_width="match_parent"
                android:layout_height="wrap_content" />
        </LinearLayout>
    </FrameLayout>

return true中隐藏onMarkerClick的InfoWidow并显示customView

 @Override
    public void onMapReady(GoogleMap googleMap) {
            mGoogleMap = googleMap;
            mGoogleMap.setOnMarkerClickListener(new GoogleMap.OnMarkerClickListener() {
                @Override
                public boolean onMarkerClick(Marker marker) {
                    Log.d("GoogleMap", " click");
//focus the market
mGoogleMap.animateCamera(CameraUpdateFactory.newLatLng(marker.g‌​etPosition()));
                    if (linearLayoutCustomView.getVisibility() == View.VISIBLE)
                        linearLayoutCustomView.setVisibility(View.GONE);
                    else
                        displayCustomeInfoWindow(marker);
                    return true;
                }
            });
    }

在视图中设置详细信息

 private void displayCustomeInfoWindow(Marker marker) {
        linearLayoutCustomView.setVisibility(View.VISIBLE);
        TextView textViewTitle = linearLayoutCustomView.findViewById(R.id.textViewTitle);
        TextView textViewOtherDetails = linearLayoutCustomView.findViewById(R.id.textViewOtherDetails);
        textViewTitle.setText(marker.getTitle());
        textViewOtherDetails.setText("LatLong :: " + marker.getPosition().latitude + "," + marker.getPosition().longitude);

    }