2014-05-22 50 views
4

我想在Google Maps V2上顯示CustomOverlay。瓷磚的裝載如預期的那樣工作,唯一的事情是,所示的瓷磚根本不顯得尖銳,有些模糊。谷歌沒有讓我得到可用的答案。Android Maps V2上的模糊自定義拼貼

我加入了古典256PX X 256PX瓷磚的TileProvider的方法。我設法得到了一個圖像爲2x(視網膜)的圖像源,這使得整個視覺體驗更加清晰,但我寧願不使用這個源,因爲數據傳輸速率高出四倍,因此無法在移動設備上使用設備和較慢的網速。

我包括所呈現的地圖的兩個不同的例子(截圖),兩者都具有相同的配置(OSM - 256×256瓦),並與所提供的TileProviderOsm。一個在Galaxy Nexus上,另一個在Nexus 5手機上。兩者看起來都不正確。

任何想法我可以做什麼來防止模糊或增加清晰度?

我TileProvider看起來像以下:

public class TileProviderOsm extends UrlTileProvider { 

    private static final String MAP_URL = "http://tile.openstreetmap.org/%d/%d/%d.png"; 

    private static int TILE_WIDTH = 256; 
    private static int TILE_HEIGHT = 256; 

    public static int MIN_ZOOM = 7; 
    public static int MAX_ZOOM = 15; 

    public TileProviderOsm() { 
     super(TILE_WIDTH, TILE_HEIGHT); 
    } 

    @Override 
    public synchronized URL getTileUrl(int x, int y, int zoom) { 

     String s = String.format(Locale.US, MAP_URL, zoom, x, y); 
     URL url = null; 
     try { 
      url = new URL(s); 
     } catch (MalformedURLException e) { 
      e.printStackTrace(); 
     } 
     return url; 
    } 
} 

下面是如何覆蓋添加到地圖:

map.addTileOverlay(new TileOverlayOptions().tileProvider(new TileProviderOsm())); 

這裏有渲染谷歌地圖的一些例子:

Google Maps V2 on a Nexus 5 - OSM Map tiles look blurry Google Maps V2 on a Galaxy Nexu - OSM Map tiles look blurry

+1

你解決這個問題?我偶然發現了同樣的問題,它真的很煩人,所有貼圖256 * 256的地圖都以這種質量顯示。 –

回答

5

這是縮放級別和縮放地圖圖塊的問題。這似乎是Android的Maps API V2的一個問題。這種行爲應該是這樣說的:gmaps-api-issues #4840

我通過從WMS請求更大的圖塊來解決它 - 只需用512x512替換256x256。

+0

不僅512x512圖塊在HDPI設備上看起來更加銳利,它們可能包含比256x256圖塊更多的地圖特徵。 USGS國家地圖拓樸底圖就是這種情況。但我不相信#4840號問題完全是由於縮放。我已經看到谷歌地圖v2顯示一張模糊的地圖,即使是512x512的圖塊。縮小和返回有時可以修復它。它可能與變焦控制有關。也許你有時最終在例如縮放3.1而不是縮放3,從縮放4看瓷磚。只是一個預感。 –

+0

我同意你@pegel,所以我將你的答案標記爲已解決。我還設法包括512x512的瓷磚,情況有所改善,但正如凱文提到的那樣,問題並沒有完全消失。我有與非整數縮放級別凱文相同的觀察,因此顯示模糊的瓷磚,因爲在非整數縮放級別顯然不合適的渲染。 – Devdroid

+0

謝謝!幫助了我很多..但如上所述..問題仍然存在,但至少看起來好多了。 –

5

我正在解決這個問題,通過繪製四個瓷磚成一個瓷磚。

我寫這TileProvider這是使用另一牌供應商創造更高分辨率的瓷磚。

import android.graphics.Bitmap; 
import android.graphics.BitmapFactory; 
import android.graphics.Canvas; 
import android.graphics.Color; 
import android.graphics.Paint; 

import com.google.android.gms.maps.model.Tile; 
import com.google.android.gms.maps.model.TileProvider; 

import java.io.ByteArrayOutputStream; 

public class CanvasTileProvider implements TileProvider { 

    static final int TILE_SIZE = 512; 
    private TileProvider mTileProvider; 

    public CanvasTileProvider(TileProvider tileProvider) { 
     mTileProvider = tileProvider; 
    } 

    @Override 
    public Tile getTile(int x, int y, int zoom) { 
     byte[] data; 
     Bitmap image = getNewBitmap(); 
     Canvas canvas = new Canvas(image); 
     boolean isOk = onDraw(canvas, zoom, x, y); 
     data = bitmapToByteArray(image); 
     image.recycle(); 

     if (isOk) { 
      Tile tile = new Tile(TILE_SIZE, TILE_SIZE, data); 
      return tile; 
     } else { 
      return mTileProvider.getTile(x, y, zoom); 
     } 
    } 

    Paint paint = new Paint(); 

    private boolean onDraw(Canvas canvas, int zoom, int x, int y) { 
     x = x * 2; 
     y = y * 2; 
     Tile leftTop = mTileProvider.getTile(x, y, zoom + 1); 
     Tile leftBottom = mTileProvider.getTile(x, y + 1, zoom + 1); 
     Tile rightTop = mTileProvider.getTile(x + 1, y, zoom + 1); 
     Tile rightBottom = mTileProvider.getTile(x + 1, y + 1, zoom + 1); 

     if (leftTop == NO_TILE && leftBottom == NO_TILE && rightTop == NO_TILE && rightBottom == NO_TILE) { 
      return false; 
     } 


     Bitmap bitmap; 

     if (leftTop != NO_TILE) { 
      bitmap = BitmapFactory.decodeByteArray(leftTop.data, 0, leftTop.data.length); 
      canvas.drawBitmap(bitmap, 0, 0, paint); 
      bitmap.recycle(); 
     } 

     if (leftBottom != NO_TILE) { 
      bitmap = BitmapFactory.decodeByteArray(leftBottom.data, 0, leftBottom.data.length); 
      canvas.drawBitmap(bitmap, 0, 256, paint); 
      bitmap.recycle(); 
     } 
     if (rightTop != NO_TILE) { 
      bitmap = BitmapFactory.decodeByteArray(rightTop.data, 0, rightTop.data.length); 
      canvas.drawBitmap(bitmap, 256, 0, paint); 
      bitmap.recycle(); 
     } 
     if (rightBottom != NO_TILE) { 
      bitmap = BitmapFactory.decodeByteArray(rightBottom.data, 0, rightBottom.data.length); 
      canvas.drawBitmap(bitmap, 256, 256, paint); 
      bitmap.recycle(); 
     } 
     return true; 
    } 

    private Bitmap getNewBitmap() { 
     Bitmap image = Bitmap.createBitmap(TILE_SIZE, TILE_SIZE, 
       Bitmap.Config.ARGB_8888); 
     image.eraseColor(Color.TRANSPARENT); 
     return image; 
    } 

    private static byte[] bitmapToByteArray(Bitmap bm) { 
     ByteArrayOutputStream bos = new ByteArrayOutputStream(); 
     bm.compress(Bitmap.CompressFormat.PNG, 100, bos); 

     byte[] data = bos.toByteArray(); 
     try { 
      bos.close(); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
     return data; 
    } 
} 
相關問題