iOS/MapKit缓存管理问题与MKTileOverlay和PINCache库

iOS/MapKit缓存管理问题与MKTileOverlay和PINCache库,ios,caching,mapkit,mktileoverlay,Ios,Caching,Mapkit,Mktileoverlay,我使用MapKit通过在地图视图上添加MKTileOverlay来创建卫星和雷达动画 使用UISlider和PlayButton,我可以创建一个动画,比如通过播放mkOverlayrender的alpha(根据滑块的位置将其设置为0或0.75)来创建GIF 动画非常流畅,我所有的卫星和雷达图块都正确加载到mapView上 我在缓存管理方面遇到了一个问题 我意识到MapKit没有为我的tileOverlay使用缓存,这就是为什么我使用库PINCache来保存我的Tile,这样它就不会在每次播放动画

我使用MapKit通过在地图视图上添加MKTileOverlay来创建卫星和雷达动画

使用UISlider和PlayButton,我可以创建一个动画,比如通过播放mkOverlayrender的alpha(根据滑块的位置将其设置为0或0.75)来创建GIF

动画非常流畅,我所有的卫星和雷达图块都正确加载到mapView上

我在缓存管理方面遇到了一个问题

我意识到MapKit没有为我的tileOverlay使用缓存,这就是为什么我使用库PINCache来保存我的Tile,这样它就不会在每次播放动画时请求和下载图像

我的实现:

我重写方法
URLForTilePath
,以便构建我的URL以获取我的平铺图像

- (NSURL *)URLForTilePath:(MKTileOverlayPath)path{

double latMin, latMax, longMin, longMax;
path.contentScaleFactor = 1.0;

NSMutableArray *result = [[NSMutableArray alloc] init];
result = getBBoxForCoordinates((int)path.x, (int)path.y, (int)path.z);

longMin = [[result objectAtIndex:0] doubleValue];
latMin = [[result objectAtIndex:1] doubleValue];
longMax = [[result objectAtIndex:2] doubleValue];
latMax = [[result objectAtIndex:3] doubleValue];

NSString *finalURL = self.url;
finalURL = [finalURL stringByReplacingOccurrencesOfString:@"DATE"
                                     withString:_date];

NSString *bbox = [NSString stringWithFormat:@"bbox=%f,%f,%f,%f", longMin, latMin, longMax, latMax];
finalURL = [finalURL stringByReplacingOccurrencesOfString:@"BBOX"
                                     withString:bbox];

return [NSURL URLWithString:finalURL];
}
调用
URLForTilePath
的关键方法是我对
loadTileAtPath
的实现:

    - (void)loadTileAtPath:(MKTileOverlayPath)path
                result:(void (^)(NSData *data, NSError *error))result
{
    if (!result)
    {
        return;
    }

    NSString *str = self.isRadar == true ? [NSString stringWithFormat:@"Radar%@", self.date] : [NSString stringWithFormat:@"Satellite%@", self.date];
    NSData *cachedData = [[PINCache sharedCache] objectForKey:str];
    if (cachedData)
    {
        result(cachedData, nil);
    }
    else
    {
        NSURLRequest *request = [NSURLRequest requestWithURL:[self URLForTilePath:path]];
        [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
            NSString *str = self.isRadar == true ? [NSString stringWithFormat:@"Radar%@", self.date] : [NSString stringWithFormat:@"Satellite%@", self.date];
            [[PINCache sharedCache] setObject:data forKey:str block:nil];
            result(data, connectionError);
        }];
    }
}
基本上,我想要实现的是:

  • 检查是否有缓存数据,如果有,则获取对象
  • 如果没有,我会请求使用
    URLForTilePath
    提供的URL下载互动程序
  • 然后我将对象设置为缓存
  • 字符串
    str
    是缓存管理的密钥
  • 我有两个重要的值来排序和区分瓷砖、类型(雷达或卫星、不同的图像、不同的URL)和日期
我可以看到缓存管理正在工作,覆盖层的渲染速度更快,但我遇到的主要问题是,它无法在相应的坐标下加载和构建分幅

我的地图视图就像一个错误构建的世界拼图


用我的代码,你能看到我做错了什么吗?

我找不到mapKit内存/缓存管理问题的原因

我决定尝试谷歌地图,它花了我不到2小时的时间来实现它,结果是惊人的

我想通过使用苹果解决方案来尊重苹果社区,但谷歌地图给了我更多的表现