2014年3月31日月曜日

iOSアプリを動作させる実機を追加する方法

iOSアプリを動作(Xcodeで)させる実機を追加する方法


最近、古いiPhoneを入手したので、開発で使うことにしました。
しかし、実機登録のやり方をすっかり忘れてしまったので、備忘録としてその方法を記載します。


Device登録


iOS Dev CenterでDeviceを登録
(事前準備としてXcodeのOrganizerで端末のIdentifier(UDID)を調べておく)

『Certificates, Identifiers & Profiles』→ iOS Apps 『Certificates』→『Devices』で新規登録



Provisioning Profileの変更

同じ画面で開発用のProvisioning Profileを変更

追加したデバイスを選択

変更したProvisioning Profileをダウンロード

ダウンロードしたProvisioning ProfileをダブルクリックなどでXcodeにインポート


Xcodeの設定


  1. Xcodeを起動して、登録した実機を繋ぎ『Organizer』を選択
  2. DEVICESの中から繋いだ実機を選んで『Use for Development』を押す
  3. デバイスに緑のアイコンが灯ればOK



デバイス名の変更



ちなみにXcode上に表示されるデバイス名は実機側で変更できます。
『設定』→『一般』→『情報』→『名前』









2014年3月28日金曜日

Objective-Cで簡単に遅延実行する方法

アプリを作っていると、処理を少し遅らせて実行したい場合があります。
Objective-Cでのやり方を備忘録として記載しておきます。


performSelectorを使用


『performSelector:withObject:afterDelay:』メソッドを使用すると簡単にできます。


=======================================

[self performSelector:@selector(hoge) withObject:nil afterDelay:1.0];

=======================================




ただ、このやり方は以下のような問題点があります

  • 並列処理では使えない
  • セレクターで呼ぶメソッドの引数を一つしか渡せない


これを解決するには、並列処理のときと同じようにGCDを使います。



GCDを使用


=======================================

dispatch_after(dispatch_time(DISPATCH_TIME_NOW, 1.0 * NSEC_PER_SEC), dispatch_get_current_queue(), ^{
    //遅延実行する処理
});

=======================================









2014年3月25日火曜日

Objective-Cで簡単に並列処理をする方法

プログラムで重い処理を実行すると、フリーズしたような状態になることがあります。
そういう場合、並列(非同期)処理をして、別スレッドに重い処理を持って行きます。
Objective-Cでのやり方を調べたので備忘録として記載しておきます。


NSOperationQueueを使用


NSOperationQueueを使用すると簡単にできます。


==========================

NSOperationQueue* queue = [[NSOperationQueue alloc] init];
[queue addOperationWithBlock:^{
    //重い処理
}];

==========================

ただ、このやり方だと次のような問題点があり、単純な処理しか行えません。

  • スレッドセーフでないオブジェクトを扱えない
  • スレッドの処理を終えた後の次の処理を行うのが簡単にできない



GCD(Grand Central Dispatch)の利用


GCDとはAPIを通して処理のブロックをキューに入れると、ランタイムの方で上手く並列実行してくれるという仕組みのことです。
このやり方だと、前の方法での問題点は解決できます。


==========================

dispatch_queue_t q_global = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_queue_t q_main   = dispatch_get_main_queue();
dispatch_async(q_global, ^{
    
    //重い処理
    
    dispatch_async(q_main, ^{
        
        //重い処理が終わった後の処理
        
    });
});

==========================



並列処理というと難しい印象がありますが、GCDを使えば簡単ですね。






2014年3月24日月曜日

Objective-Cで英字のみのデータを判別する方法

Objective-Cで英字のみのデータを判別する方法


調べても見つけづらかったので、備忘録として記載しておきます。


Objective-Cで正規表現


正規表現を使って以下のように記述する。

============================

NSError* err = nil;
NSRegularExpression* regex = nil;

// 検索する文字列
NSString* string = @"abc123";

