「未分類」カテゴリーアーカイブ

iOS8のシェア50%突破/過去との決別


iOS8のシェアがようやく50%突破

iOS8のシェアがようやく50%を超えたようだ。弊社ではiPhoneアプリを開発しているが、既に、iOS5やiOS6のサポートは切っている。iOS7は今後1年程度はサポートし続けるが、今後の開発はiOS8をターゲットに進めて行きたい。複数OSのサポートは手間がかかる。動作検証も大変だし、バージョンごとの場合分けが発生し、ソースコードが肥大しやすくなる。切り捨てるものは切り捨てることで、優れた製品を開発していきたい。

iTunes Connectのスクリーンショットはファイル名に日本語が使えない


iTunes Connectが新しくなりましたね〜!

さっそくハマりましよ笑

iTunes Connectのアプリ審査でスクリーンショットをアップするところがあったので、アップするための画像をシミュレータで撮って、アップしたら「画像ファイルが破損しています。iPhotoで開いてから再度保存してください。」みたいなメッセージがでてアップできませんでした笑

なんでやねん!とか思いつついろいろ試行錯誤、、、ふとひらめく、、、まさか・・・と思ってファイル名から日本語を消すとアップできましたー笑

忘れてましたよ笑日本語の罠を笑

てかファイル名に日本語使えません とかするなら シミュレータのスクリーンショットのデフォルトのファイル名に日本語を初めから入れないでください笑

なのでアップロードする時は、ファイル名から日本語を消してアップロードしましょう。

PS.

Appleさん。。。もうちょい分かりやすいエラーメッセージをお願いします笑

UINavigationController/フリックで親画面に戻らないようにする


iOS7では、UINavigationControllerで子画面に進んだあと、子画面を左から右にスワイプすると子画面がpopされます親画面に戻ります。この機能は以下のコードで無効化できます。

if ([self.navigationController respondsToSelector:@selector(interactivePopGestureRecognizer)]) {
    self.navigationController.interactivePopGestureRecognizer.enabled = NO;
}

How to disable back swipe gesture in UINavigationController on iOS 7

intとlongとNSInteger


iPhoneアプリにおいて、長らく、intとlongとNSIntegerは4バイトで同じサイズだった。iPhone5Sが登場し、64ビットCPUになったので、それぞれの型がどのように違うのか確認してみた。64ビット整数型を使う機会はあまり多くないかもしれないが、得点がインフレするゲームでは(約21億点 もしくは 43億点)32ビット環境と64ビット環境で動作が異なるので注意が必要だ。

int a = 1;
long b = 1;
NSInteger c = a;
   
NSLog(@"%lu %lu %lu", sizeof(a), sizeof(b), sizeof(c));

//32ビット環境 iPhone Retina(3.5inch)
2013-11-16 21:18:39.355 NSInteger[4024:70b] 4 4 4

//64ビット環境 iPhone Retina(4-inch 64bit)
2013-11-16 21:14:25.935 NSInteger[3962:70b] 4 8 8

iOS7でのレビューページへのリンク


iOS7では、iOS6までの方法では、AppStoreのレビューページに飛ばなくなっている。面倒だが、iOS6向けとiOS7向けでURLを切り替えるしかなさそうだ。

参考:iOS7でアプリからappstoreのレビューページにリンクする

#define APP_ID @"XXXXXXXXX"
NSString* url = ([[UIDevice currentDevice].systemVersion floatValue] >= 7.0)?
    // iOS7以降
    [NSString stringWithFormat:@"itms-apps://itunes.apple.com/app/id%@",APP_ID]:
    // iOS6以前
    [NSString stringWithFormat:@"itms-apps://itunes.apple.com/WebObjects/MZStore.woa/wa/viewContentsUserReviews?id=%@&onlyLatestVersion=true&pageNumber=0&sortOrdering=1&type=Purple+Software",APP_ID];
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:url]];

Block構文(クロージャー)


Block構文は、iOS4.0で導入された構文。関数をオブジェクトとして扱うことができる。Block内にstaticな変数を使うと、内部状態を持つBlockを作ることができる。Block内からBlock外の変数を参照することはできるが、変更はできない。Block外の変数を変更するには、ブロック外の変数の宣言に__blockを指定する必要がある。

カウンター

    int (^counter)() = ^(){
        static int i = 1;
        return i++;
    };
   
    NSLog(@"%d", counter());//1
    NSLog(@"%d", counter());//2
    NSLog(@"%d", counter());//3
//引数が無い場合は、()を省略できる。
    int (^counter2)() = ^{
        static int i = 1;
        return i++;
    };

数値の合計を計算

    int (^sum)(int) = ^(int num){
        static int value = 0;
        value += num;
        return value;
    };
    NSLog(@"%d", sum(3));//3
    NSLog(@"%d", sum(5));//8
    NSLog(@"%d", sum(10));//18

文字列を連結

    NSString * (^appender)(NSString *) = ^(NSString * str){
        static NSString *_str = @"";
        _str = [_str stringByAppendingString:str];
        return _str;
    };
   
    NSLog(@"%@", appender(@"test"));//test
    NSLog(@"%@", appender(@"test"));//testtest
    NSLog(@"%@", appender(@"test"));//testtesttest

外部の変数も参照できる。変数はクロージャ生成時に複製されるため、もとの変数の値が変わっても影響されない。

    int i = 3;
    int (^add3)(int) = ^(int num){
        return i + num;
    };
   
    NSLog(@"%d", add3(5));//8
   
    i = 4;
   
    NSLog(@"%d", add3(5));//8

通常、外部の変数は変更できない。__block指定子が付いている変数はBlockの中から変更できる。

    int j = 1;
    __block int k = 1;
    void (^inc)() = ^() {
        j = 2;//エラーになりコンパイルできない
        k = 2;//問題なく実行できる。
    };
    inc();

UILongPressがイベントを2重送信する


UILongPressGestureRecognizerは、長押し開始時と、長押し終了時の2回、イベントを送信する。長押し判定の秒数を1秒に指定して、3秒間の長押しをした場合、押し始めて1秒で長押し開始、離した瞬間(3秒の時点)に長押し終了イベントを発生させる。どちらか片方でしかイベントを実行したくない場合は以下のようにする。

-  (void)handleLongPress:(UILongPressGestureRecognizer*)sender {
    if (sender.state == UIGestureRecognizerStateEnded) {
      NSLog(@"UIGestureRecognizerStateEnded");
    //Do Whatever You want on End of Gesture
     }
    else if (sender.state == UIGestureRecognizerStateBegan){
       NSLog(@"UIGestureRecognizerStateBegan.");
   //Do Whatever You want on Began of Gesture
     }
  }

StackOverFlow:UILongPressGestureRecognizer gets called twice when pressing down