CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵运算的原理

转载 2016年05月30日 11:19:27

偶然间看到一片讲解 矩阵动画解释听简洁的帖子,收藏下。顺便说下,其实官方开发文档中对于很多知识点有详细的介绍,大家平时可以多阅读文档。。。(虽然是英文的)

原文地址:http://justsee.iteye.com/blog/1969933


--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

CGAffineTransformMake(a,b,c,d,tx,ty) 

ad缩放bc旋转tx,ty位移,基础的2D矩阵

 公式

    x=ax+cy+tx
    y=bx+dy+ty

 

1.矩阵的基本知识:

struct CGAffineTransform

{
  CGFloat a, b, c, d;
  CGFloat tx, ty;
};

CGAffineTransform CGAffineTransformMake (CGFloat a,CGFloat b,CGFloat c,CGFloat d,CGFloat tx,CGFloat ty);

为了把二维图形的变化统一在一个坐标系里,引入了齐次坐标的概念,即把一个图形用一个三维矩阵表示,其中第三列总是(0,0,1),用来作为坐标系的标准。所以所有的变化都由前两列完成。

以上参数在矩阵中的表示为:

 |a    b    0|

 |c    d    0|

 |tx   ty   1|

 

运算原理:原坐标设为(X,Y,1);

                            |a    b    0|

       [X,Y,  1]      |c    d    0|     =     [aX + cY + tx   bX + dY + ty  1] ;

                            |tx    ty  1|

通过矩阵运算后的坐标[aX + cY + tx   bX + dY + ty  1],我们对比一下可知:

第一种:设a=d=1, b=c=0.  

[aX + cY + tx   bX + dY + ty  1] = [X  + tx  Y + ty  1];

可见,这个时候,坐标是按照向量(tx,ty)进行平移,其实这也就是函数

CGAffineTransform CGAffineMakeTranslation(CGFloat tx,CGFloat ty)的计算原理。

第二种:设b=c=tx=ty=0.  

[aX + cY + tx   bX + dY + ty  1] = [aX    dY   1];

可见,这个时候,坐标X按照a进行缩放,Y按照d进行缩放,a,d就是X,Y的比例系数,其实这也就是函数

CGAffineTransform CGAffineTransformMakeScale(CGFloat sx, CGFloat sy)的计算原理。a对应于sx,d对应于sy。

第三种:设tx=ty=0,a=cosɵ,b=sinɵ,c=-sinɵ,d=cosɵ。

[aX + cY + tx   bX + dY + ty  1] = [Xcosɵ - Ysinɵ    Xsinɵ + Ycosɵ  1] ;

可见,这个时候,ɵ就是旋转的角度,逆时针为正,顺时针为负。其实这也就是函数

CGAffineTransform CGAffineTransformMakeRotation(CGFloat angle)的计算原理。angle即ɵ的弧度表示。

2.利用上面的变换写一个UIImage矩阵变换的例子:

下面是一个关于image的矩阵运算的例子,无外乎是运用以上三种变换的组合,达到所定义的效果

