我是iOS开发的新手,我正在努力从iOS6移植一些涉及使用MKOverlay
的代码。
当叠加半径或坐标发生变化时,渲染器应相应地实时更新显示。
这部分有效,但是如果我拖动叠加太多,它会到达某个边界并且渲染会被切断。我找不到任何有关此行为的文档或帮助。
在CircleOverlayRenderer
课程中:
- (id)initWithOverlay:(id<MKOverlay>)overlay
{
self = [super initWithOverlay:overlay];
if (self) {
CircleZone *bOverlay = (CircleZone *)overlay;
[RACObserve(bOverlay, coordinate) subscribeNext:^(id x) {
[self setNeedsDisplay];
}];
[RACObserve(bOverlay, radius) subscribeNext:^(id x) {
[self setNeedsDisplay];
}];
}
return self;
}
- (void)drawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale inContext:(CGContextRef)context
{
CGRect rect = [self rectForMapRect:[self.overlay boundingMapRect]];
CGContextSaveGState(context);
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextSetFillColorSpace(context, colorSpace);
CGColorSpaceRelease(colorSpace);
CGContextSetBlendMode(context, kCGBlendModeCopy);
CGContextSetFillColor(context, color);
CGContextSetAllowsAntialiasing(context, YES);
// outline
{
CGContextSetAlpha(context, 0.8);
CGContextFillEllipseInRect(context, rect);
}
// red
{
CGContextSetAlpha(context, 0.5);
CGRect ellipseRect = CGRectInset(rect, 0.01 * rect.size.width / 2, 0.01 * rect.size.height / 2);
CGContextFillEllipseInRect(context, ellipseRect);
}
CGContextRestoreGState(cox);
}
在CircleOverlay
课程中:
- (MKMapRect)boundingMapRect
{
MKMapPoint center = MKMapPointForCoordinate(self.coordinate);
double mapPointsPerMeter = MKMapPointsPerMeterAtLatitude(self.coordinate.latitude);
double mapPointsRadius = _radius * mapPointsPerMeter;
return MKMapRectMake(center.x - mapPointsRadius, center.y - mapPointsRadius,
mapPointsRadius * 2.0, mapPointsRadius * 2.0);
}
以下是我看到的问题的一些屏幕截图:
拖动叠加太多时出现问题:
更改半径时出现问题:
如果我继续缩小地图,问题就会消失。地图图块刷新后,叠加层不再被切断...
如果有人有类似问题,请帮助我,这让我发疯了!
答案 0 :(得分:1)
查看radius
示例,鉴于其裁剪方式,它让我怀疑boundingMapRect
。看看boundingMapRect
实施,依赖MKMapPointsPerMeterAtLatitude
(特别是当你在大片地区看时)令人担忧。例如,如果您试图找出距其他坐标10米的坐标位置,那么该函数非常有用,但是当查看非常大的跨度时,它并不总是很好。
相反,我可能会建议获得圆圈所在位置MKCoordinateRegion
的内容,然后将其转换为MKMapRect
。简单的实现可能如下所示:
- (MKMapRect)boundingMapRect {
MKCoordinateRegion region = MKCoordinateRegionMakeWithDistance(self.coordinate, _radius * 2, _radius * 2);
CLLocationCoordinate2D upperLeftCoordinate = CLLocationCoordinate2DMake(region.center.latitude - region.span.latitudeDelta / 2, region.center.longitude - region.span.longitudeDelta / 2);
CLLocationCoordinate2D lowerRightCoordinate = CLLocationCoordinate2DMake(region.center.latitude + region.span.latitudeDelta / 2, region.center.longitude + region.span.longitudeDelta / 2);
MKMapPoint upperLeft = MKMapPointForCoordinate(upperLeftCoordinate);
MKMapPoint lowerRight = MKMapPointForCoordinate(lowerRightCoordinate);
return MKMapRectMake(MIN(upperLeft.x, lowerRight.x),
MIN(upperLeft.y, lowerRight.y),
ABS(upperLeft.x - lowerRight.x),
ABS(upperLeft.y - lowerRight.y));
}
你必须对此进行调整以确保它优雅地处理第180个子午线的交叉以及当圆圈包含北极时,但它说明了基本思想:为圆圈获取MKCoordinateRegion
然后转换那到MKMapRect
。