// 正規表現オブジェクト作成(英字のみ)
regex = [NSRegularExpression
           regularExpressionWithPattern:@"([a-zA-Z]*)"
           options:NSRegularExpressionCaseInsensitive
           error:&err];

// 比較
NSTextCheckingResult *match = [regex firstMatchInString:string
                        options:0
                        range:NSMakeRange(0, string.length)];

if (match) {
    // マッチした時の処理
    NSRange matchRange = [match range]; // マッチした個数
    
    //マッチした個数と文字列の長さが同じ場合(全て英字)
    if (matchRange.length == string.length) {
        //英字のみの場合の処理
    }
}

============================





2014年3月20日木曜日

『Processing for App Store』ってどんな状態?

昨日(3/19)頃から審査の通ったアプリが『Processing for App Store』から変わらないという事象が発生しています。
私もそれに巻き込まれてしまい、ヤキモキしているところです。

そんな時、ふと次のようなことが気になりました。
そもそも、『Processing for App Store』とはどんなステータスなのでしょうか。

iTunes Connect Developer Guideにはこのように書かれています。

Your binary is being processed and will be ready for sale within 24 hours.

つまり、24時間以内に『Ready for Sale』になるということです。


通常なら、数分から1時間くらいで『Ready for Sale』になるので2~3時間も経過するとAppleに苦情を言いたくなります。
しかし、24時間以内と定義されているため、その段階で苦情を入れてもあまり意味がありません。
実際にそうした人は『最大で24時間は待ってね』と言われたらしいです。

ただ、現状は24時間以上経過している人も多数いらっしゃるので、Apple側で何か問題が発生していると思われます。

この現象に巻き込まれている人はひとまず24時間経過するのを待って、堂々とAppleに苦情を入れましょう。


タップで計算式を作って暗算する知育系アプリです。
あなたの脳偏差値はいくつかな?




2014年3月19日水曜日

App Storeランキングはマイナーカテゴリを狙うべし

前回のお話では結局は良いアプリを作るのがランキングに載る近道であるということでした。
しかし、ランキングのロジックが変わったといっても依然ダウンロード数がかなりの要素を占めています。
いくら良いモノを作っても、広告をバンバン出しているようなアプリに立ち向かうのは難しいでしょう。
では、プロモーションにお金をかけられない個人開発者がランキングに載るにはどのような策があるのでしょうか?



以下のグラフは2013年のカテゴリ別ランク1位のダウンロード数です。


一目瞭然ですが、ゲームで1位を取るのと他のマイナーなカテゴリとでは10倍以上もダウンロード数が違います。
つまり、あまりダウンロード数が多くなくてもマイナーなカテゴリであればランキングに載ることができるということです。

実際、私のアプリがランク入りしたのも『教育』カテゴリです。
ダウンロード数もさほど多いとは言えない数字で150位辺りになりました。
このカテゴリならば個人開発者でも十分に戦えると言えそうです。

ただし、マイナーなカテゴリーということはランキング自体の注目度が低いと言えます。
故にランク入りしてもダウンロード数アップの効果もそれなりになります。
私のアプリもそれなりのダウンロード数となっています。
それでも、ランキングに入ってない場合に比べれば雲泥の差があります。

複数のカテゴリに当てはまりそうなアプリの場合、あえてマイナーなカテゴリにする。
このような策がランキング入りへの有効な手段であると言えるでしょう。




今日(3/19)のApp Store教育カテゴリで210位
マイナーカテゴリでもそろそろ厳しいです


2014年3月18日火曜日

App Storeランキングはダウンロード数だけじゃない?

前回のお話ではApp Storeのランキングに載るのは非常に重要だということでした。
でも、そもそもランキングは何によって決まっているのでしょうか?
昔はダウンロード数だったようですが、今はそれだけでは無いようです。


昨年の夏頃に『Line』や『Twitter』などの定番アプリがランキング上位に入ってきたということで、その時期にロジックが変わったと言われています。
定番のアプリは既に多くの人に行き渡っていて、短期間でダウンロード数が増えることはありません。
その傾向がランキングにも現れていて中位辺りで推移していました。
ところがそういった定番アプリが軒並みランクアップしたのでダウンロード数以外を反映したランキングに変わったと推測されています。


