views:

189

answers:

1

When I add a UIImageView subclass (fullscreen) behind a couple of UIButton subclass instances, those buttons stop receiving the touches and don't function anymore. Nothing I have tried has worked to restore their connectivity to user touches.

I have tried:
a) Using a UIImageView subclass for the front view (that receives the touches) and making sure setUserInteractionEnabled is YES. Result: UIButtons are not responding when the UIView is present.

b) Explicitly passing the touches from the front view to the view controller in hopes that it will do the right thing. Result: UIButtons are not responding to the touches.

c) Calling the touchesBegan, touchesMoved and touchesEnded methods directly on the button I want to interact with when any touch on the front UIView is received. Result: Strikingly, the buttons don't respond even when I am cramming the touch events down their throat.

d) Passing the touches from the front view to the UIViewController, and iterating over all subviews handing out the touches manually. I included a touchesBegan method showing how I tried to do this. When executed the loop is infinite, it never progresses past the first view (is of type FrameUIView).

I know this problem is likely the result of my lack of understanding of proper view hierarchy or the responder chain.

if I comment the last view created after the button, then the buttons work fine. Is there something special about UIButtons in this respect?

Here is the code.

I have a UIViewController subclass, in it:

    - (void)loadView {

        mainAppView = [[UIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; 
        self.view = mainAppView;

        frameImageView = [[FrameUIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
        frameImageView.image = [UIImage imageNamed:[[[ThemeController sharedInstance] currentTheme] frameImageFilename]];
        [frameImageView setUserInteractionEnabled:YES];
        [mainAppView addSubview:frameImageView];

        zoomInButton = [[CustomUIButton alloc] initWithFrame:CGRectMake(controlsOriginX + zoomWidth + lightWidth, controlsOriginY, zoomWidth, controlsHeight)];
    [zoomInButton setTitle:@"+" forState:UIControlStateNormal];
    [[zoomInButton titleLabel] setFont:[UIFont systemFontOfSize:28]];
    [zoomInButton addTarget:self action:@selector(doMyAction) forControlEvents:UIControlEventTouchDown];
    [zoomInButton addTarget:self action:@selector(cancelMyAction) forControlEvents:UIControlEventTouchUpInside];
    [mainAppView addSubview:zoomInButton];


        FrameFrontUIView *frameFrontImageView = [[FrameFrontUIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
        frameFrontImageView.image = [UIImage imageNamed:[[[ThemeController sharedInstance] currentTheme] frameFrontImageFilename]];
        [frameFrontImageView setUserInteractionEnabled:YES];
    [mainAppView addSubview:frameFrontImageView];
}

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
    for (UIView *view in self.view.subviews) {
        NSLog(@"view is a %@", [view description]);
        [view touchesBegan:touches withEvent:event];
    }
}

Anyone with a tip on how to do this wins the internets and a cookie. Also accepting revolvers for russian roulette mayhem. Thank you.

A: 

Have you tried using the buttons without the image view behind them? Subclassing UIButton is not advisable. The way to instantiate UIButtons is with factory methods:

UIButton* myButton = [UIButton buttonWithType:UIButtonTypeCustom];

So my guess is that the CustomUIButton instances you have created are not properly set up.

Felixyz
Its definitely a good guess. I subclassed UIButton to solve a problem, namely that I want to be able to set the alpha of ONLY the background image, and not of the label or the rest of the button. I achieved this by making a subclassed button that draws two buttons on top of each other, with the top having the label and the actions, and the bottom an image button alpha set.I will investigate them a little further, my next step was to do as you suggested and try a stock button.
Royce
That doesn't sound like a good approach. Try this: zoomInButton.imageView.alpha = 0.5;
Felixyz
Will do, thanks.For the time being I shipped out on this problem by setUserInteraction = NO; This turns off the event and touch consumption by the imageview in the foreground, allowing the app to work properly.As for how to enable interaction, but yet pass on those events/touches if not consumed....well I couldn't figure it out and I tried a ton of things.
Royce