How to raise an event at any given time - c#

I'm trying to raise an event at a given time in my windows store app. Now I've done this in desktop apps countless times, and I've used System.Threading.Timer in the past and it has worked well, but that class is not available to windows store apps.
I have looked in the documentation and found a class called DispatchTimer and although it appears to be what I'm after, correct me if I'm wrong but the docs are lacking. But luckily it's pretty easy to use.
So I tried the DispatchTimer, but after using it, I'm not even sure this is what I should be using.
How can I watch for any given time and raise an event when that time is up (in a windows store app)? And do you know of any resources that do this in a metro app?

Use DispatcherTimer like this:
var timer = new DispatcherTimer { Interval = TimeSpan.FromSeconds(10) };
timer.Tick += OnTimerTick;
timer.Start();
private void OnTimerTick(object sender, object args)
{
// Do something with pickup here...
}
This will create a timer with intervals of 10 seconds.

The DispatcherTimer is the way to go. Notice that if you want your app to run in background you must declare that on the app manifest or use Background agents.

Related

How can I execute a code in C# (Windows Service) periodically in the most precise way?

I have a code with which I am reading in 35ms intervals the current and position values of a machine's CNC axis from a remote computer.
The data is read from the CNC/PLC control system of the machine
My C# code has to run on our company server with Windows Server 2019. I am sending the data to Kafka, our AI experts have to interpret the current and position curve shapes for an AI algorithm. So the data has to be read every 35 ms as precise as possible
Normally I have used first a system timer with a 35ms period. It seems to work but I am not sure if this is the best way. Is there a more precise method than using a system timer?
My code
public void Main()
{
InitializeTimer_1();
}
public void InitializeTimer_1()
{
System.Timers.Timer timer1 = new System.Timers.Timer();
timer1.Elapsed += new ElapsedEventHandler(OnTimedEvent1);
timer1.Interval = 35;
timer1.Enabled = true;
}
public void OnTimedEvent1(object sender, EventArgs e)
{
// my Data reading code
}
There are multiple ways to solve this problem.
It first depends on what kind of application you have.
If you have a console app then you can schedule it to run every 35ms using the windows task scheduler and it will work.
If it is a long-running process like windows service then you can use the same code you have
There is one very useful library hangfire, you can explore this as well.
Also, refer to this post as well, you may get more directions.
Edit: System.Timers.Timer is sufficient for most the purpose, you could also consider System.Threading.Timer for short intervals, it allows more precise timings but its will run on a separate thread so keep that in mind. There is one more option System.Diagnostics.Stopwatch which has more high precision than other approaches.
The actual precision of the timer also depends on hardware, OS and the workload on the machine.
Now you can evaluate all the approaches and chose the best one for you.
The timer accepts a direct callback method. If you want to execute something periodic, it can be done as follows:
var timer = new Timer(TimerCallback, state, startAfterTimeSpan, repeatTimeSpan);
Where you can e.g. write a method
private void TimerCallback(object state)
{
// do something
}

WPF DispatcherTimer Memory Issue

Edit: If useful, this project is on GitHub at https://github.com/lostchopstik/BetterBlync
I am building an application for the Blync status light using their provided API. This application polls the Lync/Skype for Biz client and converts the status to the appropriate light color. All aspects thus far work as expected, however when I leave this program running for an extended period of time, the memory usage grows until a System.OutOfMemory exception occurs.
I have narrowed the problem down to the DispatcherTimer holding the timer in memory and preventing it from being GCed. After reading some things online I found you could manually call for garbage collection, but this is bad practice. Regardless, here is what I have in my code right now:
private void initTimer()
{
timer = new DispatcherTimer();
timer.Interval = new TimeSpan( 0, 0, 0, 0, 200 );
timer.Tick += new EventHandler( Timer_Tick );
timer.Start();
}
private void Timer_Tick(object sender, EventArgs e)
{
// Check to see if any new lights are connected
blync.FindBlyncLights();
// Get current status from Lync client
lync.GetStatus();
// Change to new color
setStatusLight();
if ( count++ == 100 )
{
count = 0;
GC.Collect();
}
}
The timer ticks every 200ms. I commented out all methods inside the timer and just let it run empty, and it still burned memory.
I am wondering what the proper way to handle this timer is. I've used the DispatcherTimer in the past and not had this issue.
I would also be open to trying something besides the DispatcherTimer.
If it is also useful, I have been messing with MemProfiler and here as my current graph with manual GC:
http://imgur.com/Iut91mF
It's a little hard to tell without seeing the rest of the code or the class the timer belongs to. I don't see anywhere you call Stop() on the timer. Does it need to be stopped?
You could also keep a local reference to the timer in whatever class you're in and call Start() and Stop() as needed.
If the timer never needs to be stopped and runs indefinitely, I would certainly look at what you're allocating as the timer runs and that's probably where your issue is.

How to get timer running even when application is running in background or phone is locked in Windows Phone

