You can add images on top of your map as a Tile Layer. 圖塊層會放置在特定縮放等級的地圖圖塊上方。如果能提供足夠的圖塊,整份地圖的 Google 地圖資料會更完整,且適用於多個縮放等級。

簡介
圖塊圖層 (有時也稱為圖塊疊加層) 可讓您將圖片疊加在 Google 基本地圖圖塊上方。使用這項功能,在應用程式中加入興趣點或交通資訊等資料,以及當地圖像。與kGMSTypeNone地圖類型搭配使用時,圖塊圖層可有效取代 Google 的基本地圖資料。
當您想在地圖上加入大量圖像時 (通常涵蓋大範圍地理區域),圖塊圖層就非常實用。相反地,如果您想修正地圖上某個點的單張圖片,就比較適合使用區域疊加層。
圖塊座標
Maps API 會將各縮放等級的圖像分為一組正方形地圖圖塊,並排列成有序的格狀。地圖捲動到新位置或調至新的縮放等級時,Maps API 會判斷需要哪些圖塊,然後將該資訊轉譯成要擷取的一組圖塊。
在 Google 的麥卡托投影實作中,座標為 (0,0) 的圖塊一律位於地圖的西北角,同時 x 值會從西到東遞增,y 值則從北到南遞增。圖塊是使用從該原點開始的 x,y 座標來建立索引。舉例來說,縮放等級為 2 時,如果將地球區分成 16 個圖塊,每個圖塊都可使用不重複的 x,y 組合參照:

Each map tile is a 256x256 point square. 縮放等級為 0 時,全世界會算繪為單一圖塊。每個縮放等級會將地圖放大兩倍,舉例來說,縮放等級為 1 時,地圖會算繪為 2x2 的圖塊方格;縮放等級為 2 時,地圖會算繪為 4x4 的方格;縮放等級為 3 時,地圖會算繪為 8x8 的方格。如要建立圖塊圖層的圖片,請針對要支援的每個縮放等級,分別為每個圖塊建立 256x256 點的圖片。
Add a Tile Layer
- 建立
GMSURLTileLayer物件的例項,或是GMSTileLayer或GMSSyncTileLayer的自訂子類別。 - 視需要修改
zIndex屬性,調整其相對於其他圖塊圖層的位置。 - 設定地圖的
map屬性,將GMSTileLayer物件指派給地圖。
Maps SDK for iOS 提供三種類別,可用於實作圖塊層。您需要為每個類別定義如何擷取特定 {x,y,zoom} 座標集的正確地圖圖塊。可用的選項如下:
- 子類別
GMSSyncTileLayer,提供會傳回UIImage例項的tileForX:y:zoom實作項目。 - 將
GMSTileLayer子類別化,提供非同步方法requestTileForX:y:zoom的實作項目,稍後會使用圖塊圖片回呼。 - 使用現有的
GMSURLTileLayer類別,從網址自動擷取圖塊,並提供GMSTileURLConstructor區塊。GMSURLTileLayer是無法建立子類的具體類別。
如果是子類別化 GMSSyncTileLayer 或 GMSTileLayer,提供 nil 圖塊結果會告知 Maps SDK for iOS 資料無法使用,但日後可能可以使用。或者,傳回 kGMSTileLayerNoTile,表示這個位置沒有圖塊。
如果是 GMSURLTileLayer,從 GMSTileURLConstructor 傳回 nil 表示這個位置沒有圖塊。
Use GMSURLTileLayer to fetch tiles from URLs
GMSURLTileLayer 不需要子類別化,但您必須實作 GMSTileURLConstructor 區塊。以下程式碼說明如何使用 GMSURLTileLayer 顯示多層建築的樓層平面圖。
Swift
let floor = 1 // Implement GMSTileURLConstructor // Returns a Tile based on the x,y,zoom coordinates, and the requested floor let urls: GMSTileURLConstructor = { (x, y, zoom) in let url = "https://www.example.com/floorplans/L\(floor)_\(zoom)_\(x)_\(y).png" return URL(string: url) } // Create the GMSTileLayer let layer = GMSURLTileLayer(urlConstructor: urls) // Display on the map at a specific zIndex layer.zIndex = 100 layer.map = mapView
Objective-C
NSInteger floor = 1; // Create the GMSTileLayer GMSURLTileLayer *layer = [GMSURLTileLayer tileLayerWithURLConstructor:^NSURL * _Nullable(NSUInteger x, NSUInteger y, NSUInteger zoom) { NSString *url = [NSString stringWithFormat:@"https://www.example.com/floorplans/L%ld_%lu_%lu_%lu.png", (long)floor, (unsigned long)zoom, (unsigned long)x, (unsigned long)y]; return [NSURL URLWithString:url]; }]; // Display on the map at a specific zIndex layer.zIndex = 100; layer.map = mapView;
Subclass GMSSyncTileLayer to serve tiles as a UIImage
GMSSyncTileLayer 和 GMSTileLayer 是專門用於劃分子類別的抽象類別。您可以使用這些類別,將圖塊做為 UIImage 提供。以下範例說明如何透過子類別化 GMSSyncTileLayer,在部分地圖圖塊上算繪自訂圖片。
Swift
class TestTileLayer: GMSSyncTileLayer { override func tileFor(x: UInt, y: UInt, zoom: UInt) -> UIImage? { // On every odd tile, render an image. if (x % 2 == 1) { return UIImage(named: "australia") } else { return kGMSTileLayerNoTile } } }
Objective-C
@interface TestTileLayer : GMSSyncTileLayer @end @implementation TestTileLayer - (UIImage *)tileForX:(NSUInteger)x y:(NSUInteger)y zoom:(NSUInteger)zoom { // On every odd tile, render an image. if (x % 2 == 1) { return [UIImage imageNamed:@"australia"]; } else { return kGMSTileLayerNoTile; } } @end
To add the layer to your map, instantiate the object and set its map property.
Swift
let layer = TestTileLayer() layer.map = mapView
Objective-C
GMSTileLayer *layer = [[TestTileLayer alloc] init]; layer.map = mapView;
High DPI Tiles for Retina devices
您可以透過 GMSSyncTileLayer 或 GMSURLTileLayer,將 tileSize 設為 512,使用高 DPI 圖片。tileSize 屬性會指出傳回的圖塊圖片偏好顯示的像素數量,預設為 256,也就是非 Retina 裝置上 Google 地圖圖塊的維度。
如果要在高 DPI 裝置上顯示一般 DPI 圖塊,可以將 tileSize 設為 512,放大圖片。請注意,放大圖片可能會降低圖片品質,尤其是細線或文字。為獲得最佳效果,請將tileSize和圖片 DPI 設為與螢幕相符。在 Retina 裝置上顯示地圖時,如果使用 tileSize 為 512 的高 DPI 圖片,地圖看起來會最清晰;在非 Retina 裝置上顯示地圖時,如果使用一般圖片和預設的 tileSize 256,地圖看起來也會很清晰。
清除過時的圖塊
如果圖層提供的圖塊變成「過時」,則應在圖層上呼叫 clearTileCache 方法,強制重新整理。這會使系統重新載入此圖層的所有圖塊。
Swift
layer.clearTileCache()
Objective-C
[layer clearTileCache];