- (void)setButtonControlsLayout:(CGFloat)btnW {
if (!self.imageView || (!self.titleLabel || self.titleLabel.text.length == 0)) {
return;
}
CGFloat btnH = self.frame.size.height;
CGRect imageFrame = self.imageView.frame;
CGRect titleFrame = self.titleLabel.frame;
CGFloat imageX = imageFrame.origin.x;
CGFloat imageY = imageFrame.origin.y;
CGFloat imageW = imageFrame.size.width;
CGFloat imageH = imageFrame.size.height;
CGFloat labelX = titleFrame.origin.x;
CGFloat labelY = titleFrame.origin.y;
CGFloat labelW = titleFrame.size.width;
CGFloat labelH = titleFrame.size.height;
// 计算按钮图片与文字的总高度(包含间距)
CGFloat space = 3.f;
CGFloat controlsHeight = imageH+labelH;
// 边界总距离
CGFloat top = (btnH - controlsHeight - space);
[self.imageView setContentMode:UIViewContentModeCenter];
[self.titleLabel setContentMode:UIViewContentModeCenter];
CGFloat imageEdgeInsetsTop = imageY > top*2/3 ? top*2/3-imageY : imageY;
CGFloat imageEdgeInsetsLeft = (btnW - imageW)/2 - imageX;
CGFloat imageEdgeInsetsBottom = -imageEdgeInsetsTop;
CGFloat imageEdgeInsetsRight = -(btnW - imageW)/2 + imageX;
[self setImageEdgeInsets:UIEdgeInsetsMake(imageEdgeInsetsTop, imageEdgeInsetsLeft, imageEdgeInsetsBottom, imageEdgeInsetsRight)];
CGFloat labelEdgeInsetsTop = (imageY+imageH+imageEdgeInsetsTop+space)-labelY;
CGFloat labelEdgeInsetsRight = labelX-(btnW - labelW)/2;
CGFloat labelEdgeInsetsLeft = -labelEdgeInsetsRight;
CGFloat labelEdgeInsetsBottom = -labelEdgeInsetsTop;
[self setTitleEdgeInsets:UIEdgeInsetsMake(labelEdgeInsetsTop, labelEdgeInsetsLeft, labelEdgeInsetsBottom, labelEdgeInsetsRight)];
if (!self.imageView || (!self.titleLabel || self.titleLabel.text.length == 0)) {
return;
}
CGFloat btnH = self.frame.size.height;
CGRect imageFrame = self.imageView.frame;
CGRect titleFrame = self.titleLabel.frame;
CGFloat imageX = imageFrame.origin.x;
CGFloat imageY = imageFrame.origin.y;
CGFloat imageW = imageFrame.size.width;
CGFloat imageH = imageFrame.size.height;
CGFloat labelX = titleFrame.origin.x;
CGFloat labelY = titleFrame.origin.y;
CGFloat labelW = titleFrame.size.width;
CGFloat labelH = titleFrame.size.height;
// 计算按钮图片与文字的总高度(包含间距)
CGFloat space = 3.f;
CGFloat controlsHeight = imageH+labelH;
// 边界总距离
CGFloat top = (btnH - controlsHeight - space);
[self.imageView setContentMode:UIViewContentModeCenter];
[self.titleLabel setContentMode:UIViewContentModeCenter];
CGFloat imageEdgeInsetsTop = imageY > top*2/3 ? top*2/3-imageY : imageY;
CGFloat imageEdgeInsetsLeft = (btnW - imageW)/2 - imageX;
CGFloat imageEdgeInsetsBottom = -imageEdgeInsetsTop;
CGFloat imageEdgeInsetsRight = -(btnW - imageW)/2 + imageX;
[self setImageEdgeInsets:UIEdgeInsetsMake(imageEdgeInsetsTop, imageEdgeInsetsLeft, imageEdgeInsetsBottom, imageEdgeInsetsRight)];
CGFloat labelEdgeInsetsTop = (imageY+imageH+imageEdgeInsetsTop+space)-labelY;
CGFloat labelEdgeInsetsRight = labelX-(btnW - labelW)/2;
CGFloat labelEdgeInsetsLeft = -labelEdgeInsetsRight;
CGFloat labelEdgeInsetsBottom = -labelEdgeInsetsTop;
[self setTitleEdgeInsets:UIEdgeInsetsMake(labelEdgeInsetsTop, labelEdgeInsetsLeft, labelEdgeInsetsBottom, labelEdgeInsetsRight)];
}
self 是继承UIButton的一个子类,
思路是更改TitleEdgeInsets ImageEdgeInsets
EdgeInsets 是标示该空间距离父视图的边界距离,所以可以改变它而调整子控件的相对位置
EdgeInsets 是一个结构体 (上边距,左边距,下边距,右边距) = (top,left,bottom,right)
这两个属性标记标题和图片的相对位置,比如原来的frame 是 (0,0,0,0) 你想变成 (1,1,0,0)那么你可以更改EdgeInsets
也就是说 x 和 y 增加了1
left = 1- 0 = 1
top = 1- 0 = 1
这时,左移动1 那么右侧就得移动-1,这里都是绝对值想对的正负数
所以,上移动1 那么下移动-1
setTitleEdgeInsets:UIEdgeInsetsMake(1, 1, -1, -1) 即可
这种效果的按钮就可以用这个方法做成
https://github.com/imwangxuesen/JsenProjectEncapsulation 这个git仓库中有上边这个图片所示的按钮的实现过程,大家自行查阅吧