从另一个类访问viewController的方法

Old*_*her 4 iphone objective-c uibutton uiviewcontroller

我一直在尝试使用一个UIButton动作来调用另一个类中的方法(AppViewController).我首先尝试在UIButton's调用类中创建视图控制器的实例,(caller.m)然后调用该方法,但这会导致EXC_BAD_ACCESS.

我意识到我需要指向视图控制器的同一个实例,现在我正在尝试确保正确声明视图控制器实例 caller.m.

我的声明AppViewController *viewControllerAppDelegate,所以我的想法是指由同一实例caller.m.

#import "caller.h"
#import "AppDelegate.h"

@implementation caller

- (id)initWithFrame:(CGRect)frame {
...
[btnSplash addTarget:viewController action:@selector(loadSplashView) forControlEvents:UIControlEventTouchUpInside];
....
}
Run Code Online (Sandbox Code Playgroud)

但是,viewController仍显示为未声明.我尝试了其他一些东西,但知道我可能遗漏了一些基本的东西.

:::: UPDATE ::::

好的,事实证明我需要创建以下内容,以便实际声明目标"viewController"并指向正确的实例:

AppDelegate *appDelegate = (AppDelegate *)[[UIApplication sharedApplication] delegate];
AppViewController* viewController = appDelegate.viewController;
Run Code Online (Sandbox Code Playgroud)

现在可以正确调用视图控制器类中的方法.

有关此问题的更清楚解释和更一般的版本,请转到此处: Objective-c基础:在MyAppDelegate中声明的对象无法在另一个类中访问

XJo*_*nes 6

对象有多种方式可以启动操作,与其他对象通信和/或观察他们感兴趣的更改,包括:

  1. UIControl目标/动作绑定
  2. 协议
  3. 键/值观察(KVO)
  4. 通知

在这种情况下,我不认为通知是你想要的.当发布通知的对象不关心哪些对象正在观察通知并且可以有一个或多个观察者时,通知是最合适的.在按下按钮的情况下,您通常只需要特定对象来处理该动作.

我建议使用协议.您将在iOS框架中看到许多正在使用的协议,基本上任何具有delegate属性的类通常都会定义委托对象需要遵循的协议.协议是两个对象之间的契约,使得定义协议的对象知道它可以与符合协议的对象进行通信,而没有关于其类或目的的任何其他假设.

这是一个示例实现.如果有任何错别字或遗漏,请道歉.

在caller.h中(我假设调用者是一个UIViewController):

@class Caller

@protocol CallerDelegate
    - (void)userDidSplashFromCaller:(Caller *)caller;
@end

@interface Caller : UIViewController
    id <CallerDelegate>    delegate;
@end

@property (nonatomic, assign)    id <CallerDelegate>    delegate;

@end
Run Code Online (Sandbox Code Playgroud)

在caller.m中:

@implementation Caller

@synthesize delegate;

- (void)viewDidLoad {
    // whatever you need
    // you can also define this in IB
    [btnSplash addTarget:self forAction:@selector(userTouchedSplashButton)];
}

- (void)dealloc {
    self.delegate = nil;
    [super dealloc];
}

- (void)userTouchedSplashButton {
    if (delegate && [delegate respondsToSelector:@selector(userDidSplashFromCaller:)]) {
        [delegate userDidSplashFromCaller:self];
    }
}
Run Code Online (Sandbox Code Playgroud)

在otherViewController.m中:

// this assumes caller is pushed onto a navigationController
- (void)presentCaller {
    Caller *caller = [[Caller alloc] init];
    caller.delegate = self;
    [self.navigationController pushViewController:caller animated:YES];
    [caller release];
}

// protocol message from Caller instance
- (void)userDidSplashFromCaller:(Caller *)caller {
    NSLog(@"otherVC:userDidSplashFromCaller:%@", caller);
}
Run Code Online (Sandbox Code Playgroud)

[编辑:澄清]

我在再次查看你的问题和代码之后意识到我做了一些在你的代码中可能不正确的假设.您很可能仍应使用协议,但集成我的示例的确切方式取决于您的应用程序.我不知道Caller你的应用程序中有哪个类,但无论它是什么类,它都处理UIButtons,因此很可能是视图控制器或视图.

您对没有正确的appViewController实例的评论让我想知道您是否理解类和类实例之间的区别.如果我的回答对您没有帮助,请发布更多代码,说明如何创建和展示您的视图控制器以及如何配置按钮,我可以尝试澄清我的答案.