Quantcast
Channel: Ray Wenderlich » iPhone @ja @ja @ja @ja @ja @ja @ja @ja @ja @ja @ja
Viewing all articles
Browse latest Browse all 22

「客観的に言うと」: iOS 6のObjective-C集中講座

$
0
0
Warning: Objective-C Crash Course Ahead!

Warning: Objective-C Crash Course Ahead!

Rayからの一言:このチュートリアルはiOS6、及びモダンObjective-C構文に対応する為にアップデートされました。こちらはアップデートする前のチュートリアル です。もし必要ならどうぞ。
このチュートリアルはiOSチュートリアルメンバーのLinda Burkeによって執筆されました。彼女は の創立者です。canAppsの創立者です。

貴方は別のプラットフォームのソフトウエア開発者で、iPhoneアプリ開発の為にObjective-Cを勉強し始めたばかりですか?実は私もそう遠くない前までは別のプラットフォームのソフトウエア開発者でした。そして、いつの間にか開発からは遠ざかってしまっていたんです。

そして、Objective-Cの勉強を始めてから2年の間に、iPhoneとiPadの為のアプリをたくさん開発してきました。しかし、元は別のプラットフォームでの開発者故、猛勉強をしてきたんです。そしてこの機会に、私がiPhone、iPad用のアプリの開発で、私が培ってきた技術を皆さんにお分けしたいと思います。

このチュートリアルはプログラミングの経験が少しある読者諸君の為のチュートリアルです。全くの初心者の方はiOS for High School Studentsシリーズに先ず目を通してみる事をお勧めします。

このチュートリアルのゴールは、貴方が学んでいるObjective-Cの基礎に自身を持つ事です。「Objective-Cの構文を一つ一つ説明出来る様にしよう!」なんて言うアプローチではなくて、サンプルのプロジェクト作成して行く事で、実践的な経験を積んで学んで行くアプローチでいきたいと思います。そうする事で効率的にリファレンスを参照(例えばこれ)する事が出来る様になります。

今回は、格納されたリストからランダムに引用して行くだけの簡単なアプリを作成します。この勉強を通して、以下のようなObjective-Cの基本に精通する事が出来ます:

  • Variables
  • Arrays
  • Property lists
  • Strings
  • Predicates
  • Random selection
  • Simple interface objects and events

警告です!:Objective-CでのiPhone開発はとても楽しくて、病み付きになってしまいます。眠れなくなってしまう事を覚悟しといてくださいね。:]

それでは、まず始めにAppleデベロッパーに登録して、プロビジョニングの設定を済ませて、最新のXcodeがインストールされている必要があります。

全部完了したら、始めましょう! :]

Getting Started

まず始めに:Xcodeの新規プロジェクトを作成しましょう。このチュートリアルはXcode 4.5+、そしてiOS6+に対応する為に書かれています。もしアップグレードが必要な方は済ませてください。もしくはiOS6以前に対応したチュートリアルが必要な方はこちらからどうぞ。

それではXcodeを起動して、iOSApplicationSingle View Applicationテンプレートを選択して新規プロジェクトを作成しましょう。

プロダクト名をQuoteGenとして、デバイスファミリーをiPhoneに。Use Automatic Reference CountingUse Storyboardsに忘れずにチェックを入れてください。そして”Next”をクリックして、プロジェクトを保存する場所を設定してください。

Creating a new project with the Single-View Application template

プロジェクトにAppDelegate.hAppDelegate.mViewController.hViewController.m そしてMainStoryboard.storyboardが作成されている事に注意してください。

Default files in View-based application template

AppDelegateはアプリを起動する際の始まりの為のコードが含まれています。このチュートリアルではこれだけ知っていれば十分です。以下はその他のファイルの簡単な説明です。:

  • MainStoryboard.storyboardは視覚的にアプリを作成する為のツールです。
  • ViewController.mはインターフェースコントローラークラスです。インターフェースレイアウトファイルはこのクラスとリンクしています。これは自動で行われますから、今はインターフェースコントローラークラスでのオブジェクトやイベントはインターフェースレイアウトファイルとリンクするという事を理解してもらっていれば十分です。このファイルにこれから、Obejective-Cのコードを書き込んで行きます。
  • ViewController.hはインターフェースコントローラークラスのヘッダファイルです。ここにインスタンス変数やオブジェクト、そしてイベント等を宣言していきます。

 

