2010-11-06 59 views
8

希望你一切都好。Caliburn.Micro&Telerik WPF控件

我正在使用Caliburn.Micro和Telerik的WPF控件构建一个选项卡式界面。使用RadTabControl我有以下代码;

<telerik:RadTabControl x:Name="Items" Grid.Row="1" TabStripPlacement="Bottom"> 
    <telerik:RadTabControl.ItemTemplate> 
     <DataTemplate> 
      <StackPanel Orientation="Horizontal"> 
       <Image Source="{Binding DisplayIcon}" Width="16" Height="16"/> 
       <TextBlock Text="{Binding DisplayName}"/> 
      </StackPanel> 
     </DataTemplate> 
    </telerik:RadTabControl.ItemTemplate> 
</telerik:RadTabControl> 

该卡具有正确的标题,但内容为:“....../MyViewModel”(省略号代替完整路径),而不是应显示在屏幕上。

如果我将<telerik:RadTabControl...替换为<TabControl...,这一切都按预期工作。

我错过了什么?

回答

12

Caliburn的约定系统仅针对开箱即用的WPF控件进行配置。当它看到RabTabControl时,它不能识别它,所以它搜索它的类层次结构以寻找它认可的东西。在这种情况下,它可能与Selector或ItemsControl匹配。这就是为什么部分应用公约。为了得到你想要的,你需要在ConventionManager中为RadTabControl添加一个约定,该约定完全符合你的要求。这里是TabControl的惯例是如何定义的:

AddElementConvention<TabControl>(TabControl.ItemsSourceProperty, "ItemsSource", "SelectionChanged") 
.ApplyBinding = (viewModelType, path, property, element, convention) => { 
    if(!SetBinding(viewModelType, path, property, element, convention)) 
     return; 

    var tabControl = (TabControl)element; 
    if(tabControl.ContentTemplate == null && tabControl.ContentTemplateSelector == null && property.PropertyType.IsGenericType) { 
     var itemType = property.PropertyType.GetGenericArguments().First(); 
     if(!itemType.IsValueType && !typeof(string).IsAssignableFrom(itemType)) 
      tabControl.ContentTemplate = DefaultItemTemplate; 
    } 

    ConfigureSelectedItem(element, Selector.SelectedItemProperty, viewModelType, path); 

    if(string.IsNullOrEmpty(tabControl.DisplayMemberPath)) 
     ApplyHeaderTemplate(tabControl, TabControl.ItemTemplateProperty, viewModelType); 
}; 

我想你应该能够采取的代码,并与一些小的修改,让它做你想做的。请注意,以上代码中调用的一些方法实际上存在于ConventionManager中,因此您需要修复这些问题。您应该将您的约定添加到Bootstrapper的配置覆盖中。有关这方面的其他示例,请查看WP7模板的Bootstrapper,它定义了Pivot和Panarama的自定义约定。

+1

这并获得成功。非常感谢你。 – Dan 2010-11-06 15:57:51

4

Caliburn.Micro.Telerik包含Telerik的WPF控件的约定,以及一些其他Telerik + WPF特定的东西,如IWindowManager实现和两个带有示例的应用程序。

您可以查看source codenuget package

为RadTabControl的约定如下:

ConventionManager.AddElementConvention<RadTabControl>(RadTabControl.ItemsSourceProperty, 
                "ItemsSource", 
                "SelectionChanged") 
.ApplyBinding = (viewModelType, path, property, element, convention) => 
{ 
    if (!ConventionManager.SetBindingWithoutBindingOrValueOverwrite(viewModelType, 
                    path, 
                    property, 
                    element, 
                    convention, 
                    RadTabControl.ItemsSourceProperty)) 
     return false; 

    var tabControl = (RadTabControl) element; 
    if (tabControl.ContentTemplate == null 
     && tabControl.ContentTemplateSelector == null 
     && property.PropertyType.IsGenericType) 
    { 
     var itemType = property.PropertyType.GetGenericArguments().First(); 
     if (!itemType.IsValueType && !typeof (string).IsAssignableFrom(itemType)) 
      tabControl.ContentTemplate = ConventionManager.DefaultItemTemplate; 
    } 
    ConventionManager.ConfigureSelectedItem(element, 
              RadTabControl.SelectedItemProperty, 
              viewModelType, 
              path); 

    if (string.IsNullOrEmpty(tabControl.DisplayMemberPath)) 
     ConventionManager.ApplyHeaderTemplate(tabControl, 
               RadTabControl.ItemTemplateProperty, 
               RadTabControl.ItemTemplateSelectorProperty, 
               viewModelType); 
    return true; 
}; 

希望这有助于...