简体   繁体   English

WPF Treeview 使用属性值作为绑定路径

[英]WPF Treeview use property value as Binding Path

I'm trying to create a Treeview using an ObservableCollection of a custom class called MachineComponentFault, which includes a string property called FaultText, and I'd like to make the text localized.我正在尝试使用名为 MachineComponentFault 的自定义类的 ObservableCollection 创建一个 Treeview,该类包含一个名为 FaultText 的字符串属性,我想让文本本地化。

I'm using WPF Runtime Localization from Codeproject to localize texts at runtime, and it usually works as follows:我正在使用 Codeproject 中的WPF 运行时本地化在运行时本地化文本,它通常如下工作:

<TextBlock Text="{Binding Path=NameInResources, Source={StaticResource Resources}}"/>

The problem is that I can't seem to figure out how to set the value of the property to the path, so that it can retrieve the translation.问题是我似乎无法弄清楚如何将属性的值设置为路径,以便它可以检索翻译。 This is what I managed thus far:这是我迄今为止所管理的:

  <TreeView Name="myTreeView" VirtualizingPanel.IsVirtualizing="True" ItemsSource="{Binding Faults}">
    <TreeView.Resources>
      <DataTemplate DataType="{x:Type MassComponents:MachineComponentFault}">
        <StackPanel Orientation="Horizontal" >
          <TextBlock Name="Text1" Text="{Binding FaultText}"/>
          <TextBlock Name="Text2" Text="{Binding Path=FLT_PTC_1, Source={StaticResource Resources}}"/>
        </StackPanel>
      </DataTemplate>
    </TreeView.Resources>
  </TreeView>

Essentially Text1 shows FLT_PTC_1 at Runtime, while Text2 shows "Motor Overheat", which is the value of FLT_PTC_1 in Resources.resx (which can be translated).本质上Text1在Runtime显示FLT_PTC_1,而Text2显示“Motor Overheat”,这是Resources.resx中FLT_PTC_1的值(可以翻译)。 The issue is that I can't seem to be able to do what Text2 does using FaultText Property.问题是我似乎无法使用 FaultText 属性执行 Text2 的操作。

Is there a way to do it?有没有办法做到这一点?

EDIT:编辑:

Solved it using mm8 solution, while maintaining the WPF Runtime Localization.使用 mm8 解决方案解决了它,同时保持了 WPF 运行时本地化。 The solution isn't pretty at all, since it consists in creating a Binding on a dummy class and then retrieving the binding value as a string, which seems a bit convoluted, but it's the best solution I could find.该解决方案一点也不漂亮,因为它包括在虚拟类上创建一个 Binding,然后将绑定值作为字符串检索,这似乎有点令人费解,但它是我能找到的最佳解决方案。

  public class ResourceConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
      string resourceName = value as string;

      if (!string.IsNullOrEmpty(resourceName)) //look up the resource here:
      {
        Binding b = new Binding(resourceName); //Create Binding using as Path the value of FaultText
        b.Source = CultureResources.ResourceProvider; //Get the resources from WPF Runtime Localization ObjectDataProvider
        BindingOperations.SetBinding(_dummy, Dummy.ValueProperty, b); //Set the Binding to the dummy class instance
        return _dummy.GetValue(Dummy.ValueProperty); //Retrieve the value of the Binding from the dummy class instance and return it
      }

      return value;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
      throw new NotImplementedException();
    }

    //Initialize Dummy class
    private static readonly Dummy _dummy = new Dummy();

    //Create a dummy class that accepts the Binding
    private class Dummy : DependencyObject
    {
      public static readonly DependencyProperty ValueProperty =
          DependencyProperty.Register("Value", typeof(object), typeof(Dummy), new UIPropertyMetadata(null));
    }
  }

XAML same as mm8 proposed. XAML 与提议的 mm8 相同。

You could bind to the FaultText property and use a converter to look up the resource.您可以绑定到FaultText属性并使用转换器来查找资源。 Something like this:像这样的东西:

public class ResourceConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        string resourceName = value as string;
        if (!string.IsNullOrEmpty(resourceName)) //look up the resource here:
            return Resource1.ResourceManager.GetString(resourceName);

        return value;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

XAML: XAML:

<TextBlock Name="Text2">
    <TextBlock.Text>
        <Binding Path="FaultText">
            <Binding.Converter>
                <local:ResourceConverter />
            </Binding.Converter>
        </Binding>
    </TextBlock.Text>
</TextBlock>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM