我需要在所有其他注释之上绘制当前用户注释(蓝点)。现在它正在我的其他注释下面被隐藏起来。我想调整此注释视图的z-index(蓝点)并将其置于顶部,是否有人知道如何?
更新 所以我现在可以获得MKUserLocationView的处理,但是我该如何推进呢?
- (void) mapView:(MKMapView *)aMapView didAddAnnotationViews:(NSArray *)views {
for (MKAnnotationView *view in views) {
if ([[view annotation] isKindOfClass:[MKUserLocation class]]) {
// How do I bring this view to the front of all other annotations?
// [???? bringSubviewToFront:????];
}
}
}
答案 0 :(得分:34)
在Paul Tiarks的帮助下,最后使用下面列出的代码使其工作。我遇到的问题是MKUserLocation注释首先被添加到地图之前,所以当你添加其他注释时,它们的顺序似乎是随机的,并且最终仍然会在MKUserLocation注释之上。为了解决这个问题,我必须将所有其他注释移到后面,并将MKUserLocation注释移到前面。
- (void) mapView:(MKMapView *)aMapView didAddAnnotationViews:(NSArray *)views
{
for (MKAnnotationView *view in views)
{
if ([[view annotation] isKindOfClass:[MKUserLocation class]])
{
[[view superview] bringSubviewToFront:view];
}
else
{
[[view superview] sendSubviewToBack:view];
}
}
}
更新:您可能需要添加以下代码,以确保在将其从地图的可视区域滚动时在顶部绘制蓝点。
- (void)mapView:(MKMapView *)mapView regionDidChangeAnimated:(BOOL)animated
{
for (NSObject *annotation in [mapView annotations])
{
if ([annotation isKindOfClass:[MKUserLocation class]])
{
NSLog(@"Bring blue location dot to front");
MKAnnotationView *view = [mapView viewForAnnotation:(MKUserLocation *)annotation];
[[view superview] bringSubviewToFront:view];
}
}
}
答案 1 :(得分:25)
另一个解决方案: 在:
中设置注释视图图层的zPosition(annotationView.layer.zPosition
)
- (void)mapView:(MKMapView *)mapView didAddAnnotationViews:(NSArray *)views;
答案 2 :(得分:9)
该线程的官方答案是错误的......使用zPosition确实是最好的方法,使用regionDidChangeAnimated是最快的...
否则你会在地图上的许多注释遭受巨大的性能影响(因为每次帧的更改都会重新扫描所有注释)。并一直在测试......
所以在创建注释视图时(或在didAddAnnotationViews中)设置: self.layer.zPosition = -1; (低于所有其他人)
正如yuf所指出的那样: 这使得引脚覆盖了其他引脚的标注 - yuf于2013年12月5日20:25
即。注释视图将显示在其他引脚下方。
要修复,只需在选择时将zPosition重新设置为0
-(void) mapView:(MKMapView*)mapView didSelectAnnotationView:(MKAnnotationView*)view {
if ([view isKindOfClass:[MyCustomAnnotationView class]])
view.layer.zPosition = 0;
...
}
-(void) mapView:(MKMapView*)mapView didDeselectAnnotationView:(MKAnnotationView*)view {
if ([view isKindOfClass:[MyCustomAnnotationView class]])
view.layer.zPosition = -1;
...
}
答案 3 :(得分:2)
尝试获取对用户位置标注的引用(可能在mapView: didAddAnnotationViews:
中),然后在添加完所有注释后将该视图放到mapView的前面。
答案 4 :(得分:2)
我知道这是一篇过时的文章,但是该问题仍然适用,您在将其输入到您喜欢的搜索引擎中时会在这里结束。
从iOS 14,Apple introduced a zPriority
property to MKAnnotationView
开始。您可以使用它来使用predefined constants或float来为注释设置z-index。
同样,Apple使得我们最终可以自己为用户位置创建视图,并提供MKUserLocationView
作为MKAnnotationView
的子类。
From the documentation for MKUserLocationView
:
如果您要指定其他配置,例如
zPriority
, 直接创建此注释视图。要显示注释视图, 从mapView(_:viewFor:)
返回实例。
以下代码段显示了如何完成此操作(将代码添加到您的MKMapViewDelegate
):
func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
// Alter the MKUserLocationView (iOS 14+)
if #available(iOS 14.0, *), annotation is MKUserLocation {
// Try to reuse the existing view that we create below
let reuseIdentifier = "userLocation"
if let existingView = mapView.dequeueReusableAnnotationView(withIdentifier: reuseIdentifier) {
return existingView
}
let view = MKUserLocationView(annotation: annotation, reuseIdentifier: reuseIdentifier)
view.zPriority = .max // Show user location above other annotations
view.isEnabled = false // Ignore touch events and do not show callout
return view
}
// Create views for other annotations or return nil to use the default representation
return nil
}
请注意,默认情况下,用户位置注释在点击时会显示一个标注。现在用户位置已经覆盖了其他注释,您可能需要禁用它,这可以通过将.isEnabled
设置为false
来在代码中完成。
答案 5 :(得分:1)
斯威夫特3:
internal func mapView(_ mapView: MKMapView, didAdd views: [MKAnnotationView]) {
for annotationView in views {
if annotationView.annotation is MKUserLocation {
annotationView.bringSubview(toFront: view)
return
}
annotationView.sendSubview(toBack: view)
}
}
答案 6 :(得分:0)
以下是使用谓词执行此操作的方法。我认为它应该更快
NSPredicate *userLocationPredicate = [NSPredicate predicateWithFormat:@"class == %@", [MKUserLocation class]];
NSArray* userLocation = [[self.mapView annotations] filteredArrayUsingPredicate:userLocationPredicate];
if([userLocation count]) {
NSLog(@"Bring blue location dot to front");
MKAnnotationView *view = [self.mapView viewForAnnotation:(MKUserLocation *)[userLocation objectAtIndex:0]];
[[view superview] bringSubviewToFront:view];
}
答案 7 :(得分:0)
使用Underscore.m
_.array(mapView.annotations).
filter(^ BOOL (id<MKAnnotation> annotation) { return [annotation
isKindOfClass:[MKUserLocation class]]; })
.each(^ (id<MKAnnotation> annotation) { [[[mapView
viewForAnnotation:annotation] superview] bringSubviewToFront:[mapView
viewForAnnotation:annotation]]; });
答案 8 :(得分:0)
只需使用.layer.anchorPointZ
属性。
示例:
func mapView(_ mapView: MKMapView, didAdd views: [MKAnnotationView]) {
views.forEach {
if let _ = $0.annotation as? MKUserLocation {
$0.layer.anchorPointZ = 0
} else {
$0.layer.anchorPointZ = 1
}
}
}
这里有参考文献https://developer.apple.com/documentation/quartzcore/calayer/1410796-anchorpointz