检测bezier路径内的水龙头

bla*_*cos 11 core-graphics objective-c ios uibezierpath

我有一个UIView,它作为子视图添加到我的视图控制器.我在这个观点上画了一条更好的路径.我的drawRect实现如下

- (void)drawRect:(CGRect)rect
{
    CGContextRef context = UIGraphicsGetCurrentContext();
    UIBezierPath *bpath = [UIBezierPath bezierPath];

    [bpath moveToPoint:CGPointMake(50, 50)];
    [bpath addLineToPoint:CGPointMake(100, 50)];
    [bpath addLineToPoint:CGPointMake(100, 100)];
    [bpath addLineToPoint:CGPointMake(50, 100)];
    [bpath closePath];

    CGContextAddPath(context, bpath.CGPath);
    CGContextSetStrokeColorWithColor(context,[UIColor blackColor].CGColor);
    CGContextSetLineWidth(context, 2.5);
    CGContextStrokePath(context);
    UIColor *fillColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.5 alpha:0.7];
    [fillColor setFill];
    [bpath fill];
}
Run Code Online (Sandbox Code Playgroud)

我希望在这个bezier路径中检测tap,但不是在UIView内部和路径外部的点.例如,在这种情况下,如果我的触摸坐标是(10,10),则不应检测到它.我知道CGContextPathContainsPoint但是当触摸在路径内时它没有帮助.有没有办法检测bezier路径内的触摸事件?

foO*_*oOg 17

还有一个功能,CGPathContainsPoint()它可能是你的情况是有用的.

如果从superview获取手势点也要小心,测试时坐标可能不正确.您有一种方法可以将Point转换为特定视图的坐标系:

- (CGPoint)convertPoint:(CGPoint)point toView:(UIView *)view
- (CGPoint)convertPoint:(CGPoint)point fromView:(UIView *)view
Run Code Online (Sandbox Code Playgroud)


Avt*_*Avt 8

试试UIBezierPath的方法:

func contains(_ point: CGPoint) -> Bool
Run Code Online (Sandbox Code Playgroud)

返回一个布尔值,指示接收器包含的区域是否包含指定的点.


Abh*_*ore 6

在swift中检测bezier路径内的水龙头: -

最新的swift很简单,按照这些步骤操作即可获得UIBezierPath触摸事件.

步骤1: - 在您添加UIBeizerPath的视图上初始化点击事件.

///Catch layer by tap detection let tapRecognizer:UITapGestureRecognizer = UITapGestureRecognizer.init(target: self, action: #selector(YourClass.tapDetected(_:))) viewSlices.addGestureRecognizer(tapRecognizer)

第2步: - 制作"tapDetected"方法

  //MARK:- Hit TAP
public func tapDetected(tapRecognizer:UITapGestureRecognizer){
    let tapLocation:CGPoint = tapRecognizer.locationInView(viewSlices)
    self.hitTest(CGPointMake(tapLocation.x, tapLocation.y))


}
Run Code Online (Sandbox Code Playgroud)

第3步: - 制作"hitTest"最终方法

  public func hitTest(tapLocation:CGPoint){
        let path:UIBezierPath = yourPath
        if path.containsPoint(tapLocation){
            //tap detected do what ever you want ..;)
        }else{
             //ooops you taped on other position in view
        }
    }
Run Code Online (Sandbox Code Playgroud)



更新:Swift 4

步骤1: - 在您添加UIBeizerPath的视图上初始化点击事件.

///Catch layer by tap detection
let tapRecognizer = UITapGestureRecognizer(target: self, action: #selector(YourClass.tapDetected(tapRecognizer:)))
viewSlices.addGestureRecognizer(tapRecognizer)
Run Code Online (Sandbox Code Playgroud)

第2步: - 制作"tapDetected"方法

public func tapDetected(tapRecognizer:UITapGestureRecognizer){
    let tapLocation:CGPoint = tapRecognizer.location(in: viewSlices)
    self.hitTest(tapLocation: CGPoint(x: tapLocation.x, y: tapLocation.y))
}
Run Code Online (Sandbox Code Playgroud)

第3步: - 制作"hitTest"最终方法

private func hitTest(tapLocation:CGPoint){
    let path:UIBezierPath = yourPath

    if path.contains(tapLocation){
        //tap detected do what ever you want ..;)
    }else{
        //ooops you taped on other position in view
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 没问题!谢谢你的好答案!^^ (2认同)