for WPF developers
ビジー状態を表すインジケータを表示するためのコントロールです。
ページ内リンク
BusyIndicator コントロールは、UI が処理中であることを示すためのインジケータを表示するためのコントロールです。 バックグラウンドで処理をおこないながら UI を更新するため、主に非同期処理をおこなっている場合に使用します。 ここでは async/await による簡単な非同期処理を使用します。
まず、重たい処理を表現するために、次のような SampleModel クラスを定義します。
本当におこないたい処理は DoHeavyWorkCore() メソッドですが、これを実行するタスクを返すメソッドが DoHeavyWorkAsync() メソッドです。
そして、DoHeavyWorkAsync() メソッドのほうを公開することで、外側からは同じタスクで重たい処理をさせないようにしています。
namespace Section4_3.Models
{
using System.Threading;
using System.Threading.Tasks;
public class SampleModel
{
/// <summary>
/// 重たい処理を別タスクでおこないます。
/// </summary>
/// <returns></returns>
public Task DoHeavyWorkAsync()
{
return Task.Run(() =>
{
DoHeavyWorkCore();
});
}
/// <summary>
/// 重たい処理をおこないます。
/// </summary>
private void DoHeavyWorkCore()
{
// 仮想的な重たい処理として 10[s] 間待機する
Thread.Sleep(10000);
}
}
}
次に BusyIndicator コントロールを使った簡単なサンプルコードを示します。 Button コントロールと TextBlock コントロールを縦に並べた StackPanel コントロールの上に被さるように BusyIndicator コントロールを配置しています。 BusyIndicator コントロールは、IsBusy プロパティが true にならない限り表示されないため、普段は StackPanel コントロールの内容のみが表示される形となります。
なお、BusyIndicator には Message プロパティがあります。
下記のサンプルコードでは TextBlock コントロールを別に用意していますが、
BusyIndicator コントロールのインジケータ下部にメッセージを表示させることもできます。
こちらの場合、メッセージ表示用に UI のスペースを確保する必要がなくなります。
<YK:Window x:Class="Section4_3.Views.MainView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:YK="clr-namespace:YKToolkit.Controls;assembly=YKToolkit.Controls"
Title="MainView" Height="500" Width="500"
WindowStartupLocation="CenterScreen">
<Grid>
<StackPanel VerticalAlignment="Center">
<Button Content="Click me." Command="{Binding ButtonCommand}" Margin="20" />
<TextBlock Margin="20">
<Run Text="Message :" />
<Run Text="{Binding Message, Mode=OneWay}" />
</TextBlock>
</StackPanel>
<YK:BusyIndicator IsBusy="{Binding IsBusy}" />
</Grid>
</YK:Window>
上記の MainView と SampleModel をつなぐための MainViewModel クラスのコードを次に示します。
MainView のボタンを押すと重たい処理が開始されるようにするため、ButtonCommand プロパティから非同期処理が開始されるようにしています。
非同期処理をおこなうには、処理をおこなうタスクの前に await 演算子を置きます。
また、await 演算子を使用することを許可するために、そのメソッドの修飾子に async を追加します。
namespace Section4_3.ViewModels
{
using Section4_3.Model;
using YKToolkit.Bindings;
public class MainViewModel : NotificationObject
{
/// <summary>
/// サンプルモデルのインスタンス
/// </summary>
private SampleModel model = new SampleModel();
#region 公開プロパティ
private bool isBusy;
/// <summary>
/// ビジー状態かどうかを取得します。
/// </summary>
public bool IsBusy
{
get { return isBusy; }
private set { SetProperty(ref isBusy, value); }
}
private string message;
/// <summary>
/// メッセージを取得または設定します。
/// </summary>
public string Message
{
get { return message; }
set { SetProperty(ref message, value); }
}
private DelegateCommand buttonCommand;
/// <summary>
/// ボタンのコマンドを取得します。
/// </summary>
public DelegateCommand ButtonCommand
{
get
{
if (buttonCommand == null)
buttonCommand = new DelegateCommand(_ =>
{
DoCommand();
});
return buttonCommand;
}
}
#endregion 公開プロパティ
/// <summary>
/// 処理をおこないます。
/// </summary>
private async void DoCommand()
{
Message = "処理を開始します。";
IsBusy = true;
// 重たい処理を非同期でおこなう
await model.DoHeavyWorkAsync();
IsBusy = false;
Message = "処理を終了しました。";
}
}
}
上記のサンプルコードの実装結果は下図のようになります。
Designed by CSS.Design Sample