0

私は現在、Messages.appのように動作するアプリを開発しています。MasterViewControllerは、連絡先の名前、時刻、および最新のメッセージのスニペットのテーブルをロードするメインビューです。特定のセルをタップすると、DetailViewControllerにスライドし、連絡先に送信したメッセージと最新の完全なメッセージが読み込まれます。戻るボタンを押すと、MasterViewControllerに戻ります。rightBarButtonItemをタップすると、ComposeViewController(モーダル)が開き、ユーザーは特定の連絡先へのメッセージを作成できます。このアプリとデフォルトのMessages.appの違いは、メッセージが送信される前に遅延タイマーがあることです。ComposeViewControllerには、メッセージを入力するためのテキストフィールド、連絡先を選択するためのボタン、時間遅延を選択するためのボタン、送信するためのボタン、タイマーをキャンセルするためのボタンがあります。

実際のSMSメッセージを送信する機能を完全に削除しました。メッセージが送信されたことと、新しいメッセージを作成するかどうかをユーザーに通知するアラートビューをユーザーに提示しました。キャンセルを押すと、ModalViewControllerが閉じられ、MasterViewControllerに戻ります。

問題は、行をテーブルに表示できず、テーブルのセルを追加および削除することもできないことです。

MasterViewControllerのviewDidLoad内のコードは次のとおりです。

[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.

// Delete button to delete messages
UIBarButtonItem *deleteBarButtonItem = [[UIBarButtonItem alloc] 
                                      initWithBarButtonSystemItem:UIBarButtonSystemItemTrash
                                      target:self 
                                      action:@selector(deleteText)];
self.navigationItem.leftBarButtonItem = deleteBarButtonItem;


// Compose button to go to compose messages
UIBarButtonItem *composeBarButtonItem = [[UIBarButtonItem alloc] 
                                         initWithBarButtonSystemItem:UIBarButtonSystemItemCompose
                                         target:self 
                                         action:@selector(composeText)];
self.navigationItem.rightBarButtonItem = composeBarButtonItem;

[deleteBarButtonItem release];
[composeBarButtonItem release];

NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSString *message = [defaults objectForKey:kMessageText];
NSString *contactname = [defaults objectForKey:kContactNameText];
NSString *timestamp = [defaults objectForKey:kTimeStampText];

[messageDetails initWithObjectsAndKeys:contactname, kContactNameKey, message, kContactMsgKey, timestamp, kContactTimeKey, nil];

NSMutableArray *messageInfo = [[NSMutableArray alloc] initWithObjects:messageDetails, nil];

self.messagesList = messageInfo;

[messageInfo release];

[super viewDidLoad];

cellForRowAtIndexPathのコードは次のとおりです。

CustomCellViewController *customCell = (CustomCellViewController *)[tableView dequeueReusableCellWithIdentifier:@"CustomCellViewController"];

if (customCell == nil)
{
    NSArray *nib = [[NSBundle mainBundle] loadNibNamed:@"CustomCellViewController"
                                                 owner:self 
                                               options:nil];
    for (id oneObject in nib) if ([oneObject isKindOfClass:[CustomCellViewController class]])
        customCell = (CustomCellViewController *)oneObject;
}

NSUInteger row = [indexPath row];
NSDictionary *messages = [self.messagesList objectAtIndex:row];

customCell.nameLabel.text = [messages objectForKey:kContactNameKey];
customCell.nameLabel.textColor = [UIColor whiteColor];
customCell.messageLabel.text = [messages objectForKey:kContactMsgKey];
customCell.messageLabel.textColor = [UIColor lightGrayColor];
customCell.timeLabel.text = [messages objectForKey:kContactTimeKey];
customCell.timeLabel.textColor = [UIColor blueColor];

customCell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;

return customCell;

セルを削除するためのコードは次のとおりです。

- (void)tableView:(UITableView *)tableView commitEditingStyle(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (editingStyle == UITableViewCellEditingStyleDelete)
    {
    // Delete the row from the data source.        
    [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath]withRowAnimation:UITableViewRowAnimationFade];

    [messagesList removeObjectAtIndex:indexPath.row];
    [self.tableView reloadData];
    }
    else if (editingStyle == UITableViewCellEditingStyleInsert) {
    // Create a new instance of the appropriate class, insert it into the array, and add a new row to the table view.
    }   
}
4

1 に答える 1

0

マスター ビュー コントローラーの新しいインスタンスを作成する最後のコード スニペットが問題です。

これは、探しているView Controllerではありません。parentViewController詳細ビュー コントローラーをモーダルに提示したので、詳細コントローラーのプロパティを介してマスター コントローラーにアクセスできます。

MasterViewController *master = (MasterViewController*)self.parentViewController;

この状況で通常使用されるその他の設計パターン:

  • マスターコントローラーで新しいオブジェクトを作成し、テーブルに行を挿入してから、新しいオブジェクトを詳細コントローラーに渡して更新します
  • マスター コントローラーが準拠する詳細コントローラーのデリゲート プロトコルを作成します。詳細コントローラーをプッシュ時にマスター コントローラーにデリゲートするように設定する

後者は、詳細コントローラーがマスターコントローラーについて必要以上に知っていることを除いて、すべての実用的な目的で行っていることのほとんどです (つまり、マスター .h ファイルがプロトコルに準拠していることを知るだけでなく、マスター .h ファイル全体をインポートしています)。

データ構造に関して、ここに複数の行があると予想される方法がわかりません.1つのメッセージをユーザーのデフォルトに保存し、そのメッセージで配列を作成します。最終的にこれを保存するためにデフォルトを使用するつもりはないことは知っていますが、単一のキーの下にデフォルトで保存された辞書の配列が表示され、各辞書がさまざまな詳細を含むテーブルの行を表すことが期待されますメッセージ、連絡先名キーなどに対して辞書に文字列として保存されます。

常に不変の配列を返すため、デフォルトから返される配列の可変バージョンを作成する必要があります。

cellForRow... メソッドでは、配列から適切な辞書を取得し、そこからセルにデータを入力します。

新しい行を追加するときは、詳細コントローラーに渡す新しい辞書を作成します。

行を削除するときは、関連する辞書を配列から削除します。

于 2011-12-16T07:09:17.693 に答える