我在GoogleMap
中有10個標記。我想盡可能放大並保留所有標記?在早期版本中,這可以從zoomToSpan()
實現,但在V2中,我不知道如何做到這一點。此外,我知道需要可見的圓的半徑。Android地圖v2放大以顯示所有標記
回答
您應該使用CameraUpdate
類(可能)執行所有程序化的地圖移動。
要做到這一點,首先計算所有標記的範圍,像這樣:CameraUpdateFactory
:
int padding = 0; // offset from edges of the map in pixels
CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, padding);
最後移動地圖
LatLngBounds.Builder builder = new LatLngBounds.Builder();
for (Marker marker : markers) {
builder.include(marker.getPosition());
}
LatLngBounds bounds = builder.build();
通過使用工廠然後得到一個運動的描述對象:
googleMap.moveCamera(cu);
或者如果你想動畫:
googleMap.animateCamera(cu);
這是所有:)
澄清1
幾乎所有的運動方法要求已通過佈局過程中Map
對象。您可以使用addOnGlobalLayoutListener
構造等待發生這種情況。詳細信息可以在評論中找到這個答案和其餘的答案。您還可以找到一個complete code for setting map extent using addOnGlobalLayoutListener
here。
澄清2
一種意見指出,使用這種方法只有一個標記導致地圖縮放設置爲一個「奇怪的」縮放級別(這我認爲是可用於指定位置的最大縮放級別)。我認爲這是預料之中,因爲:
- 的
LatLngBounds bounds
實例將有northeast
屬性等於southwest
,這意味着本bounds
覆蓋地球面積的部分正好是零。 (這是合乎邏輯的,因爲單個標記沒有區域。) - 通過將
bounds
傳遞給CameraUpdateFactory.newLatLngBounds
您基本上要求計算這樣一個縮放級別,即bounds
(具有零區域)將覆蓋整個地圖視圖。 - 您實際上可以在一張紙上執行此計算。作爲答案的理論縮放級別是+ ∞(正無窮大)。在實踐中,
Map
對象不支持該值,因此它被限制爲給定位置允許的更合理的最大級別。
另一種方式把它:Map
對象怎麼能知道什麼縮放級別應該是選擇一個單一位置?也許最佳值應該是20(如果它代表特定的地址)。或者也許11(如果它代表一個城鎮)。或者,也許6(如果它代表一個國家)。 API不是那麼聰明,這個決定取決於你。
所以,你應該簡單地檢查是否markers
只有一個位置,如果是這樣,使用一個:
CameraUpdate cu = CameraUpdateFactory.newLatLng(marker.getPosition())
- 去標記的位置,離開當前縮放級別不變。CameraUpdate cu = CameraUpdateFactory.newLatLngZoom(marker.getPosition(), 12F)
- 去標記的位置,設置縮放級別任意選擇值12
應該指出的是,移動不能從onCreate調用發生,視圖必須被創建。我需要使用addOnGlobalLayoutListener來獲取適當的樣本。 – 2013-08-01 17:57:42
@巴爾,這部分是真的。準確地說:*一些*移動方法在創建地圖對象後不會正常工作。其原因是地圖對象尚未被測量*但尚未經過佈局處理。一個典型的解決方法是使用'addOnGlobalLayoutListener()'或'post()'和適當的'Runnable'。這正是獲取標記屏幕座標不能在'onCreate'中完成的原因 - 請參閱http://stackoverflow.com/q/14429877/1820695但是,您甚至可以在佈局發生之前使用某些方法 - 例如。 'CameraUpdateFactory.newLatLngBounds()'帶有* 4個參數*。 – andr 2013-08-01 19:18:04
男人,你救了我一天...實際上是試圖自己做,手動計算邊界,並縮放標記是在它...工作相當醜陋,但用你的簡單方法,它的作品像一個魅力。謝謝 – Bibu 2014-03-08 20:40:40
所以
I needed to use addOnGlobalLayoutListener to get the appropriate sample
例如,您的谷歌地圖裏面的RelativeLayout:
RelativeLayout mapLayout = (RelativeLayout)findViewById(R.id.map_layout);
mapLayout.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
//and write code, which you can see in answer above
}
});
我無法使用onGlobalLayoutlistener,所以這裏有另一個解決方案來防止 "Map size can't be 0. Most likely, layout has not yet occured for the map view. Either wait until layout has occurred or use newLatLngBounds(LatLngBounds, int, int, int) which allows you to specify the map's dimensions."
錯誤:
mMap.setOnMapLoadedCallback(new GoogleMap.OnMapLoadedCallback() {
@Override
public void onMapLoaded() {
mMap.moveCamera(CameraUpdateFactory.newLatLngBounds(builder.build(), 15));
}
});
這一個比OnGlobalLayoutListener更長的路,所以對我來說它仍然顯示首先映射默認區域/縮放,然後將攝像機移動到我需要的地方 – Till 2016-07-05 12:47:16
使用「getCenterCoordinate」方法獲取中心座標並在CameraPosition中使用。
private void setUpMap() {
mMap.setMyLocationEnabled(true);
mMap.getUiSettings().setScrollGesturesEnabled(true);
mMap.getUiSettings().setTiltGesturesEnabled(true);
mMap.getUiSettings().setRotateGesturesEnabled(true);
clientMarker = mMap.addMarker(new MarkerOptions()
.position(new LatLng(Double.valueOf(-12.1024174), Double.valueOf(-77.0262274)))
.icon(BitmapDescriptorFactory.fromResource(R.mipmap.ic_taxi))
);
clientMarker = mMap.addMarker(new MarkerOptions()
.position(new LatLng(Double.valueOf(-12.1024637), Double.valueOf(-77.0242617)))
.icon(BitmapDescriptorFactory.fromResource(R.mipmap.ic_location))
);
camPos = new CameraPosition.Builder()
.target(getCenterCoordinate())
.zoom(17)
.build();
camUpd3 = CameraUpdateFactory.newCameraPosition(camPos);
mMap.animateCamera(camUpd3);
}
public LatLng getCenterCoordinate(){
LatLngBounds.Builder builder = new LatLngBounds.Builder();
builder.include(new LatLng(Double.valueOf(-12.1024174), Double.valueOf(-77.0262274)));
builder.include(new LatLng(Double.valueOf(-12.1024637), Double.valueOf(-77.0242617)));
LatLngBounds bounds = builder.build();
return bounds.getCenter();
}
//For adding a marker in Google map
MarkerOptions mp = new MarkerOptions();
mp.position(new LatLng(Double.parseDouble(latitude), Double.parseDouble(longitude)));
mp.snippet(strAddress);
map.addMarker(mp);
try {
b = new LatLngBounds.Builder();
if (MapDetailsList.list != null && MapDetailsList.list.size() > 0) {
for (int i = 0; i < MapDetailsList.list.size(); i++) {
b.include(new LatLng(Double.parseDouble(MapDetailsList.list.get(i).getLatitude()),
Double.parseDouble(MapDetailsList.list.get(i).getLongitude())));
}
LatLngBounds bounds = b.build();
DisplayMetrics displayMetrics = getResources().getDisplayMetrics();
int width = displayMetrics.widthPixels;
int height = displayMetrics.heightPixels;
// Change the padding as per needed
CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, width-200, height-200, 5);
// map.setCenter(bounds.getCenter());
map.animateCamera(cu);
}
} catch (Exception e) {
}
http://i64.tinypic.com/2qjybh4.png
注意 - 這不是原來的問題的解決方案。這是對above討論的子問題之一的解決方案。
解決@andr 澄清2 -
它真的有問題時,有隻有一個邊界標記,由於它的縮放級別設置爲一個非常高的水平(級21)。而Google目前沒有提供任何設置最大縮放級別的方法。這也可能發生在有多於一個標記但它們彼此非常接近時。然後也會發生同樣的問題。
解決方案 - 假設您希望您的地圖不超過16個縮放級別。然後,後做事 -
CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, padding);
mMap.moveCamera(cu);
檢查您的縮放級別已越過16級(或任何你想要的) -
float currentZoom = mMap.getCameraPosition().zoom;
如果這個級別大於16,這也只會是如果有是非常少的標記或所有標記都非常接近對方,後來乾脆只塞汀縮放比例爲16
mMap.moveCamera(CameraUpdateFactory.zoomTo(16));
這樣,你永遠不會有在p縮小你在那個特定的位置地圖@andr也很好地解釋了「奇異」縮放級別的問題。
很好的解決方案,但是如果您將「cu」對象置於MapReady()內部,那麼在這種情況下會出現一個錯誤行爲:**收到位置 - >縮放很大,它16 - >然後用戶放大 - >位置再次收到和相機被放回到級別16 **。 當幾乎實時收到位置時,這可能會成爲問題,因爲它會一直返回到第16級。 – 2017-02-01 09:32:04
「Google現在不提供任何方法來設置最大縮放級別。」 - 不正確:https ://developers.google.com/android/reference/com/google/android/gms/maps/GoogleMap.html#setMaxZoomPreference(float) – user1209216 2017-05-22 07:01:59
這會幫助..從谷歌apis演示
private List<Marker> markerList = new ArrayList<>();
Marker marker = mGoogleMap.addMarker(new MarkerOptions().position(geoLatLng)
.title(title));
markerList.add(marker);
// Pan to see all markers in view.
// Cannot zoom to bounds until the map has a size.
final View mapView = getSupportFragmentManager().findFragmentById(R.id.map).getView();
if (mapView!=null) {
if (mapView.getViewTreeObserver().isAlive()) {
mapView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@SuppressWarnings("deprecation") // We use the new method when supported
@SuppressLint("NewApi") // We check which build version we are using.
@Override
public void onGlobalLayout() {
//Calculate the markers to get their position
LatLngBounds.Builder b = new LatLngBounds.Builder();
for (Marker m : markerList) {
b.include(m.getPosition());
}
// also include current location to include in the view
b.include(new LatLng(mLocation.getLatitude(),mLocation.getLongitude()));
LatLngBounds bounds = b.build();
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
mapView.getViewTreeObserver().removeGlobalOnLayoutListener(this);
} else {
mapView.getViewTreeObserver().removeOnGlobalLayoutListener(this);
}
mGoogleMap.moveCamera(CameraUpdateFactory.newLatLngBounds(bounds, 50));
}
});
}
}
谷歌地圖V2:爲Android棉花糖6(API 23,API 24,API 25),以及邊界最佳的工作解決方案中放大的MarkerOptions,工程在Xamarin還
LatLngBounds.Builder builder = new LatLngBounds.Builder();
//the include method will calculate the min and max bound.
builder.include(marker1.getPosition());
builder.include(marker2.getPosition());
builder.include(marker3.getPosition());
builder.include(marker4.getPosition());
LatLngBounds bounds = builder.build();
int width = getResources().getDisplayMetrics().widthPixels;
int height = getResources().getDisplayMetrics().heightPixels;
int padding = (int) (width * 0.10); // offset from edges of the map 10% of screen
CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, width, height, padding);
mMap.animateCamera(cu);
Working fine for me.
從這個代碼,我在地圖屏幕上顯示特定縮放的多個標記。
//聲明的變量
private LatLngBounds bounds;
private LatLngBounds.Builder builder;
//方法與繪製圖標添加多個標記點
private void drawMarker(LatLng point, String text) {
MarkerOptions markerOptions = new MarkerOptions();
markerOptions.position(point).title(text).icon(BitmapDescriptorFactory.fromResource(R.drawable.icon));
mMap.addMarker(markerOptions);
builder.include(markerOptions.getPosition());
}
//對於添加多個標記可見在地圖上
@Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
builder = new LatLngBounds.Builder();
for (int i = 0; i < locationList.size(); i++) {
drawMarker(new LatLng(Double.parseDouble(locationList.get(i).getLatitude()), Double.parseDouble(locationList.get(i).getLongitude())), locationList.get(i).getNo());
}
bounds = builder.build();
CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, 0);
mMap.animateCamera(cu);
我有類似的問題,使用下面的代碼解決了問題:
CameraUpdateFactory.newLatLngBounds(bounds, 200, 200, 5)
我的情況一般位置差異不超過兩個鄰居城市。
我有一個其他的方式做同樣的事情完美的作品。所以後面的想法顯示屏幕上的所有標記,我們需要一箇中心拉長和縮放級別。這裏有一個函數可以讓你和所有標記的Latlng對象作爲輸入。
public Pair<LatLng, Integer> getCenterWithZoomLevel(LatLng... l) {
float max = 0;
if (l == null || l.length == 0) {
return null;
}
LatLngBounds.Builder b = new LatLngBounds.Builder();
for (int count = 0; count < l.length; count++) {
if (l[count] == null) {
continue;
}
b.include(l[count]);
}
LatLng center = b.build().getCenter();
float distance = 0;
for (int count = 0; count < l.length; count++) {
if (l[count] == null) {
continue;
}
distance = distance(center, l[count]);
if (distance > max) {
max = distance;
}
}
double scale = max/1000;
int zoom = ((int) (16 - Math.log(scale)/Math.log(2)));
return new Pair<LatLng, Integer>(center, zoom);
}
該函數返回對對象,您可以像使用
Pair pair = getCenterWithZoomLevel(l1,l2,l3..); mGoogleMap.moveCamera(CameraUpdateFactory.newLatLngZoom(pair.first, pair.second));
可以代替使用填充您的標記從屏幕邊界保持距離,你可以通過調整-1變焦。
- 1. 縮放以適應地圖上的所有標記谷歌地圖v2 android
- 2. 谷歌地圖放大顯示所有標記
- 3. 基於谷歌地圖V2縮放調整大小標記android
- 4. 谷歌地圖v2縮放適合所有標記AND Poly Lines
- 5. Android - 谷歌地圖V2:修正縮放顯示第一個可見標記
- 6. 如何顯示地圖上的所有標記/位置android/
- 7. 谷歌地圖V3縮放以顯示所有標記不起作用
- 8. 如何設置地圖縮放以顯示tabpage中的所有標記Bootstrap?
- 9. Google地圖:並非所有標記都以某些縮放級別顯示
- 10. 設置縮放和中心顯示所有標記 - 顯示在地圖元素
- 11. Android Google地圖API V2中心標記
- 12. Android谷歌地圖v2中的標記
- 13. 谷歌地圖api v2放大標記附近
- 14. 這裏地圖 - 中心地圖顯示所有標記
- 15. 谷歌地圖Api V2 - 不顯示標記標題
- 16. 谷歌地圖v2標記拖放與提醒Android
- 17. 谷歌地圖Android API v2,標記標題/摘錄錯誤顯示
- 18. 地圖v2着色標記
- 19. 大可點擊標記谷歌android地圖api v2
- 20. android谷歌地圖標記不顯示
- 21. 谷歌地圖不顯示標記android
- 22. 在ListView中顯示Android地圖標記
- 23. 谷歌地圖v2:如何顯示具有相同座標的各種標記
- 24. 谷歌地圖v2只顯示第一個標記
- 25. 如何在谷歌地圖上顯示多個標記v2
- 26. 標記不會在Google地圖v2上顯示
- 27. android縮放到Google Map地圖上的所有標記
- 28. Android谷歌地圖API V2沒有放大到位置
- 29. iOS MKMapView縮放以顯示所有標記
- 30. Google Map API v3 - 以最大縮放顯示所有可見標記
我的答案會給你一個最新的Android API最簡單的解決方案。 http://stackoverflow.com/a/38013331/1348522 – 2016-11-08 10:12:47