iPhone协议委托传递数据

时间:2012-03-21 21:02:09

标签: iphone objective-c ios

我通过委托和协议传递字符串。正确地将字符串接收到类,但是在调用viewDidLoad方法之后会发生这种情况。 viewDidLoad方法需要传递的字符串。

关于如何在viewDidLoad之前调用委托方法的任何想法?我认为这是代理/协议数据传递的想法。

创建和推送新视图的方法:

ViewControllerTwo *two = [[ViewControllerTwo alloc] initWithNibName:@"ViewControllerTwo" bundle:nil];
two.delegate = self;
[two setString:theString];
[self.navigationController pushViewController:two animated:YES];
[two release]; 

在ViewControllerTwo中:

- (void)setString:(NSString *)str
{
    self.myString = str;
}

编辑:感谢您的输入。但是,我确实了解如何通过init方法传递此数据。我最近一直在测试协议和代表,我想知道是否有办法做到这一点。我已经成功地在另一个类中传递了这样的数据并且它有效。首先调用协议方法设置字符串。这似乎是处理传递数据的一种更清晰的方式。

5 个答案:

答案 0 :(得分:1)

我认为你可能会对Delegation的用途和原因感到有些困惑。

例如,如果您在UIViewController中执行某种操作并且需要通知另一个子类正在执行该操作,或者需要通知,则可能需要在ViewController子类中创建协议。该行动的结果。

现在为了想要知道动作(接收器)的子类,它必须在它的头文件中符合该协议。

您还必须将delegate“设置”为receiving class/controller

有很多方法可以获得receiving controller/class的引用,将其设置为delegate,但常见的错误是分配和初始化该类的新实例以将其设置为委托,该类已经被创建。这样做是将新创建的类设置为委托,而不是已经创建并等待消息的类。

您尝试做的只是将值传递给新创建的类。由于您只需创建此UIViewController类,因此receiver(ViewControllerTwo)中的属性就是一个属性。

在您的案例中NSString

 @Property (nonatiomic, retain) NSString *string; //goes in ViewControllerTwo.h

当然不要忘记在主要内容:

  @synthesize string; //Goes in ViewControllerTwo.m

现在您的ViewControllerTwo无需设置。

 - (void)setString:(NSString *)str  //This Method can be erased
    {                                  //The setter is created for free
        self.myString = str;          // when you synthesized the property
    }   

使用@synthesize时,setter和Getters是免费的。只需将值传递给ViewController即可。除了委托:

之外,实现与您的代码相同
  ViewControllerTwo *two = [[ViewControllerTwo alloc] initWithNibName:@"ViewControllerTwo" bundle:nil];
    [two setString:theString];
    [self.navigationController pushViewController:two animated:YES];
    [two release];

答案 1 :(得分:0)

如果需要在初始化阶段传递该字符串,可以在init方法中传递它。

因此,在您的控制器中,您需要创建一个属性和一个额外的init方法,如下所示:

·H

@property (nonatomic, copy) NSString* myString;

-(id)initWithString:(NSString*)theString;

的.m

@synthesize myString;

-(id)initWithString:(NSString*)theString {
    self = [super initWithNibName:@"ViewController" bundle:nil]; // I prefer to set the name of the controller internally
    if(self) {
        myString = [theString copy];
    }
    return self;
}

然后,在任意位置使用self.myString

如果您不使用ARC,请记得发布。

- (void)dealloc
{
   [myString release];
   [super dealloc];
}

答案 2 :(得分:0)

您可以为ViewControllerTwo创建自定义初始值设定项,例如

- (id)initWithString:(NSString *)aString;
{
    self = [super initWithNibName:@"ViewControllerTwo" bundle:nil];
    if( !self ) return nil;

    self.myString = aString;
    // other initialization

    return self;
}

ViewControllerOne中的初始化只是:

ViewControllerTwo *vc = [[ViewControllerTwo alloc] initWithString:theString];
[[self navigationController] pushViewController:vc animated:YES];
[vc release];

答案 3 :(得分:0)

我不会为此使用协议。要将数据从父视图控制器传递给子视图,请使用自定义初始化方法。

在ViewControllerTwo.h中:

-(id)initWithString:(NSString *)str;

然后在ViewControllerTwo.m中实现它:

-(id)initWithString:(NSString *)str {
    self = [super self];
    if(self) {
        self.myString = str;
    }
    return self;

然后在你的ViewController中调用它:

ViewControllerTwo *two = [[ViewControllerTwo alloc] initWithString:@"Cool String"];

答案 4 :(得分:0)

将数据放在init方法或viewDidLoad中将无法正常工作,因为用户可以在不卸载视图或重新初始化视图控制器的情况下来回切换。

检索更改数据的最佳位置是viewWillAppear控制器方法。这样,每次用户切换时都会更新数据。

另一种最好的方法是使用MVC架构。如果你有单独的模型类,它只保存数据,你可以从任何控制器写入/更新。