Note:Xcodeのインターフェースを作成する方法は2種類あります。一つはStoryboards、そしてもう一つはXcode Interface Builderファイル(XIBs)です。どちらを使っても構いません。しかし、このチュートリアルでは最近では主流となったStoryboardsを使って作成します。この二つの方法は非常に酷似していて、どちらかを理解すればもう一つも簡単に理解出来るはずです。
Storyboardsについてもっと情報が欲しいという方はこちらにも目を通してみてください。

 

出発進行!

まず始めにするべき事は、このアプリで表示するクォート(引用書)の為の変数を作成する事です。ノーマルのクォートと表示を変えるクォートです。

その方法は、二つのpropertyを作成する事から始めます。プロパティには少しややこしい側面もありますが、今は、クラスで変数を作成する為の物だと考えておいてください。

プロパティを作成するのはとても簡単です。クォートのarrayの為のプロパティを追加する事から始めましょう!以下をViewController.hの@interfaceから@endの間に追加してください:

@property (nonatomic, strong) NSArray *myQuotes;

少しずつ解説して行きましょう:

  • 始めに@propertyを追加して、
  • 次にプロパティの属性を指定します。簡単に言うとーnonatomicそれぞれのgetter,setterが複数のスレッドで同時に実行されるかもしれないメソッド定義(スレッドセーフでない)で、strongは強い参照を持つ属性、つまり参照しているオブジェクトが消去されないように生かし続けたい場合に使う (ARC使用時はデフォルト)
  • そして次は、プロパティのタイプです。ここではNSArray *を選択しています。これは”NSArrayクラスへのポインタ”を表しています。NSArrayはAppleによって提供されたとても使い勝手の良いクラスで、データのリストを格納します。詳しくは後ほど。
  • 最後にプロパティの名前を追加します。

この1行を加える事で、変数をこのクラスで使う準備ができました。

Note:少し前までは、プロパティを作成した後に、@synthesizeする必要がありました。それで、更にその前は、インスタンス変数をわざわざ宣言する必要さえあったのです。今では、只単に、たった1行プロパティの宣言をするだけです。

加えて、以前はメモリ管理も自分で行う必要がありました。しかし今は、Automatic Reference Counting (ARC)の登場で自動で、メモリ管理を行ってくれます。ARCに関しての情報は、こちらのチュートリアルをチェックしてください。

あっ、私の年齢がばれちゃったかな?:]

このアプリでは映画からの有名なクォートを格納します。その為には2つ目のArrayが必要になります:

@property (nonatomic, strong) NSMutableArray *movieQuotes;

ここで使用している“NSMutableArray”は単に違う種類のArrayです。違いは、“NSArray”は作成した後の変更が出来ませんが、“NSMutableArray”はいつでも追加削除が出来るんです。

手動!

これで好きなクォートをmyQuotesArrayに格納する事が出来る様になりました。この作業はviewDidLoad(Viewが作成される時に始めに呼ばれるメソッドです)で行います。
viewDidLoadで“ [super viewDidLoad];”の後に以下のコードを追加してください。もしあなたのお好きなクォートがありましたら、お好きに加えてください。これは“manual labor”と呼ばれるアプローチで、格納するリストが比較的少ない場合とても有効です。

// 1 - Add array of personal quotes
 self.myQuotes = @[
                     @"Live and let live",
                     @"Don't cry over spilt milk",
                     @"Always look on the bright side of life",
                     @"Nobody's perfect",
                     @"Can't see the woods for the trees",
                     @"Better to have loved and lost then not loved at all",
                     @"The early bird catches the worm",
                     @"As slow as a wet week"
                     ];

ここではmyQuoteのプロパティにクォートのリストを格納設定しています。もしかしたらあまり馴染みの無い構文があるかもしれないので少しずつ解説して行きますね。

  • selfは“今現在のクラス”を表しています。
  • ドット“.”を使う事でプロパティにアクセス出来ます。そしてプロパティ名をタイプします。つまり…例としてself.myQuotesとする事で、先ほど作成したmyQuotesにアクセスする事が出来るんです。
  • Arrayの作成は、非常に便利なObjective-Cのショートカット –@[ item1, item 2, item 3 ]を使います。
  • Arrayの中のそれぞれのアイテムは“String”です。Objective-CでStringを作成するには、@“…”を使います。もし他のプログラミング言語に慣れている人には少し取っ付きにくいかもしれませんね。

