如何创建可绑定到WPF TextBlock的复杂类属性且无需使用IValueConverter
问题解决方法
WPF绑定源为自定义类型、目标为string时,会优先调用该类型标注的TypeConverter的ConvertTo方法完成转换,仅当TypeConverter不存在或转换失败时才会调用ToString()方法。你遇到的空白问题大概率是LatLongTypeConverter的字符串转换逻辑未正确实现,以下方案均无需使用IValueConverter:
方案1:完善LatLongTypeConverter实现(推荐)
确保你的LatLongTypeConverter类正确实现字符串转换相关的两个方法,示例代码如下:
public class LatLongTypeConverter : TypeConverter { // 声明支持转换为string类型 public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) { return destinationType == typeof(string) || base.CanConvertTo(context, destinationType); } // 实现LatLong转string的逻辑 public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType) { if (destinationType == typeof(string) && value is LatLong latLong) { // 可直接调用已实现的显式字符串转换逻辑或者ToString逻辑 return (string)latLong; // 也可写为 return latLong.ToString(); } return base.ConvertTo(context, culture, value, destinationType); } // 原有其他转换逻辑(比如字符串转LatLong的CanConvertFrom、ConvertFrom)保留即可 }
修改完成后原有XAML绑定不需要做任何调整,即可正常显示内容。
方案2:添加辅助属性(无需修改LatLong类)
如果你不想改动LatLong类和TypeConverter的实现,可以在City类中新增只读字符串辅助属性,绑定该属性即可:
public class City : INotifyPropertyChanged { // 原有代码全部保留 // 新增只读辅助属性 public string LocationText => _Location?.ToString(); // 修改Location属性的set方法,同步触发辅助属性的变更通知 public LatLong Location { get => _Location; set { _Location = value; Notify(); Notify(nameof(LocationText)); } } }
XAML绑定调整为:
<TextBlock Text="{Binding LocationText}"/>
方案3:绑定路径显式调用ToString
如果你的LatLong.ToString()逻辑本身是正确的,也可以直接在绑定路径中显式调用ToString方法,跳过TypeConverter的转换逻辑,仅需要修改XAML绑定即可:
<TextBlock Text="{Binding Location.ToString()}"/>
内容的提问来源于stack exchange,提问作者Christopher O'Shell
相关产品推荐
相关产品推荐

