我无法使多重绑定适用于两个密码框。我确实在网上阅读了一堆尝试工作示例的文章,但没有一个是我尝试过的相同场景。问题是当我点击登录按钮时,这些密码字段不会传输到命令执行方法。
转换器的 XAML:
<Grid.Resources>
<converter:PasswordConverter x:Key="passwordConverter"/>
</Grid.Resources>
按钮的 XAML 如下所示:
<Button x:Name="loginButton"
Content="Belépés"
Margin="494,430,0,0"
VerticalAlignment="Top"
FontSize="20"
RenderTransformOrigin="-2.624,8.99"
HorizontalAlignment="Left"
Width="172"
Command="{Binding NavCommand}">
<Button.CommandParameter>
<MultiBinding Converter="{StaticResource passwordConverter}" Mode="TwoWay">
<Binding Path="Password" ElementName="userIDPasswordBox"/>
<Binding Path="Password" ElementName="leaderIDPasswordBox"/>
</MultiBinding>
</Button.CommandParameter>
</Button>
密码转换器代码:
public class PasswordConverter : IMultiValueConverter
{
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
{
return values.Clone();
}
public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
中继命令:
public class RelayCommand : ICommand
{
Action _TargetExecuteMethod;
Func<bool> _TargetCanExecuteMethod;
public RelayCommand(Action executeMethod)
{
_TargetExecuteMethod = executeMethod;
}
public RelayCommand(Action executeMethod, Func<bool> canExecuteMethod)
{
_TargetExecuteMethod = executeMethod;
_TargetCanExecuteMethod = canExecuteMethod;
}
public void RaiseCanExecuteChanged()
{
CanExecuteChanged(this, EventArgs.Empty);
}
#region ICommand Members
bool ICommand.CanExecute(object parameter)
{
if (_TargetCanExecuteMethod != null)
{
return _TargetCanExecuteMethod();
}
if (_TargetExecuteMethod != null)
{
return true;
}
return false;
}
public event EventHandler CanExecuteChanged = delegate { };
void ICommand.Execute(object parameter)
{
if (_TargetExecuteMethod != null)
{
_TargetExecuteMethod();
}
}
#endregion
}
视图模型的最后一段代码:
public class LogonViewModel : BaseViewModel
{
private Action _loginActionComplete;
public LogonViewModel(Action loginActionComplete)
{
_measureTimer = new Timer();
_measureTimer.Interval = 500D;
_measureTimer.Elapsed += measureTimer_Elapsed;
_measureTimer.Start();
_loginActionComplete = loginActionComplete;
NavCommand = new RelayCommand(loginActionComplete);
SerialPort = new SerailCommunicationNameSpace.SerialCommunication("COM3");
}
~LogonViewModel()
{
SerialPort.Close();
}
public RelayCommand NavCommand { get; private set; }
private double _measuredWeight;
public double MeasuredWeight {
get
{
return _measuredWeight;
}
set
{
SetProperty(ref _measuredWeight, value);
}
}
private Timer _measureTimer;
public SerailCommunicationNameSpace.SerialCommunication SerialPort { get; set; }
private void measureTimer_Elapsed(object sender, ElapsedEventArgs e)
{
var measuredWeight = 0D;
if (string.IsNullOrWhiteSpace(SerialPort.DataReceived) == false) {
var dataReceivedStartTrim = SerialPort.DataReceived.TrimStart();
var dataReceivedNumbersOnly = dataReceivedStartTrim.Substring(0, dataReceivedStartTrim.IndexOf(' '));
var enUSCultureInfo = new CultureInfo("en-US");
measuredWeight = double.Parse(dataReceivedNumbersOnly, enUSCultureInfo);
}
SetProperty(ref _measuredWeight, measuredWeight);
OnPropertyChanged("MeasuredWeight");
}
public string LeaderId { get; set; }
public string UserId { get; set; }
}
问题是PasswordBox
Password
属性既不是依赖属性,也不是实现INotifyPropertyChanged
。这意味着,密码的更改不会应用于绑定。
例如,如果将用于PasswordChanged
的事件处理程序添加到PasswordBox
并将密码设置为 Tag
属性,则可以绑定到Tag
,绑定将起作用。
<Button x:Name="loginButton"
Content="Belépés"
Margin="494,430,0,0"
VerticalAlignment="Top"
FontSize="20"
RenderTransformOrigin="-2.624,8.99"
HorizontalAlignment="Left"
Width="172"
Command="{Binding NavCommand}">
<Button.CommandParameter>
<MultiBinding Converter="{StaticResource passwordConverter}">
<Binding Path="Tag" ElementName="userIDPasswordBox"/>
<Binding Path="Tag" ElementName="leaderIDPasswordBox"/>
</MultiBinding>
</Button.CommandParameter>
</Button>
<PasswordBox Name="userIDPasswordBox" PasswordChanged="PasswordBox_PasswordChanged"/>
<PasswordBox Name="leaderIDPasswordBox" PasswordChanged="PasswordBox_PasswordChanged"/>
private void PasswordBox_PasswordChanged(object sender, RoutedEventArgs e)
{
var pbx = sender as PasswordBox;
if (pbx!=null)
{
pbx.Tag = pbx.Password;
}
}
当然,为了避免代码隐藏在实现后面,您应该将事件处理程序移动到行为中。