场景
xaml设计器中,当一个RadioButton选中时,对应的另一个TextBox取消激活。用代码表述如下:
if(RadioButton.IsChecked == True):
TextBox.IsEnabled = False;
else if (RadioButton.IsChecked == False):
TextBox.IsEnabled = True;
解决方案
可以在ViewModel中设计bool属性和command命令,将TextBox的IsEnabled属性绑定到ViewModel中,通过RadioButton触发命令实现bool属性的更改。
然而,还有更优雅的解决方案,使用值转换器(ValueConverter),只用写一次就可以实现整个工程中的复用。
Step 1:实现反转bool值的类
在App.xaml.cs
(即App.xaml的code behind)中补充如下代码,将传入的bool值取反。
[ValueConversion(typeof(bool), typeof(bool))]
public class InverseBooleanConverter : IValueConverter
{
#region IValueConverter Members
public object Convert(object value, Type targetType, object parameter,
System.Globalization.CultureInfo culture)
{
if (targetType != typeof(bool))
throw new InvalidOperationException("The target must be a boolean");
return !(bool)value;
}
public object ConvertBack(object value, Type targetType, object parameter,
System.Globalization.CultureInfo culture)
{
throw new NotSupportedException();
}
#endregion
}
Step 2: 加入到Resources中
在App.xaml
的ResourceDictionary
节点内添加上一步实现的值转换器。
<local:InverseBooleanConverter x:Key="InverseBooleanConverter"/>
这里可能会提示命名空间“clr-namespace:xxxxxx”中不存在“InverseBooleanConverter”名称
,但实际上VS还自动补全了名称,这个多年悬而未决的bug先不管,后面再解决。
Step 3:在TextBox标签中绑定值转换器
最后一步,在Xaml设计器中,TextBox所在的标签中,绑定指定RadioButton的IsChecked属性,并添加值转换器。
<TextBox HorizontalContentAlignment="Center"
Text="{Binding StepDistanceZ}"
IsEnabled="{Binding IsChecked,ElementName=rBtnContinue,Converter={StaticResource InverseBooleanConverter}}"/>
<RadioButton x:Name="rBtnContinue" Content="连续" IsChecked="True"/>
参考How to bind inverse boolean properties in WPF?
命名空间无效的错误
这个问题由来已久,我也还没搞清真正的原因,不过可以用以下办法解决(按顺序,如果不行再进行下一步):
- 首先确定
class
和namespace
都是正确的,并且重新生成也没能解决错误; - 将“解决方案配置”从
Debug
切换成Release
重新生成,然后切换回来; - 切换“目标平台”,重新生成;
- 重启Visual Studio;
- 删掉
.suo
文件; - 重启电脑。
可以参考stackoverflow的这个问题:The name “XYZ” does not exist in the namespace “clr-namespace:ABC”