OK!これでクォートのArrayは準備出来ました。それではこのクォートをランダムにスクリーンに表示させる為のコードを追加しましょう!

アウトレット!!

そういえば、ユーザーインターフェースの作成がまだでしたね。今回はクォートを表示する為のText Viewを追加してランダムなクォートを表示する為のボタンを追加します。

ランダムにクォートを表示するには2つの事が必要となります。適切なテキストを設定する為にText Viewへの参照と、ボタンがタップされた時の通知です。

しかしどうやってインターフェースとコードを接続するのでしょうか? 答えは2つの特別なキーワードを使って接続するんです。“IBOutlet” と“IBAction” です!

これがどういう意味か見てみましょう。まずは“IBOutlet”から始めましょう。以下をViewController.hに追加して下さい:

@property (nonatomic, strong) IBOutlet UITextView *quoteText;

ここでは先ほどの様にプロパティを宣言しています(UITextViewクラス)。しかし先ほどとの違いは – IBOutletなるキーワードですね。

“IBOutlet”とは“XIB”ファイルのインターフェース上の部品と、オブジェクトである(quote_text)を関連づける為のキーワードです。そうする事でビューコントローラーはインターフェースの部品のプロパティにアクセス出来る様になるのです。今回の場合なら、UITextViewに表示されるテキストを設定する事が出来ます。もちろんテキストの色やフォントやサイズ等、簡単に設定出来るんです。

次に以下の行を先ほど追加した@propertyの行の下に追加して下さい:

- (IBAction)quoteButtonTapped:(id)sender;

これはクラスに実装するメソッドの定義をしています。もしこれが貴方にとって初めてのメソッドの定義だった時の為に少しずつ解説していきますね:

  1. 始めに-(ダッシュ)を付けてインスタンスメソッドの定義である事を表示します。
  2. 次にメソッドの“return”値を付けます。上記のメソッドは実際には“void”に定義されてるIBActionを返します。“void”は何も返しません。
  3. 次にメソッドの名前を付けます。この場合は – quoteButtonTappedとしています。
  4. 次にコロンを付けて、丸カッコで最初の引数のタイプを表示。“id”は“NSObject”から派生した型ならどんな型でもセット出来る凡用的な型 です。通常は、ボタンやその他のコントロールが呼び出すコールバックを設定する時、それらは最初の引数にコールバックを送信しているボタン、もしくはコントロールを渡します。
  5. 次に引数の名前をつけます。この場合は – senderですね。

もし引数が1つ以上なら、ステップ3からステップ5を繰り返します。Objective-Cのメソッド名の構文は少し独特ですが慣れればとても使いやすく感じるでしょう。

次は、ViewController.mに戻って“quoteButtonTapped:”を実装します。以下の行を“@end”の上に追加してください:

-(IBAction)quoteButtonTapped:(id)sender {
    // 1 - Get number of rows in array
    int array_tot = [self.myQuotes count];
    // 2 - Get random index
    int index = (arc4random() % array_tot);
    // 3 - Get the quote string for the index
    NSString *my_quote = self.myQuotes[index];
    // 4 - Display the quote in the text view
    self.quoteText.text = [NSString stringWithFormat:@"Quote:nn%@",  my_quote];
}

ここも少しずつ解説して行きましょう:

  1. 始めにArrayの中に格納されているアイテム数(count)を取得します。これは今回のチュートリアルで初めてのObjective-Cでメソッドをコールする例です。少々変わった構文ですね。始めに“ブラケット( [ )”、続いてコールするオブジェクト名(self.myQuotes)、続いて、コールするメソッド名(count)です。最後に “クローズブラケット( ] )”となります。このメソッドには引数がない事に注意してください。ステップ4の例を確認してください。
  2. 次にarc4random関数を使って、ランダムな数字を作成します。“arc4random()”は見慣れたC言語の関数(メソッドではありません)です。この場合は、格納したクォートの中から1つをランダムに選択しています。Objective-Cでは他の言語と同様に、ランダムの値が0(1ではなく)から始まることに注意してください。
  3. 次に“myQuotes”に格納されているアイテムを調べます。Objective-Cの新しい文字列構文は、ご覧の様に非常に簡単な方法でNSArrayの要素にアクセス出来るようになりました。
  4. 最後にstringWithFormatメソッドでクォートの“string”をラベルに表示します。Objective-Cでは“%@”を使用することに注目してください。

