Androidは百度の地図を使って多角形の面積を測定します
btn_clear = (Button)findViewById(R.id.btn_clear);
btn_jisuan = (Button)findViewById(R.id.btn_jisuan);
//
mMapView = (MapView) findViewById(R.id.mapView);
mBaiduMap = mMapView.getMap();
//
mBaiduMap.setOnMapClickListener(new OnMapClickListener() {
@Override
public boolean onMapPoiClick(MapPoi arg0) {
return false;
}
@Override
public void onMapClick(final LatLng latLng) {
//
latitude = latLng.latitude;
longitude = latLng.longitude;
// Maker
LatLng point = new LatLng(latitude, longitude);
MarkerOptions options = new MarkerOptions().position(point).icon(icon_muasure);
pts.add(latLng);
// Marker,
mBaiduMap.addOverlay(options);
}
});
//
btn_jisuan.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
String area = getArea(pts);
//
OverlayOptions ooText = new TextOptions().bgColor(0xAAFFFF00)
.fontSize(48).fontColor(0xFFFF00FF).text(" :" + area + " m²")
.position(pts.get(0));
mBaiduMap.addOverlay(ooText);
}
});
//
btn_jisuan.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
pts.clear();
mBaiduMap.clear();
}
});
/**
*
* @return
*/
protected String getArea(List<LatLng> pts) {
double totalArea = 0;//
double LowX = 0.0;
double LowY = 0.0;
double MiddleX = 0.0;
double MiddleY = 0.0;
double HighX = 0.0;
double HighY = 0.0;
double AM = 0.0;
double BM = 0.0;
double CM = 0.0;
double AL = 0.0;
double BL = 0.0;
double CL = 0.0;
double AH = 0.0;
double BH = 0.0;
double CH = 0.0;
double CoefficientL = 0.0;
double CoefficientH = 0.0;
double ALtangent = 0.0;
double BLtangent = 0.0;
double CLtangent = 0.0;
double AHtangent = 0.0;
double BHtangent = 0.0;
double CHtangent = 0.0;
double ANormalLine = 0.0;
double BNormalLine = 0.0;
double CNormalLine = 0.0;
double OrientationValue = 0.0;
double AngleCos = 0.0;
double Sum1 = 0.0;
double Sum2 = 0.0;
double Count2 = 0;
double Count1 = 0;
double Sum = 0.0;
double Radius = 6378137.0;// WGS84
int Count = pts.size();
// 3
if (Count < 3) {
return;
}
for ( int i = 0; i < Count; i++) {
if (i == 0) {
LowX = pts.get(Count - 1).longitude * Math.PI / 180;
LowY = pts.get(Count - 1).latitude * Math.PI / 180;
MiddleX = pts.get(0).longitude * Math.PI / 180;
MiddleY = pts.get(0).latitude * Math.PI / 180;
HighX = pts.get(1).longitude * Math.PI / 180;
HighY = pts.get(1).latitude * Math.PI / 180;
} else if (i == Count - 1) {
LowX = pts.get(Count - 2).longitude * Math.PI / 180;
LowY = pts.get(Count - 2).latitude * Math.PI / 180;
MiddleX = pts.get(Count - 1).longitude * Math.PI / 180;
MiddleY = pts.get(Count - 1).latitude * Math.PI / 180;
HighX = pts.get(0).longitude * Math.PI / 180;
HighY = pts.get(0).latitude * Math.PI / 180;
} else {
LowX = pts.get(i - 1).longitude * Math.PI / 180;
LowY = pts.get(i - 1).latitude * Math.PI / 180;
MiddleX = pts.get(i).longitude * Math.PI / 180;
MiddleY = pts.get(i).latitude * Math.PI / 180;
HighX = pts.get(i + 1).longitude * Math.PI / 180;
HighY = pts.get(i + 1).latitude * Math.PI / 180;
}
AM = Math.cos(MiddleY) * Math.cos(MiddleX);
BM = Math.cos(MiddleY) * Math.sin(MiddleX);
CM = Math.sin(MiddleY);
AL = Math.cos(LowY) * Math.cos(LowX);
BL = Math.cos(LowY) * Math.sin(LowX);
CL = Math.sin(LowY);
AH = Math.cos(HighY) * Math.cos(HighX);
BH = Math.cos(HighY) * Math.sin(HighX);
CH = Math.sin(HighY);
CoefficientL = (AM * AM + BM * BM + CM * CM)/ (AM * AL + BM * BL + CM * CL);
CoefficientH = (AM * AM + BM * BM + CM * CM)/ (AM * AH + BM * BH + CM * CH);
ALtangent = CoefficientL * AL - AM;
BLtangent = CoefficientL * BL - BM;
CLtangent = CoefficientL * CL - CM;
AHtangent = CoefficientH * AH - AM;
BHtangent = CoefficientH * BH - BM;
CHtangent = CoefficientH * CH - CM;
AngleCos = (AHtangent * ALtangent + BHtangent * BLtangent + CHtangent* CLtangent)/ (Math.sqrt(AHtangent * AHtangent + BHtangent* BHtangent
+ CHtangent * CHtangent) * Math.sqrt(ALtangent * ALtangent + BLtangent* BLtangent + CLtangent * CLtangent));
AngleCos = Math.acos(AngleCos);
ANormalLine = BHtangent * CLtangent - CHtangent * BLtangent;
BNormalLine = 0 - (AHtangent * CLtangent - CHtangent* ALtangent);
CNormalLine = AHtangent * BLtangent - BHtangent * ALtangent;
if (AM != 0)
OrientationValue = ANormalLine / AM;
else if (BM != 0)
OrientationValue = BNormalLine / BM;
else
OrientationValue = CNormalLine / CM;
if (OrientationValue > 0) {
Sum1 += AngleCos;
Count1++;
} else {
Sum2 += AngleCos;
Count2++;
}
}
double tempSum1, tempSum2;
tempSum1 = Sum1 + (2 * Math.PI * Count2 - Sum2);
tempSum2 = (2 * Math.PI * Count1 - Sum1) + Sum2;
if (Sum1 > Sum2) {
if ((tempSum1 - (Count - 2) * Math.PI) < 1)
Sum = tempSum1;
else
Sum = tempSum2;
} else {
if ((tempSum2 - (Count - 2) * Math.PI) < 1)
Sum = tempSum2;
else
Sum = tempSum1;
}
totalArea = (Sum - (Count - 2) * Math.PI) * Radius * Radius;
return String.valueOf(Math.floor(totalArea)); //
}
効果図:
注意:このアルゴリズムはたまに面積が負の場合がありますが、まだ解決されていません.
参考記事:http://blog.csdn.net/chenguang79/article/details/40506469