mirror of
https://github.com/MarkAHamann/MorseTrainer.git
synced 2025-12-06 03:42:02 +01:00
Improved design and made the changes to tone characteristics update on next change.
This commit is contained in:
parent
e778b1d1b6
commit
8ad36377f2
|
|
@ -119,8 +119,9 @@ namespace MorseTrainer
|
|||
_runner.StopDelayEnter += _runner_StopDelayEnter;
|
||||
_runner.StopDelayExit += _runner_StopDelayExit;
|
||||
_runner.Abort += _runner_Abort;
|
||||
_player.QueueEmpty += _player_QueueEmpty;
|
||||
_player.Dequeued += _player_Dequeued;
|
||||
_player.PlayingFinished += _player_PlayingFinished;
|
||||
_toneGenerator.UpdateRequired += _toneGenerator_UpdateRequired;
|
||||
|
||||
cmbKoch.Items.Clear();
|
||||
for (int i = 0; i < Koch.Length; ++i)
|
||||
|
|
@ -216,8 +217,7 @@ namespace MorseTrainer
|
|||
{
|
||||
if (_runner.IsRunning)
|
||||
{
|
||||
_pendingWavestream = null;
|
||||
_player.Clear();
|
||||
_player.ClearQueue();
|
||||
btnStartStop.Enabled = false;
|
||||
_runner.RequestStop();
|
||||
}
|
||||
|
|
@ -234,13 +234,18 @@ namespace MorseTrainer
|
|||
|
||||
private void FirstWaveReadyCallback(IAsyncResult result)
|
||||
{
|
||||
_pendingWavestream = (WaveStream)result.AsyncState;
|
||||
WaveStream waveStream = (WaveStream)result.AsyncState;
|
||||
_player.Enqueue(waveStream);
|
||||
_runner.RequestStart();
|
||||
}
|
||||
|
||||
private void WaveReadyCallback(IAsyncResult result)
|
||||
{
|
||||
_pendingWavestream = (WaveStream)result.AsyncState;
|
||||
WaveStream waveStream = (WaveStream)result.AsyncState;
|
||||
if (waveStream != null)
|
||||
{
|
||||
_player.Enqueue(waveStream);
|
||||
}
|
||||
}
|
||||
|
||||
private void _runner_StartDelayEnter(object sender, EventArgs e)
|
||||
|
|
@ -253,21 +258,28 @@ namespace MorseTrainer
|
|||
|
||||
private void _runner_MorseEnter(object sender, EventArgs e)
|
||||
{
|
||||
_player.Start(_pendingWavestream);
|
||||
_pendingWavestream = null;
|
||||
_player.Start();
|
||||
String word = _charGenerator.CreateRandomString();
|
||||
_builder.StartBuildAsync(word, new AsyncCallback(WaveReadyCallback));
|
||||
}
|
||||
|
||||
private void _player_QueueEmpty(object sender, EventArgs e)
|
||||
private void _player_Dequeued(object sender, EventArgs e)
|
||||
{
|
||||
if (_runner.ContinueMorse)
|
||||
{
|
||||
_player.Enqueue(_pendingWavestream);
|
||||
_builder.StartBuildAsync(_charGenerator.CreateRandomString(), new AsyncCallback(WaveReadyCallback));
|
||||
}
|
||||
}
|
||||
|
||||
private void _toneGenerator_UpdateRequired(object sender, EventArgs e)
|
||||
{
|
||||
// This indicates that the tone has changed. If we are currently sending code,
|
||||
// we need to remove any queued tones and in progress tones and send new tones instead
|
||||
_toneGenerator.Update();
|
||||
_player.ClearQueue();
|
||||
_builder.StartBuildAsync(_charGenerator.CreateRandomString(), new AsyncCallback(WaveReadyCallback));
|
||||
}
|
||||
|
||||
private void _player_PlayingFinished(object sender, EventArgs e)
|
||||
{
|
||||
_runner.AcknowledgeSendEnd();
|
||||
|
|
@ -275,6 +287,8 @@ namespace MorseTrainer
|
|||
|
||||
private void _runner_MorseExit(object sender, EventArgs e)
|
||||
{
|
||||
_player.Stop();
|
||||
_player.ClearQueue();
|
||||
}
|
||||
|
||||
private void _runner_StopDelayEnter(object sender, EventArgs e)
|
||||
|
|
@ -1251,7 +1265,6 @@ namespace MorseTrainer
|
|||
private Runner _runner;
|
||||
private Analyzer _analyzer;
|
||||
private StringBuilder _recorded;
|
||||
private WaveStream _pendingWavestream;
|
||||
|
||||
#endregion
|
||||
}
|
||||
|
|
|
|||
|
|
@ -36,6 +36,7 @@ namespace MorseTrainer
|
|||
/// </summary>
|
||||
public SoundPlayerAsync()
|
||||
{
|
||||
_sending = false;
|
||||
_mediaSoundPlayer = new System.Media.SoundPlayer();
|
||||
_queue = new Queue<WaveStream>();
|
||||
_sentString = new StringBuilder();
|
||||
|
|
@ -49,6 +50,17 @@ namespace MorseTrainer
|
|||
private void ThreadMain()
|
||||
{
|
||||
while (!_stopThread)
|
||||
{
|
||||
bool go = false;
|
||||
lock (this)
|
||||
{
|
||||
if (!_sending)
|
||||
{
|
||||
System.Threading.Monitor.Wait(this);
|
||||
}
|
||||
go = _sending && !_stopThread;
|
||||
}
|
||||
if (go)
|
||||
{
|
||||
WaveStream waveToPlay = Dequeue();
|
||||
if (waveToPlay != null)
|
||||
|
|
@ -65,9 +77,10 @@ namespace MorseTrainer
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
lock(this)
|
||||
{
|
||||
_stopped = true;
|
||||
_threadStopped = true;
|
||||
System.Threading.Monitor.Pulse(this);
|
||||
}
|
||||
}
|
||||
|
|
@ -86,7 +99,7 @@ namespace MorseTrainer
|
|||
wave = _queue.Dequeue();
|
||||
if (_queue.Count == 0)
|
||||
{
|
||||
OnQueueEmpty();
|
||||
OnDequeued();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -96,12 +109,22 @@ namespace MorseTrainer
|
|||
/// <summary>
|
||||
/// Puts a WAV onto the queue and resets the strings
|
||||
/// </summary>
|
||||
/// <param name="wave">A WaveStream</param>
|
||||
public void Start(WaveStream wave)
|
||||
public void Start()
|
||||
{
|
||||
Enqueue(wave);
|
||||
lock(this)
|
||||
{
|
||||
_sending = true;
|
||||
_sentString.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
lock(this)
|
||||
{
|
||||
_sending = false;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the words sent
|
||||
|
|
@ -129,9 +152,9 @@ namespace MorseTrainer
|
|||
}
|
||||
|
||||
/// <summary>
|
||||
/// Clear all waves from the queue when aborting
|
||||
/// ClearQueue all waves from the queue when aborting
|
||||
/// </summary>
|
||||
public void Clear()
|
||||
public void ClearQueue()
|
||||
{
|
||||
lock(this)
|
||||
{
|
||||
|
|
@ -168,12 +191,12 @@ namespace MorseTrainer
|
|||
}
|
||||
|
||||
/// <summary>
|
||||
/// The queue has been emptied. Action in this should be quick
|
||||
/// The queue has been dequeued. Action in this should be quick
|
||||
/// </summary>
|
||||
public event EventHandler QueueEmpty;
|
||||
protected void OnQueueEmpty()
|
||||
public event EventHandler Dequeued;
|
||||
protected void OnDequeued()
|
||||
{
|
||||
EventHandler handler = QueueEmpty;
|
||||
EventHandler handler = Dequeued;
|
||||
if (handler != null)
|
||||
{
|
||||
handler(this, EventArgs.Empty);
|
||||
|
|
@ -190,10 +213,10 @@ namespace MorseTrainer
|
|||
if (_thread != null && !_stopThread)
|
||||
{
|
||||
_stopThread = true;
|
||||
_stopped = false;
|
||||
_threadStopped = false;
|
||||
_queue.Clear();
|
||||
System.Threading.Monitor.Pulse(this);
|
||||
if (!_stopped)
|
||||
if (!_threadStopped)
|
||||
{
|
||||
System.Threading.Monitor.Wait(this);
|
||||
}
|
||||
|
|
@ -206,7 +229,9 @@ namespace MorseTrainer
|
|||
|
||||
private System.Threading.Thread _thread;
|
||||
private bool _stopThread;
|
||||
private bool _stopped;
|
||||
private bool _threadStopped;
|
||||
|
||||
private bool _sending;
|
||||
private Queue<WaveStream> _queue;
|
||||
private System.Media.SoundPlayer _mediaSoundPlayer;
|
||||
private StringBuilder _sentString;
|
||||
|
|
|
|||
|
|
@ -85,6 +85,7 @@ namespace MorseTrainer
|
|||
_WPM = 0;
|
||||
_farnsworthWPM = 0;
|
||||
_volume = 0.0f;
|
||||
_updateRequired = true;
|
||||
}
|
||||
|
||||
private float WpmToMillesecPerElement(float wpm)
|
||||
|
|
@ -102,6 +103,10 @@ namespace MorseTrainer
|
|||
/// </summary>
|
||||
public void Update()
|
||||
{
|
||||
if (_updateRequired)
|
||||
{
|
||||
_updateRequired = false;
|
||||
|
||||
// changing tone frequency or WPM will cause the tones to be regenerated
|
||||
if (_frequency == 0 || _frequency != _newFrequency || _newWPM != _WPM || _newVolume != _volume)
|
||||
{
|
||||
|
|
@ -122,6 +127,35 @@ namespace MorseTrainer
|
|||
_msPerFarnsworthElement = WpmToMillesecPerElement(_farnsworthWPM);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The user has made a change that will require an update
|
||||
/// </summary>
|
||||
public event EventHandler UpdateRequired;
|
||||
protected void OnUpdateRequired()
|
||||
{
|
||||
if (!_updateRequired)
|
||||
{
|
||||
_updateRequired = true;
|
||||
EventHandler handler = UpdateRequired;
|
||||
if (handler != null)
|
||||
{
|
||||
handler(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets if there is a required update to generated tones
|
||||
/// </summary>
|
||||
public bool IsUpdateRequired
|
||||
{
|
||||
get
|
||||
{
|
||||
return _updateRequired;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the current frequency in Hertz
|
||||
|
|
@ -150,6 +184,7 @@ namespace MorseTrainer
|
|||
throw new ArgumentOutOfRangeException("Frequency");
|
||||
}
|
||||
_newFrequency = value;
|
||||
OnUpdateRequired();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -169,6 +204,7 @@ namespace MorseTrainer
|
|||
throw new ArgumentOutOfRangeException("Volume");
|
||||
}
|
||||
_newVolume = value;
|
||||
OnUpdateRequired();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -199,6 +235,7 @@ namespace MorseTrainer
|
|||
throw new ArgumentOutOfRangeException("WPM");
|
||||
}
|
||||
_newWPM = (float)Math.Round(value * 2) / 2;
|
||||
OnUpdateRequired();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -229,6 +266,7 @@ namespace MorseTrainer
|
|||
throw new ArgumentOutOfRangeException("WPM");
|
||||
}
|
||||
_newFarnsworthWPM = (float)Math.Round(value * 2) / 2;
|
||||
OnUpdateRequired();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -382,6 +420,7 @@ namespace MorseTrainer
|
|||
return CreateSpace(difference);
|
||||
}
|
||||
|
||||
private bool _updateRequired;
|
||||
private UInt16 _frequency;
|
||||
private UInt16 _newFrequency;
|
||||
private float _WPM;
|
||||
|
|
|
|||
Loading…
Reference in a new issue