title: iPhone - Handle touch slide in a UIViewController
body: <p>I'd like to handle touches (horizontal slide in particular) in a UIViewController subclass I did, but the problem is the controller's view contains a UIScrollView which covers the whole screen, so "touchesBegan:" and "touchesEnded:" events are never called in my controller. The scrollview only scrolls vertically.</p>
  
  <p>What would be the best way to make it able to handle these events? Make my UIViewController also inherit from UIScrollView and handle touches as needed (and remove the current scroll view), or use a UIScrollView subclass in place of my current scroll view, which will call a delegate method for the cases I need? Or maybe is there a another way?</p>
  
  <p>Here is my current code:</p>
  
  <pre><code>// View creation and adding to parent
  NewViewController* newViewController = [[newViewController alloc] initWithNibName:@"NewViewController" bundle:nil];
  [self.view addSubview:newViewController.view];
  
  // NewViewController.h
  @interface NewViewController : UIViewController {
      IBOutlet UIScrollView*  scrollView;
  
      // other outlets and properties
  }
  - (void)touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event;
  - (void)touchesEnded:(NSSet*)touches withEvent:(UIEvent*)event;
  </code></pre>
  
  <p>In IB, NewViewController's view contains scrollView which contains all other outlets (labels, buttons)...
  The goal would be to get NewViewController's scrollView to call NewViewController's touchesBegan and touchesEnded methods.</p>
  
  <p><strong>Update:</strong> The ScrollViewSuite helped me a lot to understand how the touches callbacks are handled. <code>UIScrollView</code> only calls them when the touches don't make it scroll.</p>
  
  <p>So, three cases:</p>
  
  <ul>
  <li>Oblique slide (even slightly, as soon as scrollbar appears): no <code>touches</code> method is called</li>
  <li>Perfectly horizontal slide (no scrollbar appears): <code>touchesBegan</code>, <code>touchesMoved</code> and <code>touchesEnded</code> are called</li>
  <li>Any touch that doesn't cause a scroll (touch without moving, or horizontal move) followed by a slightly vertical slide: <code>touchesBegan</code>, <code>touchesMoved</code> and <code>touchesCancelled</code> are called;</li>
  </ul>
  
  <p>Touches cancel can be avoided by setting the <code>UIScrollView</code>'s <code>canCancelContentTouches</code> to <code>FALSE</code> but this obviously only works if <code>touchesBegan</code> has been called, which means touches methods will still not be called for the first case.</p>
  
  <p>But <code>UIScrollView</code> has a property called delaysContentTouches which is set at <code>TRUE</code> by default, and causes it to wait a little bit when a touch begins in order to see if it will make him scroll. If this is set to <code>FALSE</code>, touches methods are called as soon as the touch starts and allows a subclasses to handle them as they wish.</p>
  
  <p><strong>TL;DR:</strong> What seems to be the easiest way to me (if you can't use <code>UIGestureRecognizer</code>) is to subclass <code>UIScrollView</code>, set its <code>delayContentTouches</code> property to <code>FALSE</code> and override touches functions (<code>touchesShouldBegin</code> / <code>touchesShouldCancel</code> as well as <code>touchesBegan</code> / <code>touchesMoved</code>...) according to your needs.</p>