IBOutlet未在awakeFromNib中连接

时间:2011-08-02 02:18:08

标签: ios uiscrollview iboutlet awakefromnib

此处链接的示例代码效果很好,允许UIScrollView显示带有分页的图像,并预览当前图像之前和之后的图像:

我正在尝试将示例封装在可以重用的单个控件中。所以我创建了一个PagingScrollView:

@interface PagingScrollView : UIView {
    IBOutlet UIScrollView * scrollView;
}

@property (nonatomic,retain) IBOutlet UIScrollView * scrollView;

@end

带有简单的实现

- (void) awakeFromNib
{
    [super awakeFromNib];

    NSLog(@"awake from nib");
}

在PagingScrollView.xib中,我将包含UIScrollView和ARScrollViewEnhancer的View与原始ScrollViewPagingExampleViewController xib完全相同。其File's Owner的类设置为PagingScrollView,其scrollView插座设置为子UIScrollView。

在ScrollViewPagingExampleViewController中,我只是声明:

IBOutlet PagingScrollView   *pagingScrollView;

在IB中,我拖动一个View,将其类设置为PagingScrollView,并将其pagingScrollView插座连接到PagingScrollView。

在awakeFromNib中,scrollView属性为nil。我认为既然scrollView在同一个笔尖中连接在IB中,那么它就可以使用了。

令人困惑的是,在ScrollViewPagingExampleViewController.xib中,有一个名为scrollView的空插座。这可能表明PagingScrollView的实例与PagingScrollView.xib中定义的实例不同。

因此,我无法使用实际的子视图填充UIScrollView。我在这里做错了什么?

4 个答案:

答案 0 :(得分:13)

这里有一个非常好的答案:Accessing View in awakeFromNib?

长话短说,视图可能会加载到awakeFromNib中,但其内容会被懒散加载,这就是为什么你应该使用viewDidLoad而不是awakeFromNib来实现你想要实现的目标。

答案 1 :(得分:5)

对于那些在Swift 4中寻找合适答案的人来说,你走了。

override func awakeAfter(using aDecoder: NSCoder) -> Any? {
    guard subviews.isEmpty else { return self }
    return Bundle.main.loadNibNamed("MainNavbar", owner: nil, options: nil)?.first
}

虽然,我发现真正的秘密是你没有子类化.xib文件的主视图。而是让文件所有者成为你想要的类,并在类init(

)中添加Nib
let bundle: Bundle = Bundle(for: type(of: self))
let nib: UINib = UINib(nibName: "<Nib File Name>", bundle: bundle)
if let view = nib.instantiate(withOwner: self, options: nil).first as? UIView {
    view.frame = bounds
    view.autoresizingMask = [.flexibleWidth, .flexibleHeight]
    view.translatesAutoresizingMaskIntoConstraints = true
    addSubview(view)
}

答案 2 :(得分:2)

我遇到了这个问题而且和你一样,其他文章并没有适用。我有一个ViewController,它有自己的视图。在该ViewController的.xib文件中,我放置了一个视图,并为其提供了CustomView类。除了CustomView在其自己的.xib文件中定义之外,这将非常有用,所以在awakeFromNib中,所有IBOutlet都是零。这是因为在接口构建器中无法将.xib文件链接在一起。因此,当我的ViewController视图被放到屏幕上时,它会尝试实例化CustomView,而不是加载CustomView.xib文件。

这里有一个详细的解决方法http://cocoanuts.mobi/2014/03/26/reusable/,但要点是我必须在我的CustomView类中实现以下内容

@implementation CustomView

    - (id)awakeAfterUsingCoder:(NSCoder *)aDecoder
    {
        if (![self.subviews count])
        {
            NSBundle *mainBundle = [NSBundle mainBundle];
            NSArray *loadedViews = [mainBundle loadNibNamed:@"CustomView" owner:nil options:nil];
            return [loadedViews firstObject];
        }
        return self;
    }

@end

答案 3 :(得分:2)

使用Swift,您可以在自定义视图设置后使用该项:

class PointsTableViewCell: UITableViewCell {

    @IBOutlet weak var pointsTitleLabel: UILabel! {
        didSet {
            self.pointsTitleLabel.text = "Points"
        }
    }
}