Reputation: 1414
I'm working on a Windows Phone 8.1 shopping application. I have a continously running thread in the app which downloads the users basket and saves it in a local cache to imporve performance. So far what I have is something like this:
while(UserLoggedIn)
{
await Networking.getBasket();
await Task.Delay(5000);
}
This thread is started when app resumes. My question is: What is the best approach to controll such a thread? On the app resuming it seems really slow, and sometimes it blocks the UI thread, although it's fully async. How can I improve performance?
EDIT
According to Romasz's suggestion, I used a Timer like this:
Declaring it:
Timer _getBasketTimer;
Initializing it in the App's constructor:
_getBasketTimer = new Timer(getBasketCallback, null, 5000, Timeout.Infinite);
Defining its callback:
private async void getBasketCallback(Object state)
{
if (JSONCache.getSessionID() != "" && Networking.LoginInProgress == false)
await Networking.getBasket();
//The Change method may be called when the Timer object is already Disposed (I debugged it, and the exception did occur sometimes)
try
{
_getBasketTimer.Change(5000, Timeout.Infinite);
}
catch(ObjectDisposedException)
{
}
}
Disposing it in the App's Suspending event, so the Thread won't run when the App is suspended:
_getBasketTimer.Dispose();
And start it when the app is resuming:
_getBasketTimer = new Timer(getBasketCallback, null, 5000, Timeout.Infinite);
Upvotes: 4
Views: 559
Reputation: 29792
If you want to run a something on a thread in intervals (also on thread other than UI one), you may use System.Threading.Timer. A sample can look like this:
System.Threading.Timer myTimer = new System.Threading.Timer(async (state) => { if (UserLoggedIn) await Task.Delay(1000); }, null, 0, 5 * 1000);
Note that if you would like to access UI elements from timer's Callback, then you will have to use Dispatcher.
Also don't forget to stop timers/cancel tasks once your app gets suspended, and resume them on resuming event, if still needed.
Upvotes: 1
Reputation: 2891
Its hard to tell without seeing more code, but you probably need to wrap your loop in a new thread to get it off the UI thread:
Task.Run(async () =>
{
while(UserLoggedIn)
{
await Networking.getBasket();
await Task.Delay(5000);
}
});
Upvotes: 2