Apple Watch - Only Getting Data If App on Phone Is Active

Apple Watch - only getting data if app on phone is active

If your openParentApplication:reply: method only works when the host iOS app is active, I can pretty much guarantee that your iOS app is being killed in the background before it has a chance to reply.

The solution is to have the app respond to the request as quickly as possible, then complete your normal task. There's a note about this in the developer forums: https://devforums.apple.com/thread/264473?tstart=0

I've also written a blog post detailing the methods I used before the note was added in the forums: http://www.fiveminutewatchkit.com/blog/2015/3/11/one-weird-trick-to-fix-openparentapplicationreply

Apple Watch app getting data when iOS app starts

There is a user information and watch application should request these information when it starts.

When the user glances at their watch, why should they have to wait while data is requested, received, then updated in the app?

Instead of designing the watch app to retrieve the information when the user starts the app, you should consider other approaches to keep your watch app up to date.

  • For watchOS 2, there are other ways to transfer current details in the background, such as updateApplicationContext, which Ahmed mentioned.

  • For watchOS 3, you can also use refresh tasks to update your watch app in the background.

Either of these approaches ensure that the information is already on hand, so the user doesn't have endure waiting for the watch app to update itself.

Why can my Apple Watch OS app receive message from my iOS app only when it is active?

You should not call sendMessage straight after activate - The session may not (and probably won't) be active.

You need to wait until you get the activationDidCompleteWith delegate callback and then you can attempt communication.

Before attempting to send data you should check that the session state is .active and reactivate the session if it is no longer active.

How can watchOS 2.2 app determine if its paired iPhone has switched to another Apple Watch?

A specific answer to your question:

The fact that the watch is no longer connected is not readily apparent, as all transfer methods can be used, including immediate messaging. Transfers are simply deferred until the user switches back to that watch.

Since an unconnected watch can still initiate transfers to its paired iPhone, you would likely have to implement some sort of handshake or timeout detection, and see if the phone fails to respond in time.

My findings:

It seems that the unconnected watch is not meant to know that the user has switched to a different watch. As you pointed out, the watch app's session is still active, and the watch (simulator) still reports that phone is reachable.

An unconnected watch app can continue to use all transfer methods including interactive messaging (although outgoing data does get queued by the system, and is not transferred until the user switches back to that watch).

I've verified that data is queued, using two different approaches:

  • by using transferUserInfo dictionary from a watch, letting the run loop execute, repeating that process a few times, then examining the outstandingUserInfoTransfers array.
  • by using a sendMessage reply handler which only runs after the user switches back to that watch, and a response is received.

Once switching back, all queued transfers are immediately sent to its phone, and any interactive responses are then received by the watch.

While an unconnected watch is able to queue data to its paired iPhone (since its session is still active), the phone can only communicate with its connected watch, since the phone no longer has an active session to any unconnected watch.

New sample code:

You can try out the new QuickSwitch sample code. It uses updateApplicationContext to pass a designator and color from any of the watches to the phone.

You can change the designator and color for an unused watch, use the Xcode Devices pane to switch to that watch, then notice that the iOS app immediately shows that watch's new designator and color (which was queued while the watch was unused).

Possible reachable documentation inconsistency:

In your WatchKit extension, the value of this property is YES when a matching session is active on the user’s iPhone and the device is within range so that communication may occur.

Since I don't have a second watch, I couldn't test whether an unused watch's reachability ever changes to false, once its phone moves out of range.

Can I get information if this iPhone connected with Apple watch or not through WatchConnectivity?

You can get this information from the WCSession object:

session.isPaired // true when the iPhone is paired to an Apple Watch
session.isWatchAppInstalled // true when the Watch app associated with the current iOS app is installed on the user’s Apple Watch

Be aware that this only works when you activated a WCSession on your phone and your Watch app

Apple watch app does not work when iPhone app is in terminated state?

You'll need to handle the request in the iPhone app a bit differently in order for your app to not be killed off by the OS. I've shared a similar answer here: https://stackoverflow.com/a/29848521/3704092

Apple watch keep app active by few seconds

Checkout the 2015 WWDC video "WatchKit Tips and Tricks". They go over how to use GCD's dispatch_semaphore to ask the system for extra time when the app may go into the background. Their example is with an async network request, but the same principle applies to any processing or request you are making.

Note that the amount of time you get is small - you can only get about 30 seconds of background processing time before you are suspended.



Related Topics



Leave a reply



Submit