Creating an MKMapSnapshotter with an MKPolylineRen

2019-02-16 13:27发布

I thought iOS 7's MKMapSnapshotters would be a simple way to take a snapshot of an MKMapView, the benefit is that you can do it without loading the map into view. Even though it seems like more work to add pins and overlays (because of the need for core graphics). The WWDC videos give a very good example of creating an MKMapSnapshotter with adding an MKAnnotationView.

However, for someone with not a lot of core graphics experience it's not really obvious how you create an MKMapSnapshotter from an MKPolylineRenderer.

I have tried to do this, but the path is inaccurate. It draws about 10% of the line accurately, but then draws the rest of the path straight.

Here's my code:

MKMapSnapshotter *snapshotter = [[MKMapSnapshotter alloc] initWithOptions:snapshotOptions];

[snapshotter startWithQueue:dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
          completionHandler:^(MKMapSnapshot *snapshot, NSError *error)
{
            if (error == nil)
            {
                UIImage *mapSnapshot = [snapshot image];

                UIGraphicsBeginImageContextWithOptions(mapSnapshot.size,
                                                       YES,
                                                       mapSnapshot.scale);

                [mapSnapshot drawAtPoint:CGPointMake(0.0f, 0.0f)];

                CGContextRef context = UIGraphicsGetCurrentContext();

                //Draw the points from the MKPolylineRenderer in core graphics for mapsnapshotter...
                MKPolylineRenderer *overlay = (MKPolylineRenderer *)[self.mapView rendererForOverlay:[_mapView.overlays lastObject]];

                if (overlay.path)
                {
                    CGFloat zoomScale = 3.0;

                    [overlay applyStrokePropertiesToContext:context
                                                atZoomScale:zoomScale];

                    CGContextAddPath(context, overlay.path);
                    CGContextSetLineJoin(context, kCGLineJoinRound);
                    CGContextSetLineCap(context, kCGLineCapRound);
                    CGContextStrokePath(context);
                }

                UIImage *pathImage = UIGraphicsGetImageFromCurrentImageContext();

                [map addMapIcon:pathImage];
                UIGraphicsEndImageContext();
            }
}];

Does anyone have a good workable example on how to do this please?

1条回答
【Aperson】
2楼-- · 2019-02-16 13:55

Just had the same problem, this code seems to work:

UIImage * res = nil;
UIImage * image = snapshot.image;

UIGraphicsBeginImageContextWithOptions(image.size, YES, image.scale);
[image drawAtPoint:CGPointMake(0, 0)];

CGContextRef context = UIGraphicsGetCurrentContext();

CGContextSetStrokeColorWithColor(context,  [COLOR_FLASHBLUE CGColor]);
CGContextSetLineWidth(context,2.0f);
CGContextBeginPath(context);

CLLocationCoordinate2D coordinates[[polyline pointCount]];
[polyline getCoordinates:coordinates range:NSMakeRange(0, [polyline pointCount])];

for(int i=0;i<[polyline pointCount];i++)
{
    CGPoint point = [snapshot pointForCoordinate:coordinates[i]];

    if(i==0)
    {
        CGContextMoveToPoint(context,point.x, point.y);
    }
    else{
        CGContextAddLineToPoint(context,point.x, point.y);

    }
}

CGContextStrokePath(context);

res = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
查看更多
登录 后发表回答