WPF和XAML的隐藏function?

以下是针对各种语言讨论的大量隐藏function。 现在我很好奇XAML和WPF的一些隐藏function吗?

我发现一个ListView的标题点击事件

<ListView x:Name='lv' Height="150" GridViewColumnHeader.Click="GridViewColumnHeaderClickedHandler"> 

GridViewColumnHeader.Click属性未列出。

以下是一些相关的function:

  • 多重绑定结合StringFormat

  • TargetNullValue绑定

  • TextTrimming属性

  • 标记扩展

  • 将Aero效果添加到窗口

  • 高级“标题”属性

  • XAML转换器

也可以看看:

  1. C#隐藏的function
  2. Python的隐藏function
  3. ASP.NET的隐藏function
  4. Perl的隐藏function
  5. Java的隐藏function
  6. VB.NET的隐藏function
  7. PHP的隐藏function
  8. Ruby的隐藏function
  9. C的隐藏function
  10. 等等……..

多重绑定 (与StringFormat组合):

 <TextBlock> <TextBlock.Text> <MultiBinding StringFormat="{}{0}, {1}"> <Binding Path="LastName" /> <Binding Path="FirstName" /> </MultiBinding> </TextBlock.Text> </TextBlock> 

还有PresentationTraceSources.TraceLevel技巧来debugging在任何特定情况下绑定的情况。 你所要做的就是在WindowsBase程序集中引用System.Diagnostics命名空间

 xmlns:sd="clr-namespace:System.Diagnostics;assembly=WindowsBase" 

然后将以下内容添加到绑定expression式中:

 <TextBlock Text="{Binding Message, sd:PresentationTraceSources.TraceLevel=High}" /> 

日志将如下所示:

 System.Windows.Data Warning: 52 : Created BindingExpression (hash=5923895) for Binding (hash=7588182) System.Windows.Data Warning: 54 : Path: 'Message' System.Windows.Data Warning: 56 : BindingExpression (hash=5923895): Default mode resolved to OneWay System.Windows.Data Warning: 57 : BindingExpression (hash=5923895): Default update trigger resolved to PropertyChanged System.Windows.Data Warning: 58 : BindingExpression (hash=5923895): Attach to System.Windows.Controls.TextBlock.Text (hash=65248697) System.Windows.Data Warning: 63 : BindingExpression (hash=5923895): Resolving source 

3.5sp1引入了TargetNullValue绑定。 这将设置绑定属性为空,如果input的值,如果你的属性是空的,它会显示这个值。

 <TextBox Text="{Binding Total, TargetNullValue=$0.00}" /> 

3.5sp1引入了StringFormat到绑定expression式中,例如

 <TextBox Text="{Binding Date, StringFormat='{}{0:MM/dd/yyyy}'}" /> 

有时你会得到太长的string以显示在标签上。 在这种情况下,我们可以利用TextBlockTextTrimming属性来显示省略号

 <TextBlock Name="sampleTextBlock" TextTrimming="WordEllipsis" TextWrapping="NoWrap"/> 

MSDN链接

将Aero效果添加到窗口

  <Window.Resources> <ResourceDictionary Source="/PresentationFramework.Aero, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, ProcessorArchitecture=MSIL;component/themes/aero.normalcolor.xaml" /> </Window.Resources> 

XAML中generics与x:TypeArguments

如果你想在XAML中使用ObservableCollection,你需要创build一个派生自ObservableCollection的types,因为你不能在XAML中声明它。 使用XAML 2009,您可以使用x:TypeArguments属性来定义genericstypes。

 <!-- XAML 2006 --> class EmployeeCollection : ObservableCollection<Employee> { } <l:EmployeeCollection> <l:Employee FirstName="John" Name="Doe" /> <l:Employee FirstName="Tim" Name="Smith" /> </lEmployeeCollection> <!-- XAML 2009 --> <ObservableCollection x:TypeArguments="Employee"> <l:Employee FirstName="John" Name="Doe" /> <l:Employee FirstName="Tim" Name="Smith" /> </ObservableCollection /> 

在禁用的控件上显示工具提示

Wpf允许在控件上显示工具提示,如果它处于禁用状态。

例如

 <Button Content="Disabled Button" ToolTipService.ShowOnDisabled="True" IsEnabled="False" ToolTip="This is a disabled button"/> 

使用带有x:参数的非默认构造函数

在XAML 2006中,对象必须有一个公共的默认构造函数来使用它们。 在XAML 2009中,您可以使用x:Arguments语法传递构造函数参数。

 <!-- XAML 2006 --> <DateTime>00:00:00.0000100</DateTime> <!-- XAML 2009 --> <DateTime> <x:Arguments> <x:Int64>100</x:Int64> </x:Arguments> </DateTime> 

不是一个隐藏的function,但与WPF / XAML你得到比斯托尔尼茨和乔什史密斯 。 WPF / XAML编程的皇后和国王。

标记扩展和附加属性是我最喜欢的function,它们使您能够以非常优雅的方式扩展XAML“词汇表”。

