在Main.storyboard和AppDelegate.h之间建立连接

时间:2013-10-03 15:50:48

标签: ios objective-c xcode xcode4

使用Xcode 5.0,我试图关注Big Nerd Ranch book第2版,这似乎有点过时了。

有一个带有2个标签和2个按钮的测验项目示例。

我已经从书中复制了源代码,尤其是AppDelegate.h

#import <UIKit/UIKit.h>

@interface AppDelegate : UIResponder <UIApplicationDelegate> {
    int currentQuestionIndex;
    NSMutableArray *questions;
    NSMutableArray *answers;
    IBOutlet UILabel *questionField;
    IBOutlet UILabel *answerField;
}

@property (strong, nonatomic) UIWindow *window;
- (IBAction)showQuestion:(id)sender;
- (IBAction)showAnswer:(id)sender;

@end

书中没有提及MainWindow.xib,但我确实有Main.storyboard,我放置了标签和按钮:

screenshot

我可以看到源代码编辑器左侧的4个空心小圆圈(在上面的屏幕截图中间)和“连接检查器”(例如“Touch Up Inside”),但我只能'让他们连接起来。我尝试从小圆圈拖动并按住Ctrl键拖动到按钮/标签,有一条蓝线,但它没有连接。

当我右键单击按钮/标签时,会出现一个关于“Outlets”的灰色菜单,但我的IBOutlets / IBActions都没有列在那里。

如何添加标签和按钮的连接?

更新

根据Rob的建议(谢谢+1)我已将属性和方法移至ViewController.*并能够连接标签和按钮。当我点击按钮时,我看到被调用的方法。

但是现在我遇到的问题是init类的ViewController方法没有运行,因此两个数组都是零。

还有什么进一步的提示吗?而且我不确定为什么将我的问题关闭为“太宽泛”的建议 - 我附上了(简短)代码和截图,我的2个问题非常具体(可能是基本的)。

ViewController.h:

#import <UIKit/UIKit.h>

@interface ViewController : UIViewController {
    int currentQuestionIndex;
    NSMutableArray *questions;
    NSMutableArray *answers;
    IBOutlet UILabel *questionField;
    IBOutlet UILabel *answerField;
}
- (IBAction)showQuestion:(id)sender;
- (IBAction)showAnswer:(id)sender;

@end

ViewController.m:

#import "ViewController.h"

@interface ViewController ()

@end

@implementation ViewController

- (id)init {                 // XXX is never called??
    self = [super init];

    if(self) {
        questions = [[NSMutableArray alloc] init];
        answers = [[NSMutableArray alloc] init];

        [questions addObject:@"What is 7 + 7?"];
        [answers addObject:@"14"];
        [questions addObject:@"What is the capital of Vermont?"];
        [answers addObject:@"Montpelier"];
        [questions addObject:@"From what is cognac made?"];
        [answers addObject:@"Grapes"];
    }

    return self;
}

- (IBAction)showQuestion:(id)sender // XXX runs ok when clicked
{
    currentQuestionIndex++;
    if (currentQuestionIndex == [questions count]) {
        currentQuestionIndex = 0;
    }

    NSString *question = [questions objectAtIndex:currentQuestionIndex];
    NSLog(@"displaying question: %@", question);
    [questionField setText:question];
    [answerField setText:@"???"];
}

- (IBAction)showAnswer:(id)sender  // XXX runs ok when clicked
{
    NSString *answer = [answers objectAtIndex:currentQuestionIndex];
    [answerField setText:answer];
}

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

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

@end

1 个答案:

答案 0 :(得分:2)

您的IBOutlet引用应该在视图控制器类中,而不是应用程序委托类。场景的基类(在选择场景下方的栏后,如“身份检查器”中所示)是视图控制器,因此您的IBOutlet引用将与之相关联。当您控制从故事板拖动到视图控制器类时,您会发现它将按照您的意图开始运行。

应用程序委托旨在定义应用程序启动时的行为,输入背景等行为。对于用户与应用程序交互时的行为,通常将其放在视图控制器类中。