简体   繁体   English

如何在谷歌地图android中以给定角度旋转多边形

[英]How to rotate polygon with given angle in google map android

I一世在此处输入图片说明

I am working on the app where i have to draw multiple fixed size polygons on click lets consider for example 10 x 25. so that i have archived successfully now i need to rotate the selected polygon at given angle ( let consider 0 to 360 ) when i click on + button the polygon should rotate in right direction with adding 1 degree angle, similarly clicking on - button should rotate polygon in left direction anyone have idea how to achieve this ?我正在开发应用程序,我必须在点击时绘制多个固定大小的多边形,让我们考虑例如 10 x 25。这样我现在已经成功存档,我需要以给定的角度旋转选定的多边形(让我们考虑 0 到 360)当我点击 + 按钮,多边形应该向右旋转并增加 1 度角,同样点击 - 按钮应该向左旋转多边形有人知道如何实现吗?

adding some code for the consideration.添加一些代码以供考虑。

public void drawPolygonWithGivenDimention(LatLng latLng,float width,float  height,float innerDistance,boolean forUpdate,int id)
{
    model = new ModelMarker();

    model.setId(id);

    // Paras Outer Polygon
    Location clickedPoint = new Location("clicked");
    clickedPoint.setLatitude(latLng.latitude);
    clickedPoint.setLongitude(latLng.longitude);

    LatLng latLng0 = new LatLng(clickedPoint.getLatitude(), clickedPoint.getLongitude());
    pointList.add(latLng0);

    Location loc1 = locationForAngle(0.0f, clickedPoint, width);
    LatLng latLng1 = new LatLng(loc1.getLatitude(), loc1.getLongitude());
    pointList.add(latLng1);

    Location loc2 = locationForAngle(90.0f, loc1, height);
    LatLng latLng2 = new LatLng(loc2.getLatitude(), loc2.getLongitude());
    pointList.add(latLng2);

    Location loc3 = locationForAngle(180.0f, loc2, width);
    LatLng latLng3 = new LatLng(loc3.getLatitude(), loc3.getLongitude());
    pointList.add(latLng3);

    model.setPointList(pointList);


    // Paras Inner Polygon
    Location locPeri = locationForAngle(0.0f,clickedPoint,innerDistance);//Change\
    locPeri = locationForAngle(90.0f ,locPeri,innerDistance);

    LatLng latLng10 = new LatLng(locPeri.getLatitude(), locPeri.getLongitude());
    pointListInner.add(latLng10);

    Location loc11 = locationForAngle(0.0f, locPeri, width-innerDistance*2);
    LatLng latLng11 = new LatLng(loc11.getLatitude(), loc11.getLongitude());
    pointListInner.add(latLng11);

    Location loc12 = locationForAngle(90.0f, loc11, height-innerDistance*2);
    LatLng latLng12 = new LatLng(loc12.getLatitude(), loc12.getLongitude());
    pointListInner.add(latLng12);

    Location loc13 = locationForAngle(180.0f, loc12, width-innerDistance*2);
    LatLng latLng13 = new LatLng(loc13.getLatitude(), loc13.getLongitude());
    pointListInner.add(latLng13);
    model.setPointListInner(pointListInner);

    drawOuterPolygon(forUpdate);
}


private void drawOuterPolygon(boolean forUpdate)
{
    try
    {
        pointList = model.getPointList();
        Polygon poligone;
        PolygonOptions polygoneOptions = new PolygonOptions();
        polygoneOptions.addAll(pointList);
        polygoneOptions.strokeWidth(2);
        polygoneOptions.strokeColor(Color.BLACK);

        polygoneOptions.fillColor(drawColor);

        poligone = googleMap.addPolygon(polygoneOptions);
        poligone.setClickable(true);
        if(forUpdate)
            polygons.set(selectedMarkerPosition,poligone);
        else
            polygons.add(poligone);


        model.setPolygon(poligone);
        model.setPolygons(polygons);

        drawInnerPolygon(forUpdate);
        //getCenterPoint();

    }
    catch (Exception e)
    {
        e.printStackTrace();
    }
 }

 public Location locationForAngle(float angle,Location center,float distances)
{
    //in Yard 6975174.98 radius of earth
    double distanceRadians = distances / 6967410.0; // Yards
    //6,371 = Earth's radius in km
    double bearingRadians = deg2rad(angle);
    double fromLatRadians = deg2rad(center.getLatitude());
    double fromLonRadians = deg2rad(center.getLongitude());
    double toLatRadians = Math.asin( Math.sin(fromLatRadians) * Math.cos(distanceRadians)+ Math.cos(fromLatRadians) *  Math.sin(distanceRadians) * Math.cos(bearingRadians) );
    double toLonRadians = fromLonRadians + Math.atan2(Math.sin(bearingRadians) * Math.sin(distanceRadians) * Math.cos(fromLatRadians), Math.cos(distanceRadians)- Math.sin(fromLatRadians) * Math.sin(toLatRadians));
    // adjust toLonRadians to be in the range -180 to +180...
    toLonRadians = Math.IEEEremainder((toLonRadians + 3*M_PI), ((2*M_PI)) - M_PI);
    Location result = new Location("");
    result.setLatitude(rad2deg(toLatRadians));
    result.setLongitude(rad2deg(toLonRadians));
    return result;
}

