在 MKMapView 中使用 UILongPressGestureRecognizer 和可拖动的 MKPinAnnotationView

发布于 2024-12-25 22:58:37 字数 2656 浏览 2 评论 0原文

我在将 UILongPressGestureRecognizer 与可拖动的 MKPinAnnotationView 一起使用时遇到问题。

我试图产生的行为类似于地图应用程序。

  1. 可以拖动图钉。
  2. 当长按/点击时,图钉就会掉落。

但是,我在 MKPinAnnotationView 框架之外识别长按时遇到问题。如果 Pin 不可拖动,则长按手势放下 Pin 可以正常工作。但是,当图钉可拖动时,我无法识别长按手势识别器,以便我可以放下图钉。

有什么想法吗?

顺便说一句,我尝试为长按识别器设置委托,以便

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
    return YES;
}

在这种情况下,长按手势被识别并且引脚被放下,但引脚的拖动不再起作用。

MapView 的片段(MKMapView 的子类)

- (id)initWithFrame:(CGRect)frame {

    if (self = [super initWithFrame:frame]) {

    // init the gesture recognizer
        UILongPressGestureRecognizer* lpgr = [[UILongPressGestureRecognizer alloc] 
            initWithTarget:self action:@selector(handleLongPress:)];
        lpgr.minimumPressDuration = 0.5f; //user needs to press for 2 seconds
        lpgr.delegate = self;
        [self addGestureRecognizer:lpgr];
        [lpgr release];

        //add some initial annotation
        Marker *_annotation = [[Marker alloc] initWithCoordinate:_location];
        [_annotation titleWithString:@"some title"];
        [self addAnnotation:_annotation];

    }

    return self;

}

- (void)handleLongPress:(UIGestureRecognizer *)gestureRecognizer
{
    if (gestureRecognizer.state != UIGestureRecognizerStateBegan)
    {
        return;
    }

    CGPoint touchPoint = [gestureRecognizer locationInView:self];   
    CLLocationCoordinate2D touchMapCoordinate = [self convertPoint:touchPoint toCoordinateFromView:self];

    // add marker to self-map
    // Marker is subclass of MKAnnotation
    Marker *_annotation = [[Marker alloc] initWithCoordinate:_location];
    [_annotation titleWithString:@"some title"];
    [self addAnnotation:_annotation];

}


- (MKAnnotationView *)mapView:(MKMapView *)mView viewForAnnotation:(id<MKAnnotation>) annotation {

    if([annotation isMemberOfClass:[Marker class]] ) {

        // use MKPinAnnotationView for the view
        MKPinAnnotationView *_pin = (MKPinAnnotationView *) [mView dequeueReusableAnnotationViewWithIdentifier:@"spot_pin"];

        if (_pin == nil)
        {
            _pin = [[[MKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:@"spot_pin"] autorelease];
        }
        else
        {
            _pin.annotation = annotation;
        }

        [_pin setDraggable:YES];
        [_pin setSelected:YES animated:YES];
        [_pin setCanShowCallout:YES];

        return _pin;

    } else {

        return nil;

    }

}

I have having problems using a UILongPressGestureRecognizer together a draggable MKPinAnnotationView.

The behaviour I am trying to produce is similar to the Maps App.

  1. The pin can be dragged.
  2. When there is a long press/ tap, a pin is dropped.

However, I have problems having the long press being recognized outside the frame of the MKPinAnnotationView. The long press gesture to drop the pin works fine if the Pin is not draggable. When the pin is draggable however, I can't get the long press gesture recognizer to be recognized so that I can drop pin.

Any ideas?

By the way, I have tried to set the delegate for the long press recognizer so that

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
    return YES;
}

In this case, the long press gestures are recognized and the pins are dropped, but the dragging of the pin no longer works.

Snippets of the MapView (a subclass of MKMapView)

- (id)initWithFrame:(CGRect)frame {

    if (self = [super initWithFrame:frame]) {

    // init the gesture recognizer
        UILongPressGestureRecognizer* lpgr = [[UILongPressGestureRecognizer alloc] 
            initWithTarget:self action:@selector(handleLongPress:)];
        lpgr.minimumPressDuration = 0.5f; //user needs to press for 2 seconds
        lpgr.delegate = self;
        [self addGestureRecognizer:lpgr];
        [lpgr release];

        //add some initial annotation
        Marker *_annotation = [[Marker alloc] initWithCoordinate:_location];
        [_annotation titleWithString:@"some title"];
        [self addAnnotation:_annotation];

    }

    return self;

}

- (void)handleLongPress:(UIGestureRecognizer *)gestureRecognizer
{
    if (gestureRecognizer.state != UIGestureRecognizerStateBegan)
    {
        return;
    }

    CGPoint touchPoint = [gestureRecognizer locationInView:self];   
    CLLocationCoordinate2D touchMapCoordinate = [self convertPoint:touchPoint toCoordinateFromView:self];

    // add marker to self-map
    // Marker is subclass of MKAnnotation
    Marker *_annotation = [[Marker alloc] initWithCoordinate:_location];
    [_annotation titleWithString:@"some title"];
    [self addAnnotation:_annotation];

}


- (MKAnnotationView *)mapView:(MKMapView *)mView viewForAnnotation:(id<MKAnnotation>) annotation {

    if([annotation isMemberOfClass:[Marker class]] ) {

        // use MKPinAnnotationView for the view
        MKPinAnnotationView *_pin = (MKPinAnnotationView *) [mView dequeueReusableAnnotationViewWithIdentifier:@"spot_pin"];

        if (_pin == nil)
        {
            _pin = [[[MKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:@"spot_pin"] autorelease];
        }
        else
        {
            _pin.annotation = annotation;
        }

        [_pin setDraggable:YES];
        [_pin setSelected:YES animated:YES];
        [_pin setCanShowCallout:YES];

        return _pin;

    } else {

        return nil;

    }

}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

街角迷惘 2025-01-01 22:58:37

好的,伙计们,我解决了。

显然,当我子类化 MKMapView 后,我还添加了一个方法 handleLongPress。这个方法显然干扰了MKMapView的handleLongPress方法。

只需将我的handleLongPress选择器更改为不同的名称(例如handleLongPress2)即可使其像地图应用程序一样工作。

    UILongPressGestureRecognizer* lpgr = [[UILongPressGestureRecognizer alloc] 
        initWithTarget:self action:@selector(handleLongPress2:)];

Ok guys, I solved it.

Apparently when after I subclassed MKMapView, I also added a method handleLongPress. This method apparently interfered with the handleLongPress method of the MKMapView.

Just by changing my handleLongPress selector to a different name like handleLongPress2 will make it work like the Maps app.

    UILongPressGestureRecognizer* lpgr = [[UILongPressGestureRecognizer alloc] 
        initWithTarget:self action:@selector(handleLongPress2:)];
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文