Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to pass touches from UIView to UIScrollView

Similar to this thread and many others, I've got a view controller with a NIB file which has this layout...

  • a. UIView (480 x 320) - stores a background image
  • b. UIScrollView (480 x 220) - Is a level selector scrollview
  • c. UIView (480 x 320) - contains a foreground animated graphic

All three items above are subviews of the main View in the NIB. UIView (c) is the full size of the iPhone screen and on top of the hierarchy. On it, I've placed a character which animates based on the current touch position in that view. However the issue is that with this view receiving touches, I cannot get the touches to the ScrollView (b) below it. I still need to use the touches at (c) but also need to pass relevant touches / swipes to the UIScrollView below afterwards.

Can anyone advise how this can be done? I've read various posts on using hittest but don't want to offset the touches completely, I just need to forward them after so that the scrollview still works as normal.

Thanks,

like image 584
Simon Avatar asked Sep 20 '11 16:09

Simon


2 Answers

If it were me, I would set the scrollView as the top view's delegate. This, of course, would require that the top view is a custom sublcass of UIView, so you can set

id delegate; 

and

@property (nonatomic, assign) id delegate;

in the header file. You would then set the scrollView as the delegate with something along the lines of

[topView setDelegate:scrollView];

With this in place, you can then send messages (in your case, touch events) to the scrollView when they are necessary. If, for example, you want to send all touchBegan events, you would have this:

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
    [self.delegate touchesBegan:touches withEvent:event];
}

Of course, if you only want certain events passed, you would set up your parameters in the methods to say when to call [self.delegate ....] or [super ....]. The latter will perform the action for the view rather than in the scrollView. I hope this helps

like image 132
justin Avatar answered Oct 23 '22 05:10

justin


Here's an easier solutions that worked well for me:

In view C (the foreground view that is above the UIScrollView), make the width and height both 0 (so that the view is no longer technically on top of the scrollview) and set clipsToBounds = NO (so that the contents of view C still show up on top of the scrollview). It worked like a charm for me.

 self.viewC.clipsToBounds = NO;
 CGRect frame = self.viewC.frame;
 self.viewC.frame = CGRectMake(frame.origin.x, frame.origin.y, 0, 0);

Note that if view C contains interactive controls then they will no longer work.

like image 45
bbrame Avatar answered Oct 23 '22 05:10

bbrame