标记扩展

 <!-- Binding to app settings --> <CheckBox IsChecked="{my:SettingBinding MinimizeToTray}">Close to tray</CheckBox> <!-- Fill ItemsControl with the values of an enum --> <ComboBox ItemsSource="{my:EnumValues sys:DaysOfWeek}"/> <!-- Localization --> <TextBlock Text="{my:Localize HelloWorld.Text}"/> <!-- Switch on the result of a binding --> <TextBlock Text="{my:Switch Path=IsGood, ValueIfTrue=Good, ValueIfFalse=Bad}"/> 

附加属性

 <!-- Sort GridView automatically --> <ListView ItemsSource="{Binding Persons}" IsSynchronizedWithCurrentItem="True" util:GridViewSort.AutoSort="True"> <ListView.View> <GridView> <GridView.Columns> <GridViewColumn Header="Name" DisplayMemberBinding="{Binding Name}" util:GridViewSort.PropertyName="Name"/> <GridViewColumn Header="First name" DisplayMemberBinding="{Binding FirstName}" util:GridViewSort.PropertyName="FirstName"/> <GridViewColumn Header="Date of birth" DisplayMemberBinding="{Binding DateOfBirth}" util:GridViewSort.PropertyName="DateOfBirth"/> </GridView.Columns> </GridView> </ListView.View> </ListView> <!-- Vista Glass effect --> <Window x:Class="WpfApplication1.Window1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:my="clr-namespace:WpfApplication1" Title="Window1" my:WinUtil.EnableAeroGlass="True"> ... 

GridViewSort的源代码(顺便说一下,它使用了GridViewColumnHeader.Click提到的GridViewColumnHeader.Click事件)

您可以使用加号( + )在XAML中引用嵌套types。 例如,如果我们有这个类:

 public class SomeClass { public enum SomeEnum { SomeValue }; } 

我们可以使用下面的语法在XAML中引用SomeValue

 {x:Static local:SomeClass+SomeEnum.SomeValue} 

此语法在MSDN上没有logging ,并且没有官方支持。 有人问在MSDN论坛上,显然它打破了VS2010的WPFdevise器。 已经在Microsoft Connect上报告过。

网格大小共享( 这里是一个很好的例子)。 长话短说,即使在不同的网格中,您也可以拥有网格列和行共享大小。 对于那些使用DataGrid的人来说,这将是非常宝贵的,无需编辑数据。

PriorityBinding 。 允许您以“先到先显示”顺序使用asyn绑定:

 <TextBlock.Text> <PriorityBinding FallbackValue="defaultvalue"> <Binding Path="SlowestDP" IsAsync="True"/> <Binding Path="SlowerDP" IsAsync="True"/> <Binding Path="FastDP" /> </PriorityBinding> </TextBlock.Text> 

使用x:FactoryMethod的静态工厂方法

如果您的types没有公共构造函数,但使用静态工厂方法,则必须在XAML 2006的代码中创build该types。使用XAML 2009,可以使用x:FactoryMethodx:Arguments属性来传递参数值。

 <!-- XAML 2006 --> Guid id = Guid.NewGuid(); <!-- XAML 2009 --> <Guid x:FactoryMethod="Guid.NewGuid" /> 

高级“标题”属性

另一个不太清楚的是我们习惯的一些属性的内容只包含文本。 如果GUI元素的属性是Objecttypes的,那么很有可能您不需要设置文本,而是添加一个包含一组控件的需求面板。

一个例子是MenuItem,其中Header属性(通常只包含文本)可以包含一组包含在面板控件中的gui元素(或者只需要一个gui元素)。

还要注意MenuItem上的Icon属性。 这通常包含一个图像元素,但这也可以包含任何东西!

 <MenuItem Name="MyMenuItem" Click="MyMenuItem_Click"> <MenuItem.Icon> <Button Click="Button1_Click">i</Button> </MenuItem.Icon> <MenuItem.Header> <StackPanel Orientation="Horizontal" > <Label>My text</Label> <Button Click="Button2_Click">ClickMe!</Button> </StackPanel> </MenuItem.Header> </MenuItem> 

XAML转换器

以下列表显示了由WPF社区开发的将不同格式转换为XAML的转换器,反之亦然。

Adobe Illustrator XAML导出插件

Adobe Photoshop到XAML转换器

搅拌机XAML出口插件

Lightwave XAML导出插件

Visio XAML导出

3D Studio Max到XAML转换器

玛雅到XAML转换器

Flash到XAML转换器

SVG到XAML转换器

WMF / EMF到XAML转换器

内置types

如果要今天将简单types的对象(如string或double)添加到资源字典中,则需要将所需的clr-namespaces映射到XML名称空间。 在XAML 2009中,我们使用了许多包含在XAML语言中的简单types。

 <!-- XAML 2006 --> <sys:String xmlns:sys="clr-namespace:System;assembly=mscorlib >Test</sys:String> <!-- XAML 2009 --> <x:String>Test</x:String> 

以下types包含在XAML语言中:

 <x:Object/> <x:Boolean/> <x:Char/> <x:String/> <x:Decimal/> <x:Single/> <x:Double/> <x:Int16/> <x:Int32/> <x:Int64/> <x:TimeSpan/> <x:Uri/> <x:Byte/> <x:Array/> <x:List/> <x:Dictionary/> 