Appleが公式な発表をしているわけではないのであくまで推測ですが、以下の要素がランキングに反映されているようです。

  • ダウンロード数
  • ユーザーの継続率
  • レビューの評価
つまり、定番アプリは日々のダウンロード数が爆発的に多くなくても、毎日のように継続して使われているのでランキングの上位になったということです。

このことから、以下のようなアプリはランキング上位に入りにくくなるだろうと予想されます。

  • リワード広告などでダウンロード数だけを増やしたアプリ
  • 一度遊んだら即アンインストールの一発屋的アプリ
  • 致命的なバグなどで低い評価が連発されるアプリ

つまり、そこそこの数のダウンロードがあり、何度も起動してもらえて、ユーザーが満足するアプリを作ればランキングに入れるということです。

これって結局、王道的な良いアプリを作ることですね。
チート的な抜け道を考えるならば、そのコストをより良いアプリに回す方が結果的に近道になるのかも知れないですね。



今日(3/18)のApp Store教育カテゴリで148位
しぶとくランキングに載っています


2014年3月17日月曜日

App Storeランキングに載るとどんな効果があるの?

今月の初めにリリースしたアプリが運良くApp Storeのランキングに載りました。
そこでランキングに入るとどのような効果があるのかご紹介します。


まずはランキングの推移を見てみましょう。
3/10に初めてランク入りして、その後は150〜200位の間で推移しています。

そして、その間のダウンロード数の推移がこちら。
ランク入りした3/10からランキングと同じような推移をしています。

つまり、このような効果があると考えられます。

ランキングに載る→ランキングを見てダウンロードする人が増える
→そのダウンロード数でランキングを維持する→それを見て…

とこのようなループで一度ランク入りすると暫くそれが維持されると推測されます。

ソーシャルゲームを出している企業などはこのようなランキングによる自然流入を狙って広告を出しランク入りを狙っているのです。

つまり、App Storeのランキングに入るのがかなりの宣伝効果があると言えます。
広告費に限りのある個人開発者としては最も効率の良いプロモーションになると言えるでしょう。

個人開発者のプロモーション活動は、どのようにすればランキング入りさせることができるのかを考えるのが重要なのではないでしょうか。

というわけで、これから数回に分けてランキングについて書いていこうと思います。



今日(3/17)のApp Store教育カテゴリで160位
まだまだランキングに踏みとどまっています


2014年3月15日土曜日

AdMobメディエーションで広告(Nend,iAd,AdMob)を切り替える方法

iPhone(iOS)アプリにAdMobメディエーションを実装し広告(Nend,iAd,Admob)を切り替える方法


iPhone(iOS)アプリには広告を表示することができます。
広告には様々な種類があり、国内だけのモノや海外でも使えるモノもあります。
これらの広告を切り替えて表示したいと思ったことありませんか?

AdMobメディエーションを使うと簡単にいくつかの広告を切り替えて表示することができます。
例としてAdMob,iAd,Nendを切り替えて表示する方法をご紹介します。


前提


この実装は2014/3/15時点の最新(ver6.8.0)、Xcode5.1でのものです。

事前準備


まず、Admob、Nendに申し込み、iTunes ConnectでiAdを有効にしておきます。
(iAdの有効化は実装後でもOKです)

AdMob


Nend


※API KeyとSpot IDを控えておく


メディエーションの設定


AdMobのサイトで設定

アプリを新規追加


新しいアプリを収益化


広告ユニットを追加


新しい広告ユニットを追加

広告ユニットIDを控えておく(実装時に必要)


広告ネットワークの設定


メディエーションを編集

新しい広告ネットワーク

iAdを追加

Nendを追加(API KeyとSpot IDを入力)

CPMの値で広告の優先順位を設定

優先順は国別の設定も可能
例えばNendは国内向けなので、日本以外は無効の設定にする


ダウンロード


