屏幕外iOS 6 MKMapViews和UIViewPrintFormatter - 让他们及时渲染?

时间:2013-02-01 10:04:25

标签: ios mkmapview mapkit airprint uiprintformatter

我有兴趣打印一些不属于视图层次结构的MKMapView,并且仅在用户点击Print时创建。

似乎以下情况属实:

  1. Offscreen MKMapViews根本不渲染。
  2. 打印MKMapView会打印它呈现的当前状态。
  3. 因此,为了打印我的地图视图,我需要将它们放入视图层次结构中。幸运的是,从实验开始,我似乎可以在屏幕上将一堆地图视图放在彼此的前面,它们仍然可以渲染。

    我的主要问题是我怎么知道他们已经渲染了?如果我在视图层次结构中放置地图视图后立即触发打印命令,它们将打印部分渲染,缺少位,如下所示。我想等到他们完成加载,然后运行打印作业。 (如果在打印页面在屏幕上时可以在后台加载,那就更好了,然后我只是在用户点击打印后给用户一个进度条,直到地图加载完毕。)

    (下图:显示如果打印部分加载的地图视图会发生什么情况的图像。)

    Printout

    我的第二个问题是:是否有更好的方法来打印多个地图视图?将所有内容都放到视图层次结构中并不是很好 - 它限制了我可以使用的最大大小,这意味着我有很多笨拙的代码来处理子视图。

2 个答案:

答案 0 :(得分:2)

您应该在地图视图上设置一个委托( MKMapViewDelegate )并实现 mapViewDidFinishLoadingMap:,这将在地图视图加载完必要的图块时调用。 / p>

答案 1 :(得分:0)

当地图视图不一定在屏幕上可见时,我遇到了将MKMapView渲染到图像的类似问题。我发现以下解决方案适合我。我希望这可以帮助别人。基本上,它确保地图有一个窗口。在ios6.0中,你需要给它一个窗口以便让它加载地图,然后在完成加载时,你在渲染之前等待一段时间以给瓦片一个加载的机会。在ios 5.0中,你不需要等待didfinishload,你只需确保地图在渲染功能中有一个窗口,并且瓷砖将是可见的。

{
      if ([@"5.9.9" compare:[UIDevice currentDevice].systemVersion options:NSNumericSearch] == NSOrderedAscending) {
          // actualVersion is lower than the requiredVersion 
          self.oldSuperview = nil;
          if (self.map.window == nil) {
        self.oldSuperview = self.map.superview;
              [[[[UIApplication sharedApplication] delegate] window] insertSubview:self.map atIndex:0];
          }
      } else { 
         [self performSelector:@selector(renderMap) withObject:nil afterDelay:0.10];
     }

}

-(void) renderMap {

    //map will only render tiles if it has a window, so we need to add it to
    //the main window if it does not have a window.

    if ([@"5.9.9" compare:[UIDevice currentDevice].systemVersion options:NSNumericSearch] != NSOrderedAscending) {
        if (self.map.window == nil) {
            self.oldSuperview = self.map.superview;
            [[[[UIApplication sharedApplication] delegate] window] addSubview:self.map];
        }
    }


    // Generate the image centred
    UIGraphicsBeginImageContextWithOptions(self.map.bounds.size, NO, 0.0);

    [self.map.layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage *theImage = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();


    // Save the image here


    if ([@"5.9.9" compare:[UIDevice currentDevice].systemVersion options:NSNumericSearch] != NSOrderedAscending) {

        if (self.oldSuperview) {
            [self.map removeFromSuperview];
            [self.oldSuperview addSubview:self.map];
            self.oldSuperview = nil;
        }

    }

}

}



-(void) cleanMap {
      if (self.map.superview == [[[UIApplication sharedApplication] delegate] window]) {

          if (oldSuperview) { 
              [oldSuperview addSubview:self.map];
              self.oldSuperview = nil;
          }
      }
 }
 -(void) mapViewDidFinishLoadingMap:(MKMapView *)mapView {

if ([@"5.9.9" compare:[UIDevice currentDevice].systemVersion options:NSNumericSearch] == NSOrderedAscending) { 
    if (oldSuperview) {

        [self performSelector:@selector(renderMap) withObject:nil afterDelay:1.10];
        [self performSelector:@selector(cleanMap) withObject:nil afterDelay:1.41];
    } else {
        [self renderMap];
    }
} else {
    [self renderMap];
}

 }