Как выровнять по вертикали (по центру) содержимое UITableView?

Я хочу центрировать содержание моего UITableView, которая содержит headerView и footerView создан в раскадровке, and UITableViewCells. Как я могу достичь этого?

вот что я пытаюсь реализовать, чтобы решить мою проблему, но это не работает.

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];

    CGFloat height = self.tableView.frameHeight - self.navigationController.navigationBar.frameHeight - [UIApplication sharedApplication].statusBarFrame.size.height - (self.rowCount * self.rowHeight);
    self.tableView.tableHeaderView.frameHeight = height / 2.0;
}

поэтому я вычитал высоту navigationBar & statusBar и высоту ячеек до высоты tableView, чтобы получить высоту пустой области. Теперь, когда я получаю высоту, если пустая область, я разделил ее на 2 для нижнего колонтитула и вид сверху.

8 ответов


на viewWillAppear и didRotateFromInterfaceOrientation функции :

CGFloat headerHeight = (self.view.frame.size.height - (ROW_HEIGHT * [self.tableView numberOfRowsInSection:0]))) / 2;

self.tableView.contentInset = UIEdgeInsetsMake(headerHeight, 0, -headerHeight, 0);

Это решит вашу проблему.

редактировать

вызов updateTableViewContentInset


использовать contentSize собственность UITableView, вот как вы не должны брать ячейку height или count в расчет.

- (void) updateTableInsetsForHeight: (CGFloat) height
{
    CGFloat tableViewInset = MAX((height - self.tableView.contentSize.height) / 2.0, 0.f);
    self.tableView.contentInset = UIEdgeInsetsMake(tableViewInset, 0, -tableViewInset, 0);
}

обновить contentInsets после перезагрузки tableView - данные, и когда содержащее представление tableView становится видимым (viewWillAppear:) и когда он меняет размер (viewWillTransitionToSize:withTransitionCoordinator:).

- (void) viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id<UIViewControllerTransitionCoordinator>)coordinator
{
    [self updateTableInsetsForHeight: size.height];
}

Swift 3 на основе ответа Pipiks

let headerHeight: CGFloat = (view.frame.size.height - CGFloat(Int(tableView.rowHeight) * tableView.numberOfRows(inSection: 0))) / 2
tableView.contentInset = UIEdgeInsetsMake(headerHeight, 0, -headerHeight, 0)

добавить UIView вверху (UIView должен быть родителем вашего TableView) вашего TableView из раскадровки. После этого установите его ограничения для заполнения представления. Теперь установите размер вашего TableView и установите его ограничения для центра как по вертикали, так и по горизонтали UIView. Это решит вашу проблему.


Я узнал, что вызывает мои вычисления неправильно. Ценность себя.метод TableView.границы.размер.высота отличается от фактической высоты в viewWillAppear. Я использовал self.вид.границы.размер.вместо высоты.


переопределить viewDidLayoutSubviews и сравните tableView в frame С contentSize установить contentInset. В Swift 4 :

override func viewDidLayoutSubviews() {
    super.viewDidLayoutSubviews()

    let tableViewHeight = self.tableView.frame.height
    let contentHeight = self.tableView.contentSize.height

    let centeringInset = (tableViewHeight - contentHeight) / 2.0
    let topInset = max(centeringInset, 0.0)

    self.tableView.contentInset = UIEdgeInsetsMake(topInset, 0.0, 0.0, 0.0)
}

это хорошо работает с self-sizing Table view cells


установить кадр вашего UITableView, как это

CGFloat width = self.view.frame.size.width;
CGFloat height = self.view.frame.size.height;
CGFloat tableHeight = 200.0; //your table height
self.tableView.frame = CGRectMake(0,(height-tableHeight)/2,width,tableHeight);

или попробуйте это

enter image description here


на SWIFT 3:

var headerHeight: CGFloat = (tableView.frame.size.height - CGFloat(Int(tableView.rowHeight) * tableView.numberOfRows(inSection: 0))) / 2
if headerHeight > 0 {
    tableView.contentInset = UIEdgeInsetsMake(headerHeight, 0, 0/*-headerHeight*/, 0)
} else {
    headerHeight = 0
    tableView.contentInset = UIEdgeInsetsMake(headerHeight, 0, 0/*-headerHeight*/, 0)
}

результат :

enter image description hereenter image description here enter image description hereenter image description here