2015-11-04 61 views
1

我有一个类下面,当附加到一个视图绘制曲线时,用户触摸他们的设备。问题是绘制的线条似乎滞后于手指在屏幕上的位置。当线条的新部分与手指触摸屏幕相距很小的距离时,滞后足以引起注意并且轻度恼人。绘制没有滞后的曲线?

该代码使用曲线方法addCurveToPoint。 (替代addQuadCurveToPoint曲线法似乎是在一个质量曲线而言较少优越,但确实显示在屏幕上更快。)

我怀疑,这个问题涉及当setNeedsDisplay被调用一次的counter == 4到。代码等待,直到绘制曲线之前的绘图时收到4个新的接触点。理想情况下,每个触摸点绘制一条曲线(即计数器== 1),消除滞后。 (改变Counter == 1似乎不工作)。

我迷路了,不知道如何更新代码,以进一步提高其移除短暂的延迟,但保留的曲线。 在下面的代码中需要改变以消除短时滞?

// Swift 2 code below tested using Xcode 7.0.1. 

class drawView: UIView { 

var path:UIBezierPath? 
var incrementalImage:UIImage? 

var points = [CGPoint?](count: 5, repeatedValue: nil) 
var counter:Int? 

var infoView:UIView = UIView() 
var strokeColor:UIColor? 


required init?(coder aDecoder: NSCoder) { 
    super.init(coder: aDecoder) 
    self.multipleTouchEnabled = false 
    self.backgroundColor = UIColor.whiteColor() 
    path = UIBezierPath() 
    path?.lineWidth = 20.0 
    strokeColor = UIColor.darkGrayColor() 
    path?.lineCapStyle = CGLineCap.Round 
} 

override init(frame: CGRect) { 
    super.init(frame: frame) 
    self.multipleTouchEnabled = false 
    path = UIBezierPath() 
    path?.lineWidth = 20.0 
} 


override func drawRect(rect: CGRect) { 
    incrementalImage?.drawInRect(rect) 
    strokeColor?.setStroke() 
    path?.stroke() 
} 

override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) { 
    counter = 0 
    let touch: AnyObject? = touches.first 
    points[0] = touch!.locationInView(self) 
    infoView.removeFromSuperview() 
} 

override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent?) { 
    let touch: AnyObject? = touches.first 
    let point = touch!.locationInView(self) 
    counter = counter! + 1 
    points[counter!] = point 

    if counter == 4{ 

     points[3]! = CGPointMake((points[2]!.x + points[4]!.x)/2.0, (points[2]!.y + points[4]!.y)/2.0) 
     path?.moveToPoint(points[0]!) 
     path?.addCurveToPoint(points[3]!, controlPoint1: points[1]!, controlPoint2: points[2]!) 

     self.setNeedsDisplay() 

     points[0]! = points[3]! 
     points[1]! = points[4]! 
     counter = 1 

    } 
} 

override func touchesEnded(touches: Set<UITouch>, withEvent event: UIEvent?) { 

    self.drawBitmap() 
    self.setNeedsDisplay() 
    path?.removeAllPoints() 
    counter = 0 
} 

override func touchesCancelled(touches: Set<UITouch>?, withEvent event: UIEvent?) { 
    self.touchesEnded(touches!, withEvent: event) 
} 

func drawBitmap(){ 
     UIGraphicsBeginImageContextWithOptions(self.bounds.size, true, 0.0) 
     strokeColor?.setStroke() 
     if((incrementalImage) == nil){ 
      let rectPath:UIBezierPath = UIBezierPath(rect: self.bounds) 
      UIColor.whiteColor().setFill() 
      rectPath.fill() 
     } 

     incrementalImage?.drawAtPoint(CGPointZero) 
     path?.stroke() 
     incrementalImage = UIGraphicsGetImageFromCurrentImageContext() 
     UIGraphicsEndImageContext() 
} 
} 

回答

0

首先,我认为你做错了。如果你想画出几行不是用户输入的内容,而是用圆圈,扭曲的线条,简单的东西,那么这个用户界面效果很好。

使用时:

self.setNeedsDisplay() 

您每次重绘所有的线路!这是艰难的CPU,这就是为什么你有滞后。图像用户绘制几百行然后成千上万,每次他/她触摸屏幕,它将重绘所有这些行。

好的。所以,我推荐做的是有2个UIImageView:1)mainImageView - 它将保存整个图形。 2)tempImageView - 用户将用它来绘制。

的“tempImageView”当用户触摸/绘制它吸引,直到他们放手屏幕,然后合并“tempImageView”到“mainImageView”

这里是一个教程:

http://www.raywenderlich.com/87899/make-simple-drawing-app-uikit-swift

+0

感谢您的回复。我不认为这是理由。在绘图时进行更改时调用setNeedsDisplay是有效的。一个很好的解释是:http://stackoverflow.com/a/10818417 其实您提到的示例教程是我最初开始使用的,但它在CPU上更加困难。它确实在它不应该触及的事件中绘画。实际上,示例教程中的方法,CPU最大并且应用程序在旧设备上崩溃。 上面代码中的短暂滞后从第一次触摸开始。试图找出如何改善这种情况。 干杯 – user4806509