4

私のアプリには、 ABCDの4 つのタブがあります。によってUIViewController管理されていUITabBarControllerます。アプリは回転をサポートしているため、各ビュー コントローラーは に戻りYESますshouldAutorotateToInterfaceOrientation

スプリングとストラットを使用して、ほとんどの回転は iOS によって自動的に行われます。ただし、タブAもさらに配置する必要があり、その VC のwillRotateToInterfaceOrientation方法で行われます。

タブAの VCが選択され、画面が回転されると、その VC はwillRotateToInterfaceOrientationメッセージ (から iOS によって伝搬されたUITabBarController) を受信し、結果の回転は正しくなります。

ただし、選択したタブがBで画面が回転している場合、AwillRotateToInterfaceOrientationは呼び出されません。理にかなっています。しかし、次にタブAを選択すると、そのスプリングとストラットを適用した結果のみが得られ、その による後処理は行われませんwillRotateToInterfaceOrientation

これにしばらく苦労した後、オンラインで解決策を見つけることができなかった後、次のことを思いつきました。私はサブクラスUITabBarController化し、その中で、どれが であるかにかかわらず、willRotateToInterfaceOrientationすべての VC を呼び出します。willRotateToInterfaceOrientationselectedViewController

- (void) willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration {
    if (self.viewControllers != nil) {
        for (UIViewController *v in self.viewControllers) 
            [v willRotateToInterfaceOrientation:toInterfaceOrientation duration:duration];
    }
}

それは機能しますが、ハックのように見えます。私の質問は、私が正しいことをしていたかどうかです。willRotateToInterfaceOrientation画面の回転後に初めて表示する前に、常に VC を呼び出すように iOS に指示する方法はありますか?

4

1 に答える 1

4

カスタム レイアウトを処理する最善の方法は、メソッドをサブクラス化UIViewしてオーバーライドするlayoutSubviewsことです。システムlayoutSubviewsは、ビューのサイズが変更されるたびに (およびその他の場合に) ビューに送信します。したがって、ビュー A が異なるサイズで画面に表示されようとしている場合 (ビュー B が画面上にあったときにインターフェイスが回転したため)、layoutSubviewsビューコントローラー A にメッセージを送信しなくても、システムはビュー A にメッセージを送信しwillRotateToInterfaceOrientation:ます。

iOS 5.0 以降をターゲットにしている場合は、サブクラス化する代わりに、サブクラスのviewDidLayoutSubviewsメソッドをオーバーライドしてそこでレイアウトを行うことができます。ビュー固有のロジックを制御ロジックから分離するために、ビューの でそれを行うことを好みます。UIViewControllerUIViewlayoutSubviews

willRotateToInterfaceOrientation:ビューのサイズを実際に変更する前、および回転アニメーション ブロックの前に、システムがそのメッセージを送信するため、レイアウト インを行うこともお勧めできません。willAnimateRotationToInterfaceOrientation:duration:layoutSubviews、およびメッセージを回転アニメーション ブロック内に送信するviewDidLayoutSubviewsため、回転中にビューが画面上にある場合、サブビューの再配置がアニメーション化されます。

于 2012-06-18T21:33:08.050 に答える