double M_PI  = 3.14159265358979323846264338327950288;

public double deg2rad(double degrees)
{
    return  (degrees * (M_PI/180));
}
public double rad2deg(double radians)
{
    return  (radians * (180/M_PI));
}

If all markers has same size and colors (or there is not so many different markers) seems simplest way is to use Marker.setRotation() method:如果所有标记具有相同的大小和颜色(或者没有那么多不同的标记)似乎最简单的方法是使用Marker.setRotation()方法:

public class MainActivity extends AppCompatActivity implements OnMapReadyCallback {

    private static final LatLng MAP_CENTER = new LatLng(22.3038715,70.8009047);

    private GoogleMap mGoogleMap;
    private MapFragment mMapFragment;

    private Button mButtonMinus;
    private Button mButtonPlus;

    private Marker mMarker;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        mButtonMinus = (Button) findViewById(R.id.button_minus);
        mButtonMinus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                mMarker.setRotation(mMarker.getRotation() - 1);
            }
        });

        mButtonPlus = (Button) findViewById(R.id.button_plus);
        mButtonPlus.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                mMarker.setRotation(mMarker.getRotation() + 1);
            }
        });

        mMapFragment = (MapFragment) getFragmentManager()
                .findFragmentById(R.id.map_fragment);
        mMapFragment.getMapAsync(this);
    }

    @Override
    public void onMapReady(GoogleMap googleMap) {
        mGoogleMap = googleMap;

        mGoogleMap.animateCamera(CameraUpdateFactory.newLatLngZoom(MAP_CENTER, 16));

        mMarker = mGoogleMap.addMarker(new MarkerOptions()
                .icon(BitmapDescriptorFactory.fromResource(R.drawable.ic_marker_rot))
                .position(MAP_CENTER)
                .alpha(0.75f)
                .anchor(0.5f, 0.5f)
                .rotation(0));
    }

}

where R.drawable.ic_marker_rot is North-oriented marker icon:其中R.drawable.ic_marker_rot是北向标记图标:

标记图标

and activity_main.xml is:activity_main.xml是:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="<your_package>.MainActivity">

    <fragment
        android:id="@+id/map_fragment"
        android:name="com.google.android.gms.maps.MapFragment"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

    <LinearLayout
        android:id="@+id/buttons_layout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:orientation="horizontal">

        <Button
            android:id="@+id/button_minus"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="-"/>

        <Button
            android:id="@+id/button_plus"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="+"/>

    </LinearLayout>

</RelativeLayout>

As a result you have something like that:结果你有这样的事情:

旋转标记示例

If you has several markers you need to manage it (add to list on creation, determine selected markerr, etc.)如果您有多个标记,您需要对其进行管理(添加到创建列表、确定选定的标记等)

In other case (you really need draw each marker) easiest way is to convert LatLng coords into screen coords:在其他情况下(您确实需要绘制每个标记),最简单的方法是将LatLng坐标转换为屏幕坐标:

Projection projection = mGoogleMap.getProjection();
Point screenPosition = projection.toScreenLocation(mMarker.getPosition());

than apply rotation on Point (eg like in this answer of Entreco ), than convert rotated screen coords (of each point of rectangle) back into LatLng :而不是在Point上应用旋转(例如在Entreco 的这个答案中),然后将旋转的屏幕坐标(矩形的每个点)转换回LatLng

mGoogleMap.getProjection().fromScreenLocation(screenPosition);

and draw rectangle as you already draw.并像您已经绘制的那样绘制矩形。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM