iOS图形处理相关iOS核心动画天生不是作曲家

玩转iOS中的绘图(Quartz 2D基础篇)

2016-06-07  本文已影响1671人  ZeroJ
前言: 本篇简单介绍使用Quartzs 2D来绘图.如果你在网上搜索关于iOS开发中对于图片的处理(缩放...),或者运用截取屏幕或者某一部分内容来实现一些动画交互(比如实现tableViewCell, collectionView的移动效果...), 以及自定义一些控件(比如圆形进度条...)那么大多数的处理都会涉及到绘图的处理, 也许很多功能在你需要实现的时候, 搜索一下可以找到一些解决问题的代码, 但是或许在使用很久之后还是不明白其中的知识点. 本篇大多内容源于对官方文档"Quartz 2D Programming Guide"的理解.

首先对于Quartz 2D就不多做介绍了,(处理路径的绘图, 透明度绘图, 遮盖,阴影, 颜色管理, 防锯齿渲染, 生成PDF...) 感兴趣的朋友可以查查相关的资料

1. 了解Quartz 2D的绘图机制

2.获取上下文

3. 坐标系

4. 内存管理

5. 绘制我们需要的内容

CGContextSetLineWidth() -> 线宽度
CGContextSetLineJoin() -> 线的连接点的样式
CGContextSetLineCap() -> 端点的样式
CGContextSetLineDash() -> 虚线
CGContextSetStrokeColorWithColor() -> stroke模式时的颜色
CGContextSetFillColorWithColor() -> fill模式时的颜色
```
* 绘制内容, 注意会涉及到两种方式: fill 和 stroke, 这里解释一下两者的区别

  • 当使用stroke方式 -> "描边"即只绘制路径
```
override func drawRect(rect: CGRect) {
    // Drawing code
    // 获取当前上下文
    let context = UIGraphicsGetCurrentContext()
    let strokeColor = UIColor.blueColor()
    // 设置stroke模式的颜色使用CGColor(这里涉及到颜色和颜色空间的概念)
    CGContextSetStrokeColorWithColor(context, strokeColor.CGColor)
    // 设置线的宽度
    CGContextSetLineWidth(context, 5.0)
    // 设置连接处样式...还可以设置很多其他的属性
    CGContextSetLineJoin(context, CGLineJoin.Round)
    // 起始点
    CGContextMoveToPoint(context, 10.0, 10.0)
    // 在点(10.0, 10.0)和(10.0, 80.0)之间画一条线 所以点(10.0, 80.0)被设置为下一个起始点
    CGContextAddLineToPoint(context, 10.0, 80.0)
    //在点(10.0, 80.0)和(80.0, 80.0)之间画一条线 所以点(80.0, 80.0)被设置为下一个起始点
    CGContextAddLineToPoint(context, 80.0, 80.0)
    // 设置为封闭路径, 会将首尾点连接起来
    // CGContextClosePath(context)
    // 绘制当前的路径
    CGContextStrokePath(context)
    
}

```
不封闭路径png 封闭路径.png

fill模式绘制相同的路径

     let fillColor = UIColor.blueColor()
     // 设置fill模式的颜色使用CGColor(这里涉及到颜色和颜色空间的概念)
     CGContextSetFillColorWithColor(context, fillColor.CGColor)
     // 起始点
     CGContextMoveToPoint(context, 10.0, 10.0)
     // 在点(10.0, 10.0)和(10.0, 80.0)之间画一条线 所以点(10.0, 80.0)被设置为下一个起始点
     CGContextAddLineToPoint(context, 10.0, 80.0)
     //在点(10.0, 80.0)和(80.0, 80.0)之间画一条线 所以点(80.0, 80.0)被设置为下一个起始点
     CGContextAddLineToPoint(context, 80.0, 80.0)
     //        CGContextClosePath(context)
     // 绘制当前的路径
     CGContextFillPath(context)
   ```

![fill方式.png](http:https://img.haomeiwen.com/i1271831/3729cb7a3c50b757.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

stroke模式绘制圆

    // 设置stroke模式的颜色使用CGColor(这里涉及到颜色和颜色空间的概念)
    CGContextSetStrokeColorWithColor(context, strokeColor.CGColor)
    // 设置线的宽度
    CGContextSetLineWidth(context, 5.0)
    // 设置连接处样式
    CGContextSetLineJoin(context, CGLineJoin.Round)
    // 起始点
    let circleCenter = CGPoint(x: rect.width * 0.5, y: rect.height * 0.5)
    CGContextMoveToPoint(context, circleCenter.x*2, circleCenter.y)
    // 画圆
    // x -> 圆心的x坐标
    // y -> 圆心的y坐标
    // radius -> 圆的半径
    // startAngle -> 起始角度 (弧度制) 所以上面调整了起始点
    // endAngle -> 结束角度(弧度制)
    CGContextAddArc(context, circleCenter.x, circleCenter.y, rect.width * 0.5, 0.0, CGFloat(M_PI) * 2, 0)
    CGContextStrokePath(context)

![stroke圆png](http:https://img.haomeiwen.com/i1271831/80e1a3a80711373c.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

fill方式绘制圆

    // 设置fill模式的颜色使用CGColor(这里涉及到颜色和颜色空间的概念)
    CGContextSetFillColorWithColor(context, fillColor.CGColor)
    // 起始点
    let circleCenter = CGPoint(x: rect.width * 0.5, y: rect.height * 0.5)
    CGContextMoveToPoint(context, circleCenter.x*2, circleCenter.y)
    // 画圆
    // x -> 圆心的x坐标
    // y -> 圆心的y坐标
    // radius -> 圆的半径
    // startAngle -> 起始角度 (弧度制) 所以上面调整了起始点
    // endAngle -> 结束角度(弧度制)
    CGContextAddArc(context, circleCenter.x, circleCenter.y, rect.width * 0.5, 0.0, CGFloat(M_PI) * 2, 0)
    // 绘制当前的路径
    CGContextFillPath(context)

![fill方式.png](http:https://img.haomeiwen.com/i1271831/da58c13499f817c6.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

-----
#####仅仅介绍了上面的几种看上去很简单的绘制方法, 也许你会觉得没有什么实际用处, 但是实际上是很有用处的, 因为到现在为止, 你可以使用Quartzs 2D来实现自定义的各种圆形进度条了,(可能使用到stroke和fill的混合模式), 只需要在提供的progress属性设置时调用setNeedsDisplay()就可以触发drawRect()方法进行重绘, 而在这里面你就可以利用progress来改变绘制的内容了, 从而实现进度条的效果
---
> 限于篇幅和时间, 这篇中只是梳理了一些基本的绘图概念和绘制简单的图形(实际上看看API就可以类似的使用相关的方法绘制出其他的图形 -- 椭圆...), 而实际上还有比较多的东西需要研究, 以后有必要在补上. [Demo](https://github.com/jasnig/DrawingStudy)
上一篇下一篇

猜你喜欢

热点阅读