// --------------------------------------------------------------------------------------------------------------------
//
// This file is part of the HandBrake source code - It may be used under the terms of the GNU General Public License.
//
//
// The refire control.
//
// --------------------------------------------------------------------------------------------------------------------
namespace HandBrakeWPF.Controls
{
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Threading;
using System.Windows;
///
/// The refire control.
///
public class RefireControl
{
#region Constants and Fields
///
/// How long stages last.
///
private const int StageDurationMsec = 900;
///
/// The delays. At each stage the refire rate increases.
///
private static readonly List Delays = new List { 500, 200, 100, 50, 20 };
///
/// The refire action.
///
private readonly Action refireAction;
///
/// The refire sync.
///
private readonly object refireSync = new object();
///
/// The refire timer.
///
private Timer refireTimer;
///
/// The running.
///
private bool running;
///
/// The stopwatch.
///
private Stopwatch stopwatch;
#endregion
#region Constructors and Destructors
///
/// Initializes a new instance of the class.
///
///
/// The refire action.
///
public RefireControl(Action refireAction)
{
this.refireAction = refireAction;
}
#endregion
#region Public Methods
///
/// The begin.
///
public void Begin()
{
lock (this.refireSync)
{
this.stopwatch = Stopwatch.StartNew();
this.running = true;
// Fire once immediately.
this.refireAction();
this.refireTimer = new Timer(
obj =>
{
lock (this.refireSync)
{
if (this.running)
{
var stage = (int)(this.stopwatch.ElapsedMilliseconds / StageDurationMsec);
int newDelay = stage >= Delays.Count ? Delays[Delays.Count - 1] : Delays[stage];
Application.Current.Dispatcher.BeginInvoke(this.refireAction);
this.refireTimer.Change(newDelay, newDelay);
}
}
},
null,
Delays[0],
Delays[0]);
}
}
///
/// The stop.
///
public void Stop()
{
lock (this.refireSync)
{
this.stopwatch.Stop();
this.running = false;
if (this.refireTimer != null)
{
this.refireTimer.Dispose();
}
}
}
#endregion
}
}