AdmobメディエーションSDKのダウンロード



iAdアダプターのダウンロード



Nend SDKのダウンロード


Nendのサイトでダウンロード


実装


サンプルとして「Single View Application」へ実装します。
基本的には以下のGoogleのドキュメントのやり方で良いのですが、抜けがあったりするので注意してください。


ファイル追加


ダウンロードしたファイルをプロジェクトに追加
サンプルとしてこのようなディレクトリ階層にしてますが、以下のファイルが追加されていればどのような形でも問題ありません。

AdMob
  • GADAdMobExtras.h
  • GADAdNetworkExtras.h
  • GADAdSize.h
  • GADBannerView.h
  • GADBannerViewDelegate.h
  • GADInterstitial.h
  • GADInterstitialDelegate.h
  • GADRequest.h
  • GADRequestError.h
  • libGoogleAdMobAds.a

AdMob/Mediation
  • GADCustomEventBanner.h
  • GADCustomEventBannerDelegate.h
  • GADCustomEventExtras.h
  • GADCustomEventInterstitial.h
  • GADCustomEventInterstitialDelegate.h
  • GADCustomEventRequest.h

AdMob_iAdAdapter
  • libAdapterIAd.a

Nend
  • NADView.h
  • libAdapterNend.a
  • libNendAd.a

ライブラリ追加


TARGETS→General→Linked Frameworks and Libraries→+


以下のライブラリを追加
(ファイルを追加した時点で既に追加されているモノもあり)
  • AdSupport.framework ※
  • AudioToolbox.framework
  • AVFoundation.framework
  • CoreGraphics.framework
  • MessageUI.framework
  • StoreKit.framework
  • SystemConfiguration.framework
  • CoreTelephony.framework (サイトに書かれていない)
  • iAd.framework (iAdで必要)
  • Security.framework(Nendで必要)←抜けてました(4/21追記)

(以下は既に追加されているはず)
  • libGoogleAdMobAds.a
  • libAdapterIAd.a
  • libAdapterNend.a
  • libNendAd.a
※Deployment TargetがiOS6未満の場合はAdSupport.frameworkの設定をRequiredからOptionalに切り替える必要がある

Other Linker Flagsの追加


PROJECT→BuildSettings→Linking→Other Linker Flagsに「-ObjC」を追加


コーディング


ViewController.h
================================================

// SDK から GADBannerView の定義をインポートする
#import "GADBannerView.h"


@interface ViewController : UIViewController {
    // インスタンス変数として 1 つ宣言する
    GADBannerView *bannerView_;
}

================================================


ViewController.m
================================================

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    //バナーユニットID
    NSString *MY_BANNER_UNIT_ID = @"ca-app-pub-1234567890123456/1234567890";
    
    // 画面上部に標準サイズのビューを作成する
    // 利用可能な広告サイズの定数値は GADAdSize.h で説明されている
    bannerView_ = [[GADBannerView alloc] initWithAdSize:kGADAdSizeBanner];
    
    // 広告ユニット ID を指定する
    bannerView_.adUnitID = MY_BANNER_UNIT_ID;
    
    // ユーザーに広告を表示した場所に後で復元する UIViewController を
    // ランタイムに知らせてビュー階層に追加する
    bannerView_.rootViewController = self;
    [self.view addSubview:bannerView_];
    
    // 一般的なリクエストを行って広告を読み込む
    [bannerView_ loadRequest:[GADRequest request]];
}


================================================


実行


画面上部に広告が表示される

おわりに


事前準備の申し込みが面倒だったり、設定や実装が大変そうに見えますが、一度やってしまえば後はコピペでいけるので楽になります。

ある広告会社がトラブルで広告が配信されなくなっても、メディエーションで切り替えるようにしておけば他の会社の広告が表示されるので保険としても役立ちます。

特にこの広告でなければダメというこだわりが無いのなら、とりあえずAdMobメディエーションを組み込んでおくのが無難なのではないでしょうか。




『パズ銭』はハマり過ぎ注意な中毒者続出のパズルゲーム