I have a timer in my application in Windows Phone 7.1 implemented using
DispatcherTimer _timer;
Initialized as
Sample._timer = new DispatcherTimer();
Sample._timer.Interval = new TimeSpan(0, 0, 1);
Sample._timer.Tick += new EventHandler(Timer_Tick);
Sample._timer.Start();
private void Timer_Tick(object sender, EventArgs e)
{
double newValue = Sample.Value + 1.686;
if (newValue >= 100)
newValue = 0;
Sample.Value = newValue;
txtDigitalClock.Text = GetTime();
}
public string GetTime()
{
time += TimeSpan.FromSeconds(1);
return string.Format("{0:D2}:{1:D2}:{2:D2}", time.Hours, time.Minutes, time.Seconds);
}
This is working fine in normal condition
Here is my problem
1) Timer is not running when phone is in locked state(screen is loced)
2) Timer is not running when application is running in background (When you press start button in windows phone the app goes to background).
any help would be greatly appreciated..
To run your App (and Timer) under lock screen, you have to disable ApplicationIdleDetectionMode.
If you don't disable idle your App will stop as it is said at MSDN:
This event (Deactivation) is also raised if the device’s lock screen is engaged, unless application idle detection is disabled.
If you want to run Timer in the background (eg. after pressing Start buton), you won't be able to do this as MSDN says:
When the user navigates forward, away from an app, after the Deactivated event is raised, the operating system will attempt to put the app into a dormant state. In this state, all of the application’s threads are stopped and no processing takes place, but the application remains intact in memory.
The bigger problem is when your App is tombstoned - the app doesn't ramain (all) in memory.
You can try to do your job with Background Agents, but that is other story.
Also remember about Certification requirements when your App disables Idle or uses Background Agent.
Similar problem was here.
I searched for your question on google (cuz I'm not into Winphone) and found
http://stackoverflow.com/questions/8352515/how-can-i-run-my-windows-phone-application-in-background
apparently it simply is not possible.
I hope this answers your question
Please write below line timer Initialization
ApplicationIdleModeHelper.Current.HasUserAgreedToRunUnderLock = true;
I resolved this issue by saving the starting timer of the value on isolated storage
IsolatedStorageSettings.ApplicationSettings.Add("TimerStarted",DateTime.UtcNow);
And when the app is reactivated after going to background, i will look for this value in isolated storage and use that to show the timer

Update View automatically

I have a TextBox which tells the status of a running application (lets say notepad). If notepad is running Text of TextBox is running and not running for other case.
public string ProcessStatus
{
get
{
IsProcessRunning("Notepad.exe")
return "Running";
return "Not Running";
}
}
Now problem here is that view updates itself only once when it is launched. At that time if notepad is running it works fine. Now lets suppose I ran my application and notepad was not running then TextBox says not running. Now I launch notepad, now application is still saying not running as application has not updated the view. If I call notify of property changed event for the TextBox then it will say running. But I want here is that TextBox updates automatically.
The only solution what I am thinking right now is that I start a background process which keeps on updating ProcessStatus. But is this the right way? Is there any better way? Something like DirectoryWatcher for processes?
You could use a System.Windows.Threading.DispatcherTimer to check at regular intervals:
DispatcherTimer timer = new DispatcherTimer();
timer.Interval = TimeSpan.FromMilliseconds(10000); // checks every 10 seconds
timer.Tick += Timer_Tick;
timer.Start();
...
private void Timer_Tick(object sender, EventArgs e)
{
// do your checks here
textbox.Text = ProcessStatus;
}
You can find out more about the DispatcherTimer class from the DispatcherTimer Class page at MSDN.
Why not use the timer class to periodically run ProcessStatus, you can define the interval.
On this other question Can I Get Notified When Some Process Starts? there are two answers on how you can get notified if a process (e.g. Notepad.exe) starts. Both are neither ideal nor simple, I would probably stick to polling as Sheridan and NSmeef suggested.

How to make my wpf app wait for 3 minutes before re-loading data?

I am using VS2010 - WPF - C#
in my application I fetch data from a web server and view it on my interface
the problem is that I want to keep fetching data and keep refreshing my interface every 3 minutes but I don't know how to do that...
I tried (Thread.Sleep(18000)) and it didn't work because my interface wouldn't show at all
I don't know how to use the Timer for such reason and I couldn't find what I'm looking for elsewhere
Please can you help me with it ?
Best Regards
What programming model? Stock or something more sane with a MVVM approach?
Anyhow, use a TIMER to request a callback after 3 minutes. In the callback invoke back to the dispatcher thread of the window once you got the results of the web service call. Finished.
Use a DispatcherTimer, there are also examples how to use it on the given link
Use a dispatch timer like this
Delcare it
public System.Windows.Threading.DispatcherTimer timer1;
In the constructor
timer1 = new System.Windows.Threading.DispatcherTimer();
timer1.Interval = TimeSpan.FromSeconds(180); // 3 mintues interval
timer1.Tick += TimerTicked; // Event for handling the fetching data
Do your job
private void TimerTicked(object sender, EventArgs args)
{
//Fetch the data
}
timer1.start(); // Whereever you want to start the timer

Categories