2011-11-26 26 views
13

我有一个ComboBox有相当复杂的模板个别项目,其中包括两个图像和几行文字:不同的模板在组合框的下拉列表中的项目和所选项目

enter image description here

然而, ComboBox本身中的选定项目无法正确显示,因为垂直空间太有限(我无法将其更高,因为它是ToolBar的一部分)。

如何使组合框为ComboBox本身显示的项目使用不同的模板?(默认ToString表示法就可以了)

谢谢!

+0

是使用DataTemplateSelector会做的伎俩,为您或您正在寻找一个其他soluion?也许我没有得到正确的答案? – sll

+0

@sll我不认为DataTemplateSelector可以做到这一点(尽管我没有尝试),IIRC它只在项目被加载时才被评估。无论如何,我宁愿一些简单的解决方案,不会涉及我创建的每个组合框的类(将有几个)。 –

+0

好的你想达到什么目的?基于某些条件的项目的不同UI表示? – sll

回答

27

选择的项目(在ComboBox本身,而不是下拉)不是ComboBoxItem里面,所以你可以做这样的事情:

<ComboBox.ItemTemplate> 
    <DataTemplate> 
     <ContentControl Content="{Binding}"> 
      <ContentControl.Style> 
       <Style TargetType="{x:Type ContentControl}"> 
        <!-- Complex default template --> 
        <Setter Property="ContentTemplate"> 
         <Setter.Value> 
          <DataTemplate> 
           <Image Source="{Binding XPath=media:thumbnail/@url}" Width="100" Height="100" /> 
          </DataTemplate> 
         </Setter.Value> 
        </Setter> 
        <Style.Triggers> 
         <!-- Simple selection box template --> 
         <DataTrigger 
           Binding="{Binding RelativeSource={RelativeSource AncestorType=ComboBoxItem}}" 
           Value="{x:Null}"> 
          <Setter Property="ContentTemplate"> 
           <Setter.Value> 
            <DataTemplate> 
             <TextBlock Text="{Binding XPath=title}" /> 
            </DataTemplate> 
           </Setter.Value> 
          </Setter> 
         </DataTrigger> 
        </Style.Triggers> 
       </Style> 
      </ContentControl.Style> 
     </ContentControl> 
    </DataTemplate> 
</ComboBox.ItemTemplate> 

编辑:注意,在为绑定选择框会抛出错误,因为没有找到RelativeSource。有多种选择可以规避这种情况,一种是自定义值转换器,根据祖先是否存在(手动树行走)返回truefalse。)

+0

谢谢,工作很棒! –

+0

不客气,很高兴帮助:) –

+0

太棒了!谢谢! Ymmd :) – pr0gg3r

5

我正在寻找一个标准(不是hacky而且没有绑定错误)解决这个问题。我发现它here:使用DataTemplateSelector

这与@H.B. answer的想法是一样的:每当有一个ComboBoxItem作为视觉树中的父项时检查。

public class ComboBoxItemTemplateSelector : DataTemplateSelector 
{ 
    public DataTemplate SelectedTemplate { get; set; } 
    public DataTemplate DropDownTemplate { get; set; } 

    public override DataTemplate SelectTemplate(object item, DependencyObject container) 
    { 
     while (container != null) 
     { 
      container = VisualTreeHelper.GetParent(container); 
      if (container is ComboBoxItem) 
       return DropDownTemplate; 
     } 
     return SelectedTemplate; 
    } 
} 

用法:

<ComboBox.ItemTemplateSelector> 
    <local:ComboBoxItemTemplateSelector> 
     <local:ComboBoxItemTemplateSelector.SelectedTemplate> 
      <DataTemplate> 
       ... simple template for selected item 
      </DataTemplate> 
     </local:ComboBoxItemTemplateSelector.SelectedTemplate> 
     <local:ComboBoxItemTemplateSelector.DropDownTemplate> 
      <DataTemplate> 
       ... complex template used by dropdown items 
      </DataTemplate> 
     </local:ComboBoxItemTemplateSelector.DropDownTemplate> 
    </local:ComboBoxItemTemplateSelector> 
</ComboBox.ItemTemplateSelector> 
相关问题