Swift:为什么在touchesBegan()中引用UIView的帧大小为(0.0,0.0)?

时间:2016-02-14 07:50:21

标签: ios swift uiview core-graphics

我只是想在一个愚蠢的iOS应用程序中进行简单的实验,我想绘制轴作为参考,而可拖动的UIImageView移动到UIView。问题是,当我可以touchesBegan()方法时,绘制轴的引用UIView的帧大小(0.0,0.0),我得到这个错误:

Feb 14 08:44:08 Fishmeter[30272] <Error>: CGContextSetRGBStrokeColor: invalid context 0x0. If you want to see the backtrace, please set CG_CONTEXT_SHOW_BACKTRACE environmental variable.

这是我的可拖动UIImageView的代码:

class PinImageView: UIImageView {
  var viewForAxis:AxisView!

  ...
  init(imageIcon: UIImage?, location:CGPoint, father:UIImageView, name:String, axisView:AxisView) {
    ...
    self.viewForAxis = axisView
    print(self.viewForAxis.frame.size)
    ...
  }

   override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) {
    if let touch: UITouch = touches.first {
        print(self.viewForAxis.frame.size)
        self.viewForAxis.hidden = false
        self.viewForAxis.pin = self
        //self.viewForAxis.setNeedsDisplay()
        self.viewForAxis.drawAxis(CGPointMake(self.center.x, self.viewForAxis.frame.origin.y), to: (CGPointMake(self.center.x, self.viewForAxis.frame.origin.y + self.viewForAxis.frame.height)))

    }
  }
}

