将UITabBarItem图像下移?

111

通常在UITabBar的每个标签页上,您都会有一个小图像和一个命名该标签页的标题。 图像位于/居中于选项卡的顶部,以适应其下方的标题。 我的问题是:如果您想要具有仅包含图像而没有标题的tabBar,是否有一种方法可以将图像向下移动,使其在选项卡内更好地居中?

我目前正在使用(请参见下文):

[tabBarItem setFinishedSelectedImage:tabSelected withFinishedUnselectedImage:tabUnselected];

目前我希望使用没有标题的更大的图像,但是如果我将图像放大到大约70像素@2x以上,它会开始从UITabBar的顶部边缘滑出,同时底部留下很多未使用的空间。

11个回答

195

尝试调整tabBarItemimageInsets(以移动图标图像),并将控制器的标题设置为nil(这样不会显示标题)。在视图控制器的-init-viewDidLoad方法中放置类似以下代码:

Objective-C

self.tabBarItem.imageInsets = UIEdgeInsetsMake(6, 0, -6, 0);
self.title = nil;

Swift

self.tabBarItem.imageInsets = UIEdgeInsets(top: 6, left: 0, bottom: -6, right: 0)
self.title = nil

UITabBarItemUIBarItem的子类,它具有UIEdgeInsets imageInsets属性。根据您的选项卡图标图像,微调插图,直到看起来不错。

iPad特定调整

iPad上的选项卡项目在水平方向上分布(图标和标签并排)。

要调整图标和标签之间的间距,请调整水平的imageInsets而不是垂直的。


5
@Lukas:但这会使图像变小。 - Sourabh Bhardwaj
1
@Sourabh 对我来说不会缩小它们。 - TigerCoding
8
如果您需要像素完美的话,实际的缩进值是5.5f。 - user
1
@rr1g0 将徽章移动到自定义位置是不可能的。如果您需要自定义徽章位置或自定义徽章外观,则必须自行实现。 - Lukas Kukacka
1
@Sourabh,你需要使用负值来偏移底部,以避免缩小图像。 - Rmalmoe
显示剩余6条评论

156

你也可以通过Storyboard来完成。选择你的TabBarItem,进入Size Inspector并分配适当的插图(insets)。

这里输入图片描述

*演示在Xcode Version 7.3.1 (7D1014)上实现。


nice and clean! - ken
最好的答案......非常感谢@Neil Galiaskarov - Venkatesh Chejarla
不适用于我。 - Eric

55

创建一个 UITabBarController 的子类,在其 viewDidLoad 方法中:

- (void)viewDidLoad
{
    [super viewDidLoad];
    [self.viewControllers enumerateObjectsUsingBlock:^(UIViewController *vc, NSUInteger idx, BOOL *stop) {
        vc.tabBarItem.title = nil;
        vc.tabBarItem.imageInsets = UIEdgeInsetsMake(5, 0, -5, 0);
    }];
}

Swift 3:

for vc in self.viewControllers! {
    vc.tabBarItem.title = nil
    vc.tabBarItem.imageInsets = UIEdgeInsetsMake(5, 0, -5, 0)
}

这对我有用。只是对于Swift,方法enumerateObjectsUsingBlock不再可用。 - Junchao Gu
不要使用子类,而是将此代码放入您的AppDelegate中。 - Laszlo
1
将这段代码放在AppDelegate中也可以工作,但它并不比子类化更好。不过你可以有自己的偏好 :) - Brian

11

这对我很有效

Swift 4

let array = tabBarController?.customizableViewControllers
for controller in array! {
    controller.tabBarItem.imageInsets = UIEdgeInsetsMake(5, 0, -5, 0)
}

10

如果您正在使用Xamarin,这个代码可以使用:

screen.TabBarItem.ImageInsets = new UIEdgeInsets(5, 0, -5, 0);
screen.TabBarItem.Title = "";

2

iOS 11需要重写TraitCollection方法,除了设置ImageInsets之外。请在您的子类化UITabBarController类中添加该方法。

public override UITraitCollection TraitCollection {
 get {
  return UITraitCollection.FromHorizontalSizeClass(horizontalSizeClass: UIUserInterfaceSizeClass.Compact);
 }
}

好的提示帮助我解决了与iPad和iOS 11上选项卡栏项目图像位置相关的问题。但是在视图控制器级别覆盖特征集合太过严厉,更好的方法是子类化UITabBar类并在那里覆盖traitCollection属性。同时,返回仅具有水平类的特征集合将删除其他特征集合属性。return UITraitCollection(traitsFrom: [ super.traitCollection, UITraitCollection(horizontalSizeClass: .compact)]) 对我很有帮助。 - Emmanuel Paris

2

SWIFT 3.0

您可以根据设计需求设置图像的内边距,包括上、左、下和右。

self.tabBarItem.imageInsets = UIEdgeInsets(top: 5, left: 0, bottom: 0, right: 0)

2
在Swift 4.2中,UIEdgeInsetsMake已经被弃用,我们应该使用UIEdgeInsets
let array = tabBarController?.customizableViewControllers
    for controller in array! {
        controller.tabBarItem.imageInsets = UIEdgeInsets(top: 5, left: 0, bottom: -5, right: 0)
    }

1
//On tabbar viewDidload
override func viewDidLoad() {
    super.viewDidLoad()
    self.delegate = self
    
    tabBar.items![0].imageInsets = UIEdgeInsets(top: 6, left: 0, bottom: -6, right: 0)
}

我该如何使用SwiftUI实现这个?在onAppear/init()中,我尝试做类似于以下的事情:UITabBar.appearance().items?[0].imageInsets = UIEdgeInsets(top: 6, left: 0, bottom: -6, right: 0)但是好像不起作用,有什么建议吗? - Natto

1

2021年,Objective-C

我尝试了所有的方法,但都没有奏效。最终我发现问题出在使用SF符号作为tabbaritem图像上。如果我用自定义图像替换它,事情就会起作用。

    NSArray *tabItems = [self.tabBar items];
    // set tabItem icon, remove blue image with render mode set.
    UIImage *image1 = [[UIImage imageNamed:@"myIcon"] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
    
    // set title offset
    [tabItems[0] setTitlePositionAdjustment:UIOffsetMake(0, 20)];
    [tabItems[1] setTitlePositionAdjustment:UIOffsetMake(-20, 20)];
    [tabItems[2] setTitlePositionAdjustment:UIOffsetMake(20, 20)];
    [tabItems[3] setTitlePositionAdjustment:UIOffsetMake(0, 20)];

    // set image offset
    [tabItems[0] setImageInsets:UIEdgeInsetsMake(0, 0, -30, 0)];
    ...

对于uitabbaritem图像分辨率,@2x应为50x50px,@3x应为75x75px。

非常感谢,我已经搜索了几个小时并尝试弄清楚为什么它对我无效,因为我正在使用 SF 符号。 - dreampowder
1
使用 imageWithoutBaseline() 与 SF Symbols 一起使用以使 imageInsets 生效。 - Oleg Barinov

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接