How do you optionally use iPhone OS 3.0 features in a 2.0 compatible app?
Asked Answered
F

5

42

I'd like to use some features of iPhone OS 3.0 in my 2.0 app when it runs on a 3.0 device. I don't want to go 3.0 all the way because there are customers who do not want to update yet.

I experimented a bit with weak linking of the MapKit.framework (-weak_framework MapKit). I found it quite cumbersome, since I had to trick the compiler/linker to use the 2.0 SDK with all code except the one which uses MapKit.

Has anybody more experience with this? What are you doing to make it compile/link. Has anybody already submitted an app to Apple, which weak-links frameworks from other OS versions?

Fluttery answered 12/6, 2009 at 13:16 Comment(0)
B
36

Apple has an example of how to do this, specifically making a 2.x-compatible app that uses MFMailComposeViewController....

http://developer.apple.com/iphone/library/samplecode/MailComposer/index.html

the answer involves compiling with the 3.0 SDK, setting the deployment target to 2.x, ensuring that the 3.0 frameworks are marked as "weak" references, and then doing the right thing to make your code work if you're on a device where the new frameworks aren't present.

Beast answered 22/6, 2009 at 5:32 Comment(4)
Great! This is the answer I was looking for!Fluttery
It should be noted that there are reports that Apple has rejected apps that have weak linked StoreKit in an effort to use in-app purchasing if running on 3.x (otherwise not if under 2.x). So, YMMV.Trifurcate
do you have a link? I can see Apple being extra touchy about in-app purchasing. In any case, I have a couple of apps in the store that weak-link the MessageUI framework.Beast
Always use the latest stable SDK available, set the deployment target to the lowest version you want to support. Then write conditional runtime code: Check for the presence of a class if(NSClassFromString(@"NSSomeNewClass")) {...} Check for the presence of a method if ([NSSomeClass instancesRespondToSelector(someSelector:)]) {...}Hesitate
H
5

You can always link to frameworks that are not part of the current SDK using the dlopen function. Of course, this is not recommended for frameworks that are not public (not recommended == forbidden on the app store, in this case). However, as new frameworks in unreleased versions of the OS become public, it's an option. Just check your version number, and open frameworks as available. Useful for individual features, not so much if you're making heavy use of new stuff.

Helainehelali answered 12/6, 2009 at 13:58 Comment(6)
The dlopen solution has the same weakness as the -weak_framework approach: You have to compile code that uses the 3.0 framework's symbols with the 3.0 SDK.Fluttery
no, you can build against the 2.x SDK, and just NSClassFromString to get class names.Helainehelali
I consider not being able to use the original headers a weakness. One workaround I could image would be to build the 3.0 related parts in a static library and link this to the 2.0 app. I have not tested this yet.Fluttery
That might be a workable solution. I've used this technique (dlopen) to extract a single piece of functionality from 3.0 frameworks, while still having a 2.0-compatible app. If you're minimally accessing the 3.0 classes, you shouldn't have too many issues.Helainehelali
Sounds good. Did you submit this to the App Store? What library did you dlopen()?Fluttery
I think we actually ended up removing the feature, but I see no issues about submitting it. This was to access a feature of MapKit.Helainehelali
M
1

This probably isn't the answer you're looking for, but the method I use is to just have two separate apps. Rather than updating my existing apps with 3.0 upgrades, I just release this as a new app. Old users can use the 2.0 app for as long as they want, and people that want the 3.0 features can upgrade.

Massie answered 12/6, 2009 at 13:43 Comment(2)
That's what I would have used if my app was free. But since there are customers who did pay before, I cannot ask them to buy the app again to get the 3.0 features.Fluttery
Sure you can. Unless you're charging a huge amount of money for your app, priced upgrades are very common. You put more work into the program and should get paid for it. Apple is charging another $29 for the upgrade to their os...Massie
G
0

Great howto on Weak Linking (both Libraries and Frameworks) here:

http://developer.apple.com/mac/library/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html#//apple_ref/doc/uid/20002378-107262

Although it's a little out of date... with the latest x-code the process for weak linking an entire framework is actually easier:

  1. Right click the target and select Get Info
  2. Go to the "General" tab
  3. In the linked libraries section towards the bottom change the Type from required to weak for all libraries that you would like to weak link.
  4. Profit
Geology answered 25/8, 2010 at 22:35 Comment(0)
D
-1

I don't think you can. 3.0 and 2.x use completely different SDKs, and and link to a completely different set of files and libraries. I'm not certain, but I don't think you can link to the 3.0 SDK and still be 2.X compatible.

(please add a comment if I'm wrong).

Dropkick answered 12/6, 2009 at 13:49 Comment(1)
Well, it appears that it's working, at least with my devices. I tried it on one iPhone 2.2.1 and another with the 3.0 GM. The frameworks have exactly the same names (the framework versioning stuff seems to be dropped on iPhone OS: no 'versions/A' in the path). It seems that Apple tries to keep frameworks compatible from OS to OS, now that they have non-fragile instance variables.Fluttery

© 2022 - 2024 — McMap. All rights reserved.