iOS上图形和动画处理

苹果公司在iOS和OS X上向开发者提供了强大的框架来处理图形和动画,这些框架和技术有:

UIKit:高层次的框架,允许开发人员创建视图、窗口、按钮和其他UI相关的组件。它还将一些低级别的API引入到易于使用的高级别的API中。

Quartz 2D:iOS上绘图的主要引擎,UIKit就使用Quartz。

Core Graphics:它支持图形上下文、加载图像、绘制图像,等等。

Core Animation:iOS上实现动画的框架。

1 绘制文本

  public func drawAtPoint(point: CGPoint, withAttributes attrs: [String : AnyObject]?)

  public func drawInRect(rect: CGRect, withAttributes attrs: [String : AnyObject]?)

    override func drawRect(rect: CGRect) {
        
        let string: NSString = "Some String";
        
        let attr: [String: AnyObject] = [NSFontAttributeName: UIFont.init(name: "HelveticaNeue-Bold", size: 30)!,
                                         NSForegroundColorAttributeName: UIColor(red: 0.5, green: 0.0, blue: 0.5, alpha: 1.0),
                                         NSBackgroundColorAttributeName: UIColor.lightGrayColor()]
        
        string.drawAtPoint(CGPointMake(40, 180), withAttributes: attr)
        
        let string2: NSString = "I Learn Really Fast"
        
        string2.drawInRect(CGRectMake(40, 250, 100, 100), withAttributes: attr)
    }

 2 绘制图形

  UIKit帮助你轻松的绘制图像,你所需要做的是需要把你的图像加载在UIImage类的实例中。UIImage类提供了各种类方法和实例方法来加载图像。

   public func drawAtPoint(point: CGPoint) 

     public func drawInRect(rect: CGRect)

override func drawRect(rect: CGRect) {
  let image = UIImage(named: "f015")
  image?.drawAtPoint(CGPointMake(40, 80))       //按照图片的原始大小绘制
        
  let image2 = UIImage(named: "f015")
  image2?.drawInRect(CGRectMake(40, 200, 10, 10))  //在矩形区域内绘制
}

3 绘制线条

  路径是由屏幕上一个或一系列点构成。路径和线条有很大的区别,路径可以包含很多线条,但线条不能包含很多路径。把路径当做一系列的点,就是这么简单。

  必须使用路径来绘制线条。指定起点和终点,然后要求Core Graphics来绘制路径。

  绘制线条的步骤:

  (1)为图形上下文选定一个颜色;

  (2)使用UIGraphicsGetCurrentContext函数获取图形上下文句柄;

  (3)使用CGContextSetLineWidth设置线条的宽度;

  (4)使用CGContextMoveToPoint过程设置线条的起点;

  (5)使用CGContextAddLineToPoint过程在图形上下文移动画笔来设置线条的终点;

  (6)使用CGContextStrokePath过程创建已设置好的路径。

override func drawRect(rect: CGRect) {
        
        UIColor.blueColor().set()
        
        let context = UIGraphicsGetCurrentContext()
        
        CGContextSetLineWidth(context, 5.0)
     
//.Miter:尖角,默认样式 .Round:圆角 .Bevel:平角 CGContextSetLineJoin(context, CGLineJoin.Round)
        CGContextMoveToPoint(context, 40, 80)
        CGContextAddLineToPoint(context, 80, 160)
        CGContextAddLineToPoint(context, 120, 80)
     CGContextStrokePath(context)
}

4 绘制路径

  路径属于正在绘制他们的图形上下文。路径没有边界(Boundary)或特定的形状,但路径有边界框(Boundary boxes)。Boundary和Boundary Boxes完全不一样,Boundary限制你在画布上哪些不可以用来绘画,而Boundary Boxes是包含了所有路径上的形状、点和其他已经绘制的对象额最小矩形。你可以在图形上下文中对路径进行填充,或者对它进行描边。下面是你会用到的一些方法:

  (1)CGPathCreateMutable函数:创建一个类型为CGMutablePathRef的可变路径,并返回其句柄。每次使用完这个路径,我们都应该为其做善后工作。

  (2)CGPathMoveToPoint过程:在路径上移动当前的位置到一个点。

  (3)CGPathAddLineToPoint过程:从当前的画笔位置向指定位置绘制线条。

  (4)CGContextAddPath过程:添加一个路径到图形上下文。

  (5)CGContextDrawPath过程:在图形上下文绘制给出的路径。

  (6)CGPathRelease过程:释放为路径句柄分配的内存。(ARC环境下不需要自己手动释放,系统会自己释放)

  (7)CGPathAddRect过程:向路径添加一个矩形。

  (8)kCGPathStroke:使用当前选定的描边颜色为路径描边。

  (9)kCGPathFill:使用当前选定的颜色填充路径所包围的区域。

  (10)kCGPathFillStroke:组合描边和填充。

    override func drawRect(rect: CGRect) {
        
        let path: CGMutablePathRef = CGPathCreateMutable()
        
        CGPathMoveToPoint(path, nil, rect.origin.x, rect.origin.y)
        CGPathAddLineToPoint(path, nil, rect.size.width, rect.size.height)
        
        CGPathMoveToPoint(path, nil, rect.size.width, rect.origin.y)
        CGPathAddLineToPoint(path, nil, rect.origin.x, rect.size.height)
        
        let context = UIGraphicsGetCurrentContext()
        
        CGContextAddPath(context, path)
        
        UIColor.brownColor().setStroke()
        
        CGContextDrawPath(context, CGPathDrawingMode.Stroke)
        
    }

    override func drawRect(rect: CGRect) {
        
        let path: CGMutablePathRef = CGPathCreateMutable()
        
        CGPathMoveToPoint(path, nil, 40, 80)
        CGPathAddLineToPoint(path, nil, 100, 150)
        CGPathAddLineToPoint(path, nil, 120, 100)
        CGPathAddLineToPoint(path, nil, 40, 80)
        
        let context = UIGraphicsGetCurrentContext()
        
        CGContextAddPath(context, path)
        
        UIColor.redColor().setStroke()
        UIColor.blueColor().setFill()
        
        CGContextDrawPath(context, CGPathDrawingMode.FillStroke)
        
    }

