I have a search dialog where I want to disable the search button during the search. This is the current code but the button does not get deactivated
View:
<Button Content="Search"
Command="{Binding StartSearchCommand}"
IsEnabled="{Binding IsNotSearching}" />
ViewModel:
private bool _isNotSearching;
public bool IsNotSearching
{
get { return _isNotSearching; }
set
{
_isNotSearching = value;
OnPropertyChanged("IsNotSearching");
}
}
private RelayCommand<object> _startSearchCommand;
public ICommand StartSearchCommand
{
get
{
if (_startSearchCommand == null)
_startSearchCommand = new RelayCommand<object>(p => ExecuteSearch());
return _startSearchCommand;
}
}
private void ExecuteSearch()
{
IsNotSearching = false;
//do some searching here
IsNotSearching = true;
}
I've made an AsyncDelegateCommand for that reason (based on famous DelegateCommand), it internally disable command (in UI) during executing command action:
public class AsyncDelegateCommand : ICommand
{
readonly Action<object> _execute;
readonly Predicate<object> _canExecute;
bool _running;
public event EventHandler CanExecuteChanged;
public AsyncDelegateCommand(Action<object> execute, Predicate<object> canExecute = null)
{
_execute = execute;
_canExecute = canExecute;
}
public bool CanExecute(object parameter)
{
return (_canExecute == null ? true : _canExecute(parameter)) && !_running;
}
public async void Execute(object parameter)
{
_running = true;
Update();
await Task.Run(() => _execute(parameter));
_running = false;
Update();
}
public void Update()
{
if (CanExecuteChanged != null)
CanExecuteChanged(this, EventArgs.Empty);
}
}
xaml:
<Button Command="{Binding SomeCommand}" .../>
ViewModel:
AsyncDelegateCommand SomeCommand { get; }
// in constructor
SomeCommand = new AsyncDelegateCommand(o => { Thread.Sleep(5000); }); // code to run
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With