原文:WPF - Group分组对ListBox等列表样式的约束

  在做WPF主题支持时,出现一个分组引起的莫名错误,可是折腾了我一番。在没有使用样式时,列表分组很正常,使用了别人写的ListBox列表样式后,发现GroupItem分组区没有内容,是空的,本篇把这一问题的解决过程给大家说一下,做主题时可以注意分组对列表样式的限制了。

ListBox增加分组

  WPF为ItemsControl提供很多的样式扩展,要想实现列表分组也很简单,只需要做以下几步就可以了:

  1. 给列表控件增加分组样式

    代码

    <Style x:Key="GroupContainerStyle" TargetType="{x:Type GroupItem}">
    <Setter Property="Template">
    <Setter.Value>
    <ControlTemplate TargetType="{x:Type GroupItem}">
    <Expander IsExpanded="True">
    <Expander.Header>
    <Grid>
    <Grid.ColumnDefinitions>
    <ColumnDefinition Width="Auto"/>
    <ColumnDefinition />
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
    <RowDefinition/>
    </Grid.RowDefinitions>
    <StackPanel Orientation="Horizontal" Margin="0,0,10,0">
    <TextBlock Text="{Binding Path=Name}" FontWeight="Bold" />
    <TextBlock FontWeight="Bold" Text="{Binding Path=ItemCount, StringFormat=(共{0}条)}"/>
    </StackPanel>
    <Line Grid.Column="" SnapsToDevicePixels="true" X1="" X2="" Stretch="Fill" StrokeThickness=""/>
    </Grid>
    </Expander.Header>
    <ItemsPresenter />
    </Expander>
    </ControlTemplate>
    </Setter.Value>
    </Setter>
    </Style>
    GroupStyle gs = new GroupStyle();
    gs.ContainerStyle = Application.Current.TryFindResource("GroupContainerStyle") as Style;
    lbModule.GroupStyle.Add(gs);
  2. 给数据增加分组

    代码

    <UserControl.Resources>
    <CollectionViewSource Source="{x:Static oea:ApplicationModel.DefaultBusinessObjectInfos}" x:Key="cvs">
    <CollectionViewSource.GroupDescriptions>
    <PropertyGroupDescription PropertyName="Catalog" />
    </CollectionViewSource.GroupDescriptions>
    </CollectionViewSource>
    </UserControl.Resources>

使用ListBox样式后

  用了别人的一个ListBox样式文件,样式如下:

代码

<Style TargetType="{x:Type ListBox}">
<Setter Property="Background" Value="{DynamicResource {x:Static SystemColors.WindowBrushKey}}" />
<Setter Property="BorderBrush">
<Setter.Value>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="{DynamicResource PrimaryColor}" Offset="" />
<GradientStop Color="{DynamicResource SecondaryColor}" Offset="" />
</LinearGradientBrush>
</Setter.Value>
</Setter>
<Setter Property="BorderThickness" Value="" />
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" />
<Setter Property="ScrollViewer.HorizontalScrollBarVisibility" Value="Auto" />
<Setter Property="ScrollViewer.VerticalScrollBarVisibility" Value="Auto" />
<Setter Property="ScrollViewer.CanContentScroll" Value="true" />
<Setter Property="VerticalContentAlignment" Value="Center" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBox}">
<Border x:Name="Bd" SnapsToDevicePixels="true" Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Padding="" CornerRadius="4,4,4,4">
<Grid>
<ScrollViewer Padding="{TemplateBinding Padding}" Focusable="false" x:Name="scrollViewer">
<StackPanel Margin="" IsItemsHost="true"/>

<!--<ItemsPresenter SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" />-->
</ScrollViewer>
<Border CornerRadius="4,4,4,4" Visibility="Collapsed" x:Name="border" Margin="-2,-2,-2,-2">
<Border.Background>
<SolidColorBrush Color="{DynamicResource DisabledColor}"/>
</Border.Background>
</Border>
</Grid>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Visibility" TargetName="border" Value="Visible"/>
</Trigger>
<Trigger Property="IsGrouping" Value="true">
<Setter Property="ScrollViewer.CanContentScroll" Value="false" />
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>

用完之后运行发现界面不对,点击分组标题后列表内容没有显示???

  

查找原因

  自己想了一下,原因不明,无奈自己对WPF实现只了解一点,于是网上搜索ItemsPresenter empty,找到第一条网页ItemsPresenter + ItemsPanelTemplate vs Panel marked with IsItemsHost,进去后发现他提出了一个问题,就是在分组时如何取ItemsPresenter,发现Reflector工具可以看到以下代码:

代码
internal static ItemsPresenter FromGroupItem(GroupItem groupItem)
{
if (groupItem == null)
{
return null;
}
Visual parent = VisualTreeHelper.GetParent(groupItem) as Visual;
if (parent == null)
{
return null;
}
return (VisualTreeHelper.GetParent(parent) as ItemsPresenter);
}

这个帖子上面也解释了为什么这么设计,我就不再重复了,原来在分组时对控件样式有要求,那就是控件样式必须存在ItemsPresenter。

确认原因