Java代码  收藏代码
  1. //UIImageOrientation的定义,定义了如下几种变换  
  2. typedef enum   
  3. {  
  4.     UIImageOrientationUp,            // default orientation  
  5.   
  6.    UIImageOrientationDown,          // 180 deg rotation  
  7.   
  8.    UIImageOrientationLeft,          // 90 deg CCW  
  9.       
  10.     UIImageOrientationRight,         // 90 deg CW  
  11.       
  12.     UIImageOrientationUpMirrored,    // as above but image mirrored along other axis. horizontal flip  
  13.       
  14.     UIImageOrientationDownMirrored,  // horizontal flip  
  15.       
  16.     UIImageOrientationLeftMirrored,  // vertical flip  
  17.       
  18.     UIImageOrientationRightMirrored, // vertical flip  
  19.   
  20. } UIImageOrientation;  
  21.   
  22. //按照UIImageOrientation的定义,利用矩阵自定义实现对应的变换;  
  23.   
  24. -(UIImage *)transformImage:(UIImage *)aImage    
  25.   
  26. {    
  27.   
  28.     CGImageRef imgRef = aImage.CGImage;    
  29.       
  30.     CGFloat width = CGImageGetWidth(imgRef);    
  31.       
  32.     CGFloat height = CGImageGetHeight(imgRef);    
  33.        
  34.     CGAffineTransform transform = CGAffineTransformIdentity;    
  35.       
  36.     CGRect bounds = CGRectMake(00, width, height);    
  37.          
  38.     CGFloat scaleRatio = 1;    
  39.          
  40.     CGFloat boundHeight;    
  41.       
  42.     UIImageOrientation orient = aImage.imageOrientation;    
  43.       
  44.     switch(UIImageOrientationLeftMirrored)    
  45.       
  46.     {    
  47.               
  48.         case UIImageOrientationUp:    
  49.               
  50.             transform = CGAffineTransformIdentity;  
  51.   
  52.             break;    
  53.                          
  54.         case UIImageOrientationUpMirrored:   
  55.               
  56.             transform = CGAffineTransformMakeTranslation(width, 0.0);    
  57.               
  58.             transform = CGAffineTransformScale(transform, -1.01.0); //沿y轴向左翻   
  59.               
  60.             break;    
  61.                          
  62.         case UIImageOrientationDown:              
  63.             transform = CGAffineTransformMakeTranslation(width, height);    
  64.               
  65.             transform = CGAffineTransformRotate(transform, M_PI);    
  66.               
  67.             break;    
  68.                          
  69.         case UIImageOrientationDownMirrored:   
  70.               
  71.             transform = CGAffineTransformMakeTranslation(0.0, height);    
  72.               
  73.             transform = CGAffineTransformScale(transform, 1.0, -1.0);    
  74.               
  75.             break;    
  76.                         
  77.         case UIImageOrientationLeft:     
  78.               
  79.             boundHeight = bounds.size.height;    
  80.               
  81.             bounds.size.height = bounds.size.width;    
  82.               
  83.             bounds.size.width = boundHeight;    
  84.               
  85.             transform = CGAffineTransformMakeTranslation(0.0, width);    
  86.               
  87.             transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);    
  88.               
  89.             break;  
  90.                          
  91.         case UIImageOrientationLeftMirrored:     
  92.               
  93.             boundHeight = bounds.size.height;    
  94.               
  95.             bounds.size.height = bounds.size.width;    
  96.               
  97.             bounds.size.width = boundHeight;    
  98.               
  99.             transform = CGAffineTransformMakeTranslation(height, width);    
  100.               
  101.             transform = CGAffineTransformScale(transform, -1.01.0);    
  102.               
  103.             transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);    
  104.               
  105.             break;    
  106.               
  107.         case UIImageOrientationRight: //EXIF = 8    
  108.               
  109.             boundHeight = bounds.size.height;    
  110.               
  111.             bounds.size.height = bounds.size.width;    
  112.               
  113.             bounds.size.width = boundHeight;    
  114.               
  115.             transform = CGAffineTransformMakeTranslation(height, 0.0);    
  116.               
  117.             transform = CGAffineTransformRotate(transform, M_PI / 2.0);    
  118.               
  119.             break;  
  120.                          
  121.         case UIImageOrientationRightMirrored:   
  122.               
  123.             boundHeight = bounds.size.height;    
  124.               
  125.             bounds.size.height = bounds.size.width;    
  126.               
  127.             bounds.size.width = boundHeight;    
  128.               
  129.             transform = CGAffineTransformMakeScale(-1.01.0);    
  130.               
  131.             transform = CGAffineTransformRotate(transform, M_PI / 2.0);    
  132.               
  133.             break;    
  134.                                                                      
  135.         default:    
  136.               
  137.             [NSException raise:NSInternalInconsistencyException format:@"Invalid image orientation"];    
  138.               
  139.     }    
  140.        
  141.     UIGraphicsBeginImageContext(bounds.size);    
  142.              
  143.     CGContextRef context = UIGraphicsGetCurrentContext();    
  144.             
  145.     if (orient == UIImageOrientationRight || orient == UIImageOrientationLeft) {    
  146.           
  147.         CGContextScaleCTM(context, -scaleRatio, scaleRatio);    
  148.           
  149.         CGContextTranslateCTM(context, -height, 0);    
  150.           
  151.     }    
  152.       
  153.     else {    
  154.           
  155.         CGContextScaleCTM(context, scaleRatio, -scaleRatio);    
  156.           
  157.         CGContextTranslateCTM(context, 0, -height);    
  158.           
  159.     }    
  160.          
  161.     CGContextConcatCTM(context, transform);    
  162.          
  163.     CGContextDrawImage(UIGraphicsGetCurrentContext(), CGRectMake(00, width, height), imgRef);    
  164.       
  165.     UIImage *imageCopy = UIGraphicsGetImageFromCurrentImageContext();  
  166.          
  167.     UIGraphicsEndImageContext();    
  168.          
  169.     return imageCopy;    
  170.       
  171. }   

 

 

