ストーリーボードを使用したカスタムビュー


96

複雑な画面(View Controllers)では、全体を細かく分割するために使用していました(ウィジェットと呼びます)。これらのウィジェットは基本的にMyWidget.hMyWidget.mファイルおよびファイルで構成されMyWidget.xib、ルート要素はでUIViewあり、MyWidgetクラスはUIViewのファイル所有者です。このウィジェットの初期状態では、を実行しloadNibNamedます。

次に、ビューコントローラーでを実行し[[MyWidget alloc] init]、ビューのコントローラーのメインビューにサブビューとして追加します。これまでのところ、完全に動作します。

ストーリーボードで同じようにするにはどうしたらいいのかと思っています。UIViewどこかにドラッグし始めることができないので、常にから始めUIViewControllerなければなりません。

ストーリーボードでこれを実行する方法がない場合は、メイン画面とセグエにストーリーボードを使用し、別の.xibファイルを使用してカスタムビューを定義することで、以前の方法で単純に実行できますか?


xibストーリーボードではなく、ビューコントローラのを個別に作成しますか?
tipycalFlow 2012

これに対する解決策を見つけましたか?
aryaxt

@aryaxt:ストーリーボードとxibを組み合わせて使用​​しています。メイン画面とxibのストーリーボード。UIViewのみが複雑なビューまたはウィジェットのルートになります。(ストーリーボードを使用して)元の質問に対する実際の回答ではありませんが、基本的には以前に行ったのと同じことをします。
znq

最近では、コンテナービューを使用するだけです。これは本当にシンプルです..stackoverflow.com
questions/23399061/

回答:


189

ウィジェット/ビューを別の.xibファイルに配置することは機能し、特に複数のビューコントローラーから同じビューを参照する場合に適しています。

ただし、同じストーリーボード内で追加のビュー/ウィジェットを表示したい場合もあり、それは可能です。方法は次のとおりです。

  1. IBでビューコントローラーを選択し(ビューの下の黒いバーをクリックします)、UIViewをオブジェクトライブラリから黒いバーにドラッグします。

    ここに画像の説明を入力してください

  2. ビューが黒いバーにある場合、それはIBの他のビューと同様にインスタンス化されますが、コードで追加するまで、ビュー階層に追加されません。必要に応じて、ビューのクラスを変更して独自のサブクラスに一致させます。

    ここに画像の説明を入力してください

  3. 他のビューを接続するのと同じように、ビューコントローラーに接続できます。 ここに画像の説明を入力してください

  4. 追加されたビューがドキュメントアウトラインに表示され、アクションと参照をそこにフックすることもできます。

    ここに画像の説明を入力してください


さて、残っている問題は、何度クリックしたりダブルクリックしたりしても、実際にはビューを表示できないことです。これは、同じストーリーボードにビューを配置する目的全体を無効にすることになります。幸い、私が知っている2つの回避策があります。

最初の回避策は、黒いバーからビューコントローラーのビューにビューをドラッグして戻し、編集し、完了したら黒いバーにドラッグして戻すことです。これは面倒ですが信頼できます。

他の回避策はもっと厄介ですが、すべてのビューを同時に表示できるので、私はそれを好みます。

  1. オブジェクトライブラリから新しく追加したビューにUITableViewをドラッグします。

  2. 次に、UITableViewCellをそのUITableViewにドラッグします。

    ここに画像の説明を入力してください

  3. これを行うと、ビューがサイドで魔法のように飛び出しますが、不要なUITableViewがあります。これを0x0にサイズ変更するか、削除してもUIViewは(通常は)表示されたままです。

  4. 場合によっては、セカンダリビューがIBで再び非表示になることがあります。UITableViewを削除した場合、またはUITableViewが階層内にある場合は、UITableViewCellをクリックするだけで上記の手順を繰り返すことができ、ビューが再び表示されます。

