100ミリ秒ごとに何かを描画することになっているフォームにPictureBoxコントロールがあります。
バックグラウンドスレッドはループ内で計算を実行し、反復するたびにイベントを発生させます。
編集済み (コメントへの返信として):
World world = new World();
void CreateBackgroundThread() {
Thread backgroundThread = new Thread(world.BackgroundWorkerFunction);
backgroundThread.Start();
}
public class World {
void BackgroundWorkerFunction() {
IPiece piece = PieceFactory.Create();
for (int i = 0; i < stepsCount; i++) {
piece.Calculate();
if (OnPieceStep != null) {
OnPieceStep(piece);
}
}
}
}
メインフォーム内には、次のように設定されたハンドラーがあります。
world.OnPieceStep += DrawScreen;
およびInvokeラッパー(描画されるコントロールはUIスレッドで作成されるため)。
void DrawScreen(IPiece piece) {
this.Invoke(new PieceStep(_drawScreen), piece);
}
void _drawScreen(IPiece piece) {
drawer.Draw(world.Board, piece);
}
ここで、各反復の後にforループを100ミリ秒一時停止したいので、Thread.Sleep(100);を追加しました。イベントを発生させる前:
for (int i = 0; i < stepsCount; i++) {
IPiece piece = Calculate();
if (OnPieceStep != null) {
Thread.Sleep(100);
OnPieceStep(piece);
}
}
ただし、これは100ミリ秒ごとにpictureBoxを更新するのではなく、ループの最後の反復のみを描画し、ループが終了した後にのみ描画します。
Thread.Sleepは、UIスレッドではなく、呼び出されたスレッドを一時停止するべきではありませんか? 更新:バックグラウンドスレッドの計算中にアプリをクリックしようとしました。プログラムはブロックする(「応答しない」)ので、Thread.Sleepは明らかにUIスレッドで呼び出されました。これは予想される動作ですか、それともスレッドに問題がありますか?