print()的第一个(303.0, 414.0)内,touchesBegan()(0.0, 0.0)内,它变为AxisView然后我收到了该错误。 课程class AxisView: UIView { var pin:PinImageView? func drawAxis(from:CGPoint, to:CGPoint) { let context = UIGraphicsGetCurrentContext() switch (self.pin!.id) { case "redPinA","redPinB": CGContextSetRGBStrokeColor(context, 1.0, 0.0, 0.0, 1.0) break case "bluePinA, bluePinB": CGContextSetRGBStrokeColor(context, 0.0, 0.0, 1.0, 1.0) break default: break } /* line width of axes */ CGContextSetLineWidth(context, 0.5) /* draw vertical axis inside magnifier */ CGContextMoveToPoint(context, from.x, from.y) CGContextAddLineToPoint(context, to.x, to.y) /* draw horizontal axis inside magnifier */ //CGContextMoveToPoint(context, self.zoomedPoint!.x - (self.frame.size.width / 2), self.zoomedPoint!.y) //CGContextAddLineToPoint(context, self.zoomedPoint!.x + (self.frame.size.width / 2), self.zoomedPoint!.y) CGContextStrokePath(context) } /*override func drawRect(rect: CGRect) { if (pin != nil) { self.drawAxis(CGPointMake((self.pin?.center.x)!, self.frame.origin.y), to: CGPointMake(self.pin!.center.x, self.frame.origin.y + self.frame.height)) } }*/ } 是:

drawRect()

这样做的正确方法是什么?正如您从评论中看到的那样,我也尝试将所有内容放在setNeedsDisplay()方法中,但self.view.addSubview(self.axisView) self.axisView.hidden = true self.redPinA = PinImageView(imageIcon: UIImage(named: "icons/red_pin.png"), location: CGPointMake(40, 110), father: self.imageView, name: "redPinA", axisView: self.axisView) self.redPinB = PinImageView(imageIcon: UIImage(named: "icons/red_pin.png"), location: CGPointMake(80, 110), father: self.imageView, name: "redPinB", axisView: self.axisView) self.bluePinA = PinImageView(imageIcon: UIImage(named: "icons/blue_pin.png"), location: CGPointMake(200, 110), father: self.imageView, name: "bluePinA", axisView: self.axisView) self.bluePinB = PinImageView(imageIcon: UIImage(named: "icons/blue_pin.png"), location: CGPointMake(240, 110), father: self.imageView, name: "bluePinB", axisView: self.axisView) self.view.addSubview(self.redPinA) self.view.addSubview(self.redPinB) self.view.addSubview(self.bluePinA) self.view.addSubview(self.bluePinB) 未被调用,因为大小为(0.0,0.0)...谢谢大家。

这是我在主视图控制器中所做的事情:

abstract class db_table {

static function get_all_rows() {
    ...
       while(...) {
           $rows[] = new static();
           ...
       }
       return $rows;
    }
}

1 个答案:

答案 0 :(得分:1)

该错误正确指出url.com正在调用touchesBegan,它正在调用drawAxis个函数,但您不在有效的上下文中(因此,“无效的上下文0x0 “)。

您不应直接呼叫CGContext中的任何CGContext个功能。您可以更新状态变量,然后调用touchesBegan,这将导致操作系统调用setNeedsDisplay,您可以绘制轴。但是不要试图自己绘制它们。

但我尝试了以下内容并且工作正常:

drawRect

我在您的评论中推断您尝试直接调用此代码以解决class AxisView: UIView { var pin:PinImageView? func drawAxis(from:CGPoint, to:CGPoint) { let context = UIGraphicsGetCurrentContext() switch pin!.id { case "redPinA", "redPinB": CGContextSetRGBStrokeColor(context, 1.0, 0.0, 0.0, 1.0) case "bluePinA", "bluePinB": CGContextSetRGBStrokeColor(context, 0.0, 0.0, 1.0, 1.0) default: break } /* line width of axes */ CGContextSetLineWidth(context, 0.5) /* draw vertical axis inside magnifier */ CGContextMoveToPoint(context, from.x, from.y) CGContextAddLineToPoint(context, to.x, to.y) /* draw horizontal axis inside magnifier */ CGContextStrokePath(context) } override func drawRect(rect: CGRect) { if pin != nil { drawAxis(CGPointMake(pin!.center.x, frame.origin.y), to: CGPointMake(pin!.center.x, frame.origin.y + frame.height)) } } } class PinImageView: UIImageView { var lastLocation:CGPoint! var id:String! var viewForAxis:AxisView! init(imageIcon: UIImage?, location:CGPoint, name:String, axisView:AxisView) { super.init(image: imageIcon) lastLocation = location id = name viewForAxis = axisView print(viewForAxis.frame.size) center = location frame = CGRect(x: location.x, y: location.y, width: 40.0, height: 60.0) userInteractionEnabled = true } required init?(coder aDecoder: NSCoder) { fatalError("init(coder:) has not been implemented") } override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) { if let _ = touches.first { print(viewForAxis.frame.size) viewForAxis.hidden = false viewForAxis.pin = self viewForAxis.setNeedsDisplay() } } override func touchesEnded(touches: Set<UITouch>, withEvent event: UIEvent?) { viewForAxis.hidden = true } override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent?) { if let touch: UITouch = touches.first { center = touch.locationInView(superview) viewForAxis.setNeedsDisplay() } } } class ViewController: UIViewController { var axisView: AxisView! var redPinA: PinImageView! var redPinB: PinImageView! var bluePinA: PinImageView! var bluePinB: PinImageView! override func viewDidLoad() { super.viewDidLoad() axisView = AxisView() axisView.frame = view.bounds axisView.backgroundColor = UIColor.clearColor() view.addSubview(axisView) axisView.hidden = true redPinA = PinImageView(imageIcon: UIImage(named: "red_pin.png"), location: CGPointMake(40, 110), name: "redPinA", axisView: axisView) redPinB = PinImageView(imageIcon: UIImage(named: "red_pin.png"), location: CGPointMake(80, 110), name: "redPinB", axisView: axisView) bluePinA = PinImageView(imageIcon: UIImage(named: "blue_pin.png"), location: CGPointMake(200, 110), name: "bluePinA", axisView: axisView) bluePinB = PinImageView(imageIcon: UIImage(named: "blue_pin.png"), location: CGPointMake(240, 110), name: "bluePinB", axisView: axisView) view.addSubview(redPinA) view.addSubview(redPinB) view.addSubview(bluePinA) view.addSubview(bluePinB) } } 未导致setNeedsDisplay被调用的问题。这听起来像是一个单独的问题。解决方案不是自己调用drawRect(或drawRect),而是找出drawAxis没有完成工作的原因。但问题不在你问题的代码中,而是显然是其他问题的结果。