LoginSignup
8
10

More than 5 years have passed since last update.

UIPageViewControllerやContainer View上のUITableViewやUIWebViewでバーのtranslucentに対応する

Last updated at Posted at 2016-04-08

もう懐かしい話となってしまいますが、UITableViewControllerやUICollectionViewController、WebViewを全画面で配置する際には、上端と下端をLayout Guide ではなく UIViewControllerのrootの view全体に 対するConstraintsを追加する必要があります。

これによって、UITableView、UICollectionView、UIScrollView、UIWebViewがUINavigationBar、UITabBar、UIToolBarの下に潜り込み(automaticallyAdjustsScrollViewInsetsがオンの場合)、透過されたBarの下にも表示されるようになります。

ただ、automaticallyAdjustsScrollViewInsetsは Child View Controller に対しては働かないという弱点があります。Child View Controllerとは、View Controllerの中にView Controllerを埋め込んでいる状態です。例えば、 UIPageViewContorller やInterface Builder上で指定できる Container View を使った場合はこの状態になります。

そこで、Layout Guideのある一番親のViewControllerまでさかのぼって、Layout Guideの幅をゲットし、それをUIScrollViewにセットするスニペットを使っています。

+ (void)setupInsetForScrollView:(UIScrollView *)scrollView onChildViewController:(UIViewController *)viewController
{
    if (!viewController.automaticallyAdjustsScrollViewInsets) {
        return;
    }
    UIViewController *currentViewController = viewController;
    UIViewController *rootParentViewController;
    while (currentViewController.parentViewController) {
        currentViewController = currentViewController.parentViewController;
        if ([currentViewController isKindOfClass:[UITabBarController class]] ||
            [currentViewController isKindOfClass:[UINavigationController class]] ||
            [currentViewController isKindOfClass:[UIPageViewController class]]) {
            continue;
        }
        rootParentViewController = currentViewController;
    }
    if (!rootParentViewController) {
        return;
    }

    // http://stackoverflow.com/a/21541533/1474113
    CGFloat topLength = rootParentViewController.edgesForExtendedLayout & UIRectEdgeTop ?
        rootParentViewController.topLayoutGuide.length : 0;
    CGFloat bottomLength = rootParentViewController.edgesForExtendedLayout & UIRectEdgeBottom ?
        rootParentViewController.bottomLayoutGuide.length : 0;
    UIEdgeInsets insets = UIEdgeInsetsMake(topLength, 0.0, bottomLength, 0.0);
    scrollView.contentInset = scrollView.scrollIndicatorInsets = insets;
}

これをChild View Controllerからこんな感じでviewWillLayoutSubviewsの時に呼び出せば自動調整されます・・!

- (void)viewWillLayoutSubviews
{
    [super viewWillLayoutSubviews];
    [YPLayoutGuideHelper setupInsetForScrollView:self.collectionView onChildViewController:self];
}

※UIWebViewの場合はwebView.scrollViewを渡してください!

8
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
8
10