4

I have a UINavigationController which contains a UITableViewController. This navigation controller pushes other UITableViewControllers around and eventually these table view controllers will have a prompt.

The problem is when I set this prompt programmatically it overlaps the content of the table view underneath it.

enter image description here

(A search bar is being hidden by the navigation bar)

I was looking around in SO and found this answer. I tried the suggestion there in two different ways in the affected view controller but nothing changed:

override func viewDidLoad() {
    super.viewDidLoad()
    self.edgesForExtendedLayout = .None;
    self.extendedLayoutIncludesOpaqueBars = false;
    self.navigationItem.title = NSLocalizedString("Add Anime or Manga", comment: "")
    self.navigationItem.prompt = NSLocalizedString("Search media belonging to this series.",  comment: "")
}

-

override func viewDidLoad() {
    super.viewDidLoad()
    self.navigationItem.title = NSLocalizedString("Add Anime or Manga", comment: "")
    self.navigationItem.prompt = NSLocalizedString("Search media belonging to this series.",  comment: "")
    self.edgesForExtendedLayout = .None;
    self.extendedLayoutIncludesOpaqueBars = false;
}

A comment in that same answer linked to this Apple guide on preventing views from overlapping each other. The problem is UITableViewController doesn't appear to have top/bottom layout guides so I can't create a constraint (another SO answer says having said layouts in table view controllers is irrelevant).

As such I have exhausted all my options.

Cœur
  • 37,241
  • 25
  • 195
  • 267
Andy Ibanez
  • 12,104
  • 9
  • 65
  • 100
  • Have you found how to work it out? I'm facing the exact same problem, just with a `UIViewController` and a `UITableView`. Thanks. – Zaphod Nov 05 '15 at 14:39
  • @Zaphod Unfortunately no. I ended up adapting my design to something else. – Andy Ibanez Nov 06 '15 at 19:28
  • So did I... Well, may be an iOS bug. Are you aware of some kind of radar opened on the subject? – Zaphod Nov 07 '15 at 21:03

4 Answers4

6

I have tried to reproduce your problem and it seems that when not all the viewControllers have a prompt the navigationBar is somehow not resizing properly.

It seems you need to somehow trigger the layouting for the UINavigationController. The only way I could make it work properly was by adding this in viewWillAppear:

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

    [self.navigationController setNavigationBarHidden:YES];
    [self.navigationController setNavigationBarHidden:NO];

}

Maybe this prompt is meant to be used consistently across the entire application (meaning having one for all viewControllers or none of them), that's why the UINavigationController does not layout it's subviews when it changes.

Hope this works for you too.

Catalina T.
  • 3,456
  • 19
  • 29
  • For some reason, this doesn't seem to be working for me. I'm not sure if it has to do with the fact that setNavigationBarHidden also expecteds a bool parameter for animation, but when the navbar reappears, it still overlaps. I will go ahead and open a bug report with Apple. Thank you for your help! – Andy Ibanez Mar 17 '15 at 23:01
2

Select your TableViewController from document outline and change the value to translucent navigation bar of top bar in attributes inspector. Be sure that you will not select uitableview you should select your your table view controller(aka File's Owner) from document outline.

miletliyusuf
  • 982
  • 1
  • 10
  • 12
2

You have to set prompt only if view did appear, then it works:

    override func viewDidAppear(_ animated: Bool) {
         navigationItem.prompt = "your prompt here"
    }
birdy
  • 943
  • 13
  • 25
0

It's 2019 and this is still not fixed. Slow Clap. I refuse to be cowed by such things so I hammered iOS into submission with the dirtiest trick in the book. I fixed this by doing a disgusting -44 "y trick" on the UINavigation while placing the UITableView in top 44, I know it's stupid, but it works.. I am sure new fangled phones will ruin my genius.. but hey ho.. I have lazily left irrelevant code (because I am idle) but hopefully you can see what I did.

WITHOUT THE y: -44 Hack enter image description here WITH THE y: -44 Hack enter image description here

let screenSize: CGRect = UIScreen.main.bounds
let navBar = UINavigationBar(frame: CGRect(x: 0, y: -44, width: screenSize.width, height: 44)) //<<--note minus 44
navBar.barTintColor = Globals.Color_BackgroundGrey()
navBar.isTranslucent = false
tableView.contentInset = UIEdgeInsets(top: 44, left: 0, bottom: 0, right: 0); //<--note plus 44
self.edgesForExtendedLayout = []
let navItem = UINavigationItem(title: "Boaty Mc Boatface")
let doneItem = UIBarButtonItem(title: "Back", style: .plain, target: self, action: #selector(done))
navItem.rightBarButtonItem = doneItem
navBar.setItems([navItem], animated: false)
view.addSubview(navBar)
Mr Heelis
  • 2,370
  • 4
  • 24
  • 34