5 绘制矩形

    override func drawRect(rect: CGRect) {
        
        let path: CGMutablePathRef = CGPathCreateMutable()
        
        CGPathAddRect(path, nil, CGRectMake(40, 80, 100, 100))  //绘制一个矩形

      CGPathAddRects(path, nil, [CGRectMake(40, 80, 100, 100), CGRectMake(40, 200, 100, 100)], 2)  //可以绘制多个矩形

        let context = UIGraphicsGetCurrentContext()
        
        CGContextAddPath(context, path)
        
        UIColor.brownColor().setStroke()
        UIColor.redColor().setFill()
        
        CGContextSetLineWidth(context, 5.0)
        
        CGContextDrawPath(context, CGPathDrawingMode.FillStroke)
    }

6 为形状添加阴影

  (1)CGContextSetShadow:将会创建黑色或灰色阴影

  (2)CGContextSetShadowWithColor:可以自己设置阴影的颜色

    override func drawRect(rect: CGRect) {
        
        let context = UIGraphicsGetCurrentContext()

        CGContextSetShadow(context, CGSizeMake(5, 5), 3.0)
        
       // CGContextSetShadowWithColor(context, CGSizeMake(5, 5), 3.0, UIColor.lightGrayColor().CGColor)
        
        let path: CGMutablePathRef = CGPathCreateMutable()
        
        CGPathAddRect(path, nil, CGRectMake(40, 80, 100, 100))
        
        CGContextAddPath(context, path)
        
        UIColor(red: 0.2, green: 0.6, blue: 0.8, alpha: 1.0).setFill()
            
        CGContextDrawPath(context, CGPathDrawingMode.Fill)
    }

7 创建和绘制渐变

    override func drawRect(rect: CGRect) {
        
        let context = UIGraphicsGetCurrentContext()
        
        CGContextSaveGState(context)
        
        let colorSpace: CGColorSpaceRef? = CGColorSpaceCreateDeviceRGB()
        
        //蓝色作为起点
        let startColor = UIColor.blueColor()
        
        let startColorComponents = CGColorGetComponents(startColor.CGColor)
        
        //橘色作为终点
        let closeColor = UIColor.orangeColor()
        
        let closeColorComponents = CGColorGetComponents(closeColor.CGColor)
        
        let colorComponents = [startColorComponents[0],
                               startColorComponents[1],
                               startColorComponents[2],
                               startColorComponents[3],
                               closeColorComponents[0],
                               closeColorComponents[1],
                               closeColorComponents[2],
                               closeColorComponents[3]]
        
        let colorIndices: [CGFloat] = [0.0, 1.0]
        
        let gradient = CGGradientCreateWithColorComponents(colorSpace, colorComponents, colorIndices, 2)
        
        //起点
        let startPoint = CGPointMake(80.0, 80.0)
        //终点
        let closePoint = CGPointMake(250.0, 80.0)
        
        //.DrawsAfterEndLocation:扩展整个渐变到渐变的终点之后的所有点
        //.DrawsBeforeStartLocation:扩展整个渐变到渐变的起点之前的所有点
        CGContextDrawLinearGradient(context, gradient, startPoint, closePoint, [.DrawsAfterEndLocation, .DrawsBeforeStartLocation])
        
        CGContextRestoreGState(context)
        
    }

 8 平移图形上下文的形状

  第一种方法:CGPathAddRect方法的第二个参数是一个CGAffineTransform类型的变换对象。

    override func drawRect(rect: CGRect) {

        //平移图形上下文的形状//第一种方法:CGPathAddRect方法的第二个参数是一个CGAffineTransform类型的变换对象        
        let path = CGPathCreateMutable()
        let rectangle = CGRectMake(10, 80, 200, 300)
        var transform = CGAffineTransformMakeTranslation(100, 0)
        
        CGPathAddRect(path, &transform, rectangle)
        let context = UIGraphicsGetCurrentContext()
        CGContextAddPath(context, path)
        
        UIColor.purpleColor().setStroke()
        UIColor.blueColor().setFill()
        
        CGContextSetLineWidth(context, 5.0)
        
        CGContextDrawPath(context, .FillStroke)
  }

  第二种方法:通过CGContextTransformCTM过程对图形上下文应用变换,这将把一个平移变换应用到当前变换矩阵(CTM:current transformation matrix)。把CTM认为是它设置了你的图形上下文的中心,是它把你绘制的每个点投射到屏幕上。通过改变CTM的配置,强制把所有绘制在图形上下文的形状转移到画布上的另一个地方。

    override func drawRect(rect: CGRect) {
//平移图形上下文的形状//第二种方法:通过CGContextTransformCTM过程对图形上下文应用变换,这将把一个平移变换应用到当前变换矩阵(CTM:current transformation matrix)。把CTM认为是它设置了你的图形上下文的中心,是它把你绘制的每个点投射到屏幕上。通过改变CTM的配置,强制把所有绘制在图形上下文的形状转移到画布上的另一个地方。 let path = CGPathCreateMutable() let rectangle = CGRectMake(10, 80, 200, 300) CGPathAddRect(path, nil, rectangle) let context = UIGraphicsGetCurrentContext() CGContextSaveGState(context) CGContextTranslateCTM(context, 100, 0) CGContextAddPath(context, path) CGContextSetLineWidth(context, 5.0) UIColor.purpleColor().setStroke() UIColor.blueColor().setFill()
CGContextDrawPath(context, .FillStroke)
  }

