用法一

 <ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<PathGeometry x:Key="TreeArrow" Figures="M0,0 L0,6 L6,0 z"/>
<Style x:Key="ExpandCollapseToggleStyle" TargetType="{x:Type ToggleButton}">
<Setter Property="Focusable" Value="False"/>
<Setter Property="Width" Value=""/>
<Setter Property="Height" Value=""/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Border Background="Transparent" Height="" Padding="5,5,5,5" Width="">
<Path x:Name="ExpandPath" Data="{StaticResource TreeArrow}" Fill="Transparent" Stroke="#FF989898">
<Path.RenderTransform>
<RotateTransform Angle="" CenterY="" CenterX=""/>
</Path.RenderTransform>
</Path>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Stroke" TargetName="ExpandPath" Value="#FF1BBBFA"/>
<Setter Property="Fill" TargetName="ExpandPath" Value="Transparent"/>
</Trigger>
<Trigger Property="IsChecked" Value="True">
<Setter Property="RenderTransform" TargetName="ExpandPath">
<Setter.Value>
<RotateTransform Angle="" CenterY="" CenterX=""/>
</Setter.Value>
</Setter>
<Setter Property="Fill" TargetName="ExpandPath" Value="#FF595959"/>
<Setter Property="Stroke" TargetName="ExpandPath" Value="#FF262626"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style TargetType="{x:Type TreeViewItem}">
<Setter Property="Background" Value="Transparent"/>
<Setter Property="HorizontalContentAlignment" Value="{Binding HorizontalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="VerticalContentAlignment" Value="{Binding VerticalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="Padding" Value="1,0,0,0"/>
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
<Setter Property="FocusVisualStyle" Value="{x:Null}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TreeViewItem}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width=""/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<Border Grid.ColumnSpan="" Margin="-1600,0,0,0" x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" SnapsToDevicePixels="true"/>
<ToggleButton x:Name="Expander" ClickMode="Press" IsChecked="{Binding IsExpanded, RelativeSource={RelativeSource TemplatedParent}}" Style="{StaticResource ExpandCollapseToggleStyle}"/>
<ContentPresenter Grid.Column="" x:Name="PART_Header" ContentSource="Header" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"/>
<ItemsPresenter x:Name="ItemsHost" Grid.ColumnSpan="" Grid.Column="" Grid.Row=""/> </Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsExpanded" Value="false">
<Setter Property="Visibility" TargetName="ItemsHost" Value="Collapsed"/>
</Trigger>
<Trigger Property="HasItems" Value="false">
<Setter Property="Visibility" TargetName="Expander" Value="Hidden"/>
</Trigger>
<Trigger Property="IsSelected" Value="true">
<Setter Property="Background" TargetName="Bd" Value="#FF404040" />
<Setter Property="Background" TargetName="Expander" Value="#FF404040"/>
</Trigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsSelected" Value="true"/>
<Condition Property="IsSelectionActive" Value="false"/>
</MultiTrigger.Conditions>
<Setter Property="Background" TargetName="Bd" Value="#FF404040"/> <Setter Property="Background" TargetName="Expander" Value="#FF404040"/>
</MultiTrigger>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style> </ResourceDictionary>

这种用法只能显示背景,无法显边框 ,原因在于:

<Border Grid.ColumnSpan="2" Margin="-1600,0,0,0"  x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}"  SnapsToDevicePixels="true"/>  中的margin设置成-1600;无法精确的设置margin

方法二(转截没有确正可行性)

方法更可行,但操作困难些

记得原来做Winfrom通过Item的Bounds可以获得整行的区域,但是在WPF中进行了几个布局方式都没能成功!
VS中的解决方案效果布局如下:

这样在第一行第二列方式Border控件,此为选中区域。而如果要实现右侧系统的效果,必须要在选中区域的时候补齐第二行第一列的宽度,但是如果在TreeViewItem的Template不设置子节点列表缩进的话,将无法定位子节点列表缩进!
对比了Winform的TreeNode类型有两个关键的属性:FullPath和Level。只要知道一个就可以根据Indent算出相应的缩进宽度,从这样的思路上,这个Item布局结构就要更改如下了:
 
代码结构如下:

<StackPanel>

<Border x:Name=”itemBorder”>

<Grid>

