2016-06-28 27 views
2

マップベースのアプリケーションで作業しています。動的コンテンツを表示するにはMKTileOverlayを使用しました。新しい情報が到着したときに、特定のタイルを再ロードする必要が生じることがあります。MKTileOverlay:特定のタイルまたは領域を再読み込みする方法

メインスレッドでoverlayRenderer.setNeedsDisplayInMapRect(mapRect)を呼び出そうとしましたが、明らかに私のケースではマップの再描画が実行されません。今のところ唯一のアプローチはoverlayRenderer.reloadData()です。しかし、これにより(特定の領域のみではなく)コンテンツ全体が再読み込みされ、ビュー内でちらつきが発生するため、これは私の選択肢ではありません。

誰でもこれに関するアドバイスをいただけますか?ありがとう&乾杯。

+0

このことができますかどうかを確認:http://stackoverflow.com/questions/10128447/setneedsdisplayinmaprect-doesnt-trigger-newを-drawmaprect-call – user1046037

+1

ありがとうございます。私はこの記事で述べたアプローチを試しました。それらのどれも私のために働かない。 –

答えて

2

最後に私はそれを理解しました。実際、オーバーレイは更新されません。setNeedsDisplayInMapRectが原因ではありません。いくつかのチェックの後、私はsetNeedsDisplayInMapRectが実際にdrawMapRect:zoomScale:inContext:の実行を引き起こしていることを発見しましたが、何とかデフォルトの再描画によって同じタイルイメージが生成されます。私はこれがMKTileOverlayRenderの内部キャッシュのためかもしれないと思います。

私のためのソリューションはMKTileOverlayRenderをサブクラス化することで、新しいクラスで:

override func canDrawMapRect(mapRect: MKMapRect, zoomScale: MKZoomScale) -> Bool { 

    let tilePath = self.tilePathForMapRect(mapRect, andZoomScale: zoomScale) 
    let tilePathString = stringForTilePath(tilePath) 
    if let _ = self.cache.objectForKey(tilePathString) { 
     return true 
    } else { 
     let tileOverlay = self.overlay as! MKTileOverlay 
     tileOverlay.loadTileAtPath(tilePath, result: { 
      data, error in 
      if error == nil && data != nil { 
       if let image = UIImage(data: data!) { 
        self.cache.setObject(image, forKey: tilePathString) 
        self.setNeedsDisplayInMapRect(mapRect, zoomScale: zoomScale) 
       } 
      } 
     }) 

     return false 
    } 
} 

override func drawMapRect(mapRect: MKMapRect, zoomScale: MKZoomScale, inContext context: CGContext) { 
    let tilePath = self.tilePathForMapRect(mapRect, andZoomScale: zoomScale) 
    let tilePathString = stringForTilePath(tilePath) 

    if let image = self.cache.objectForKey(tilePathString) as? UIImage { 
     CGContextDrawImage(context, self.rectForMapRect(mapRect), image.CGImage) 
    } else { 
     super.setNeedsDisplayInMapRect(mapRect, zoomScale: zoomScale) 
    } 

    self.cache.removeObjectForKey(tilePathString) 
} 
関連する問題