I have a settings bundles that I use with my watch app. I am migrating my app to watchOS 2. Does anyone know how setting bundles are supposed to work? Does the iPhone transfer the values to a the standard user defaults or to a user defaults with a suite name for a shared app group? I can't get either to work and I can't find any documentation on how setting bundles are supposed to work with watchOS 2.
The accepted answer is wrong. You can use Shared App Groups for the Settings bundle on WatchOS 2 and access the values via NSUserDefaults. No Watch Connectivity required. It is just tricky to set up and the official documentation is missing crucial info.
Recently discovered how to do it in my question here.
The 2 important points are:
You need to enable Shared App Groups on all 3 targets (iOS app, Watchkit app, WatchKit extension)
It only works on the real device, not simulator. You might need to remove the app from both devices and reinstall to have it start working.
In Watch OS 2.0 since the Watch App extension is in the Apple Watch (not in the iOS App as in Watch 1.0) you can't transfer data through user defaults, so you should use instead WatchConnectivity.
If you have a settings bundle or a framework and you want to use it in the AW App extension and in the iOS APP, you should import it in every target of your project.
Related
I've set up Siri on my iOS app- I am able to call intents using INAddTasksIntent and it works great.
When I say "Hey Siri, add task clean my room to JoshApp" it works great.
However, Siri does not work on my Apple watch, using the same commands. When I say "Hey Siri, add task clean my room to JoshApp", it will say it cannot find the app or to look on the app store.
Do I need to create a separate Apple watch app and handle the Siri intents there? Based on my research (which incidentally, there is very little documentation around it), it doesn't seem like it is possible unless you set up a watchOS app.
Intents are delivered to individual devices as part of app bundles:
Overview
Interactions with SiriKit occur through your Intents app extension, which you deliver inside your iOS or watchOS app bundle.
[...]
Enable the Siri Capability
Enabling the Siri capability adds a set of entitlements to your app. The App Store requires the presence of these entitlements for any iOS app or watchOS app containing an Intents extension.
[...]
Source: Creating an Intents App Extension
Without the associated app bundle being installed on the watchOS device, it's (loosely, I'll admit) implied that you won't be able to add an Intents extension to meet your requirements.
Apple documentation says "Also, iOS automatically forwards a read-only copy of your iOS app’s preferences to Apple Watch. Your WatchKit extension can read those preferences using an NSUserDefaults object...". https://developer.apple.com/library/prerelease/watchos/documentation/General/Conceptual/WatchKitProgrammingGuide/SharingData.html#//apple_ref/doc/uid/TP40014969-CH29-SW1
But I can't read defaults in my WatchKit app that were saved in my iPhone app, am I doing something wrong?
In the WatchKit app, can I even save to (a WatchKit only) defaults, or does that not even work?
iPhone Data:
let defaults = NSUserDefaults.standardUserDefaults()
defaults.setObject(dataArray, forKey: "DataSaved"
Watch ExtensionDelegate:
let defaults = NSUserDefaults.standardUserDefaults()
print(defaults.arrayForKey("DataSaved"))
print(defaults.objectForKey("DataSaved"))
arrayForKey and objectForKey for print nil.
I must be doing something wrong, do you know what it would be?
Difference between NSUserDefaults
NSUserDefaults is a unit of memory on any device, so it is completely different in iOS and watchOS, as well in tvOS, etc.
For example, if you run a code that adds a new key called "key1" to NSUserDefaults on iOS (assuming you are using NSUserDefaults.standardUserDefaults()) , when you request to read its data on watchOS, it gives you an empty dictionary.
That's because it the first time, you store the dictionary only in iOS App Target and not in a shared space between two devices. When the WatchKit extension wants to use NSUserDefaults, it reads the (empty) dictionary saved in WatchKit Target and not the (filled) dictionary in iOS Target.
Sharing Data
There are some ways of sharing dictionaries between watchOS and iOS:
1- Using WatchConnectivity framework in watchOS 2, you could pass data between two targets. You can use sendMessage or similar functions in WCSession classes to do so. Just don't forget to add WCSessionDelegate to your InterfaceController (in watchOS) or ViewController (in iOS) classes and app delegates for the app to be able to receive data from WatchConnectivity.
2- Using online/cloud storages, you could upload the dictionary from iOS App there, and then download it to watchOS App. However, this needs an Internet connection, and is not suitable in many cases, for example if your app does not need to connect to the Internet to do other tasks, and you force the user to connect to the Internet just in order to sync a simple dictionary between the two targets.
3- Using App Groups (if you are using watchOS 1), which I don't describe it more, because it is outdated and you probably don't want to make your app just for watchOS 1.
Conclusion
1- NSUserDefaults returns two different dictionaries in watchOS and iOS, respectively.
2- To share data between watchOS and iOS, you could use WatchConnectivity, the Internet (not recommended) and App Groups (in watchOS 1).
More Resources
For more details about WatchConnectivity, the modern answer to your question, you should check out Apple Documentation in Apple Developer Portal.
Also you should see this WWDC session talking about this great framework included in watchOS 2.
Sorry. You can't read any defaults in WatchKit app, because from watchOS2 it has it's own memory to be used. so You can not access value from iOS's NSUserDefaults in watchOS
You have to use WatchConnectivity to share data for watch OS2.
To be clear, NSUserDefaults.standardUserDefaults() will give you two different dictionaries when calling on the watch and on the phone.
For WatchConnectivity check out https://developer.apple.com/videos/play/wwdc2015/713/
Apple docs:
https://developer.apple.com/library/watchos/documentation/WatchConnectivity/Reference/WatchConnectivity_framework/index.html
Ns defaults.standard is particular to that target by using it you can access data within that target, in your case you need to access data in another target so listen you need to do two things one is
1. use app groups
2. don't use user defaults.standard use UserDefaults(suiteName:"group.yourgroup")
to store and access the data
refer this Link might be useful.
Has anyone combined these two new features in iOS8 yet? I'm attempting to access HealthKit from a widget. But since the application and extension use two separate App IDs - the widget automatically rejects access to HealthKit. The Notification Center/Today view doesn't display any prompt to allow access. I notice it attempts to because I see an "unbalanced view controller transition" warning in the console, but nothing is displayed.
For a manual fix - the Health app will display the bundle ID with permissions that can be manually changed. However, there's no app icon and the extension is listed as its bundle ID and not listed as its product name. This makes me think this is still something they are working on in the beta.
You could try to access the HealthKit data from your containing app and then share those data with your extension through App Group.
I haven't looked at HealthKit yet, but in another case the App Group feature worked fine for me.
I haven't tried doing this type of combination between those features in my app yet, but while integrating the HealthKit capabilities, I happened to see the following in HealthKit documentations:
Both HealthKit and the Health app are unavailable on iPad. The HealthKit framework cannot be used in an app extension
So I assume a direct way is not available... You can read more here: HealthKit_Framework Documentation
You won't be able to access HealthKit. To quote Apple's App Extension Programming Guide:
Some APIs Are Unavailable to App Extensions
Because of its focused role in the system, an app extension is ineligible to participate in certain activities. An app extension cannot: …
Use any API marked in header files with the NS_EXTENSION_UNAVAILABLE macro, or similar unavailability macro, or any API in an unavailable framework
For example, in iOS 8.0, the HealthKit framework and EventKit UI framework are unavailable to app extensions.
[emphasis added.]
I need to restrict my IOS app in only IPAD 1. Other IPADs are ok. It supports IPHONE 4 and above too.
Is there a way?
As you can see here:
App-Related Resources
under the Declaring the Required Device Capabilities section, you can declare UIRequiredDeviceCapabilities in your Info.plist file. It means that you declare hardware that your app requires in order to run. The App Store uses the contents of this key to prevent users from downloading your app onto a device that cannot possibly run it.
In your case, I think you can require the front-facing-camera to exclude the iPad 1gen.
Another way is to set the development target to iOS 6.0 which is not supported on the iPad 1.
I am ready to submit my iOS application to Apple Store. But I want to add specific requirements such as "app requires iOS 4 or greater ,iphone 4 , ipod touch 4g,ipad ,camera & multitasking support". I don't know where should I set these requirements.
I set the base sdk & deployement target to 4.0.
Any help is appreciated. Thanks.
You need to add UIRequiredDeviceCapabilities key to info.plist file and set still-camera value.
Here is a table of all possible iDevice requirements.
As for target iOS version and backgrounding it's right to set deployment target at least 4.0.
If you require iOS 4, you already have multitasking support. There's no way (that I know of) for any user to disable that.
Camera is trickier though. Make it very clear in your app description that your app requires a camera. And that caveat ("you must have a camera") should keep non-camera device using people from downloading.
I got it. Brigadir is right. When you setUIRequiredDeviceCapabilities key to info.plist file & set the required values then it will automatically list the devices required. See Appendix C: Device Compatibility Matrix in itunes_connect_developer_guide.pdf.