2013年12月28日土曜日

iOSで詳細ビューを追加する


前回作成したテーブルビューから遷移する詳細ビューを追加する。
詳細ビューとして、ストーリーボードにView Controller(紐づけるクラス名はDetailViewControllerとする)を追加する。

Table View Controller(クラス名:ViewController)からView Controller(クラス名:DetailViewController)へのセグエを設定する。
Storyboard Segue: 「identifier」に"getDetail"と入力、「Style」に"push"を選択する。


Table View Controller(クラス名:ViewController)のバックボタン表示名を変更する
Navigation Item: 「Back Button」に"プロ野球"と入力する。


詳細ビュー(クラス名:DetailViewController)をコーディングする。
#import <UIKit/UIKit.h>

@interface DetailViewController : UIViewController

@property (weak, nonatomic) IBOutlet UILabel *detailLabel;
@property (strong, nonatomic) NSString *detailItem;

@end
#import "DetailViewController.h"

@implementation DetailViewController

- (void)viewDidLoad
{
    [super viewDidLoad];
    self.detailLabel.text = self.detailItem;
    NSLog(@"self.detailItem is %@", self.detailItem);
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
}

@end


テーブルビュー(クラス名:ViewController)をコーディングする。
ViewController.mにおいてDetailViewController.hをインポートし、prepareForSegue: sender:メソッドを追加する。
#import "ViewController.h"
#import "DetailViewController.h"

@interface ViewController ()

@end

@implementation ViewController {
    @private
    NSArray *_leagueKinds;
    NSArray *_leagues;
    NSArray *_leaguePrefixes;
}

#pragma mark - Navigation

// In a story board-based application, you will often want to do a little preparation before navigation
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    // Get the new view controller using [segue destinationViewController].
    // Pass the selected object to the new view controller.
    if ([[segue identifier] isEqualToString:@"getDetail"]) {

        NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
        NSArray *teams = _leagues[indexPath.section];
        NSArray *teamPrefixes = _leaguePrefixes[indexPath.section];
        
        [[segue destinationViewController] setTitle:teams[indexPath.row]];
        [[segue destinationViewController] setDetailItem:teamPrefixes[indexPath.row]];
    }   
}
@end

2013年12月23日月曜日

iOSでテーブルビューを使う


環境
  • Xcode 5.0.2
  • ARC ON
  • iOSシミュレータ 7.0

ストーリーボードにNavigation ControllerとTable View Controllerを追加する。

Table View Cell: 「Style」から"Subtitle"を選択、「Identifier」に"Cell"と入力する。

この紐付けをしておかないと実行時に下記エラーが吐かれる。
Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'unable to dequeue a cell with identifier Cell - must register a nib or a class for the identifier or connect a prototype cell in a storyboard'


Navigation Item: 「Title」に"日本プロ野球チーム"と入力する。


UITableViewControllerを継承したクラス(今回の例ではViewController)を作成する。

tableView: cellForRowAtIndexPath:メソッドとtableView: viewForHeaderInSection:メソッドはテーブルビュー初回描画時と画面スクロールが発生するたびに呼ばれる。
#import <UIKit/UIKit.h>

@interface ViewController : UITableViewController

@end
#import "ViewController.h"

@interface ViewController ()

@end

@implementation ViewController {
    @private
    NSArray *_leagueKinds;
    NSArray *_leagues;
    NSArray *_leaguePrefixes;
}

- (id)initWithStyle:(UITableViewStyle)style
{
    self = [super initWithStyle:style];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];

    // Uncomment the following line to preserve selection between presentations.
    // self.clearsSelectionOnViewWillAppear = NO;
 
    // Uncomment the following line to display an Edit button in the navigation bar for this view controller.
    // self.navigationItem.rightBarButtonItem = self.editButtonItem;
    
    _leagueKinds = @[@"セントラル・リーグ", @"パシフィック・リーグ"];
    
    _leagues = @[
                @[@"ジャイアンツ", @"タイガース", @"ドラゴンズ", @"ベイスターズ", @"カープ", @"スワローズ"],
                @[@"バッファローズ", @"ホークス", @"ファイターズ", @"マリーンズ", @"ライオンズ", @"ゴールデンイーグルス"]
                ];
    
    _leaguePrefixes = @[
                       @[@"読売", @"阪神", @"中日", @"横浜DeNA", @"広島東洋", @"東京ヤクルト"],
                       @[@"オリックス", @"福岡ソフトバンク", @"北海道日本ハム", @"千葉ロッテ", @"埼玉西武", @"東北楽天"]
                       ];
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

#pragma mark - Table view data source

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    // Return the number of sections.
    return [_leagueKinds count];
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    // Return the number of rows in the section.
    return [_leagues[section] count];
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];

//    if (!cell) {
//        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
//    }
 
    NSArray *teams = _leagues[indexPath.section];
    NSArray *teamPrefixes = _leaguePrefixes[indexPath.section];
    cell.textLabel.text = teams[indexPath.row];
    cell.detailTextLabel.text = teamPrefixes[indexPath.row];
    
    return cell;
}

- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
    static NSString *HeaderIdentifier = @"Header";
    UITableViewHeaderFooterView *view = [tableView dequeueReusableHeaderFooterViewWithIdentifier:HeaderIdentifier];
    
    if (!view) {
        view = [[UITableViewHeaderFooterView alloc] initWithReuseIdentifier:HeaderIdentifier];
    }
    
    view.textLabel.text = _leagueNames[section];

    return view;
}

- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
{
    return 40;
}

@end