1、iOS坐标系
在iOS坐标系中,以屏幕左上角为坐标原点(0, 0),往右是X
正方向,往下是Y
正方向。
2、frame与bouns
bounds
和frame
都是CGRect
类型,CGRect
是包含一个CGPoint
和一个CGSize
的结构体。
struct CGRect {
CGPoint origin;
CGSize size;
};
origin
决定view
的原点(左上角点)的位置,size
决定view
的长宽。
从源码看bounds
和frame
区别:
-(CGRect)frame{
return CGRectMake(self.frame.origin.x,self.frame.origin.y,self.frame.size.width,self.frame.size.height);
}
-(CGRect)bounds{
return CGRectMake(0,0,self.frame.size.width,self.frame.size.height);
}
frame
表示子view
在父view
的坐标系统中的位置和大小,子view以
父view
的坐标系统为参考系统。
bounds
表示该view
在本地坐标系统中的位置和大小,参考系统是本地坐标系统,且本地坐标系统原点默认为(0,0)。
3、举栗子看区别
frame大家都很熟悉,反而是
bounds
比较容易迷惑人,所以我们专门研究一下bounds的机制
。
UIView *viewA = [[UIView alloc] initWithFrame:CGRectMake(50, 50, 200, 200)];
viewA.backgroundColor = [UIColor blueColor];
[self.view addSubview:viewA];
UIView *viewB = [[UIView alloc] initWithFrame:CGRectMake(50, 50, 100, 100)];
viewB.backgroundColor = [UIColor yellowColor];
[viewA addSubview:viewB];
在上面的基础上,我们来修改viewA的Bounds的原点位置。
[viewA setBounds:CGRectMake(-20, -20, 200, 200)];
看到viewA
本身的位置并没有发生变化,而viewA
的子viewB
的位置往右下方移动了(20,20)。
因为此时viewA的左上角点相对于viewA的
本地坐标系统是为(-20,-20),viewB的左上角点才是viewA的
本地坐标系统的原点,所以viewB要往右下方移
。
可以看到,设置viewA的
Bounds并不会影响viewA的位置,只会影响子视图viewB的位置。
接着我们恢复viewA的Bounds的原点位置,只修改viewA的Bounds的大小。
[viewA setBounds:CGRectMake(0,0, 300, 300)];
可以看到,viewA的位置和大小都改变了,因为修改Bounds的大小,view是以中心点向四周伸缩,不变的是中心点,左上角点的位置因为而改变。
4、总结
通过上面的几个栗子,我们可以得出下面的几个结论:
frame
不管改变位置还是大小,都会影响自己,但不会影响自己子视图相对于自己的位置。frame
大小改变时,自己的左上角位置不会发生改变,只是大小发生变化。bounds
改变位置时,不会影响自己的位置,但自己的子视图的位置会改变。bounds
大小改变时,自己的中心点不会变化,以中心点向四周伸缩,也就是说大小和位置都会改变。