これでクォートをスクリーンに表示する準備ができました。続いてこのクラスのアウトレットをXIBファイルのTextフィールドに関連づけます。

コントロールの接続

この関連付けは手動で行います。MainStoryboard.storyboardを開いてください。次にXcodeウィンドウの右サイドバーを見てください。もし右サイドバーが確認出来ない時はスクリーン上のツールバーのViewボタンの一番右のボタンをクリックしてください。

スクリーン右サイドバーの下半分のセクションにある4つのタブの右から2番目の“Object Library”を確認してください。

“Object Library”から“Text View control”と“Round Rect Button”をViewに以下の様にドラッグして配置してください。ボタンの“title”を“Quote”追加して、以下の様にcolorとfontをお好みに変更してください。これらのコントロール部品のプロパティのほとんどは右サイドバーの上半分の“ Attributes Inspector”(左から4番ものタブ)で設定可能です。

Storyboard layout for Objective-C tutorial

テキストは表示専用とするので“Behavior”の“Editable”のチェックを外してください。

次はボタンとテキストビューのコントロール部品を、クラスで既に実装済みの“outlet”と“action”に関連づけます。

“View Controller Scene”の“View Controller”からctrlとクリックでText Viewへドラッグして、リリースします。すると“Outlets”のポップアップ画面が表示されるのでリストから“quoteText”を選択します。

Connecting the text view to the outlet

もしくは、“VIew Controller Scene”のView Controllerを選択して、右サイドバーの“Connections Inspector”(一番左のタブ)を選択します。すると、View Controllerへの接続可能リストが表示されるので、それぞれのリストからそれぞれのコントロール部品へドラッグします。

Connections Inspector

“Storyboard”が“quoteText”プロパティを知っているのは、先ほど“IBOutlet”のキーワードを追加した為です。

Actionへの接続

アクションとメソッドの関連づけはコントロールとプロパティの関連づけと非常に似ています。

今回は“Button”からctrl&ドラッグで“View Controller”へ。するとポップアップウィンドウが開き、接続可能のリストが表示されます。リストの中から“quoteButtonTapped:”をクリック:

Hooking up an action to a method

もしくは、“VIew Controller Scene”の“Button”を選択して、右サイドバーの“Connections Inspector”(一番左のタブ)を選択します。次に“Sent Event”リストから“Touch Up Inside”を選択し、Ctrl&ドラッグで“VIew Controller Scene”の“View Controller”でリリースすると“quoteButtonTapped:”がポップアップするので選択してクリック。

いよいよランしてみましょうか?

さて、これでランする準備ができました。それではXcodeの“Run”ボタンをクリックしてください。一番上左のボタンです。すると、シミュレーターが起動します。

もしエラーが表示されてもパニックにならないで下さい!Xcodeは大文字と小文字を区別します。多くの場合変数の宣言時等のスペルミスが原因だったりします。

アプリがコンパイル&ランしたら“Quote”ボタンをクリックしてみて下さい。ランダムにQuoteが表示されるはずです:

これでなんとか機能するアプリが作成出来ました。実はこの間にたくさんのObjective-Cを学習しました。プロパティを作成して、そしてメソッド、クラスの使用等々!

でも待って下さい!まだあるんです!今はクォートのリストはコードで作成していますね。もしこれが別のファイルから読み込んで表示出来れば楽だと思いませんか?

そして、ここでプロパティリストの登場です。

プロパティリスト!最高!

プロパティリストは、文字列、数値、配列、辞書のように基本的なデータ型を格納するように設計されているアップル社によって定義された特殊なXMLフォーマットです。作成や読み書きは非常に簡単で、アプリにデータを得るための素晴らしい方法です。