パズ銭 ~スワイプで両替パズル

2014年3月14日金曜日

『Does your app contain, display, or access third-party content?』はこう答える

iOSアプリの申請時にAppleから質問をされます。
その質問が微妙に変わっていたり、増えていたりして毎回焦ってしまいます。
なので、落ち着いて答えられるように答え方を記載しておきます。


質問されるタイミング


最初にiTunes Connectで新しいアプリを作るとステータスは「Prepare for Upload」となっています。
このままではバイナリをアップロードできないので、「Ready to Upload Binary」ボタンを押してアップ可能なステータスに変えます。
このボタンを押したときに質問されます。


質問内容(2014/3/12時点)


【質問1】


Have you added or made changes to encryption features since your last submission of this app?
Export laws require that products containing encryption must be properly authorized for export.
Failure to comply could result in severe penalties. Learn more about export requirements.
(あなたはこのアプリの最後の提出以来、暗号化機能の追加または変更をしましたか?)
(輸出法は、暗号化を含む製品が適切に輸出が認可されなければならないことを要求している。) 
(守らないと、厳しい処罰の対象となる可能性があります。輸出条件については、こちらをご覧ください。)



【質問2】


※いつの間にかこの質問が増えてる
Does your app contain, display, or access third-party content?
(あなたのアプリは、サードパーティのコンテンツが表示される、含まれている、またはにアクセスしていますか?)



【質問3】


※これはアップデート時に出る質問です
Are you updating this app because of a significant usability issue or for a legal issue, such as an infringement claim?
(あなたは侵害の主張、大幅なユーザビリティの問題、または法的な問題のために、このアプリを更新していますか?)



質問の答え方


【質問1】

暗号化機能を使ってなければ「No」
(私はこれしか答えたことはありません)

【質問2】

※いつの間に増えていた質問
第三者のコンテンツを表示していなければ「No」で良いと思います。
私は広告を表示していて、これが第三者のコンテンツにあたると思うので「Yes」と答えました。
すると、追加で次の質問が。

==================

Do you have all necessary rights to that content or are you otherwise permitted to use it under the laws of each App Store territory in which your app is available?
(あなたは、そのコンテンツを表示する権利を持っていますか、そうでなければ、アプリを使用できる各App Storeの地域の法律の下でそれを使用することが許可されていますか?)

==================

広告を表示する権利を持っているはずなので「Yes」にしました。
ちなみにここを「No」だと申請できないようです。


【質問3】

質問された問題に対応した更新だったら「Yes」
それ以外の普通の更新ならば「No」
ちなみに私は「No」しか答えたことがありません。



回答実績


今まで回答したことあるのは以下の通りです。

【質問1】No 【質問2】Yes - Yes 【質問3】No



結果


今まで問題なく申請は通っています。
特に増えた質問に対する回答はそれで良かったのか不安だったのですが、この答え方で問題ありませんでした。

質問の意味は分かっても、答え方が本当にそれで良いのか分からなかったりします。
今回、記載した答え方は申請に通った実績のある回答なので、参考になさってください。





今日(3/14)のApp Store教育カテゴリで164位
なんとかランキングに踏みとどまっています


2014年3月13日木曜日

Xcode5.1で『Unused function』の警告が出るようになった場合の対処法

昨日に引き続き、Xcode5.1のお話です。
ようやくビルドできるようになったのですが、今度は今まで出ていなかった『Unused function』という警告がでるようになりました。
ワーニングなので出ていても特に問題は無いのですが、消す方法が分かったのでご紹介します。


TARGETS→Build Settings(All)→Apple LLVM 5.1 -Warnings - All languages

Unused Functionを『NO』にする


どうやら、Xcode5.1にアップデートしたときに設定が変わったようです。
先日のビルドが通らなくなる件も設定が変わったことによるものでした。
Xcodeを5.1にアップデートしての不具合は、まず設定を疑った方が良いのかも知れません。





本日(3/13)付けのApp Store教育カテゴリでランキング155位に上がりました!