写在前面
虽然前面也写了一篇有关Btn的titleEdgeInsets和imageEdgeInsets的介绍的,但是感觉可能存在问题,而且每次使用这两个属性的时候都没有那么的得心应手,有强迫症的我决定花点时间拿下这两个属性。下面,记录我的探索过程。(虽然现在的我已经知道如何使用了,但并不算正规,还请大神不吝赐教!!!)
正文
零、理论
首先,你得知道titleEdgeInsets和imageEdgeInsets的作用是用来移动btn两个子空间的排布的,且它们只是image和label相较于原来位置的偏移量,那什么是原来的位置呢?其实就是不设置Insets的那个状态。下面为不设置insets的状态。
发现在默认情况下,imageView和titleLable是靠在一起并居中显示的。
其次,在同时有image和label且在默认情况下,这时候image的上左下边界是相对于button,右边是相对于label的;label的上右下边界是相对于button,左边是相对于image的。
最后
UIEdgeInsetsMake(CGFloat top, CGFloat left, CGFloat bottom, CGFloat right)
四个属性分别是对于控件的下边界,右边界,上边界,左边界。
结合上面知识举个例子:
btn.imageEdgeInsets = UIEdgeInsetsMake(0, 5, 0, -5);
这行代码的意思是对于image来说,下边界和上边界不动,右边界相对于label的左边界向右偏移5,左边界相对于btn的左边界向左偏移-5,也就是向右偏移5。所以可以想象image整体向右偏移5了。
再举个例子:
btn.titleEdgeInsets = UIEdgeInsetsMake(5, -5, -5, 5);
这行代码的意思是对于label来说,下边界相对于btn的下边界向下偏移5,右边界相对于btn的右边界向右偏移-5,上边界相对于btn的上边界偏移-5,左边界相对于image的右边界向左偏移5。所以可以想象label整体向左偏移5,向下偏移了5。
下面我来亲测是否真的是这样的。
一、前戏
首先,我先写了一个小demo来作为实验工具,界面如下:
我放了一个slider和一个现实效果用的button。每次滑动slider都会改变titleEdgeInsets或者imageEdgeInsets。具体代码:(这里暂时写imageEdgeInsets好了)
UIButton *btn = [self.view viewWithTag:1];
btn.imageEdgeInsets = UIEdgeInsetsMake(0, self.slider1.value * 100, 0, -self.slider1.value * 100);
至于那个按钮,我给他定了50的高,120的宽,代码如下:
UIButton *btn1 = [UIButton new];
btn1.frame = CGRectMake(100, 300, 120, 50);
btn1.backgroundColor = [UIColor blueColor];
[btn1 setTitle:@"加好友" forState:UIControlStateNormal];
[btn1 setTitleColor:[UIColor lightGrayColor] forState:UIControlStateNormal];
btn1.titleLabel.font = [UIFont systemFontOfSize:14];
[btn1 setImage:[UIImage imageNamed:@"btnArea_add@2x"] forState:UIControlStateNormal];
btn1.titleLabel.backgroundColor = [UIColor redColor];
btn1.imageView.backgroundColor = [UIColor yellowColor];
btn1.tag =1 ;
[self.view addSubview:btn1];
二、测试
测试a
我们拿imageView的左右偏移来测试,滑动slider。
响应代码:
btn.imageEdgeInsets = UIEdgeInsetsMake(0, self.slider1.value * 100, 0, -self.slider1.value * 100);
效果图:
测试b
再拿label的上下偏移来测试,滑动slider。
响应代码:
btn.titleEdgeInsets = UIEdgeInsetsMake(self.slider1.value * 100, 0, -self.slider1.value * 100, 0);
效果图:
综上发现的确是理论说的那样的。
三、使用练习
既然已经知道了这些参数的使用规律,那就成热打铁练习一下。
练习一:让图片和文字改变位置,但仍然居中
代码:
CGFloat btnW = btn1.bounds.size.width;
CGFloat btnH = btn1.bounds.size.height;
CGFloat imageW = btn1.imageView.bounds.size.width;
CGFloat imageH = btn1.imageView.bounds.size.height;
CGFloat labelW = btn1.titleLabel.bounds.size.width;
CGFloat labelH = btn1.titleLabel.bounds.size.height;
btn1.imageEdgeInsets = UIEdgeInsetsMake(0,0 + labelW,0,0 - labelW);
btn1.titleEdgeInsets = UIEdgeInsetsMake(0,0 - imageW,0,0 + imageW);
效果:
再次讲一下代码的意思吧。以image为例,他的右边界相当于label的左边界向右偏移labelW,左边界相当于btn的左边界向左偏移-labelW。上下不变。
然后label,他的右边界相对于btn的右边界向右偏移-imageW,左边界相对于image的右边界向左偏移imageW。
练习二:让image上label下
CGFloat imageOffsetX = (imageW + labelW) / 2 - imageW / 2;
CGFloat imageOffsetY = imageH / 2;
btn1.imageEdgeInsets = UIEdgeInsetsMake(-imageOffsetY, imageOffsetX, imageOffsetY, -imageOffsetX);
CGFloat labelOffsetX = (imageW + labelW / 2) - (imageW + labelW) / 2;
CGFloat labelOffsetY = labelH / 2;
btn1.titleEdgeInsets = UIEdgeInsetsMake(labelOffsetY, -labelOffsetX, -labelOffsetY, labelOffsetX);
虽然麻烦,但是不难。其余的自己去试喽~
三、求大神解
但是,求问大神,当我的响应代码变为如下:
UIButton *btn = [self.view viewWithTag:1];
btn.imageEdgeInsets = UIEdgeInsetsMake(0, self.slider1.value * 100, 0, 0);
效果为什么变成这样:
真的无法理解啊!特别最后还会瞬间移动,这是为什么呢!!
虽然使用不成问题,但还是很想彻底了解。