Как добиться плавного изменения размера MKCircleView в UIMapView при настройке NSSlider? Apple удалось сделать это в Найти друзей приложение при создании geofences (http://reviewznow.com/wp-content/uploads/2013/03/find-my-friends-location-alerts-01.jpg), так что, я думаю, это возможно в некотором роде. До сих пор я попытался следующие решения, но в результате очень «flickery»:Плавное изменение размера MKCircle
Первая попытка
Я добавил новый MKCircleView с обновленным радиусом и сразу после удаления одного, который был (как предлагаемый здесь MKOverlay not resizing smoothly), когда ползунок изменил значение. Я также пробовал наоборот: сначала удаляю оверлей, а затем добавляю новый, но с тем же результатом «мерцания».
- (void)sliderChanged:(UISlider*)sender
{
double radius = (sender.value * 100);
[self addCircleWithRadius:radius];
[mapView removeOverlays:[self.mapView.overlays firstObject]];
}
Вторая попытка
В связанный SO ответ, он предполагает, что NSOperation может быть использован для «поможет вам создать объекты, с которыми MKCircle быстрее» и, таким образом, делая изменения размера ровнее с использованием описанного выше способа добавления/удаление наложений, когда слайды меняют значение. Я сделал реализацию, где я начинаю новый поток всякий раз, когда изменяется ползунок. В каждом потоке я удаляю все старые наложения и добавляю новый с обновленной шкалой. Возможно, у него есть какая-то другая реализация, потому что, как я это делал, я все равно получаю такое же мерцание при смене слайдера.
- (void)sliderChanged:(UISlider*)sender
{
NSInvocationOperation *operation = [[NSInvocationOperation alloc] initWithTarget:self
selector:@selector(updateOverlayWithScale:)
object:[NSNumber numberWithFloat:sender.scale]];
[self.queue addOperation:operation];
}
Метод, который работает каждый поток I:
- (void)updateOverlayWithScale:(NSNumber *)scale
{
MKCircle *circle = [MKCircle circleWithCenterCoordinate:self.currentMapPin.coordinate
radius:100*[scale floatValue]];
[self.mapView performSelectorOnMainThread:@selector(removeOverlays:) withObject:self.mapView.overlays waitUntilDone:NO];
[self.mapView performSelectorOnMainThread:@selector(addOverlay:) withObject:circle waitUntilDone:NO];
}
Третья попытка
Я также попытался реализации мой собственный подкласс MKOverlayView, который привлекает сама основана на его шкале ценностей. Всякий раз, когда изменяется слайдер, я вызываю setNeedsDisplay и позволяю ему перерисовывать себя, но я получаю такое же мерцание.
- (void)sliderChanged:(UISlider*)sender
{
self.currentOverlayView.scale = sender.scale
[self.currentOverlayView setNeedsDisplay];
}
И в мой пользовательский вид наложения я реализую drawMapRect: zoomScale: InContext: (CGContextRef) контекст, как этот
- (void)drawMapRect:(MKMapRect)mapRect
zoomScale:(MKZoomScale)zoomScale
inContext:(CGContextRef)context
{
double radius = [(MKCircle *)[self overlay] radius];
radius *= self.scale;
// ... Create a rect using the updated radius and draw a circle inside it using CGContextAddEllipseInRect ...
}
Итак, у вас есть какие-нибудь идеи? Заранее спасибо!
я борюсь с этим тоже, как ты это сделал? –