The Base SDK is the version of SDK that will be used when compiling your application – the compiler will use the headers and libraries of this specific SDK. For example, in the image below notice that there are only two choices for the Base SDK for both the device and simulator, versions 3.2 and 4.0.
However, we have an issue here, if you build an application with the latest SDK and deploy on a device with an earlier OS, chances are your application will crash if you reference any code in a 4.x API while running the application on a 3.x device. Also, the 3.2 SDK is for the iPad only, so this isn’t an option when deploying to an iPhone or iPod touch.
To specify which OS version is the minimum that your application will support, you set the deployment target. Your application will then run on this minimum OS as well as all later versions.
This is all well and good, however, the obvious question is how to deploy on an earlier OS version yet take advantage of features for those devices that are running a later OS?
When targeting an earlier OS as mentioned above, yet you want to take advantage of features of a later OS for devices that support it, you can use the method respondsToSelector to check if the receiver implements or inherits a method that can respond to a specified message. This approach follows Apple’s recommendation to check for availability of features versus a specific OS version.
In the example below the code will check if the object returned by [UIDevice currentDevice] will respond to the selector shown, if so, you can write relevant multi-tasking code:
if ([[UIDevice currentDevice] respondsToSelector:@selector(isMultitaskingSupported)]) { // Multi-tasking code for supported devices } else { // Devices without multi-tasking support }
Another time when that you may choose to use respondsToSelector is for cases when the implementation of the same API has changed with a later OS version. I ran into this particular case when writing code for displaying movies using the MPMoviePlayerController. In the 4.x SDK the notifications have changed slightly – in 2.0 to 3.1 MPMoviePlayerContentPreloadDidFinishNotification was the notification you would use to receive notice that a movie was ready to play. With 3.2 (iPad) and later, MPMoviePlayerContentPreloadDidFinishNotification has been deprecated and MPMoviePlayerLoadStateDidChangeNotification has taken its place.
The code example below shows how you may go about using respondsToSelector to figure out which notification you should request based on the whether or not the movie player can return information about its load state:
MPMoviePlayerController *mp = [[MPMoviePlayerController alloc] initWithContentURL:movieURL]; // This method is available on 3.2 and greater... if ([mp respondsToSelector:@selector(loadState)]) { // Register to receive notification when load state changed // (check for playable, stalled...) [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(moviePlayerLoadStateChanged:) name:MPMoviePlayerLoadStateDidChangeNotification object:nil]; } else { // Register to receive a notification when the movie is ready to play. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(moviePreloadDidFinish:) name:MPMoviePlayerContentPreloadDidFinishNotification object:nil]; }
Beyond working with objects, if you need to check for the availability of a specific function, you do so by comparing the function to NULL. In the example below I check for a function related to creating a PDF-based graphics context (available in 3.2 and later).
if (UIGraphicsBeginPDFContextToFile != NULL) { // The function is available }
Unfortunately, with the upgrade to the latest Xcode (3.2.3) there are no simulators for 3.1.x and earlier OS versions. Although it has always been recommended to test your apps on device, at this point it becomes a necessity.
http://iphonedevelopertips.com/xcode/base-sdk-and-iphone-os-deployment-target-developing-apps-with-the-4-x-sdk-deploying-to-3-x-devices.html