9 缩放图形上下文的形状

  同上两种方法。

  第一种方法:var transform = CGAffineTransformMakeScale(1.0, 0.5)

  第二种方法:CGContextScaleCTM(context, 1, 0.5)

10 旋转图形上下文的形状

  同上两种方法。

  第一种方法:var transform = CGAffineTransformMakeRotation(-CGFloat(M_2_PI)/2.0)

  第二种方法:CGContextRotateCTM(context, -CGFloat(M_2_PI)/2.0)

11 动画--移动视图、缩放视图、旋转视图

  在iOS上有各种方式可以实现动画:在一个较低的层次提供了这种能力,在更高的层次也提供这种能力。我们可以获得的最高层次的动画能力是通过UIKit。UIKit中包括一些Core Animation的较低层次的功能,并且包装成非常简洁的API供我们使用。

  UIKit中实现动画的起点是调用UIView类的类方法beginAnimations:context:。其第一个参数是一个可选的动画的名字,第二个是一个可选的上下文,在之后传递给动画的委托方法时你可以获得它。

  在你通过beginAnimations:context:方法开始一个动画之后,它实际上不会马上执行,而是直到你调用UIView类的commitAnimation类方法。在beginAnimation:context:和commitAnimation之间,你对一个视图对象的计算将在commitAnimation被调用之后开始进行动画。

  使用UIKit执行动画时常用的方法:

  (1)beginAnimations:context:开始一个动画块。调用这个类方法之后,你对视图任何动画属性的改变,都会在动画块提交之后形成动画。

  (2)setAnimationDuration:以秒为单位设置动画的持续时间。

  (3)setAnimationDelegate:设置一个对象来接受动画开始之前、动画期间或动画结束之后发生的各种事件的委托对象。设置一个委托对象不会立即开始发送动画委托消息。你必须对视图对象使用其他的setter方法来告诉UIKit你的委托对象中的哪个选择器(selector)要接受哪些委托消息。

  (4)setAnimationDidStopSelector:设置动画完成时委托对象中用过被调用的方法。这个方法按照以下顺序接受是哪个参数:

  • NSString类型的动画标识:它包含在动画开始时传给beginAnimations:context:方法的动画标识。
  • 一个“已完成”的标识,NSNumber类型:此参数包含一个由NSNumber包装的布尔值,如果动画在被其他代码停止之前能够完整地执行,运行时(Runtime)将它设置为YES。如果这个值被设置为NO,意味着动画在完后之前被中断了。
  • 一个void *类型的上下文:这是动画开始时传给beginAnimations:context:方法的上下文。

  (5)setAnimationWillStartSeletor:设置动画即将开始时委托对象中被顶选择器,参数通上。 

  (6)setAnimationDelay: 设置一个动画启动的延迟时间。 

  (7)setAnimationRepeatCount:设置一个动画块需要重复它的动画次数。 

UIView.beginAnimations("iconAnimation", context: nil)
UIView.setAnimationDuration(3.0) 
//可以直接通过改变frame来移动视图
self.iconImage.frame = CGRectMake(UIScreen.mainScreen().bounds.width - 100, UIScreen.mainScreen().bounds.height - 100, 100, 100)
//缩放视图--缩放后,视图的中心不变        
self.iconImage.layer.setAffineTransform(CGAffineTransformMakeScale(2.0, 2.0))
//旋转视图       
self.iconImage.layer.setAffineTransform(CGAffineTransformMakeRotation(CGFloat(M_PI)))
        
UIView.commitAnimations()

转载于:https://www.cnblogs.com/muzijie/p/5842843.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值