Garbled exception when implementing UIPopoverBackgroundView subclass
Asked Answered
A

1

4

I've implemented this class as follows:

#import "JKBackgroundView.h"

@implementation JKBackgroundView

static CGFloat jkArrowBase = 26.0;
static CGFloat jkArrowHeight = 16.0;

// Background image insets
static CGFloat jkBackgroundTopInset = 68.0f;
static CGFloat jkBackgroundLeftInset = 16.0f;
static CGFloat jkBackgroundBottomInset = 16.0f;
static CGFloat jkBackgroundRightInset = 34.0f;

// Content view insets
static CGFloat jkContentTopInset = 40.0f;
static CGFloat jkContentLeftInset = 6.0f;
static CGFloat jkContentBottomInset = 8.0f;
static CGFloat jkContentRightInset = 7.0f;

+(CGFloat)arrowBase {
    return jkArrowBase;
}

-(UIPopoverArrowDirection)arrowDirection {
    return UIPopoverArrowDirectionUp;
}

-(CGFloat)arrowOffset {
    return 0.0f;
}

+(CGFloat)arrowHeight {
    return jkArrowHeight;
}

+(UIEdgeInsets)contentViewInsets {
    return UIEdgeInsetsMake(jkContentTopInset, jkContentLeftInset, jkContentBottomInset, jkContentRightInset);
}

-(void)drawRect:(CGRect)rect {
    UIEdgeInsets popoverInsets = UIEdgeInsetsMake(jkBackgroundTopInset, jkBackgroundLeftInset, jkBackgroundBottomInset, jkBackgroundRightInset);
    UIImage *popoverImage = [[UIImage imageNamed:@"popover_stretchable.png"] resizableImageWithCapInsets:popoverInsets];
    [popoverImage drawInRect:rect];
}

-(id)initWithFrame:(CGRect)frame {
    self = [super initWithFrame:frame];
    if (self) {
        self.backgroundColor = [UIColor clearColor];
    }
    return self;
}

-(void)setArrowDirection:(UIPopoverArrowDirection)arrowDirection {
    // Do nothing
}

@end

I add it to my UIPopoverView (not a subclass) using this code:

_logoutPopover.popoverBackgroundViewClass = [JKBackgroundView class];

When I run the project, though, I receive a crazy error message as follows:

* Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: '-[UIPopoverBackgroundView º¯lå] must be implemented by subclassers.'

Does anyone has any idea what method it thinks I didn't implement? It appears to just be a bunch of gibberish. Thanks!

Edit It looks like I forgot to implement setArrowOffset:. It works after adding that. Apple's error message was just garbled.

Albur answered 2/2, 2012 at 16:37 Comment(1)
Can you show us the interface too?Outlander
O
3

According to the docs for UIPopoverBackgroundView you are required to also implement setters for the properties in UIPopoverBackgroundView (i.e. arrowDirection and arrowOffset.) You've just got the getters in your implementation.

Outlander answered 2/2, 2012 at 16:51 Comment(4)
Should be fixed with a few synthesizes.Frodin
@JoePasq true but it's not necessarily correct in this situation. Firstly it depends on his interface which he hasn't shared with us yet: if the properties are atomic then you can't mix synthesised setters with hand-made getters. Unlikely here, but a consideration. Secondly he needs the roll-your-own getters to force return of his static arrow heights & offsets; given that, it's more readable if he implements the setters manually since they will not actually do anything (if he synthesises, they'll set 'phantom' ivars which are never read.) That's ugly.Outlander
I realized it was a problem with a missing implementation method, but the error message was garbled. I had needed assistance with figuring out what I was missing. Thanks everyone!Albur
Right, that would be ugly and there would be phantoms. Huh, I didn't know you can't mix'em with atomic.Frodin

© 2022 - 2024 — McMap. All rights reserved.