web-dev-qa-db-ja.com

UINavigationControllerを使用せずにStoryboardでUINavigationBarの高さを変更する方法はありますか?

ビューの1つでUINavigationBar階層の一部ではないカスタムUINavigationControllerを使用したい。 UINavigationBarをStoryboardにドラッグすると、次のように表示されます。

UINavigationBar

このバーは44ピクセルです。これは、ステータスバーがこのスペースを共有しない場合に十分です。 iOS7では、ステータスバーのスペースを含む画面全体を使用できるため、UINavigationBarの高さは44ピクセルではなく64ピクセルにする必要があります。

ビューをUINavigationControllerの階層に接続すると、正しいことが表示されます。

UINavigationController

ifUINavigationBarのプロパティbarPosition:UIBarPositionTopAttachedに設定されている場合、バーは64pxになります。ただし、これはreadonly-プロパティです。

私の検索結果には、「回避策」と思われるものだけが表示されています。このUINavigationControllerの前に無用のUIViewControllerを追加することにより、階層を持っているふりをすることができ、UINavigationBarを64pxで自動的に追加します。

本当に 64pxをカバーする '不正'(ナビゲーションコントローラーの助けなしで)UINavigationBarを使用する方法はありませんか?その場合、その理由に関して正当な理由はありますか?

(デフォルトではUINavigationBarが64pxであるべきだと言っているわけではありませんが、インスペクターにオプションがあるはずです)

(これを解決するためのプログラム的な方法で答える人もいます。これらの答えは機能しますが、それでもストーリーボードをdesignする必要があります。 (ギャップ)。これをストーリーボードで設定できるかどうか、または許可されない理由を知りたいのですが。)

59
Sti

プロパティbarPositionUIBarPositionTopAttachedに別の方法で設定できます!

  1. UINavigationBarにデリゲートを追加します。
  2. デリゲートクラスに-positionForBar:を実装します。

    - (UIBarPosition)positionForBar:(id<UIBarPositioning>)bar
    {
        return UIBarPositionTopAttached;
    }
    

ナビゲーションバーの上部も上部レイアウトガイドに固定する必要があります。

45
user3269713

ナビゲーションバーの高さをプログラムで変更できます。

[navBar setFrame:CGRectMake(0, 0, 320, 64)];

編集:コメントで書いたように、自動レイアウトを回避するためにviewDidLayoutSubviewsにこの行を入れる必要があるかもしれません。

26
Lyndsey Scott

Interface Builderの「Identity Inspector」の「User Defined Runtime Attributes」を使用して、ビューの上部にアタッチするように設定できます。 barPositionプロパティを設定します。

enter image description here

barPositionプロパティのドキュメントは次のとおりです。 https://developer.Apple.com/library/ios/documentation/uikit/reference/UIBarPositioning_Protocol/Reference/Reference.html

10
joerick

UINavigationControllerを使用するか、プログラムで設定することなく、これを実現する方法があります。ナビゲーションバーの高さの制約を任意の値(この場合は64)に設定するだけです。

同じことをプログラムで次のように達成できます。

[self.view addConstraint:[NSLayoutConstraint constraintWithItem:navigationBar attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeHeight multiplier:1 constant:64.0f]];

編集:

@ nerdist-colonyが指摘したように、Autolayoutを使用するときは、常にtranslatesAutoresizingMaskIntoConstraintsNOに設定する必要があります。そうしないと、制約に矛盾が生じる可能性があります。

8
barndog

私はスタンドアロンのUINavigationBarも使用していますが、同じ問題が発生しました。これを適切に修正する方法は2つあります。

制約と親UIViewを使用して修正しました。ストーリーボードのこのUIViewを、{0、0、320、64}フレームのUINavigationBarの親ビューとして設定します。 UINavigationBarに必要なサイズを強制する制約または制約のセットを追加できます。また、親UIViewのストーリーボードに正しいフレームがある場合、ストーリーボードの他のビューを通常どおりレイアウトできます。

これで、自動レイアウトが無効になっている場合、リンジーの答えで説明されているように、プログラムでバーの高さを変更できます。 -(void)viewDidLayoutSubviewsはそれを行うのに適した場所のようです。

3
kketch

Autolayoutを使用する場合、UINavigationBarの制約の高さを64以上のイベントに設定できます。

2
mrcuongth

メインストーリーボードを使用するSwift 3では、制約を使用して高さを変更し、機能させることができます。これは、実装が簡単だとわかった方法でした。

制約の作成。

最終的にどのように見えるか

1
FreitDev

最小限のコード介入でこれを行う方法を詳しく説明したブログ記事を書きました。バーはストーリーボードにギャップを表示しますが、デバイスでは正常に機能します。要するに、手順は次のとおりです。

1)ストーリーボードのView Controllerにナビゲーションバーを追加します。

2)ストーリーボードのナビゲーションバーの制約を設定します。
-Navigation Bar.Top = Top Layout Guide.Bottom
-Navigation Bar.Leading = Superview.Leading
-Navigation Bar.Trailing = Superview.Trailing

3)ストーリーボードのナビゲーションバーを@IBOutletとしてView Controllerに接続します。

4)View Controllerのクラスで、クラス宣言にUINavigationBarDelegateプロトコルを追加します。

5)View ControllerのviewDidLoadメソッドで、Navigation Barのデリゲートをselfに設定します。

6)View Controllerで、バーポジショニングデリゲートのpositionForBarメソッドを追加します。 TopAttachedを表すUIBarPositionを返します。 (注:UINavigationBarDelegateはUIBarPositioningDelegateからこのメソッドを継承します。)

GIF画像の完全な投稿はこちらです:
対応するNavigation ControllerなしでNavigation Barを簡単に使用

これらの手順は、Swift 2.1/Xcode 7.2以降で機能します

1
leanne

@startupThekid:

uINavigationControllerによって管理されているUINavigationBarの自動サイズ変更マスクを変更しようとすると、iOSは例外を生成します。

ただし、投稿したObjective Cコードに相当するSwiftは次のとおりです。

var navBar = self.navigationController!.navigationBar 

in viewDidAppear():

navBar.setTranslatesAutoresizingMaskIntoConstraints = false

制約を設定する必要がある場合:

var navBarHeightConstraint = 
      NSLayoutConstraint(item: navBar, attribute: .Height,
            relatedBy: .Equal, toItem: nil, 
            attribute: .Height, multiplier: 1, constant: height)

self.view.addConstraint(navBarHeightConstraint)

その後、必要に応じて、デバイスの向きの変更など、ナビゲーションバーの高さを変更するために、制約の定数プロパティを変更できるはずです

1
clearlight

私は同じ船に乗っていて問題を抱えていましたが、今では修正しました。フレームを明示的に設定することを避けるために正しいことをしようとしています。これは、さまざまなデバイスサイズの将来の保証と簡単なサポートに望ましいものです。私の場合、ナビゲーションバーの下にWebビューが必要です。

ser3269713's answer のように、View ControllerをUINavigationBarDelegateに設定し、positionForBar:を実装してUIBarPositionTopAttachedを返します。他のトリックは、自動レイアウトを使用してtopLayoutGuideの下にバーを配置することであるように思えました。

これはナビゲーションバーとWebviewをプログラムで作成した後、viewDidLoadで使用していたコードでしたが、バーが高さ44で止まっているのが見えました。しかし、すぐに理由を見ることができませんでした:

    [navigationBar sizeToFit];
    navigationBar.delegate = self;
    [self.view addSubview:navigationBar];
    [self.view addSubview:webView];
    id guide = self.topLayoutGuide;
    NSDictionary *viewNamesDict = NSDictionaryOfVariableBindings(webView, navigationBar, guide);
    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[webView]|" options:0 metrics:nil views:viewNamesDict]];
    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[guide][navigationBar][webView]|" options:0 metrics:nil views:viewNamesDict]];

しかし、私はさらにいくつかのことを考えて自動レイアウトをいじりましたが、それだけで私の問題の原因であることがわかりました。自動サイズ変更マスクからナビゲーションバーの翻訳された制約に依存しようとしていましたが、明示的に定義する必要があることがわかりました。動作する新しいviewDidLoadコードを次に示します。

    [navigationBar sizeToFit];
    navigationBar.delegate = self;
    navigationBar.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:navigationBar];
    [self.view addSubview:webView];
    id guide = self.topLayoutGuide;
    NSDictionary *viewNamesDict = NSDictionaryOfVariableBindings(webView, navigationBar, guide);
    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[navigationBar]|" options:0 metrics:nil views:viewNamesDict]];
    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[webView]|" options:0 metrics:nil views:viewNamesDict]];
    NSString *verticalLayoutVisualExpression = [NSString stringWithFormat:@"V:|[guide][navigationBar(%f)][webView]|", navigationBar.frame.size.height];
    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:verticalLayoutVisualExpression options:0 metrics:nil views:viewNamesDict]];

そして、はい、私が望んでいたように、これは横向きになると自動的にバーを移動し、ステータスバーは非表示になります。

(レイアウトコードをより簡潔にするMasonryのような自動レイアウトヘルパーを心からお勧めします。1つは、MasonryがtranslatesAutoresizingMaskIntoConstraintsをオフにしてくれます)

0
Pierre Houston

これは非常にハッキーな方法ですが、私にとってはうまくいきました。 NavigationViewControllerがあり、上部に[完了]ボタンと[キャンセル]ボタンがあるUINavigationBarがあるViewControllerをモーダルにロードしたい。これは次のように見えました: enter image description here

ご覧のとおり、UINavigationBarと同じ色にしたい上部に白い帯があります。 UINavigationBarの高さをプログラムで変更する代わりに、新しいビューを作成し、その背景色をUINavigationBar(HEX = F8F8F8、RGBA = 248,248,248,1.0)に設定しました。繰り返しになりますが、これは非常にハッキーです。これが今の様子です

enter image description here

0
sbru