2016-11-02 16 views
1

MVVMデザインプロパティを使用するWPFアプリケーションがあります。ビジー状態のカーソルを表示したいグリッドにデータを挿入するプロセスは長時間実行されています。私は、カーソルの働きを変更する部分を持っています。私が持っている問題は、カーソルがIsBusyというブールにバインドされていることです。しばらくの間実行されるメソッドが呼び出されると、IsBusyをtrueに設定し、メソッドが完了したらfalseに戻します。WPF MVVMリフレッシュビュー

public void LongProcedure(){ IsBusy=true; ... long running code here IsBusy=false; } `

私は

IsBusy=!IsBusy; 

を行い、それがカーソルを切り替えない別の方法でそれをテストしたので、私はIsBusyへの結合カーソルが機能している知っています。私が抱えている問題は、メソッドのコードが実行されている間、ビューが更新されないように見えるということです。 IsBusyをtrueに設定した後、ビューを再描画させる方法はありますか?

+0

同じスレッドで長期実行タスクを実行していますか? – XAMlMAX

+0

はい、私はそれを簡単に保つことを望んでいました。プロセスには5〜10秒かかり、実行中は何もできません。私は何かが起こっていることをユーザーに知らせるために待機カーソルを表示したかったのです。 – Pedler

+0

@Pedler残念ながら、画面を更新するには同じスレッドが必要です。それは他のものを実行しているため、画面を更新するために使用することはできません。 – Aron

答えて

3

すべてのウィンドウアプリケーションには、アプリケーションのビジュアル表現を扱うための専用のスレッドが1つあります。このスレッドはthe UI threadです。コードがウィンドウイベント(Loadedイベントやユーザーがボタンをクリックするなど)に反応して実行されるとき、このUIスレッドで実行されます。あなたのコードが実行されている間、あなたの仕事を実行するUIスレッドが占有されており、ウィンドウの視覚的表現を更新することはできません。極端な場合(作業が完了するまでに時間がかかります)、ウィンドウはロックされた状態で表示されます。

UIスレッドを使用して長時間実行する作業を行っている場合は、正しく実行していません。 async-awaitを使用するか、またはをバックグラウンドスレッドで実行するためにTask.Run()を使用するか、を使用する必要があります。

LongProcedure()がIOバインド(どこかからデータを待つような場合)の場合は、async-awaitを使用する必要があります。それはCPUバウンド(データ処理/計算のロット)である場合は、使用する必要がありますTask.Run()

非同期のawait:

public async Task LongProcedure() 
{ 
    IsBusy = true; 

    await GetDataFromSomewhereAsync(); 

    IsBusy = false; 
} 

public async void CallingMethod() 
{ 
    ...... 
    await LongProcedure(); 
} 

Task.Run:

public void LongProcedure() 
{ 
    IsBusy = true; 
    ... // long running code here 
    IsBusy = false; 
} 
public async void CallingMethod() 
{ 
    ...... 
    await Task.Run((Action) LongProcedure); 
} 

ことに注意してくださいバックグラウンドスレッドからUIを直接更新することはできません。通常は、マーシャルのUIコードを更新する必要があります。これにはさまざまな方法があり、使用するWindowsアプリケーションの種類(windows formsWPFなど)によって異なります。

+0

助けてくれてありがとう。これは正しい方向に私を指摘した。私はBackgroundWorkerクラスを使用して終了しました。 – Pedler