13 | 12月 | 2012 | HMDT Blog

カテゴリー : 2012年 12月13日

SKStoreProductViewControllerでハマったこと


iOS 6から、SKStoreProductViewControllerっていうクラスが追加された。アプリ内でApp Storeの購入画面を表示できるスグレもの。ユーザの導線をアプリ内から逃がさずに、他のアプリを紹介できる。

こいつには、loadProductWithParameters:completionBlock:っていうメソッドが用意されていて、これにストアで表示させる項目をいろいろと設定する。

    // Create controller
    SKStoreProductViewController*   controller;
    controller = [[SKStoreProductViewController alloc] init];
    controller.delegate = self;

    // Set parameter
    NSDictionary*   parameters;
    parameters = [NSDictionary dictionaryWithObjectsAndKeys:
            @"500860946", SKStoreProductParameterITunesItemIdentifier,
            nil];

    // Present controller
    [self presentViewController:controller animated:YES completion:^() {
        // Load product
        [controller loadProductWithParameters:parameters
                    completionBlock:^(BOOL result, NSError* error)
        {
            // For success
            if (result) {
                //...
            }
            // For error
            else {
                //...
            }
        }];
    }];

このコードで、表示できる事が確認できた。

ちなみにドキュメントの方を確認すると、このメソッドの使い方としてこう書いてある。

In most cases, you should load the product information and then present the view controller.
(多くの場合、プロダクト情報を読み込んでから、ビューコントローラを表示するべきでしょう)

これ、そのまんまの通りに解釈すれば、loadProductWithParameters:を呼んで、それが成功したらpresentViewController:する、って思うでしょ。始めそれでやってみたんだけど、それだとアクセスに失敗したときにエラーも何も返ってこない。completion blockがまったく呼ばれないの。最初に実験したとき、間違ったプロダクトIDを与えていて、それでなんの音沙汰もなし。

なんでじゃー、といろいろいじくっていたら、presentViewController:を呼んでおかないと、エラーのときのcompletion blockは呼ばれなかった。ということで、なにはともあれpresentViewController:することにした。でもそれなら、ドキュメントに書いてある事まぎらわしくねー?