Как получить ширину UITabBarItem?
ширина UITabBarItem варьируется, в зависимости от того, сколько есть.
как определить, насколько широки мои элементы панели вкладок?
Я ищу свойство, если это возможно, в отличие от математической формулы, так как на iPad также есть проблема заполнения по обе стороны панели вкладок. Рассмотрим эти скриншоты. Обратите внимание на заполнение с обеих сторон элементов панели вкладок на iPad (выделено красными полями). Эта обивка не существует на iPhone.
iPad:
в iPhone:
7 ответов
редактировать: в комментариях ниже было отмечено, что это решение не работает в бета-версии iOS 5, поэтому будьте готовы изменить его для удовлетворения ваших потребностей.
Я думаю, чтобы сделать это правильно, вы должны иметь возможность добраться до рамки каждого элемента панели вкладок. К счастью, это возможно:
CGFloat tabBarTop = [[[self tabBarController] tabBar] frame].origin.y;
NSInteger index = [[self tabBarController] selectedIndex];
CGFloat tabMiddle = CGRectGetMidX([[[[[self tabBarController] tabBar] subviews] objectAtIndex:index] frame]);
приведенный выше код дает вам координату y верхней части панели вкладок и координату x середины выбранного элемента вкладки. От здесь вы можете добавить представление индикатора в представление контроллера панели вкладок относительно этой точки.
отказ от ответственности: опасность при таком подходе заключается в том, что он заглядывает под капот UITabBar
класс, обратившись к его иерархии представлений и frame
свойство экземпляров private UITabBarButton
класса. Возможно (однако маловероятно), что этот подход может быть затронут/нарушен будущим обновлением iOS. Однако вы не получаете доступа к частным API, поэтому это не должно получить ваше приложение отклонено из App Store.
Я простой проект iPad, демонстрирующий, как он работает, в комплекте с анимацией.
uitabbaritem наследует от UIBarItem, который наследует от NSObject. Поскольку он не наследуется от UIView, я не знаю, сможете ли вы получить нужную информацию только с помощью свойства. Я знаю, что вам не нужен математический способ сделать это, но казалось бы, что получение кадра панели вкладок и разделение на # вкладок было бы разумным вариантом, который должен работать независимо от оборудования (iphone vs ipad). Обивка не должна влиять на это, верно? Так что есть:
tabSize = tabbar.frame.size.width / [tabbar.items count];
tabBarStart = tabbar.frame.origin.x;
// Assume index of tabs starts at 0, then the tab in your pic would be tab 4
// targetX would be the center point of the target tab.
targetX = tabBarStart + (tabSize * targetTabIndex) + (tabSize / 2);
мне также интересно узнать, находит ли кто-то простое свойство, чтобы дать эту информацию.
глядя на ответ выше:
- элементов
UITabBar
работа различная в iPhone и iPad. В iPhone они заполняют всю ширину, в iPad они центрированы по горизонтали. - существует интервал между элементами в iPad.
- вы можете установить значения для ширины и расстояния с помощью
tabBar.itemWidth
илиtabBar.itemSpacing
. Вы не можете прочитать системный интервал или ширину из него-вы получите0
если вы не установите он.
вот мой образец, как получить кадры всех UITabBarItems
:
// get all UITabBarButton views
NSMutableArray *tabViews = [NSMutableArray new];
for (UIView *view in self.tabBar.subviews) {
if ([view isKindOfClass:[UIControl class]]) {
[tabViews addObject:[NSValue valueWithCGRect:view.frame]];
}
}
// sort them from left to right
NSArray *sortedArray = [tabViews sortedArrayUsingComparator:^NSComparisonResult(NSValue *firstValue, NSValue *secondValue) {
CGRect firstRect = [firstValue CGRectValue];
CGRect secondRect = [secondValue CGRectValue];
return CGRectGetMinX(firstRect) > CGRectGetMinX(secondRect);
}];
теперь у вас есть таблица кадров, соответствующих вашему вкладка элементы. Вы можете например. поместите imageView на выбранную рамку кнопки индекса.
CGRect frame = self.tabBar.bounds;
CGSize imageSize = CGSizeMake(CGRectGetWidth(frame) / self.tabBar.items.count, self.imageView.image.size.height);
CGRect selectedRect = sortedArray.count > self.selectedIndex ? [sortedArray[self.selectedIndex] CGRectValue] : CGRectZero;
[self.imageView setFrame:CGRectIntegral(CGRectMake(CGRectGetMinX(selectedRect), CGRectGetMaxY(frame) - imageSize.height,
CGRectGetWidth(selectedRect), imageSize.height))];
я попробовал эти 2 свойства UITabBar:
@property(nonatomic) CGFloat itemWidth NS_AVAILABLE_IOS(7_0) UI_APPEARANCE_SELECTOR;
@property(nonatomic) CGFloat itemSpacing NS_AVAILABLE_IOS(7_0) UI_APPEARANCE_SELECTOR;
но получите нулевое значение, как сказал Vive. Поэтому я написал несколько кодов, чтобы получить правильную ширину:
CGFloat tabBarItemWidth = 0;
for (UIView *view in [self.tabBarController.tabBar subviews]) {
if ([view isKindOfClass:NSClassFromString(@"UITabBarButton")]) {
if (tabBarItemWidth == 0) {
tabBarItemWidth = view.frame.origin.x;
} else {
tabBarItemWidth = view.frame.origin.x - tabBarItemWidth;
break;
}
}
}
почему бы не использовать ширину первого UITabBarButton? Потому что есть пробелы между кнопками панели вкладок. :)
вы можете получить вид tabBarItem с помощью частной собственности view
. Потом просто сделать вид frame
.
- (CGRect)rectForTabBarItem:(UITabBarItem *)tabBarItem {
UIView *itemView = [tabBarItem valueForKey:@"view"];
return itemView.frame;
}
Swift 3
Я создал общий экземпляр в UIApplication, затем вытащил ширину моих подвидов
tabBarController?.tabBar.subviews[1].frame.width
просмотрите подвиды таббара и найдите представления с классом "UITabBarButton". Это представления для каждого элемента вкладки.
for (UIView *view in self.tabBar.subviews) {
if ([view isKindOfClass:NSClassFromString(@"UITabBarButton")]) {
// view.frame contains the frame for each item's view
// view.center contains the center of each item's view
}
}