<Grid.ColumnDefinitions>

<ColumnDefinitions Width=”19” />

<ColumnDefinitions Width=”*” />

</Grid.ColumnDefinitions>

<Path x:Name=”TreeArrow” Grid.Column=”0” />

<ContentPresenter ContentSource=”Header” Grid.Column=”1”  />

</Grid>

</Border>

<ItemsPresenter x:Name="ItemsHost" />

</StackPanel>

可是此时的子节点列表没有缩进怎么办?
做几个预备动作,在TreeViewItem里面有一个TreeNode的特殊特性,叫做Level,获得节点所在的层级,在这里我做了个Extensions类:

用来获得TreeViewItem在TreeView里面的层级深度。然后就是怎么将缩进的绑定到它该在的地方了!

在上面那段TreeViewItem的Template代码里面的itemBorder就是节点项的整体范围了,如果我们想让选中边框始终保持Aero样式中满行选中的状态就只能在itemBorder中的Grid上做手脚了,上面扩展了TreeViewItem对象,可以获取的到层级深度,而缩进值则等于节点层级和缩进值的乘积,而应用缩进值需要实现一个缩进的转换类型方法:

 namespace WJ.Controls.Functions
{
public class IndentConverte : IValueConverter
{
public int Indent { get; set; }
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
var item = value as TreeViewItem;
if (null == item)
return new Thickness();
int i = Indent * this.GetLevels(item);
return new Thickness(Indent *( this.GetLevels(item) * - ), , , );
} public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
throw new NotImplementedException();
} public int GetLevels(TreeViewItem item)
{
FrameworkElement elem = item;
while (elem.Parent != null)
{ var tvi = elem.Parent as TreeViewItem;
if (null != tvi)
return this.GetLevels(tvi) + ; elem = elem.Parent as FrameworkElement; }
return ;
}
}
}

然后就是改造上一段模板内容。完整代码如下:

<Style TargetType="{x:Type TreeViewItem}" x:Key="aaa">
       <Setter Property="FocusVisualStyle" Value="{StaticResource TreeViewItemFocusVisual}"/>
       <Setter Property="Template">
           <Setter.Value>
               <ControlTemplate TargetType="{x:Type TreeViewItem}">
                   <ControlTemplate.Resources>
                      <o2ds:IndentConverter Indent="19" x:Key="indentConverter" />
                   </ControlTemplate.Resources>
                   <StackPanel>
                       <Border Name="itemBackground" Background="{TemplateBinding Background}"
                                BorderBrush="{TemplateBinding BorderBrush}"
                                BorderThickness="{TemplateBinding BorderThickness}"
                                Padding="{TemplateBinding Padding}">
                           <Grid Margin="{Binding Converter={StaticResource indentConverter},RelativeSource={RelativeSource TemplatedParent}}">
                               <Grid.ColumnDefinitions>
                                   <ColumnDefinition Width="19" />
                                   <ColumnDefinition />
                               </Grid.ColumnDefinitions>
                               <ToggleButton Grid.Column="0" x:Name="ArrowButton" Style="{StaticResource TreeViewArrowButtonStyle}"
                                             IsChecked="{Binding Path=IsExpanded, RelativeSource={RelativeSource TemplatedParent}}"
                                             ClickMode="Press" />
                               <ContentPresenter Grid.Column="1" x:Name="PART_Header" ContentSource="Header"
                                                 HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" />
                           </Grid>
                       </Border>
                       <ItemsPresenter x:Name="ItemsHost" />
                   </StackPanel>

<ControlTemplate.Triggers>

Trigger something…
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

