Objective c 如何将NSString从一个视图控制器传递到另一个视图控制器?

Objective c 如何将NSString从一个视图控制器传递到另一个视图控制器?,objective-c,properties,uiviewcontroller,nsstring,scope,Objective C,Properties,Uiviewcontroller,Nsstring,Scope,我用两个视图控制器制作了一个非常简单的基于故事板的项目 我只想从VC2访问VC1中声明的字符串。第二个VC应该在按下按钮后在文本字段中显示文本 我不想使用委托,一个用于全局数据或全局变量和外部变量的单独类。相反,我读到使用一个VC对另一个VC的引用很容易实现变量共享 对于下面显示的代码,XCode没有抱怨,但是我的问题是:第二个VC中的NSLog返回null。 如果有人能告诉我如何修改代码,将字符串传递给第二个VC/告诉我哪里出错了,我将不胜感激 VC1标题: #import <UIKit

我用两个视图控制器制作了一个非常简单的基于故事板的项目

我只想从VC2访问VC1中声明的字符串。第二个VC应该在按下按钮后在文本字段中显示文本

我不想使用委托,一个用于全局数据或全局变量和外部变量的单独类。相反,我读到使用一个VC对另一个VC的引用很容易实现变量共享

对于下面显示的代码,XCode没有抱怨,但是我的问题是:第二个VC中的NSLog返回null。

如果有人能告诉我如何修改代码,将字符串传递给第二个VC/告诉我哪里出错了,我将不胜感激

VC1标题:

#import <UIKit/UIKit.h>

@interface ViewController : UIViewController

@property NSString* textToPassToOtherVC;
VC2标题:

#import <UIKit/UIKit.h>

@class ViewController;

@interface ViewController2 : UIViewController

@property (nonatomic, strong) ViewController *received;

@property (strong, nonatomic) IBOutlet UITextField *textDisplay;

- (IBAction)textButton:(id)sender;

@end

您是否已检查您的
self.received
是否不为null/nil

在代码中设置一个断点,以查看
self.received
是否已实际初始化(如果未初始化,则这就是您未看到任何内容的原因):


您是否已检查您的
self.received
是否不为null/nil

在代码中设置一个断点,以查看
self.received
是否已实际初始化(如果未初始化,则这就是您未看到任何内容的原因):


你的错误是基于对财产的根本误解。属性仅仅是处理getter和setter的样板文件和实现细节的语法糖。虽然设置_texttopasstouthervc确实会使属性返回该值,但它不会“通知”另一个,因为它对“received”的引用默认设置为nil,并且您从未设置过

如果在您实际检查此共享文本的值之前的任何地方,您有以下行:

ViewController *myVC1; 
ViewController2 *myVC2;

// ...some initialization.

myVC2.received = myVC1;
// Now the IBAction will display the correct text.

一切都会成功。

你的错误是基于对属性的根本误解。属性仅仅是处理getter和setter的样板文件和实现细节的语法糖。虽然设置_texttopasstouthervc确实会使属性返回该值,但它不会“通知”另一个,因为它对“received”的引用默认设置为nil,并且您从未设置过

如果在您实际检查此共享文本的值之前的任何地方,您有以下行:

ViewController *myVC1; 
ViewController2 *myVC2;

// ...some initialization.

myVC2.received = myVC1;
// Now the IBAction will display the correct text.

一切正常。

尝试使用NSNotification。当您需要发送字符串时,使用对象发布NSNOTITIONG

当您想要发送字符串时放置(当然,在您给字符串一个值之后):

在第二个视图控制器中:

-(void)viewDidLoad:
{
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(ThingYouWantToDoWithString:) name:@"sendString" object:nil];
}

- (void)ThingYouWantToDoWithString:(NSNotification *)notification{
        // Make sure you have an string set up in your header file or just do NSString *theString = [notification object] if your using ARC, if not allocate and initialize it and then do what I just said
        theString = [notification object];
        NSLog("%@", theString);
        [self performSelector:@selector(OtherThings:) object:theString];
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    if ([segue.identifier isEqualToString:@"mySegue"])
    {
        ViewController2 *targetVC = (ViewController2*)segue.destinationViewController;
        targetVC.received = self;
    }
}

希望这有帮助

尝试使用NSNotification。当您需要发送字符串时,使用对象发布NSNOTITIONG

当您想要发送字符串时放置(当然,在您给字符串一个值之后):

在第二个视图控制器中:

-(void)viewDidLoad:
{
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(ThingYouWantToDoWithString:) name:@"sendString" object:nil];
}