それでは試してみましょう!左サイドバー“ Project Navigator”のプロジェクトルートを右クリックしてNew Fileを選択。iOSResourceProperty Listテンプレートを選択してNextをクリック。新しいファイルの保存場所を選択しファイル名をquotes.plistとしてCreateをクリック。

プロパティリストはXcode内からグリッドビューもしくはテキストを変更する事が出来ます。テキストファイルでプロパティリストを変更したい時は“Project Navigator”のquotesを右クリックして“Open AsSource Code”を選択してください。

もし、全てのクォートをコピー&ペーストで追加したいのなら、“Source Code”モードで編集するのが一番の近道かもしれません。

それでは以下のquotes(Source Codeモード)をコピー&ペーストで追加してください:

<!--?xml version="1.0" encoding="UTF-8"?-->
 
<!--  Quotes  -->
 
            category  classic
            quote  Frankly my dear, I don't give a dam.
            source  Gone with the wind
 
            category  classic
            quote  Here's looking at you kid.
            source  Casablanca
 
            category  classic
            quote  There's no place like home.
            source  Wizard of Oz
 
            category  classic
            quote  Play it again sam.
            source  
 
            category  classic
            quote  Elementary my dear Watson.
            source  Sherlock Holmes
 
            category  classic
            quote  Fasten your seatbelts. It's going to be a bumpy night.
            source  All about Eve
 
            category  classic
            quote  I have not the pleasure of understanding you.
            source  Pride and Predice
 
            category  classic
            quote  O Romeo, Romeo! wherefore art thou Romeo?
            source  Romeo and Juliet
 
            category  classic
            quote  To be or not to be
            source  Hamlet
 
            category  classic
            quote  ...Crime is only a left-handed form of human endeavor.
            source  The Asphalt Jungle
 
            category  classic
            quote  That's, uh, quite a dress you almost have on...What holds it up?
            source  An American in Paris
 
            category  classic
            quote  Love, desire, ambition, faith - without them life is so simple, believe me
            source  Invasion of the Body Snatchers
 
            category  modern
            quote  Go ahead make my day.
            source  Dirty Harry
 
            category  modern
            quote  May the Force be with you.
            source  Star wars
 
            category  modern
            quote  Hasta la vista, baby
            source  Terminator
 
            category  modern
            quote  I feel the need for speed.
            source  Top Gun
 
            category  modern
            quote  She doesn't even go here.
            source  Mean Girls
 
            category  modern
            quote  It takes a great deal of bravery to stand up to your enemies, but a great deal more to stand up to your friends.
            source  Harry Potter
 
            category  modern
            quote  I solemnly swear that I am up to no good.
            source  Harry Potter
 
            category  modern
            quote  You like pain? Try wearing a corset.
            source  Pirates of the Carribean
 
            category  modern
            quote  Houston, we have a problem.
            source  Apollo 13
 
            category  modern
            quote  I'll be back.
            source  The Terminator
 
            category  modern
            quote  E.T. phone home.
            source  E.T.
 
            category  modern
            quote  Why are you trying so hard to fit in when you were born to stand out?
            source  What a girl wants
 
            category  modern
            quote  Watch you talkin about Willis?
            source  Different Strokes
 
            category  modern
            quote  The plane, the plane
            source  Fantasy Island
 
            category  modern
            quote  D'oh
            source  The Simpsons
 
            category  modern
            quote  Kids, you tried your best and you failed miserably. The lesson is, never try.
            source  The Simpsons
 
            category  modern
            quote  You don’t win friends with salad.
            source  The Simpsons
 
            category  modern
            quote  Whoever said that money doesn't buy happiness didn't know where to shop.
            source  Gossip Girl
 
            category  modern
            quote  If I were you, I'd accessorize with some gloves. Even a manicure can't mask those peasant hands.
            source  Gossip Girl
 
            category  modern
            quote  I tried to be diplomatic, but mostly I just lied a lot.
            source  Twilight
 
            category  modern
            quote  Once people start throwing wet stuff, I go inside.
            source  Twilight
 
            category  modern
            quote  I don’t like to lie – so there’d better be a good reason why I’m doing it..
            source  Twilight

