UITableView
iOS
Swift
programming
development

Remove empty space before cells in UITableView

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions

Introduction

The blank area before the first UITableViewCell is usually not random layout drift. It is almost always one of a small set of causes: a section header, automatic content inset adjustment, grouped-style padding, or a header view you forgot was there.

Identify the source of the gap

Before changing properties blindly, determine what kind of space you are seeing.

  • If the gap is above the first section and scrolls with the table, suspect tableHeaderView or content inset.
  • If the gap looks like section spacing, suspect header height defaults.
  • If it only appears on newer iOS versions, check sectionHeaderTopPadding.
  • If the table is under a navigation bar, automatic safe-area adjustment may be involved.

That distinction matters because the fix for one cause can make another layout worse.

A reliable baseline configuration

The following UITableViewController setup removes the common top spacing sources while keeping the table behavior predictable.

swift
1import UIKit
2
3final class ListViewController: UITableViewController {
4    private let items = ["One", "Two", "Three"]
5
6    override func viewDidLoad() {
7        super.viewDidLoad()
8
9        tableView.tableHeaderView = UIView(frame: .zero)
10        tableView.contentInset = .zero
11        tableView.scrollIndicatorInsets = .zero
12        tableView.estimatedSectionHeaderHeight = 0
13        tableView.estimatedSectionFooterHeight = 0
14        tableView.sectionHeaderHeight = .leastNormalMagnitude
15        tableView.sectionFooterHeight = .leastNormalMagnitude
16
17        if #available(iOS 15.0, *) {
18            tableView.sectionHeaderTopPadding = 0
19        }
20    }
21
22    override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
23        items.count
24    }
25
26    override func tableView(
27        _ tableView: UITableView,
28        cellForRowAt indexPath: IndexPath
29    ) -> UITableViewCell {
30        let cell = tableView.dequeueReusableCell(withIdentifier: "Cell")
31            ?? UITableViewCell(style: .default, reuseIdentifier: "Cell")
32        cell.textLabel?.text = items[indexPath.row]
33        return cell
34    }
35
36    override func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
37        .leastNormalMagnitude
38    }
39
40    override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
41        nil
42    }
43}

Two details are easy to miss. First, a grouped table can still reserve header space even when you think the header height is zero. Using .leastNormalMagnitude is more reliable than returning plain zero in those cases. Second, iOS 15 introduced extra top padding for section headers, so sectionHeaderTopPadding = 0 is often the missing fix.

When content insets are the real problem

If the table view sits under a navigation bar or inside a container controller, the top gap may come from automatic inset adjustment rather than headers. In that case, inspect contentInsetAdjustmentBehavior and the surrounding layout.

You can turn that behavior off, but do it only if you control the full-screen layout and understand the tradeoff.

swift
1override func viewDidLoad() {
2    super.viewDidLoad()
3    tableView.contentInsetAdjustmentBehavior = .never
4}

This removes the automatic safe-area compensation, which can be correct for edge-to-edge designs and incorrect for standard navigation layouts. If your rows end up under the navigation bar, the fix was too aggressive.

Debugging the issue quickly

The fastest way to debug is to strip the table down:

  1. set tableHeaderView to nil or a zero-sized view
  2. return nil for section headers
  3. set header heights explicitly
  4. inspect content inset values at runtime

Once the gap disappears, add back only the behavior you actually need. That is more reliable than stacking one workaround on top of another.

Common Pitfalls

  • Returning zero for a grouped section header and expecting all spacing to disappear.
  • Forgetting sectionHeaderTopPadding on iOS 15 and later.
  • Clearing content insets when the real source is a section header.
  • Disabling automatic inset adjustment without checking how the table sits under bars and safe areas.
  • Leaving an empty tableHeaderView attached and overlooking it during debugging.

Summary

  • Top space before the first cell usually comes from headers, content insets, or iOS default padding.
  • Start by checking tableHeaderView, section header heights, and sectionHeaderTopPadding.
  • Use .leastNormalMagnitude for section header height when plain zero does not remove the gap.
  • Change contentInsetAdjustmentBehavior only when the layout truly requires it.
  • Diagnose by removing one spacing source at a time instead of layering random fixes.

Related reading
Free course
Beginner
7 lessons
2 hours
Tackling System Design Interview Problems

A short course that equips you with the skills to approach system design interviews methodically.

Start the free course
Track what you have practised

A free account saves your progress, solutions and study plan across every problem on Codemia.

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions

All Rights Reserved.