【iOS】【swift】アニメーション付き円グラフ

こちらのswift版
http://qiita.com/drafts/91c6031ab903523b8cd7/edit
円グラフをアニメーション付きに。下のような感じで。

<img src="https://oneworld2.sakura.ne.jp/blog/graph1.gif" width=100>
<img src="https://oneworld2.sakura.ne.jp/blog/graph2.gif" width=100>

真ん中くりぬきと、そうじゃないバージョンで。

```swift:PieGraphView.swift

import UIKit

class PieGraphView: UIView {
    
    var _params:[Dictionary<String,AnyObject>]!
    var _end_angle:CGFloat!
    
    required init(coder aDecoder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    init(frame: CGRect,params:[Dictionary<String,AnyObject>]) {
        super.init(frame: frame)
        _params = params;
        self.backgroundColor = UIColor.clearColor();
        _end_angle = -CGFloat(M_PI / 2.0);
    }

    
    func update(link:AnyObject){
        var angle = CGFloat(M_PI*2.0 / 100.0);
        _end_angle = _end_angle +  angle
        if(_end_angle > CGFloat(M_PI*2)) {
            //終了
            link.invalidate()
        } else {
            self.setNeedsDisplay()
        }
        
    }

    func startAnimating(){
        let displayLink = CADisplayLink(target: self, selector: Selector("update:"))
        displayLink.addToRunLoop(NSRunLoop.currentRunLoop(), forMode: NSRunLoopCommonModes)
    }
    
    
    // Only override drawRect: if you perform custom drawing.
    // An empty implementation adversely affects performance during animation.
    override func drawRect(rect: CGRect) {
        // Drawing code

        let context:CGContextRef = UIGraphicsGetCurrentContext();
        var x:CGFloat = rect.origin.x;
        x += rect.size.width/2;
        var y:CGFloat = rect.origin.y;
        y += rect.size.height/2;
        var max:CGFloat = 0;
        for dic : Dictionary<String,AnyObject> in _params {
            var value = CGFloat(dic["value"] as! Float)
            max += value;
        }
        
        
        var start_angle:CGFloat = -CGFloat(M_PI / 2);
        var end_angle:CGFloat    = 0;
        var radius:CGFloat  = x - 10.0;
        for dic : Dictionary<String,AnyObject> in _params {
            var value = CGFloat(dic["value"] as! Float)
            end_angle = start_angle + CGFloat(M_PI*2) * (value/max);
            if(end_angle > _end_angle) {
                end_angle = _end_angle;
            }
            var color:UIColor = dic["color"] as! UIColor

            CGContextMoveToPoint(context, x, y);
            CGContextAddArc(context, x, y, radius,  start_angle, end_angle, 0);
            //ここのコメントアウトを解除すると、中くりぬき
            //CGContextAddArc(context, x, y, radius/2,  end_angle, start_angle, 1);
            CGContextSetFillColor(context, CGColorGetComponents(color.CGColor));
            CGContextClosePath(context);
            CGContextFillPath(context);
            start_angle = end_angle;
        }

    }

}

```


利用イメージは以下のようなものを検討しています。

```swift:ViewController.swift

import UIKit

class ViewController: UIViewController {
    var graphView:PieGraphView!;
    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        // Do any additional setup after loading the view, typically from a nib.
        var params = [Dictionary<String,AnyObject>]()
        params.append(["value":7,"color":UIColor.redColor()])
        params.append(["value":5,"color":UIColor.blueColor()])
        params.append(["value":8,"color":UIColor.greenColor()])
        params.append(["value":10,"color":UIColor.yellowColor()])
        graphView = PieGraphView(frame: CGRectMake(0, 30, 320, 320), params: params)
        self.view.addSubview(graphView)
    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    @IBAction func start(sender: AnyObject) {
        graphView.startAnimating()
        
    }

}

```

ソースをアップしました。
https://github.com/kitanoow/SwiftPieGraphView