3

Xcode 4.3.2 で空のアプリ テンプレートを使用すると、プロジェクトが作成されるため、関連する NIB はありません。

FooViewController.m

-(void) loadView {
    UIView *view = [[UIView alloc] init];
    view.backgroundColor = [UIColor yellowColor];
    self.view = view;                     
}

ビューがインスタンス化され、 に割り当てられself.viewます。2 つの方法:

- (void)viewDidLoad {
    [super viewDidLoad];

    NSLog(@"self.view is %@", self.view);
}

-(void) viewDidAppear:(BOOL)animated {
    NSLog(@"self.view is %@", self.view);
}

最初の方法は印刷されます

self.view is <UIView: 0x18e4d0; frame = (0 0; 0 0); layer = <CALayer: 0x182a00>>

2番目のものが印刷されている間

self.view is <UIView: 0x18e4d0; frame = (0 20; 768 1004); layer = <CALayer: 0x182a00>>

との間viewDidLoadviewDidAppear、ビューのサイズが変更されます。それをリサイズしたメカニズムは何ですか?私たちは実際にそれを当てにすることができますか?高く評価されている本 Programming iOS, 2nd Ed の著者である Matt Neuburg でさえ、この方法でそれを行っているためです (508 ページのように)。

4

4 に答える 4

3

ViewController のライフサイクルを理解する必要があります。viewDidLoad ではビューが作成されますが、境界/寸法は設定されません。これは、次のステップで行われます。ディメンションの設定に viewWillAppear を使用できます (ほとんどの人が行うことです)。ViewDidAppear が最後に発生し、最終的な外観とアニメーションが既に開始されています。

ええ、viewDidLoad と viewDidAppear の間で、ビューはその次元と境界を取得します。これは完全に信頼性が高く、ViewController ドキュメントにも記載されています。

ビューを作成する必要があるたびに viewDidLoad が呼び出されることにも注意してください (初回およびメモリ不足の警告の後 - 通常、メモリが必要になるとビューの割り当てが解除されます)。スタックとそのビューがレンダリングされようとしています。

ビューの外観に関連するドキュメントをご覧ください: http://developer.apple.com/library/ios/#featuredarticles/ViewControllerPGforiPhoneOS/RespondingtoDisplay-Notifications/RespondingtoDisplay-Notifications.html#//apple_ref/doc/uid/TP40007457- CH12

于 2012-05-24T20:42:04.810 に答える
0

これを' sにするとviewController ' sのviewサイズが変更されたように見えます。それ以外の場合は、フレームを手動で設定する必要があります。viewControllerrootViewControllerapplicationwindow

私はこのコードを試しました:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    self.window.backgroundColor = [UIColor whiteColor];

    FooViewController *viewController = [[FooViewController alloc] init];

    self.window.rootViewController = viewController; 
    [self.window makeKeyAndVisible];

    FooViewController *viewController2 = [[FooViewController alloc] init];
    [viewController.view addSubview: [viewController2 view]];

    return YES;
}

viewControllerサイズが変更されましたが、そうでviewController2はありませんでした。

またviewController、このすべてのメソッドが呼び出されました:

viewDidLoad
viewWillLayoutSubviews
viewDidLayoutSubviews
viewDidAppear

と呼ばれただけviewController2です。viewDidLoadviewDidAppear

また興味深い:それが呼び出されるviewController前にサイズ変更されました。viewWillLayoutSubviews

編集:

これはさらにテストする価値があると思いました。次のコードを使用します。

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    self.window.backgroundColor = [UIColor whiteColor];

    FooViewController *viewController = [[FooViewController alloc] init];
    NSLog(@"after init: self.view is %@", viewController.view);
    self.window.rootViewController = viewController; 
    NSLog(@"after setting to rootViewController: self.view is %@", viewController.view);
    [self.window makeKeyAndVisible];
    NSLog(@"after makeKeyAndVisible: self.view is %@", viewController.view);

    return YES;
}

結果は次のとおりです。

viewDidLoad:                         frame = (0 0; 0 0)
after init:                          frame = (0 0; 0 0)
after setting to rootViewController: frame = (0 0; 0 0)
after makeKeyAndVisible:             frame = (0 20; 320 460)
viewWillLayoutSubviews:              frame = (0 20; 320 460)
viewDidLayoutSubviews:               frame = (0 20; 320 460)
viewDidAppear:                       frame = (0 20; 320 460)

[self.window makeKeyAndVisible];犯人もそうです。

于 2012-05-26T10:13:24.113 に答える
0

デフォルトでは、このautoresizesSubviewsプロパティにより、ビューが表示されるときにサブビューのサイズが変更されます。

于 2012-05-24T20:21:09.023 に答える
0

self.view は、画面に表示されるまで実際には作成されません。遅延ロードです。が呼び出された後viewWillAppear、フレームが設定されます。はい、これらの値は電話の画面と向きに応じて設定されているため、信頼できます。

self.view はかなり特別なビューです。私はしばしばそれを直接操作しません。通常は、コンテナー サブビューを追加して、それをプライマリ ビューとして扱います。サイズ変更のため、self.view を静的エンティティとして扱わないことをお勧めします。サブビューの自動サイズ変更マスクを適切に設定して、self.view が変更されたときに適切に表示されるようにしてください。

さらに質問に答えるために、UIKit は、画面のサイズ、向き、ナビゲーション バー、ステータス バー、ツールバーなどを考慮して、ビューのフレームを具体的に設定します。viewWillAppear呼び出される前に設定したフレームが、同じ。実際、ナビゲーション バー、方向、またはその他の要因が変化すると、self.view はさらに変化します。したがってviewWillDisplay、self.view の静的サイズが保証されていない場合でも、それを変更すると、デバイスのそのステータスを反映するように適切にリセットされます。

UIKit はこの実装の詳細を処理します。デバイス固有の変更を考慮する必要がなく、サブビューの自動サイズ変更が適切に設定されていることを確認するだけで、あとは UIKit が処理するため、これは贅沢なことです。

于 2012-05-24T20:39:55.757 に答える