I need to share bundled resources between the app and extension. At first, I was thinking I could copy them into the shared group area on first launch, but what if the user calls up the extension and never launches the app?
As mxcl notes, you can include the assets in both targets but that will expand the size of your final submitted binary.
I've confirmed putting assets in a framework works in Xcode 6.1 (it may have worked before, but I'm just trying it now):
You can have standalone images in your framework or an asset catalog. Both will work.
In the framework, just set up a class with accessor methods that return UIImage
objects. Something like this (Objective-C):
@implementation AssetService
+ (UIImage *)frameworkImageNamed:(NSString *)name {
return [UIImage imageNamed:name
inBundle:[NSBundle bundleForClass:[self class]]
compatibleWithTraitCollection:nil];
}
@end
Or in Swift:
public class AssetService {
public init() {
}
// class method version
public class func frameworkImageNamed(name: String) -> UIImage? {
return UIImage(named: name,
inBundle: NSBundle(forClass: AssetService.self),
compatibleWithTraitCollection: nil)!
}
}
Note that since the above code is inside the framework but will run in "app space" you need to specify the bundle.
Then, your app or extension can just link in the framework, and call [AssetService frameworkImageNamed:@"myimage"]
or AssetService.frameworkImageNamed("myimage")
.
Caveat: despite returning an optional UIImage?
the code gets very angry if it can't find the image named and will crash. But if it's your own framework, you should know what's in there and catch this kind of bug.