私はC#でWindowsフォームプロジェクトを持っています。このプロジェクトには別のスレッドで再生されるWaveOutデバイスがあります。この再生スレッドは、定期的にUIスレッドメソッドを呼び出し、それに何らかのデータ(サウンドカードに渡されているオーディオ情報を保持する配列)を渡す必要があります。 passAudioメソッドは、接続されたEventHandlerを定期的に呼び出します。C#で呼び出すためにUIメソッドを別のスレッドに渡す
は今、waveoutデバイス(WaveOutPlayer.cs)はイベントハンドラを持っています
public class WaveOutPlayer : IDisposable
{
public event EventHandler<AudioEventArgs> BufferSwapped;
...
private void passAudio(byte[] pAudiodata)
{
AudioEventArgs args = new AudioEventArgs();
args.Data = pAudiodata;
args.WaveFormat = ws.Format;
if (BufferSwapped != null)
{
BufferSwapped.Invoke(this, args);
}
}
}
また、Windowsフォームのインスタンスは、このイベントハンドラに接続します。
private void Start()
{
WaveStream Audio = new WaveStream("sine440hz_16bit_stereo.wav");
WaveOutPlayer wp = new WaveOutPlayer(audio, 0);
wp.BufferSize = 8192; // testing
wp.Repeat = false; // 'true' not implemented yet
wp.BufferSwapped += Wp_BufferSwapped;
}
private void Wp_BufferSwapped(object sender, AudioEventArgs e)
{
// The audio buffer data can be found in the event args.
// So analyze this Audio and manipulate some of the forms' controls
// accordingly.
this.labelForAmplitude.Text = "some value";
}
しかし、これは例外が発生しますWp_BufferSwapped-Methodは実際に再生スレッドに属しているため、ラベルのテキストを操作できない可能性があります。
Now: Windowsフォームのコードをより難しくすることなくこの問題を解決するにはどうすればよいですか?その理由は、私の学生(高等学校)が配列と簡単なユーザーインターフェイスでいくつかのクールなものをやり遂げることができるようにするためです。しかし、現時点では、ユーザーインターフェース作業について非常に基本的な知識しかありません。彼らはまだBeginInvokeやMethodInvokerのようなものについては何も知らない。 WaveOutPlayerをDLLの形で与えたいのですが、Windowsフォームに対処する必要があります。 この特定の種類の問題を解決する方法はありますか?
'this.labelForAmplitude.Text'を' ref'to 'Wp_BufferSwapped-Method'として送ることができます –
[C#の別のスレッドからGUIを更新するにはどうすればいいですか?](https://stackoverflow.com)/question/661561/how-do-i-update-the-another-thread-in-c) – PaulF
@Usmanlqbal変更するラベルが1つまたは2つしかない場合は、解決策になります。しかし、どのラベルや絵の枠を変更するかを学生に決定させたいと思っています。 – AudioGuy