2番目の方法はUIViewsでは機能しますが、UIToolbarsではあまり機能せず、UIButtonsでは不可能です。そのため、多くの異なるサブビューを含める必要があるときに私が見つけた最もクリーンな解決策は、単一のセカンダリUIViewをコンテナーとしてビューコントローラーにアタッチすることです。決して表示されず、すべてのセカンダリビューをそこに配置し、UITableViewCellトリックを使用してすべてを表示します。ダミーのUITableViewを0x0にサイズ変更して、それを非表示にします。これがすべて一緒に見える様子のスクリーンショットです。

ここに画像の説明を入力してください


2013年3月、私はこれを行う必要はありませんでした。黒いバーを完全に無視して、ビューをメインビューに直接ドラッグアンドドロップする必要があります。これは正常に機能します(Xcode 4.5以降)
Adam

同じViewControllerでそのカスタムuivewを再利用することは可能ですか?2つのカスタムuivewsが必要-そして、それがどのように行われるか?
Morten Gustafsson 2013年

2
ダン、私は単に別のxibを作成することを好みます。6か月以内にアプリを更新する必要がある場合、おそらくこのことをすべて覚えていません。
サンディ

これは素晴らしい答えですが、誤って別の方法を見つけました。アウトレットを実際のビューコンポーネントに接続する場合。このような内部ビューのコンポーネントに少しカーソルを合わせると、ポップアップ表示されて選択しやすくなります。その後、ストーリーボードに表示されます...
Oded Ben Dov 2013

7
これは信じられないほど素晴らしい歴史的回答ですが、実際には完全に古くなっています。Appleは、「コンテナービュー」を導入することで問題全体を修正しました。これは、アプリを作成するときに行う中心的で基本的なことです-すべてが常に「コンテナービュー」です。おかげさまで、とても簡単になりました。
Fattie

11

ビューコントローラーを他の場所(ストーリーボードではなく)に作成したいだけの場合は、これを実現する非常に簡単な方法があります。

1)通常どおり、個別のsを使用してCustomViewControllerabcdController私が試したコードで)sを作成しますxib

2)ストーリーボードにUIViewController(またはのスーパークラスであったものは何でも)追加しますCustomViewController

3)次に示すように、CustomViewController代わりにCustomClassを設定しUIViewControllerます。

ここに画像の説明を入力してください

4)最後に、でviewDidLoad、カスタムxibをロードして完了です。

- (void)viewDidLoad
{
    [super viewDidLoad];
    [[NSBundle mainBundle] loadNibNamed:@"abcdController" owner:self options:nil];
    // Do any additional setup after loading the view from its nib.
}

3
非常に詳細な回答をありがとうございましたが、実際にはカスタムビューコントローラーではなく、標準のUIViewControllerに追加されるカスタムビュー(ウィジェット)を探しています。したがって、ビューコントローラーは問題ではありませんが、カスタムウィジェットを作成するための最良の方法は何なのかと思っていました。A)以前と同じように、.xibファイルを使用してそれを実行するか、B)まだ知らない他のいくつかのアプローチ:-)
znq

1
うーん...私はあなたが欲しいものを得たと思います。基本的には、同じコントローラーで複数のビューを処理したいですか?それ以外の方法は考えられませんloadNibNamed... XO
tipycalFlow

これは私のためにこの問題を解決しました:stackoverflow.com/questions/11047991/… しかし、viewDidLoadの代わりに、loadViewを使用しました...
Morkrom

1
繰り返しますが、これはすべてです(ありがとうございます!)コンテナービューがここにあるため、完全に古くなっています。コンテナービューをクリックするだけで完了です
Fattie

1

ストーリーボードから特定のビューコントローラーのインスタンスを取得し、その上でビューを使用するには、このようなことを行うことができると思います。

ex:
MyViewController* myViewController = [[UIStoryboard storyboardWithName:@"Main"  bundle:nil] instantiateViewControllerWithIdentifier:@"myViewController"];
UIView* view = myViewController.view; //Get the view from your StoryBoard.

お役に立てれば

ありがとうVijay

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.