#c# #wpf #xaml
#c# #wpf #xaml
Вопрос:
Я хочу привязать кнопку IsEnabled
к результату логического выражения.
Я нахожу только довольно сложные решения с использованием конвертеров или других методов. Возможно ли это более простым способом?
Пример кода:
<Button IsEnabled="{ Binding Path=IsRecordingEnabled }" />
public partial class MainWindow : Window
{
public bool IsRecording { get; set; } = false;
public string LoggingFolder { get; set; } = null;
public bool IsRecordingEnabled
{
get
{
return !IsRecording amp;amp; LoggingFolder != null;
}
}
// ...
}
Очевидно, что кнопка не обновляется при изменении выражения. Я понимаю, что мне нужно уведомить графический интерфейс через OnNotifyPropertyChanged
или аналогичный. Но как это сделать в моем случае, когда я хочу обработать логическое выражение, которое не имеет set
метода, но изменяется с помощью композиции IsRecording
и LoggingFolder
.
Ответ №1:
Вам придется вызывать PropertyChanged
событие при изменении либо IsRecording
или ReplayLogFile
. В аргументах события вы должны указать, что свойство IsRecordingEnabled
изменилось:
public partial class MainWindow : Window,INotifyPropertyChanged
{
private bool _isRecording = false;;
public bool IsRecording
{
get => _isRecording;
set
{
_isRecording = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(IsRecordingEnabled)));
}
private string _replayLogFile = null;
public string ReplayLogFile
{
get => _replayLogFile;
set
{
_replayLogFile = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(IsRecordingEnabled)));
}
}
public bool IsRecordingEnabled
{
get
{
return !IsRecording amp;amp; LoggingFolder != null;
}
}
// ...
}
Комментарии:
1. Отлично, я использую смесь этого ответа и ответа MindSwipe.
Ответ №2:
Фактическая реализация по умолчанию PropertyChanged
:
protected void OnPropertyChanged([CallerMemberName] string name = null)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(name));
}
Вы можете видеть, что у него есть параметр name
, украшенный атрибутом [CallerMemberName]
, который «Позволяет вам получить имя метода или свойства вызывающего метода». (источник). Это означает, что вы можете вручную указать, какое свойство было изменено, передав имя. Это означает, что вы можете сообщить GUI, что свойство изменено, без необходимости устанавливать и устанавливать его. Вот так:
private bool _isRecording = false;
public bool IsRecording
{
get => _isRecording;
set
{
_isRecording = value;
// You could omit the next line, if the UI doesn't bind to this property
OnPropertyChanged();
OnPropertyChanged(nameof(IsRecordingEnabled));
}
}
Ответ №3:
Вместо кнопки можно использовать переключатель.
WPF:
<ToggleButton x:Name="record" Content="Record" .../>
В главном окне вы можете использовать:
запись.IsChecked = true / false; для установки или сброса состояния кнопки переключения
if (record.IsChecked == true amp;amp; LoggingFolder == null)
{
//Do what you want
}
Вы также можете использовать событие щелчка
private void record_Click(object sender, RoutedEventArgs e)
{
LoggingFolder != null;
}
Комментарии:
1. Спасибо за подсказку относительно
ToggleButton
. Идеальное улучшение для моего варианта использования. Однако, обновляя графический интерфейс, я хочу использовать «декларативный» подход вместо «импаративного», который вы предлагаете.