协议/代表不起作用

时间:2017-04-21 11:06:17

标签: ios objective-c iphone uiviewcontroller delegates

我有三个UIViewcontroller,即ViewController,BViewController和CViewController,ViewController是来自UINavigationController的RootViewController,

我从ViewController推送 - > BViewController - > CViewController,通过按钮操作。

我在CViewController中声明了协议。这个协议方法适用于BViewController,但我不了解如何在ViewController中将其作为委托方法。

我在View Controller中创建了一个CViewController对象,然后为该委托声明了self,虽然它不起作用,下面是我的代码。请帮我。我在这里做错了!

我的Root View Controller,即ViewController

#import "ViewController.h"
#import "BViewController.h"
#import "CViewController.h"

@interface ViewController ()<testDelegates>

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    CViewController *cVC = [self.storyboard instantiateViewControllerWithIdentifier:@"CViewController"];
    cVC.mydelegate = self;
}

- (IBAction)nextAction:(id)sender {

    BViewController *bViewC = [self.storyboard instantiateViewControllerWithIdentifier:@"BViewController"];

    [self.navigationController pushViewController:bViewC animated:YES];
}

-(void)TestMethod{

    NSLog(@" Its NOT Working");
}

我的第二个视图控制器,即BViewController

#import "BViewController.h"
#import "CViewController.h"

@interface BViewController ()<testDelegates>

@end

@implementation BViewController

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

- (IBAction)bNextAction:(id)sender {

    CViewController *cVC = [self.storyboard instantiateViewControllerWithIdentifier:@"CViewController"];

//    cVC.mydelegate = self;
    [self.navigationController pushViewController:cVC animated:YES];
}

-(void)TestMethod{

    NSLog(@" Its Working If I uncomment to cVC.mydelegate = self");
}

我的第三个View Controller,我在.h文件中声明了一个协议,即CViewController

#import <UIKit/UIKit.h>

@protocol testDelegates <NSObject>

-(void)TestMethod;

@end

@interface CViewController : UIViewController

@property (weak) id <testDelegates> mydelegate;

@end

在.m文件中

#import "CViewController.h"

@interface CViewController ()

@end

@implementation CViewController

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

- (IBAction)cNextAction:(id)sender {

    [self.mydelegate TestMethod];
}

4 个答案:

答案 0 :(得分:1)

离开viewDidLoad方法后,您创建了类并且此类正在销毁。

- (void)viewDidLoad {
    [super viewDidLoad];

    CViewController *cVC = [self.storyboard instantiateViewControllerWithIdentifier:@"CViewController"];
    cVC.mydelegate = self;
}

据我所知,你需要从CViewController在ViewController中执行一些方法。

您可以将viewController作为委托传递给BViewController,然后将它传递给CViewController。

或者你可以使用这样的代码:

- (IBAction)cNextAction:(id)sender {
    id< testDelegates > delegate = self.navigationController.viewControllers[0];
    if([delegate conformsToProtocol:@protocol(testDelegates)])
    {
        [delegate TestMethod];
    }
}

这不是最好的方法,但它会起作用。

答案 1 :(得分:1)

试试这个

self.delegate = self.navigationController.viewControllers[0];

答案 2 :(得分:1)

你需要在BViewController类中声明另一个Protocol。

Please follow below steps.

第1步:BViewController.h

@protocol testDelegates2 <NSObject>

-(void)TestMethod2;

@interface BViewController : UIViewController

@property (weak) id <testDelegates> mydelegate;


@end
@implementation CViewController

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

- (IBAction)cNextAction:(id)sender {

    [self.mydelegate TestMethod2];
}

Step 2. In ViewController class conform Protocol
@interface ViewController ()<testDelegates>

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    CViewController *cVC = [self.storyboard instantiateViewControllerWithIdentifier:@"CViewController"];
    cVC.mydelegate = self;
}

- (IBAction)nextAction:(id)sender {

    BViewController *bViewC = [self.storyboard instantiateViewControllerWithIdentifier:@"BViewController"];
cVC.mydelegate = self; //important line
    [self.navigationController pushViewController:bViewC animated:YES];
}

-(void)TestMethod2{

    NSLog(@"Final Output");
}

答案 3 :(得分:1)

如果您正在尝试将CViewController的委托设置为ViewController 试着把

self.mydelegate = self.navigationController.viewControllers[0]

在CViewController的viewDidLoad方法上。

此外,您正在尝试使ViewController和BViewController都是CViewController的委托,那么这是不可能的,因为对象的委托只能是唯一的。这意味着委托只是一个保存对象引用的变量,因为您知道变量的值在某个时刻可以是唯一的。

所以如果你愿意在Viewcontroller和BViewController上做一些任务,那么使用通知模式。 See apple doc here