如何根据WPF中的数据绑定类类型加载不同的控件

时间:2014-08-10 17:50:46

标签: c# xaml mvvm data-binding

我遇到了一个我自己解决的问题,但我不喜欢这个解决方案,因为它的复杂性和许多事件的依赖性并不符合MVVM的指导原则,所以我会喜欢以正确的方式做到并重新考虑它。 此外,我必须强调,这是问题的简化示例

在所有事情之前,我有一个基类

public abstract class CommonBaseClass
{
    public int ID { get; set; }
}

此外,我还有几个继承自基类

的类
public class DateClass : CommonBaseClass
{
    public DateTime Value { get; set; }
    public string Name { get; set; }
}

public class TextClass : CommonBaseClass
{
    public string Value { get; set; }
}

public class TrueClass : CommonBaseClass
{
    public bool Value { get; set; }
}

我是一个usercontrol我有一个可观察的基类对象集合。

ObservableCollection<CommonBaseClass> DataCollection = new ObservableCollection<CommonBaseClass>(); 

The Collection&#34; DataCollection&#34;绑定到itemscontrol。

    <ItemsControl ItemsSource="{Binding DataCollection}">

    </ItemsControl>

我想以一种方式绑定到itemscontrol的集合,这取决于继承基类的类的类型,将加载不同的控件并以最大的自定义数据绑定

所以如果控件中的一个项是TextClass的一个类型,那么该对象将绑定到一个标签,如果它是一个TrueClass类型,它将绑定到一个ChackBox,如果它是一个CateClass,它将被绑定自定义UserControl,包含DatePicker,textBox和执行某些代码的Button。

我已经有一个正在运行的解决方案,但在我看来它非常糟糕,因为它在转换器中创建了不同的控件,并且它等待不同的加载事件并手动绑定所有内容。正如我说的那么糟糕。

我确信必须有一个更好的&#34; MVVM方式&#34;在XAML中实现这一点。

我正在使用转换器,模板和资源词典(也是合并的),所以我很欣赏真实的#34;通过书籍解决方案&#34;

提前致谢;)

3 个答案:

答案 0 :(得分:1)

如果在如何根据绑定选择正确的模板涉及更复杂的逻辑时,最终将DataTemplates与DataTemplateSelectors结合使用,通常会解决此问题。 对于所描述的场景,在资源中定义特定数据模板并指定DataTemplate的DataType属性应该足够了。 然后,WPF根据绑定对象的类型选择正确的模板。

技术细节在MSDN

中描述

答案 1 :(得分:1)

使用数据模板选择器。如果您想要一个精简的完整示例,请参阅我对this stack overflow question.

的回答

答案 2 :(得分:0)

我曾经通过在ItemControl ItemTemplate中指定所有三个潜在控件来解决类似问题,并使用转换器将两个控件的Visibility设置为{{1}根据实际数据类型,一个到Hidden。这允许您设置所有三个控件,包括XAML中的绑定,而无需代码发送或事件代码。

VisibleTextClass类型的情况下,一个问题可能是,DatePicker控件仍然存在于DataTemplate中(虽然不可见)并且绑定到TrueClass属性在当前类型中不存在 - 但是如果不尝试,我会假设XAML足够宽容,可以忽略这种不适当的绑定。