We're writing a cross-platform C# "Xamarin" application; right now we're just targeting the iPad. The application has two features relevant to this question:
The app requires that the user authenticate to the app (in addition to logging onto the iPad)
The app connects to a remote device over Bluetooth
So the question becomes, what happens when the user switches to another app, which results in our app's OnSleep() being called. In OnSleep() we could immediately disconnect Bluetooth and log out the user, but that seems like poor usability, especially if they are just quickly checking some alarm that triggered or an instant message that came in.
For the sake of usability, we're thinking to have a 1-minute timeout; if the user does in fact pop out and quickly pop back into the app, we'd like things to simply continue on without any loss of communication or re-authentication.
If, in OnSleep(), I set up a timer using Xamarin.Forms.Device.StartTimer(), that timer does not fire while the app is "asleep".
What does it take to have a small background task/thread/process execute, even while the app is asleep? Something that simply waits 1 minute, and then shuts down the Bluetooth communication and sets a flag indicating re-authentication is needed?
Related
I have Win32 desktop bridge application that uses background task to receive push notifications from WNS. I use UWP background task APIs over C++-WinRT
I'd like to be able to receive push notifications even when OS is in sleep so that it wakes up and the app handles push notification. By default OS does not wake up. It did only after manually changing settings value in System->Battery->See which apps are affecting your battery life->Click my app ->Uncheck Let Windows decide option (by default it is always checked) and check Allow the app to run background taks. Now I'd like to do this is manual work on code for better user experience.
RequestAccessKindAsync API allows to let user to change above setting value by showing popup notification to the user and I could do it without any problem in UWP C# sample app. But same code does not show pop notification from my desktop bridge over C++-WinRT. It simply returns false value for below code
auto result = co_await BackgroundExecutionManager::RequestAccessKindAsync(BackgroundAccessRequestKind::AlwaysAllowed,
L"App needs to use background to catch push notifications while device is in sleep");
Can anyone confirm that RequestAccessKindAsync API works from desktop bridge? If not then how I can make sure OS and the app will always be able to wake up from sleep when it receives push notification?
UPD: Raised request to enable this API from desktop brige here
This is a missing feature. When we designed this API a couple of releases ago we didn't consider desktop bridge apps would be calling it - but clearly there is a use case for supporting this. I have notified the team about this gap, but I'd also encourage you to log a feature request here: https://wpdev.uservoice.com/
Two possible workarounds:
(1) you could add a dummy/empty UWP foreground app to your desktop bridge app. You can then launch this on startup and request the background access from there. This will be a bit ugly, but you could make it look like a splash screen :-)
(2) you can instruct the user to go into the Settings app to set your app to always allowed. You can help them do that with a deep link to the battery save settings, but they will still need to manually flip the switch.
My Windows Phone 8 application checks network connectivity in OnNavigatedTo method. If the application finds out there's no network available, what should my program do?
If it was a desktop application, I would pop up a message box, saying "network is required", and exit the program.
I hear in WP exiting is not recommended; we don't often call Application.Current.Terminate().
Is there a way to suspend the application, return to the "desktop" and when users turned on Wifi, he can run my program and raises OnNavigatedTo again?
I know turning on Wifi automatically by the program or navigating to Setting page would be a good design. But I'm currently curious about suspending/minimizing the application.
No. There is no good way to programmatically suspend the app. You could hack it by launching another app, but that wouldn't be a very good user experience.
In your case I'd display a message that the app cannot continue without network access and wait for the network. The app isn't completely dead since the network may connect either on its own or by user action.
Flaky network connections are annoying enough without being compounded by the app exiting and users needing to restart it if they temporarily move in and out of a dead spot.
See How to detect network changes for Windows Phone 8
I have a simple xaml form which, when LoadState is called, enables a Dispatch Timer. When the dispatch timer fires, it checks a service for new items. If a new item meets a certain criteria, it adds the message to a local variable (which ends up being bound to a listview), and we use the ToastNotification framework to create a new toast. However, one thing I've noticed is that the ToastNotifications appear only to work when the app is focused (which, of course, defeats the point). I think this makes sense, in part, because my app is suspended when not focused.
However, I know my DispatchTimer is executed when the app is suspended, because I see the web requests firing off to the service. It must mean that my call to send the notification is deferred somehow. I guess conceptually, how do I get the toast notifications to execute if my app is suspended? I have read up on BackgroundTasks, but those only respond to system events. What I really want is for my app to poll for messages regardless of its suspended state, update the UI when it can and update notifications whether the app is supended or not.
Unfortunately the only reliable way to achieve your scenario is with a BackgroundTask, that you can run every 30 minutes. DispatcherTimer requires the UI thread, which will only run if your app has focus. If you are seeing web requests go out it may be due to some other anomaly, but effectively when your app is suspended no further user code is guaranteed to run - including popping a toast.
It sounds like you might be looking for something more like push notifications. Would these work for you? You could use them to display toast notifications, update your live tile etc.
Notification Platform Development on Windows
Mobile Push Notifications to Any Client with Azure Notification Hubs
Get started with push notifications in Mobile Services
I have an issue about Windows Mobile thread scheduling: I have an application (C#) that detects incoming calls on the telephone. It is said that the operating system is "fully multitasking and multithreaded".
Still, I can detect an incoming call, but after the call is detected, the system application, showing that there is a call incoming, takes over the focus.My application doesn't get to execute itself until the system window (with the call) is deactivated. (something happens with the call).
Is there anything I can set so that my thread (application) executes even when the system window is focused?
All solutions you can come up with for this are based on one thing: a hack. Windows Mobile is not meant to be customized as you wish - Windows CE is. You cannot override the default Windows Mobile phonecall UI, but you can put your own app above it with the correct API calls. However, it will flicker and it will look like s...t.
Is it possible to subscribe to a Windows event that fires when Windows is going into or coming out of Sleep or Hibernate state?
I need my application to be made aware when the computer is going to sleep to do some cleanup and avoid timing issues when it comes out of sleep.
Microsoft.Win32.SystemEvents.PowerModeChanged event will give you this information. This event is available in all variants of the .NET framework released by Microsoft so far.
In .NET, use the PowerModeChanged event.
In Win32, use the WM_POWERBROADCAST message.
You can monitor Win32_PowerManagementEvent WMI event
In a Visual Studio 2005 C++ MFC application you will need to add an ON_MESSAGE() to your message map looking for the WM_POWERBROADCAST message as in this example:
BEGIN_MESSAGE_MAP(CFrameworkWndDoc, CWindowDocument)
//{{AFX_MSG_MAP(CFrameworkWndDoc)
ON_WM_CHAR()
ON_WM_TIMER()
//}}AFX_MSG_MAP
ON_MESSAGE(WM_POWERBROADCAST, OnPowerMsgRcvd)
END_MESSAGE_MAP()
Then you will need to add the message handler function along with the class definition change to declare the member function for the message handler so that you can check the wParam variable for the message type as in this skeleton:
// Handle the WM_POWERBROADCAST message to process a message concerning power management
// such as going to Sleep or Waking Up.
LRESULT CFrameworkWndDoc::OnPowerMsgRcvd(WPARAM wParam, LPARAM lParam)
{
switch (wParam) {
case PBT_APMPOWERSTATUSCHANGE:
TRACE0("PBT_APMPOWERSTATUSCHANGE received\n");
break;
case PBT_APMRESUMEAUTOMATIC:
TRACE0("PBT_APMRESUMEAUTOMATIC received\n");
break;
case PBT_APMRESUMESUSPEND:
TRACE0("PBT_APMRESUMESUSPEND received\n");
break;
case PBT_APMSUSPEND:
TRACE0("PBT_APMSUSPEND received\n");
break;
}
return 0;
}
What I have seen is that a test using the above in an application running on Windows 7 that is started in the debugger and then I manually make my PC running the application to Sleep I will see the following message:
PBT_APMSUSPEND received
Then when the PC is restarted and I sign-in what I will see in the debugger output window are two messages one after the other:
PBT_APMRESUMESUSPEND received
PBT_APMRESUMEAUTOMATIC received
Everything that I have found thus far indicates that you have no indication whether you are coming out of a Sleep state or a Hibernate state. I am still doing further research on what needs to be done when suspending or when resuming so far as file and device handles. I have seen indications that file handles to COM ports are no longer valid after resuming. I also am unsure about interfaces to other processes for instance database connections.
In addition to the standard Sleep and Hibernate power management states Microsoft has introduced the Connected Standby power state with Windows 8 and 8.1 which has some application design ramifications depending on the type of application.
Desktop applications typically require no extra work to integrate with
connected standby.
The Desktop Activity Moderator (DAM) is the Windows component that
pauses all desktop applications and throttles the runtime of
third-party system services during connected standby. The purpose of
the DAM is to maintain basic software compatibility with existing
applications and services, but mitigate their impact on battery life
during sleep.
Windows prevents desktop applications from running during any part of
connected standby after the DAM phase completes. Windows allows
third-party system services to execute in a throttled mode after
completing the DAM phase. In this mode, a third-party service can run
for no more than one second of wall-clock time every 30 seconds.
The Art of Graceful Application Suspension by Lynn Merrill from Intel has some information about handling the various Windows message types associated with Power Management under Windows however it is date 2005 so not all material may pertain to Windows after Windows XP. There is at least one no longer used message in the message sequence described in this document as beginning with Windows Vista the PBT_APMQUERYSUSPEND message which was used to request whether an application was able to suspend is no longer used by Windows. The SetThreadExecutionState() function is now used to indicate that a thread can not be interrupted with a change to Sleep or Hibernate state. See the answers in stackoverflow Can't catch sleep suspend messages (winxp) for details on Power Management state message changes.
System power state events since Windows XP
Microsoft has improved power management since Windows XP as the various versions of the Windows OS share more components and versions of Windows are now being deployed on smaller devices with battery requiring more careful power management. See Registering for Power Events. There is both a RegisterPowerSettingNotification() function and an UnregisterPowerSettingNotification() function.
An application or service uses the RegisterPowerSettingNotification
function to register for notifications. When the corresponding power
setting changes, the system sends notifications as follows:
An application receives a WM_POWERBROADCAST message with a wParam of PBT_POWERSETTINGCHANGE and an lParam that points to a
POWERBROADCAST_SETTING structure.
A service receives a call to the HandlerEx callback function it registered by calling the RegisterServiceCtrlHandlerEx function. The
lpEventData parameter sent to the HandlerEx callback function
points to a POWERBROADCAST_SETTING structure.
In the POWERBROADCAST_SETTING structure, the PowerSetting member
contains the GUID that identifies the notification and the Data member
contains the new value of the power setting.
See also Power Management Functions for the list of the power management functions in the Windows API since Windows Vista.
System power status and battery condition
You can use the Windows System Services API function GetSystemPowerStatus() to retrieve the current power status.
Retrieves the power status of the system. The status indicates whether
the system is running on AC or DC power, whether the battery is
currently charging, how much battery life remains, and if battery
saver is on or off.
However note that the information returned in the SYSTEM_POWER_STATUS struct is about battery status and AC/DC power source and not the actual device power state such as Sleep or Hibernate.
And if the Windows device is in a Sleep or Hibernate state, your application will not be running so this function can not be used to determine the current Windows power state. I include this note as it may be useful for someone who arrives at this post while researching this topic.
GetSystemPowerStatus function (winbase.h)
SYSTEM_POWER_STATUS structure (winbase.h)
Not sure how often you want to monitor this, but if you write a service in .NET you can override ServiceBase, set CanHandlePowerEvent to true, and then you'll be notified of power changes via the PowerBroadcastStatus enumeration.
You can subscribe to NetworkChange.NetworkAvailabilityChanged and NetworkChange.NetworkAddressChanged.
I generally start a two second timer so that I can resume network communications after being in sleep mode when it times out.