上記のクォートは只の1例に過ぎません。もちろん上記にあなたのお好きなクォートを追加してみるのも楽しいと思います。

これらのクォートは訳あって“classic”と“modern”の2種類にカテゴリーを分けています。詳しくは後ほど解説します。

もちろん“Property List”モードもあります。“Project Navigator”の“Quotes.plist”を右クリックして“Open AsProperty List”を選択して、先ほどコピー&ペーストしたファイルがどのようにオーガナイズされているかそれそれの値を確認してください。その上でプロパティーリストをどのようにエディットするか考えてみてください。このようにモードの切り替えは簡単にいつでも行えます。

プロパティーリストはとても有用なのですが、エラーが出ると非常に厄介な一面も持っています。開発初心者がよくやってしまう間違いはエンドタグの記入を忘れてしまったり、気付かないうちに“<”や“>”を消してしまっている事です。もし貴方のプロパティーリストが読み込まれない時は、上記の間違いを気にして、もう一度よーく確認してみてください。以前のXcodeはエラーの詳細が記述される機能があって間違いを見つけやすかったのですが、バージョン4以降はその機能がなくなってしまったようです。

でもどうしても読み込まれない等のエラーが起こってしまった時は、ファイルを隅から隅まで確認する以外に方法はありません。

さて、話を戻します。これでプロパティーリストが作成されましたね。これで、表示する為にArrayに読み込む準備ができました。それでは、ViewController.mに戻って、以下をviewDidLoadのメソッド内の最後に加えてください:

// 2 - Load movie quotes
NSString *plistCatPath = [[NSBundle mainBundle] pathForResource:@"quotes" ofType:@"plist"];
self.movieQuotes= [NSMutableArray arrayWithContentsOfFile:plistCatPath];

ね、こんなに簡単なんです!これでプロパティーリストに追加した全ての映画のクォートを格納したArrayができました。

ここで、皆さんは「なんだ、後は今までの“myQuotes”を記述していた箇所を“movieQuotes”に全部変更してquoteButtonTapped:の“myQuotes”の参照を“movieQuotes”に変更すればいいんでしょ!」って思うでしょう?

「あれ、でもうまくいきませんね、えっ、なんで?」理由は“myQuotes”はArray型だからなんです。でも“movieQuotes”はArray型ではありません。その代わりにユニークな“key”で“value“の値にアクセスする“Dictionary”型のArrayなんです。

「えっ、でもなんで、、、???」先ほど設定したプロパティーリストを確認してください。

Note:“Dictionaries”は“key”と“value”を格納し、“valueForKey”メソッドを使用します。

それでは“quoteButtonTapped:”を以下に変更してください。以下ではArrayを“movieQuotes”に置き換えて、それぞれのクォートに“key”を追加しています:

-(IBAction)quoteButtonTapped:(id)sender {
    // 1 - Get number of rows in array
    int array_tot = [self.movieQuotes count];
    // 2 - Get random index
    int index = (arc4random() % array_tot);
    // 3 - Get the quote string for the index
    //NSString *my_quote = [self.myQuotes objectAtIndex:index];
    NSString *my_quote = self.movieQuotes[index][@"quote"];
    // 4 - Display the quote in the text view
    self.quoteText.text = [NSString stringWithFormat:@"Quote:nn%@",  my_quote];
}

上記の様に前に記述したセクション#3はコメントアウトしたままにして於いてください。それではビルド&ランして、新しいクォートをお楽しみください。

Movie Quotes

どうですか?これで外部のファイルからのクォートの読み込みに成功しました!この方法はもし、他の誰かが作成したファイルを読み込む場合にとても有効です。

次に、もしユーザーが表示するクォートを“myQuotes”と“movieQuotes”から、そして“classic”と“modern”から選択する事が出来たらカッコいいと思いませんか?

すべてはオプションなり!

始めにクラスのヘッダーファイルに戻りましょう。ViewController.hに以下の新しいプロパティを追加してください:

@property (nonatomic, strong) IBOutlet UISegmentedControl *quoteOpt;

上記では、複数のオプションのリストから、1つ選択出来る“Segmented Control”のプロパティを追加しています。今回のクォートタイプの選択に適しています。