- (void)ThingYouWantToDoWithString:(NSNotification *)notification{
        // Make sure you have an string set up in your header file or just do NSString *theString = [notification object] if your using ARC, if not allocate and initialize it and then do what I just said
        theString = [notification object];
        NSLog("%@", theString);
        [self performSelector:@selector(OtherThings:) object:theString];
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
    if ([segue.identifier isEqualToString:@"mySegue"])
    {
        ViewController2 *targetVC = (ViewController2*)segue.destinationViewController;
        targetVC.received = self;
    }
}

希望这有帮助

第二个视图控制器需要将其
received
属性设置为表示第一个视图控制器的值

对于基于情节提要的项目,这通常在
prepareforsgue:
中完成。在执行到第二个视图控制器的转换之前,将在第一个视图控制器中调用此方法

(在我看来,最好只将字符串传递给第二个视图控制器,而不要将指针传递给整个视图控制器,因为这样可以减少依赖性,并且这是第二个视图控制器真正需要的唯一信息,但不要让事情复杂化。)

以下是我认为您需要执行的步骤:

  • 在情节提要中为从第一个视图控制器到第二个视图控制器的序列命名。对于这个示例,我将其称为
    mySegue
  • 在“ViewController.m”中导入“ViewController2.h”-您的第一个视图控制器将需要知道第二个视图控制器有一个
    接收的属性
  • 在第一个视图控制器中添加类似的
    prepareforsgue:
    方法:

    -(void)viewDidLoad:
    {
            [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(ThingYouWantToDoWithString:) name:@"sendString" object:nil];
    }
    
    - (void)ThingYouWantToDoWithString:(NSNotification *)notification{
            // Make sure you have an string set up in your header file or just do NSString *theString = [notification object] if your using ARC, if not allocate and initialize it and then do what I just said
            theString = [notification object];
            NSLog("%@", theString);
            [self performSelector:@selector(OtherThings:) object:theString];
    }
    
    - (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
    {
        if ([segue.identifier isEqualToString:@"mySegue"])
        {
            ViewController2 *targetVC = (ViewController2*)segue.destinationViewController;
            targetVC.received = self;
        }
    }
    

希望这段代码的作用相当清楚

第二个视图控制器需要将其
received
属性设置为表示第一个视图控制器的值

对于基于情节提要的项目,这通常在
prepareforsgue:
中完成。在执行到第二个视图控制器的转换之前,将在第一个视图控制器中调用此方法

(在我看来,最好只将字符串传递给第二个视图控制器,而不要将指针传递给整个视图控制器,因为这样可以减少依赖性,并且这是第二个视图控制器真正需要的唯一信息,但不要让事情复杂化。)

以下是我认为您需要执行的步骤:

  • 在情节提要中为从第一个视图控制器到第二个视图控制器的序列命名。对于这个示例,我将其称为
    mySegue
  • 在“ViewController.m”中导入“ViewController2.h”-您的第一个视图控制器将需要知道第二个视图控制器有一个
    接收的属性
  • 在第一个视图控制器中添加类似的
    prepareforsgue:
    方法:

    -(void)viewDidLoad:
    {
            [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(ThingYouWantToDoWithString:) name:@"sendString" object:nil];
    }
    
    - (void)ThingYouWantToDoWithString:(NSNotification *)notification{
            // Make sure you have an string set up in your header file or just do NSString *theString = [notification object] if your using ARC, if not allocate and initialize it and then do what I just said
            theString = [notification object];
            NSLog("%@", theString);
            [self performSelector:@selector(OtherThings:) object:theString];
    }
    
    - (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
    {
        if ([segue.identifier isEqualToString:@"mySegue"])
        {
            ViewController2 *targetVC = (ViewController2*)segue.destinationViewController;
            targetVC.received = self;
        }
    }
    

希望这段代码的作用相当清楚

您在ViewController2中设置“received”的位置?嗨,Michael,我没有设置“received”,但这应该是对VC1的引用,因此在本例中,代码self.received.texttopastothervc;应该给我字符串“hereissometext”在哪里声明“
\u texttopasstouthorthervc
?除了在您的“
@synthesis
”行中引用它之外,我在其他任何地方都没有看到它。嗨,Michael,也许我离这里很远,但是“\u texttopastothervc”在VC1中声明,应该传递给VC2,或者我希望如此。但我没有看到在VC1中声明的“
\u texttopastothervc
”。您在ViewControl中的何处设置“已接收”