参考地址:https://developer.apple.com/library/ios/documentation/GraphicsImaging/Conceptual/drawingwithquartz2d/dq_affine/dq_affine.html

CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵运算的原理

简记: CGAffineTransformMake(a,b,c,d,tx,ty)  ad缩放bc旋转tx,ty位移,基础的2D矩阵  公式     x=ax+cy+tx    y=bx+dy+...
  • cactusz
  • cactusz
  • 2017年07月06日 16:29
  • 193

CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵运算的原理

简记: CGAffineTransformMake(a,b,c,d,tx,ty)  ad缩放bc旋转tx,ty位移,基础的2D矩阵  公式     x=ax+cy+tx   ...
  • xin_g_zhang
  • xin_g_zhang
  • 2015年01月21日 22:19
  • 395

CGAffineTransformMake(a,b,c,d,tx,ty)

CGAffineTransformMake(a,b,c,d,tx,ty)  ad缩放bc旋转tx,ty位移,基础的2D矩阵  公式     x=ax+cy+tx     y=bx+...
  • li198847
  • li198847
  • 2016年03月17日 14:21
  • 215

CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵

官方介绍:Quartz 2D-Transforms  a、d缩放,b、c旋转,tx、ty平移; 基础的2D矩阵基本公式:     x=ax+cy+tx     y=bx+d...
  • qq348931837
  • qq348931837
  • 2016年12月07日 17:15
  • 237

Core Animation研究系列 : CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵运算的原理

简记: CGAffineTransformMake(a,b,c,d,tx,ty)  ad缩放bc旋转tx,ty位移,基础的2D矩阵  公式     x=ax+cy+tx   ...
  • shaobo8910
  • shaobo8910
  • 2015年06月18日 10:39
  • 505

iOS CGAffineTransform详解

UIView的transform属性是一个CGAffineTransform类型,用于在二维空间做旋转,缩放和平移。CGAffineTransform是一个可以和二维空间向量(例如CGPoint)做乘...
  • Ashiyanshi
  • Ashiyanshi
  • 2015年09月01日 17:10
  • 4377

iOS 集移动,旋转,缩放于一体的函数:CGAffineTransformMake(a,b,c,d,tx,ty)

CGAffineTransformMake(a,b,c,d,tx,ty)  对应的参数: ad缩放 bc旋转 tx,ty位移(以被移动的对象多中心点为基准)...
  • flash_rensheng
  • flash_rensheng
  • 2014年12月16日 12:15
  • 714

杭电ACM--HDU-2053a/b+c/d和HDU-2504又见gcd

这两个题目都用到了求最大公约数的方法,进行调用 HDU   2054    又见gcd 题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=250...
  • hj1214ing
  • hj1214ing
  • 2016年07月23日 19:48
  • 312

三元运算符var a=b>c?:b:c

三元运算符 var a=b?c:d   //解释:如果b为true,则a=c ,否则a=d     也就是,当b为true的时候,返回c,此时a=c了,如果当b=false的时候,返回d,此时a=d了...
  • Fanbin168
  • Fanbin168
  • 2014年07月26日 19:25
  • 1319

有A、B、C、D四个人过桥问题

题目: 有A、B、C、D四个人,要在夜里过一座桥。他们通过这座桥分别需要耗时1、2、5、10分钟,只有一支手电,并且同时最多只能两个人一起过桥。请问,如何安排,能够在17分钟内这四个人都过桥...
  • u013634862
  • u013634862
  • 2014年09月14日 11:03
  • 979
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:CGAffineTransformMake(a,b,c,d,tx,ty) 矩阵运算的原理
举报原因:
原因补充:

(最多只允许输入30个字)