Pages

Wednesday, October 20, 2010

Software design and Design Patterns

        As part of my day job, I have been participating in interviews for prospective job candidates. In performing these interviews, I have realized that there is a general lack of knowledge of object oriented programming principals in the candidates that we have interviewed.
        I am particularly surprised that most of the candidates have little or no knowledge of design patterns. So, I’ve decided to do a series of posts on this important topic. How many (or few) posts that I do on the topic are dependent on your feedback. If you feel like the topic is interesting and my posts are useful, let me know. If not, also let me know so that I can abort and spend my time writing about topics that are more interesting and/or relevant to you.
        First things first, if you haven’t already read it, log on to Amazon right now and pick up a copy of Design Patterns: Elements of Reusable Object-Oriented Software by Gamma, Helm, Johnson and Vlissides. This is the undisputed bible of design patterns. The book is so well known that it is referred to as the GoF (Gang of Four) book. These guys coined the term “Design Pattern.” The book is well written and includes very readable plain language descriptions of the patterns, use cases for the patterns, UML diagrams that illustrate the design of the patterns and sample code that shows how to implement the patterns.
        You may be wondering why design patterns matter. Well, there are at least a couple of reasons why you should learn about design patterns, not the least of which is that you will probably be asked about them in your next interview if you claim to know about OO software design.
        First, design patterns provide a common vocabulary that you can use to communicate your designs to other developers. For example, when building applications that perform database access, I like to use a data access facade so that it is easy to change the underlying database without messing with other code. If you know what the Facade pattern is, you will immediately understand that I am talking about building an abstraction layer that provides a consistent interface to an underlying sub-component of a system, in this case the database. Don’t worry, I plan on covering the Facade pattern as the first in this series.
        Second, design patterns provide proven solutions for common software design problems. Have you ever built an application that used only one instance of a particular class, for example a settings object that maintains all of the user defined settings for your application? Did you implement this class yourself from scratch? How did you ensure that there was only a single instance of this class at any time in your program? This is the very definition of the Singleton design pattern. This pattern ensures that there is only a single instance of the class at any time and provides a global entry point for access to that class. The point here is that you do not need to come up with new designs if you recognize that a pattern exists that meets your needs. After all, isn’t one of the goals of OO programming reusability? Why not reuse the same proven designs that have been successfully implemented in thousands of other applications?
        If you are currently building iOS applications, whether you know it or not, you are already using design patterns. MVC, Model-View-Controller is a crucial pattern in iOS application architecture, one with which I am (almost) certain that you are already familiar. Delegation is another pattern that, while not documented in the GoF book, is well understood and prevalent in the iOS framework. My point is that you have nothing to fear. Patterns are your friend. Embrace patterns and your applications will be more robust, scalable and modular making it easier for you to enhance them in the future.
        Next time, I’ll delve into the Facade pattern. Don’t forget to let me know in the comments if you think that this is a topic that I should continue to explore.

Friday, September 10, 2010

Detecting tap and double-tap with Gesture Recognizers

Now that I am finished with my book I am getting back to work on writing apps. In the original design for the current app that I am working on, I wanted a UIView that responded to taps and double taps. If you don’t already, know, as of iOS 3.2 there is a new way to handle user interaction events called gesture recognizers.

Gesture recognizers are basically exactly what they sound like; classes that you can use to recognize when a user has performed a gesture. Using gesture recognizers simplifies event handling because you do not have to write all of the code to track touches like you would have done in the past. You can simply create an instance of a gesture recognizer, configure it, and add it to a view. Then, when the gesture recognizer recognizes a gesture, it simply calls back a selector that you define.

UIGestureRecognizer is an abstract base class that you can use as a starting point to implement your own gesture recognizer. In addition to providing this base class, the iOS SDK provides several concrete UIGestureRecognizer subclass implementations that you can use to recognize the following gestures as documented in the iOS documentation:

Tapping (any number of taps)

UITapGestureRecognizer

Pinching in and out (for zooming a view)        

UIPinchGestureRecognizer

Panning or dragging

UIPanGestureRecognizer

Swiping (in any direction)        

UISwipeGestureRecognizer

Rotating (fingers moving in opposite directions)

UIRotationGestureRecognizer

Long press (also known as “touch and hold”)                

UILongPressGestureRecognizer

In my case, I wanted to create two different actions, one for when a user tapped a view and another for when the user double-tapped. This may seem straight forward as you can configure the UITapGestureRecognizer to call a selector when it detects a specific number of taps by setting the numberOfTapsRequired property. So, my idea was to use a UITapGestureRecognizer with numberOfTapsRequired set to 1 to call a selector called handleSingleTap and a second UITapGestureRecognizer with numberOfTapsRequired set to 2 to call a selector called handleDoubleTap.

This was all well and good. When I built and ran my application, single tap event handling worked like a charm. Every time I tapped on the view, I saw the behavior that I expected. The problem occurred when I tried to double tap. The double tap selector was called as expected, however, the single tap selector was always called first. I guess that, in hindsight, I should have expected this as it is impossible to tap twice without tapping once. One particularly important thing that you should keep in mind when using gesture recognizers is that they are not a part of the responder chain. If you are relying on handling events using the responder chain and you introduce gesture recognizers, events that are recognized by the gesture recognizer will not be sent through the responder chain.

What I needed was a way to set up a relationship between the two gesture recognizers. I needed to be able to detect if a double tap was happening and if it was, to ignore the single tap gesture. Fortunately, Apple thought ahead and designed a way to do this into the architecture. This is a case where you only want the single tap selector called if the double tap gesture recognizer fails. To implement this, you send the message requireGestureRecognizerToFail: to the single tap gesture recognizer with the double tap recognizer as its argument. This tells the single tap gesture recognizer to wait to fire until the double tap gesture recognizer transitions to the UIGestureRecognizerStateFailed state. Doing this solved the problem. At this point, the correct selector was called when a double tap was recognized and the single tap selector was not called.

However, this caused another issue. The issue was that when a user would single tap, the action that would result from a single tap was delayed as the single tap gesture recognizer was forced to wait to ensure that the double tap gesture recognizer failed before calling the single tap selector. This behavior is documented in the Event Handling Guide for iPhone OS. For many applications, this may be acceptable, however the lag between a single tap and the gesture recognizer calling its selector was too long for my application. I searched for a way to adjust the timeout for a gesture recognizer to transition to UIGestureRecognizerStateFailed to no avail. It seemed that the only way to get the behavior that I wanted was to write some custom gesture recognizers.

In the end, I decided to not use the double click gesture recognizer and to handle my user interactions differently by not requiring a double tap at all. So, keep in mind that it is possible to set up dependencies between gesture recognizers however when implementing discrete behaviors for single and double tap, you may want to go a different route. Gesture recognizers are a convenient way to react to user input and can be configured in a variety of way depending on the needs of your application. If worst comes to worst, you can always write your own concrete subclass of UIGestureRecognizer.