2014-08-31 3 views
2

Редактировать 1: Я думаю, что я понял проблему, я просто не смог ее решить. В SecondViewController.m, где textFieldShouldReturn определен, «if ([self.delegate отвечаетSoSelector: @selector (passString :)])» возвращает false, поскольку NSLog не запускался.Как передать строку из текстового поля (встроенного в ячейку таблицы) во втором контроллере обратно на метку в 1-м контроллере (также встроенной в ячейку таблицы)?

Редакция 2: Проверка NSLogs того, кто является делегатом в обоих ViewControllers, дал хорошее представление о проблеме. В FirstViewController prepareForSegue назначает правильный делегат. После перехода в SecondViewController делегат становится «null».

Это то, чего я пытался добиться в течение недели без успеха. Я понимаю, что мне нужно передать данные обратно в двухслойный стек навигации с помощью делегатов. Однако я не уверен, почему мой код не работает (строка не проходит).

Было бы также признательно, если кто-нибудь сможет мне рассказать (ссылки и другие ресурсы), как правильно сделать вид формы/представления (второй контроллер) для ввода данных, который можно повторно использовать для редактирования ярлыков конкретных ячеек на дисплее Вид (1-й контроллер).

Вот мой код:

SecondViewController.h

#import <UIKit/UIKit.h> 

@protocol PassStringDelegate 
- (void)passString:(NSString *)stringFromTextField; 
@end 

@interface SecondViewController : UIViewController <UITableViewDataSource, UITableViewDelegate, UITextFieldDelegate> 

@property (strong, nonatomic) IBOutlet UITableView *detailTable; 

@property (weak, nonatomic) id <PassStringDelegate> delegate; 

@end 

SecondViewController.m

#import "SecondViewController.h" 
#import "CustomCell.h" // My cell is custom built in IB. 

@interface SecondViewController() 

@end 

@implementation SecondViewController 

@synthesize delegate; 

@synthesize stringFromTextField; 

- (void)viewDidLoad 
{ 
    ...    
    NSLog(@"%@", self.delegate);       // Returns "(null)". 
}  

... 

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath 
{ 
    CustomCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Data Entry" forIndexPath:indexPath]; 
    [cell setEditing:YES animated:YES]; 
    cell.customTextField.clearsOnBeginEditing = NO; 
    cell.customTextField.returnKeyType = UIReturnKeyDone; 
    cell.customTextField.delegate = self;     // customTextField is a custom textfield embedded in the custom cell. 
    [self textFieldShouldReturn:cell.customTextField]; // This function supposedly will trigger passString:stringFromTextField when the cell is done with editing. 

    return cell; 
} 

... 

- (BOOL)textFieldShouldReturn:(UITextField *)textField 
{ 
    [textField resignFirstResponder]; 
    if ([self.delegate respondsToSelector:@selector(passString:)]) { 
     [self.delegate passString:textField.text]; 
     NSLog(@"Sent back: %@", textField.text);   // I checked NSLog, this was never called. 
    } 
    return YES; 
} 

FirstViewControll er.h

#import <UIKit/UIKit.h> 
#import "SecondViewController.h" 

@interface FirstViewController : UIViewController <UITableViewDataSource, UITableViewDelegate, UITextFieldDelegate, PassStringDelegate> 

@property (strong, nonatomic) IBOutlet UITableView *table; 

@property (copy, nonatomic) NSArray *myList; 

@property (weak, nonatomic) NSString *obtainedString; 

@end 

FirstViewController.m

#import "FirstViewController.h" 
#import "CustomCell.h" 

@interface FirstViewController() 

@end 

@implementation FirstViewController 

@synthesize obtainedString; 

... 

- (void)viewDidAppear:(BOOL)animated 
{ 
    [super viewDidAppear:animated]; 
    [self passString:obtainedString]; 
} 

... 

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath 
{ 
    CustomCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Display" forIndexPath:indexPath]; 
    cell.customLabel.text = obtainedString;    // I want the label to display the text in the text field in the second controller. 
    cell.detailCustomLabel.text = self.myList[indexPath.row]; 

    return cell; 
} 

... 

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender 
{ 
    if ([segue.identifier isEqualToString:@"segue"]) 
    { 
     SecondViewController *detailedView = [[SecondViewController alloc] init]; 
     detailedView.delegate = self; 
     NSLog(@"%@", detailedView.delegate);   // Returns "<SecondViewController: 0x10967b590>". 
    } 
} 

... 

- (void)passString:(NSString *)stringFromTextField 
{ 
    obtainedString = stringFromTextField; 
} 

Пожалуйста, проверьте мой путь делегата и призывает, чтобы увидеть, если то, что я был близок к подходящим. Большое спасибо!

+0

Если в будущем вы не хотите связываться с написанием всего кода формы и передачей информации назад, вы можете проверить https://github.com/mamaral/MAFormViewController – Mike

+0

Конечно, я проверю это: D –

ответ

1

Попробуйте это:

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender 
{ 
    if ([segue.identifier isEqualToString:@"segue"]) { 
     //SecondViewController *detailedView = [[SecondViewController alloc] init]; 
     //this creates a new object of SecondViewController that has nothing to do 
     //with the segue 

     //this should fix it: 
     SecondViewController *detailedView = [segue destinationViewController]; 
     detailedView.delegate = self; 
    } 
} 

Вы создавали новый объект SecondViewController и устанавливали на нем делегат.
К сожалению, этот объект не использовался вообще, так как segue уже создал объект и нажав , что объект вместо того, который вы создаете здесь.

+0

Фантастический! Я забыл о части [segue destinationViewController]! Хотя текст в текстовом поле по-прежнему не отображается, NSLog в FirstViewController по крайней мере получил текст текстового поля. Спасибо: D Если вы не возражаете, чтобы помочь мне исправить текстовый дисплей, я бы очень признателен. –

+0

@StackAsker :) отлично. как для текстового дисплея ... не уверен в этом (_right now_), но это может быть связано с тем, что 'receivedString' имеет ссылку« слабый ». Сделайте это «сильным» и проверьте. – staticVoidMan

+0

@StackAsker: подождите, не стоит ли использовать 'полученную строку 'каким-то образом? Кажется, ваш метод '-passString:' является неполным. – staticVoidMan

0

Добавить свойство @property (сохранить) FirstViewControllor * parentController во втором viewcontrollor и перед и нажать SecondViewControllor

добавить

secondviewcontrollor.parentController=self; 

и в

- (void)textFieldDidEndEditing:(UITextField *)textField 
{ 
    (FirstViewControllor)self.parentController.obtainedString=textField.text; 
} 
+0

она не работает :( это, кажется, не признают stringFromTextField во 2-м контроллере. Я подозреваю, что это что-то делать с методом textFieldDidEndEditing, который я не думаю, что называется. –

+0

ты пользуешься navigationcontrollor? –

+0

Да, есть контроллер навигации, толкает два вида выше. –