使用{x:Reference}的简单对象引用

如果你今天想创build一个对象引用,你需要做一个数据绑定,并用一个ElementName声明源。 在XAML 2009中,您可以使用新的{x:Reference}标记扩展

 <!-- XAML 2006 --> <Label Target="{Binding ElementName=firstName}">FirstName</Label> <TextBox x:Name="firstName" /> <!-- XAML 2009 --> <Label Target="{x:Reference firstName}">FirstName</Label> <TextBox x:Name="firstName" /> 

系统颜色使用

 <Border Background="{DynamicResource {x:Static SystemColors.InactiveBorderBrushKey}}"/> 

支持任意字典键

在XAML 2006中,所有显式的x:Key值被视为string。 在XAML 2009中,您可以通过在ElementSyntax中编写密钥来定义任何types的密钥。

 <!-- XAML 2006 --> <StreamGeometry x:Key="CheckGeometry">M 0 0 L 12 8 l 9 12 z</StreamGeometry> <!-- XAML 2009 --> <StreamGeometry>M 0 0 L 12 8 l 9 12 z <x:Key><x:Double>10.0</x:Double></x:Key> </StreamGeometry> 

按代码设置ValidationError

BindingExpression中的ValidatioRule仅在绑定的目标侧发生变化时触发。 如果你想通过代码设置validation错误,你可以使用下面的代码片段。

设置validation错误

 ValidationError validationError = new ValidationError(regexValidationRule, textBox.GetBindingExpression(TextBox.TextProperty)); validationError.ErrorContent = "This is not a valid e-mail address"; Validation.MarkInvalid( textBox.GetBindingExpression(TextBox.TextProperty), validationError); 

清除validation错误

 Validation.ClearInvalid(textBox.GetBindingExpression(TextBox.TextProperty)); 

将元素embedded到TextBlock中的能力

我不知道这是多么有用(虽然它可以隐藏起来),但是当我第一次遇到它的时候,它确实让我感到无奈 :

 <Grid x:Name="LayoutRoot"> <TextBlock HorizontalAlignment="Center" VerticalAlignment="Center"> <Grid> <Rectangle Fill="AliceBlue" Width="25" Height="25"/> </Grid> </TextBlock> </Grid> 

你可以争辩下面的xaml可能是有用的(即把graphics放在一些文本的末尾):

 <Grid> <TextBlock HorizontalAlignment="Center" VerticalAlignment="Center" Text="Hello World"> <TextBlock.Resources> <DrawingBrush x:Key="exclamationPoint" Stretch="Uniform"> <DrawingBrush.Drawing> <DrawingGroup> <DrawingGroup.Children> <GeometryDrawing Brush="#FF375CE2" Geometry="F1 M 7.968,58.164L 0,58.164L 1.914,49.921L 9.882,49.921L 7.968,58.164 ZM 21.796,0L 11.054,42.148L 4.403,42.148L 13.049,0L 21.796,0 Z "/> </DrawingGroup.Children> </DrawingGroup> </DrawingBrush.Drawing> </DrawingBrush> </TextBlock.Resources> <Grid> <Rectangle Width="100" Height="100" Fill="{StaticResource exclamationPoint}"/> </Grid> </TextBlock> </Grid> 

上面的xaml呈现如下:

你好,世界

debugginganimation

常见错误

如果出现以下错误:无法在不可变对象实例上设置“(0)。(1)”。 这可能是您遇到以下限制之一:

  • 您正在animation一个依赖项属性而不设置本地值
  • 您正在为依赖项属性设置animation,该属性的当前值在未合并到资源字典中的另一个程序集中定义。
  • 您正在animation一个当前数据绑定的值

绑定没有INotifyPropertyChanged或DependencyProperties

正如这里所讨论的,你可以绑定一个普通的CLR对象属性,而不需要INotifyPropertyChanged,它就可以工作

这里是我所指的论坛。

引用:

WPF的数据绑定引擎将数据绑定到PropertyDescriptor实例,如果源对象是普通的CLR对象并且不实现INotifyPropertyChanged接口,该实例将包装源属性。 数据绑定引擎将尝试通过PropertyDescriptor.AddValueChanged()方法来订阅属性已更改的事件。 而当目标数据绑定元素更改属性值时,数据绑定引擎将调用PropertyDescriptor.SetValue()方法将更改的值传回给源属性,同时引发ValueChanged事件以通知其他订户(在此情况下,其他订阅者将是ListBox中的TextBlocks。

如果您正在实施INotifyPropertyChanged,则完全有责任在需要将数据绑定到UI的属性的每个设置器中实施更改通知。 否则,这个改变将不会像你期望的那样同步。

这是另外一篇关于这个主题的伟大而详细的文章 。

注意这只在使用绑定时才起作用 。 如果您更新代码中的值, 则不会通知更改。 […]

实现INotifyPropertyChanged可能是一件乏味的开发工作。 但是,您需要权衡WPF应用程序的运行时间占用空间(内存和CPU)。 自己实现INPC将节省运行时CPU和内存