Search code examples
swiftswift2core-animationdrawrectuibezierpath

Simple line drawing animation in Swift


I am new to swift and got frustrated with this issue that I'm having.

What I am trying to do is very simple: draw a straight line in the center of the screen and animate it. Sounds very simple, right? Yeah.. so that's what I have at the moment.

import UIKit

class Drawings: UIView {


    override func drawRect(rect: CGRect) {

        let screensize: CGRect = UIScreen.mainScreen().bounds
        let screenWidth = screensize.width
        let screenHeight = screensize.height

        //context
        let context = UIGraphicsGetCurrentContext()
        CGContextSetLineWidth(context, 7.0)
        CGContextSetStrokeColorWithColor(context, UIColor.whiteColor().CGColor)

        //path
        CGContextMoveToPoint(context, screenWidth, screenHeight * 0.5)
        CGContextAddLineToPoint(context, screenWidth * 0.5, screenHeight * 0.5)

        CGContextSetLineCap(context, CGLineCap.Round)

        //draw
        CGContextStrokePath(context)

    }

}

The reason I'm asking is that I've found that I cannot animate it, since it's in drawRect function. Is that true? Need some explanation from you guys. Thanks!

Image


Solution

  • You shouldn't draw shapes in drawRect like this, especially if you're going to animate.

    Instead, make a CAShapeLayer, and you can use Core Animation to animate that.

    // Create the path using UIBezierPath.
    // Position can start at 0,0 because we'll move it using the layer
    let linePath = UIBezierPath()
    linePath.moveToPoint(CGPoint(x: 0, y: 0))
    linePath.addLineToPoint(CGPoint(x: CGRectGetMidX(frame), y: 0))
    
    // Create the shape layer that will draw the path
    let lineLayer = CAShapeLayer()
    
    // set the bounds to the size of the path. 
    // You could also set to the size of your view, 
    // but if i know the size of my shape ahead of time, 
    // I like to set it to be the same.
    lineLayer.bounds = linePath.bounds
    
    // give it the same position as our view's layer.
    // layers have an anchor point of 0.5, 0.5 (their center)
    // so this will put the layer in the center of the view.
    lineLayer.position = layer.position
    
    // finally, set up the shape properties. set the path and stroke etc
    lineLayer.path = linePath.CGPath
    lineLayer.strokeColor = UIColor.whiteColor().CGColor
    lineLayer.lineWidth = 4
    
    // add it to your view's layer and you're done!
    layer.addSublayer(lineLayer)
    

    Now you can animate properties on lineLayer using Core Animation.