そしてMainStoryboard.storyboardを選択して“Segmented Control”をライブラリからドラッグしてViewに追加してください。

Adding a segmented control

追加した“Segmented Control”のプロパティを以下の様に設定してください:

  • Style: Bar (my personal preference)
  • Segments: 3
  • Segment: 0を選択して タイトルを: Classic
  • Segment: 1を選択してタイトルを: Modern
  • Segment :2を選択してタイトルを: Mine

この設定では3種類のクォートタイプから選択出来る様にします。

“Segmented Control”を作成するにあたってクラスのアウトレットに関連付けなければなりません。前述と同じメソッドを使って“quoteOpt”プロパティに関連付けましょう。

この部品には“action”イベントは必要ありません。

それでは、ビルド&ランしてみましょうか。スクリーンに“Segmented Conrol”が表示されましたね。今は選択ボタンをクリックしても何も起こりませんが、表示されるだけで気分が良くなりますね!

Segmented control now appears

“Predecate”を使っちゃおう!

NSPredicate は、NSArray で要素をフィルターするための条件を表したり、Core Data で取ってくるデータの条件を表すためのクラスです。そして“Predecate”はプロパティリストを項目毎に分類する場合に非常に便利です。項目毎にプロパティリストをわけて作成する必要がないからです。

すみませんが、またまたViewController.mquoteButtonTapped:で“movieQuotes”の代わりに“myQuotes”に再び変えて下さい。これから映画用クォートの為に今までとは違った方法を取ります。条件の指定です。上記は“Segmented Control”の3番目のオプションを選択した場合にのみ実行されます。

お望みならばquoteButtonTapped:を以下のコードと置換えて下さい:

-(IBAction)quoteButtonTapped:(id)sender {
    // 1 - Get personal quotes when the final segment is selected
    if (self.quoteOpt.selectedSegmentIndex == 2) {
        // 1 - Get number of rows in array
        int array_tot = [self.myQuotes count];
        // 2 - Get random index
        int index = (arc4random() % array_tot);
        // 3 - Get the quote string for the index
        NSString *my_quote = self.myQuotes[index];
        // 4 - Display the quote in the text view
        self.quoteText.text = [NSString stringWithFormat:@"Quote:nn%@",  my_quote];
    }
}

さてユーザーが3番目を選択した場合にのみ“myQuotes”が表示されるわけですが、ご覧のように残りのコードは今までと同じです。違いはセグメントのインデックス2が選択された時にクォート(myQuotes)が表示されるという事です。あっ、セグメントコントロールは“index 0”から始まるので“index 2”は3番根のアイテムという事になります。注意して下さいね。

それではビルド&ランして、セグメントの“Mine”を選択した時のみクォートが表示される事を確認して下さい。

ここで、“Predecate”の話に戻しますが、始めに選択されたセグメントコントロールをベースに必要なカテゴリを把握してから、カテゴリを使って一致するクォートのフィルターArrayを作成します。

以下はquoteButtonTapped:のif文の“else”以降のコードとなります。以下のコードをif文の“ } ”の後に続けて追加して下さい:

// 2 - Get movie quotes
else {
    // 2.1 - determine category
    NSString *selectedCategory = @"classic";
    if (self.quoteOpt.selectedSegmentIndex == 1) {
        selectedCategory = @"modern";
    }
    // 2.2 - filter array by category using predicate
    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"category == %@", selectedCategory];
    NSArray *filteredArray = [self.movieQuotes filteredArrayUsingPredicate:predicate];
    // 2.3 - get total number in filtered array
    int array_tot = [filteredArray count];
    // 2.4 - as a safeguard only get quote when the array has rows in it
    if (array_tot &gt; 0) {
        // 2.5 - get random index
        int index = (arc4random() % array_tot);
        // 2.6 - get the quote string for the index
        NSString *quote = filteredArray[index][@"quote"];
        self.quoteText.text = [NSString stringWithFormat:@"Movie Quote:nn%@",  quote];
    } else {
        self.quoteText.text = [NSString stringWithFormat:@"No quotes to display."];
    }
}

いいでしょう!それではビルド&ランして下さい。選択にあったクォートが表示されているかを確認して下さい。もし貴方のクォートが毎回同じタイプが表示されるのなら、考えられる事は、“Segmented Control”とクラスがうまく関連づけされていない可能性があります。

