简体   繁体   中英

get EXEC_BAD_ACCESS inside initWithCoder

I have a problem during loading/creating a new view form xib file. I get EXEC_BAD_ACCESS code=2 and on my call stack i see multiple call of initWithCoder method. I do not understand why it is happened since i call alloc init for my class only once. Below my code:

@interface SongListView :  NSView
@property (nonatomic, strong) IBOutlet NSScrollView* view;
@end

@implementation SongListView

- (id)initWithFrame:(NSRect)frameRect
{
    self = [super initWithFrame:frameRect];

    if(self)
    {
        [self setup];
    }
    return self;
}

- (id)initWithCoder:(NSCoder *)aDecoder
{
    self = [super initWithCoder: aDecoder];

    if(self)
    {
        [self setup];
    }

    return self;
}

- (void)setup
{
    NSArray *nib;

    [[NSBundle mainBundle] loadNibNamed:@"scrollTabViewItemWithTableView"
                                  owner:self
                        topLevelObjects:&nib];
    [self addSubview: self.view];
}

@end

and this is how I create SongListView:

SongListView* tableView = [[SongListView alloc] init];

Can someone explain me what happens, why i get mutiple call of initWithCoder method, and how to fix it?

Generally your NSView subclasses shouldn't load XIBs. They should either be IN a XIB (and thus created when the XIB loads) or created in code.

In your case there are a number of architecturally strange things, but I suspect the crash is caused by you having a SongListView instance inside scrollTabViewItemWithTableView.xib, so when you load the XIB you run setup and load the XIB and run setup and load the XIB and run setup and...

You are trying to add your view as a subview of itself:

[self addSubview:self.view];

Code like this hurts my eyes. You have a SongListView object, but you've named it tableView . You've defined an initialiser for initWithFrame: but you are sending it the init message when you are creating it.

Loading nib causes a call to -initWithCoder: on the related class and passing self as owner assigns the top-level view in nib as self. You have a recursion because with each load, you try to load the view again.

Once you loaded the nib, in -initWithCoder: your view is already loaded, and you don't have to load nib or add subview.

What usually goes in setup are some UI additions, or some others things that couldn't be done in IB.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM