gpt4 book ai didi

ios - Objective C block 变为 Nil

转载 作者:行者123 更新时间:2023-12-01 20:05:21 27 4
gpt4 key购买 nike

我正在从 xib 创建一个名为 HeaderView 的自定义 UIView。我在这个 HeaderView 中有一个 UIButton,在按钮点击时,我希望在 ViewController 上调用一个 block ,其中正在添加 HeaderView。这是我的 HeaderView 的代码。

头文件代码

@interface HeaderView : UIView

- (instancetype)initWithFrame:(CGRect)frame;

@property (copy) void(^seeAllHandler)();

@end

实现文件代码
@interface HeaderView()

@property (weak, nonatomic) IBOutlet UILabel *titleLabel;
@property (weak, nonatomic) IBOutlet UIButton *seeAllButton;
@property (nonatomic, strong) UIView *contentView;

@end

@implementation HeaderView


- (instancetype)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
[self setup];
}
return self;
}

- (instancetype)initWithCoder:(NSCoder *)coder
{
self = [super initWithCoder:coder];
if (self) {

}
return self;
}

- (void)awakeFromNib
{
[self.seeAllButton setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
[self.seeAllButton setTitle:@"SEE ALL") forState:UIControlStateNormal];
[self.titleLabel setText:@"My Label")];

}

#pragma mark - Private methods

- (void)setup
{
//Setup view from the xib file.
self.contentView = [[[NSBundle mainBundle] loadNibNamed:NSStringFromClass(self.class) owner:self options:nil] firstObject];
[self.contentView setFrame:self.bounds];
[self addSubview:self.contentView];
self.contentView.backgroundColor = [UIColor ccNordeaPink];
self.contentView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
self.clipsToBounds = YES;
}

- (IBAction)sellAllTapped:(UIButton *)sender {
if(self.seeAllHandler != nil){
self.seeAllHandler();
}

}

@end

这是我的 ViewController viewDidLoad 方法。
@interface ViewController () <UIScrollViewDelegate, UICollectionViewDataSource, UICollectionViewDelegate>

@property (nonatomic, strong) HeaderView *headerView;

@end



- (void)viewDidLoad
{
[super viewDidLoad];
[self setupSubviews];
[self setupConstraints];

}

- (void)setupSubviews
{

self.headerView = [[HeaderView alloc] init ];
self.headerView.translatesAutoresizingMaskIntoConstraints = NO;

self.headerView.seeAllHandler = ^{
DDLogDebug(@"See all Tapped");
};

[self.view addSubView: self.headerView];


}

问题是当按钮被点击时,分配的 block 是 nil,因此它不会被调用。

最佳答案

所以发生的事情是您在 ViewController 的 viewDidLoad 中分配 block (通过 setupSubviews 方法)。我可以看到您正在以编程方式实例化 HeaderView。因此,当您分配 block 时,您实际上是在向实例发送消息。

但是,您还通过调用 loadNibNamed 来膨胀另一个实例。里面setup HeaderView 的方法。并且那个 HeaderView 没有你的 block ,这就是在 UI 中显示的那个。您在 contentView 中有另一个 HeaderView您的 HeaderView。

因此,实际/屏幕上的 HeaderView 实例的处理程序属性为 nil,因此当它尝试将 block 返回给您时,它也使用 nil。

处理正在发生的事情的最佳方法是进入 HeaderView 并在 awakeFromNib 中设置断点。和 setup 中的另一个断点.您会看到首先调用了设置。如果您 po self在 lldb 中,您将获得当前实例的地址。接下来发生的事情是 awakeFromNib 被调用并且它到达那里的断点。如果你这样做 po self再次,您会看到不同的地址。不一样的例子!这是您在 UI 中看到的。而且它没有设置处理程序!

如果您想保留这种加载 View 层次结构的方法,那么一个简单的解决方法是从 ViewController 中的 nib 实例化 HeaderView。

所以不要做 self.headerView = [[HeaderView alloc] init] , 你来做这件事:

self.headerView = [[[NSBundle mainBundle] loadNibNamed:@"HeaderView"owner:self options:nil] firstObject];

关于ios - Objective C block 变为 Nil,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39125223/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com