TreeViewItem实现整行选中 (两种用法)的更多相关文章

  1. JSP中的include的两种用法

    1.两种用法 <%@ include file=” ”%> <jsp:include page=” ” flush=”true”/> 2.用法区别 (1)执行时间上区别 < ...

  2. 子查询。ANY三种用法。ALL两种用法。HAVING中使用子查询。SELECT中使用子查询。

    子查询存在的意义是解决多表查询带来的性能问题. 子查询返回单行多列: ANY三种用法: ALL两种用法: HAVING中的子查询返回单行单列: SELECT中使用子查询:(了解就好,避免使用这种方法! ...

  3. jsp中include的两种用法

    JSP中的include的两种用法 1.两种用法 <%@ include file=” ”%> <jsp:include page=” ” flush=”true”/> 2.用 ...

  4. c++ operator操作符的两种用法:重载和隐式类型转换,string转其他基本数据类型的简洁实现string_cast

    C++中的operator主要有两个作用,一是操作符的重载,一是自定义对象类型的隐式转换.对于操作符的重载,许多人都不陌生,但是估计不少人都不太熟悉operator的第二种用法,即自定义对象类型的隐式 ...

  5. jsp中两种include的区别【转】

    引用文章:http://www.ibm.com/developerworks/cn/java/j-jsp04293/ http://www.cnblogs.com/lazycoding/archive ...

  6. operator 的两种用法

    C++,有时它的确是个耐玩的东东,就比如operator,它有两种用法,一种是operator overloading(操作符重载),一种是operator casting(操作隐式转换).1.操作符 ...

  7. Service的两种用法及其生命周期

    先来一点基础知识: Service 是android的四大组件之一,与Activity同属于一个级别,它是运行在后台进行服务的组件(例如在后台播放的音乐,播放音乐的同时并不影响其他操作).Servic ...

  8. JSP中两种include的区别

    首先说明这两种都是什么: <%@ include file=”relativeURI”%> 可以叫作静态include(静态包含),是jsp指令中的一种,(JSP指令控制JSP编译器如何去 ...

  9. Comparable和Comparator的区别&Collections.sort的两种用法

    在Java集合的学习中,我们明白了: 看到tree,可以按顺序进行排列,就要想到两个接口.Comparable(集合中元素实现这个接口,元素自身具备可比性),Comparator(比较器,传入容器构造 ...

随机推荐

  1. 《Java程序设计》终极不改版

     半年前的作品,上传只为纪念~ 成绩: ____0.1______ Java程序设计  课程设计 题 目:大学生信息管理系统 学 院:  计算机与软件学院 专 业:     网络工程_____­ .  ...

  2. C++ Primmer 学习笔记

    一.开始 (一)输入输出 1.endl的作用 endl操纵符用于结束当前行,将与设备关联的缓冲区内容刷新到设备中.如果没有这个字符,一旦程序突然崩溃,就可能导致输出还停留在缓冲区里,而不显示到设备. ...

  3. mysql的压缩特性-需求

    需求:最近有个插入量比较大的应用需要上,每天的插入量在1亿左右,同时会有较少的查询,表的单行长度在0.5k,就数据而言每天有近50G数据,由于每天写一张新表,保留30天的数据,一个月下来也要1.5T, ...

  4. JavaScript 的使用基础总结②DOM

    HTML DOM 通过 HTML DOM,可访问 JavaScript HTML 文档的所有元素. 当网页被加载时,浏览器会创建页面的文档对象模型(Document Object Model). HT ...

  5. 201521123003《Java程序设计》第8周学习总结

    1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结集合与泛型相关内容. 2. 书面作业 本次作业题集集合 1.List中指定元素的删除(题目4-1) 1.1 实验总结 我们利用Sca ...

  6. 201521145048 《Java程序设计》第3周学习总结

    1. 本章学习总结 学会了对于一个基本类的创建,需要有属性(private public protected),方法( 静态方法 非静态方法),构造函数,main函数,在定义属性时一般使用privat ...

  7. 201521123108《Java程序设计》第3周学习总结

    1. 本章学习总结 2. 书面作业 Q1. 代码阅读 public class Test1 { private int i = 1;//这行不能修改 private static int j = 2; ...

  8. locale命令设置语言环境

    locale命令设置语言环境 在Linux中通过locale来设置程序运行的不同语言环境,locale由 ANSI C提供支持.locale的命名规则为_.,如zh_CN.GBK,zh代表中文, CN ...

  9. Android事件机制

    一句话描述: 用户和程序之间的互动机制 什么是事件? 用户和程序交互时触发的程序操作. 只要是事件,必须具备三方面: 1 事件的发生者 2 事件接受者 3 事件触发和传递 事件处理的方法 观察者模式: ...

  10. mysql数据库-初始化sql建库建表-关联查询投影问题

    下面是一个简易商城的几张表的创建方式 drop database if exists shop ; create database shop CHARACTER SET 'utf8' COLLATE ...