使用《WPF - Visual调试工具Snoop》工具查看一下,发现GroupItem下的ItemsPresenter是空的

切换回不使用样式再看看,发现在GroupItem之上有一个ItemsPresenter,而应用上面样式之后就没有了,果然就是样式文件的控件模板缺少ItemsPresenter的原因。

解决问题

原因知道了,解决问题也就非常简单了,修改样式表,主要就是把

<StackPanel Margin="2" IsItemsHost="true"/>

该为

<ItemsPresenter SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"

修改后再次运行,界面正确,如下:

更多内容: 开源信息系统开发平台之OpenExpressApp框架.pdf

欢迎转载,转载请注明:转载自周金根 [ http://zhoujg.cnblogs.com/ ]

WPF - Group分组对ListBox等列表样式的约束的更多相关文章

  1. C# WPF DataGrid 分组(Group)

    原文:C# WPF DataGrid 分组(Group) 效果如图,每个列的名字可以自定义.我随便用了”File”和”Attachment Name”.  在Window的Resources里面设置S ...

  2. WPF中修改ListBox项的样式病修改选中项的背景颜色

    最终效果: 1 <ListBox Name="cmb"> 2 <!--修改颜色--> 3 <ListBox.Resources> 4 <! ...

  3. signalr中Group 分组群发消息的简单使用

    前一段时间写了几篇关于signalr的文章 1.MVC中使用signalR入门教程 2.mvc中signalr实现一对一的聊天 3.Xamarin android中使用signalr实现即时通讯 在平 ...

  4. WPF 4 DataGrid 控件(自定义样式篇)

    原文:WPF 4 DataGrid 控件(自定义样式篇)      在<WPF 4 DataGrid 控件(基本功能篇)>中我们已经学习了DataGrid 的基本功能及使用方法.本篇将继续 ...

  5. 浅析mongodb中group分组

    这篇文章主要介绍了浅析mongodb中group分组的实现方法及示例,非常的简单实用,有需要的小伙伴可以参考下. group做的聚合有些复杂.先选定分组所依据的键,此后MongoDB就会将集合依据选定 ...

  6. CSS3初学篇章_5(背景样式/列表样式/过渡动画)

    背景样式 1.背景颜色语法:background-color : transparent | color body { background-color:#CCCCCC;} 2.渐变色彩语法:back ...

  7. WPF后台设置xaml控件的样式System.Windows.Style

    WPF后台设置xaml控件的样式System.Windows.Style 摘-自 :感谢 作者: IT小兵   http://3w.suchso.com/projecteac-tual/wpf-zhi ...

  8. WPF如何用TreeView制作好友列表、播放列表

    WPF如何用TreeView制作好友列表.播放列表 前言 TreeView这个控件对于我来说是用得比较多的,以前做的小聊天软件(好友列表).音乐播放器(播放列表).类库展示器(树形类结构)等都用的是T ...

  9. SharePoint 2010 修改默认列表样式

    SharePoint 2010  修改默认列表样式 :可以通过修改 下面两个全局配置进行修改.(未完..更新中...)  C:\Program Files\Common Files\Microsoft ...

随机推荐

  1. HDU - 3078 Network(暴力+LCA)

    题目大意:给出n个点的权值.m条边,2种操作 0 u num,将第u个点的权值改成num k u v,询问u到v这条路上第k大的权值点 解题思路:该点的话直接该,找第k大的话直接暴力 #include ...

  2. Django日志器的使用

    Logging Mudel A quick logging primer Django uses Python’s builtin logging module to perform system l ...

  3. [tmux] Customize tmux with tmux.conf

    You can modify tmux's behavior with your tmux configuration file, .tmux.conf. You can use your tmux ...

  4. J2EE学习篇之--JQuery技术具体解释

    前面我们解说了的J2EE的技术都是服务端的技术,以下我们来看一下前端的一些开发技术,这一篇我们来看一下jQuery技术 简单介绍: jQuery由美国人John Resig创建,至今已吸引了来自世界各 ...

  5. iOS9.0 生成证书流程一(非推送)

    1.首先进入网址 http://developer.apple.com 2.第二登入,点击  

  6. log4erl Configuration

    https://github.com/ahmednawras/log4erl/blob/master/CONFIGURATION.txt Configuration Guide: ========== ...

  7. Redis数据存储解决方案

    http://www.tuicool.com/articles/77nUZn 1.背景 1.1 Redis简介 官方网站: http://redis.io/ ,Redis是REmote DIction ...

  8. 【u119】中位数

    Time Limit: 1 second Memory Limit: 128 MB [问题描述] 给出一个长度为N的非负整数序列A[i],对于所有1 ≤ k ≤ (N + 1) / 2,输出A[1], ...

  9. boost1.59编译安装(可以完全安装,也可定制安装--buildtype=complete,link=static)

    1.下载: 网址:http://sourceforge.net/projects/boost/files/boost/1.59.0/ 选择:boost_1_59_0.7z或者boost_1_59_0. ...

  10. XMPP之安装mySQL--Mac OS(一)

    come from:http://www.cnblogs.com/xiaodao/archive/2013/04/04/2999426.html 一.安装 到MySQL官网上http://dev.my ...