文字列の調和

ここまでは順調ですね!今度は、Objective-Cの中でいくつかの文字列オプションと構文を探ってみましょう!

ところで、プロパティリストにクォートのソースがあって、それを表示させる事が出来たら更にカッコいいですよね。“String”の値があるかどうかを確認するには、“String”の“length”をチェックします。

それでは以下をquoteButtonTapped:セクション#2.6の後に追加して下さい:

// 2.7 - Check if there is a source    
NSString *source = [[filteredArray objectAtIndex:index] valueForKey:@"source"];
if (![source length] == 0) {
    quote = [NSString stringWithFormat:@"%@nn(%@)",  quote, source];
}
// 2.8 - Set display string

そして、以下の行をコメントアウトして下さい:

//self.quoteText.text = [NSString stringWithFormat:@"Movie Quote:nn%@",  quote];

Arrayからソースを取得し、“length”が0ではないかどうかを判断する事で、値をチェックしています。!は“NOT”と同意です。 ==integerが値と同じかどうかを調べる場合に使用します。

そしてstringWithFormatを使って“quote”と“source”を合わせて“String”を表示させます。

もっと面白くする為には、選択されたクォートのカテゴリの値をチェックする事で、“Classic”からのクォートの表示には少しだけ変化をつけてみましょう!

それでは以下をquoteButtonTapped:のセクション#2.8と置換えて下さい:

// 2.8 - Customize quote based on category
if ([selectedCategory isEqualToString:@"classic"]) {
    quote = [NSString stringWithFormat:@"From Classic Movienn%@",  quote];
} else {
    quote = [NSString stringWithFormat:@"Movie Quote:nn%@",  quote];
}
// 2.9 - Display quote
self.quoteText.text = quote;

上記“String”が(今回の例では)“classic”と値が同じかどうかをチェックし、カテゴリーをベースにクォートのラベルをカスタマイズします。

もちろん、特定の値で始まる特定の映画のタイトルをチェックする事も出来ます。例えば“Harry Potter”からのクォートだとして、ちょっとした追加のテキストを表示してみたいなら、以下をセクション#2.9の上に追加して下さい:

if ([source hasPrefix:@"Harry"]) {
    quote = [NSString stringWithFormat:@"HARRY ROCKS!!nn%@",  quote];
}

ご想像の通り、hasPrefixは“String”の始まりが、特定の文字列かどうかをチェックします。

それではビルド&ランして、何も問題が無いかチェックして下さい。別カテゴリや“Harry Potter”の映画のクォートに注意して、適切に表示されているかどうか確認して下さい。

クォートの雨

ちょっと遊びで、数もあんまり多くはありませんから、全てのクォートを一度に連結して表示させましょう。以下は、配列内の各アイテムを反復したい場合の為にArrayをループする方法を解説しています。

quoteButtonTapped:でセクション#1を以下に置換えて下さい:

if (self.quoteOpt.selectedSegmentIndex == 2) {
    // 1.1 - Get array count
    int array_tot = [self.myQuotes count];
    // 1.2 - Initialize string for concatenated quotes
    NSString *all_my_quotes = @"";
    NSString *my_quote = nil;
    // 1.3 - Iterate through array
    for (int x=0; x &lt; array_tot; x++) {
        my_quote = self.myQuotes[x];
        all_my_quotes = [NSString stringWithFormat:@"%@n%@n",  all_my_quotes,my_quote];
    }
    self.quoteText.text = [NSString stringWithFormat:@"%@", all_my_quotes];
}

“for”ループは0行から最後の行に配列をループするために使用されます。 xは行を把握するために使用されるカウンタです。

それではコンパイル&ランして結果をチェックして下さい:

申し訳ございませんが、この続きは客観的に言うと: iOS 6のObjective-C集中講座 Part2を参照して下さい。

「客観的に言うと」: iOS 6のObjective-C集中講座 is a post from: Ray Wenderlich

The post 「客観的に言うと」: iOS 6のObjective-C集中講座 appeared first on Ray Wenderlich.


Viewing all articles
Browse latest Browse all 22

Trending Articles