123

这是针对各种语言讨论的大量隐藏功能。现在我很好奇 XAML 和 WPF 的一些隐藏特性?

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

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

GridViewColumnHeader.Click 属性未列出。

到目前为止的一些相关功能:

也可以看看:

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

25 回答 25

87

多重绑定(结合 StringFormat):

<TextBlock>
  <TextBlock.Text>
    <MultiBinding StringFormat="{}{0}, {1}">
      <Binding Path="LastName" />
      <Binding Path="FirstName" />
    </MultiBinding>
  </TextBlock.Text>
</TextBlock>
于 2009-07-14T13:54:57.177 回答
58

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

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

然后在绑定表达式中添加以下内容:

<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 
于 2009-07-14T14:15:22.157 回答
44

3.5sp1 将 StringFormat 引入绑定表达式,例如

<TextBox Text="{Binding Date, StringFormat='{}{0:MM/dd/yyyy}'}" />
于 2009-07-14T13:50:06.213 回答
44

3.5sp1 将 TargetNullValue 引入绑定。如果输入了值,这会将绑定属性设置为 Null,如果您的属性为 Null,它将显示此值。

<TextBox Text="{Binding Total, TargetNullValue=$0.00}" />
于 2009-07-14T14:02:57.213 回答
29

有时你得到的字符串太长而无法在标签上显示。在这种情况下,我们可以利用 的TextTrimming属性TextBlock来显示椭圆

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

MSDN 链接

于 2009-09-07T12:25:41.450 回答
27

将 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>
于 2009-08-24T13:14:28.293 回答
21

XAML 中的泛型与 x:TypeArguments

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

<!-- 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 />
于 2009-09-10T12:16:37.810 回答
19

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

在 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>
于 2009-09-10T12:12:42.537 回答
19

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

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

例如

<Button Content="Disabled Button" ToolTipService.ShowOnDisabled="True" IsEnabled="False" ToolTip="This is a disabled button"/> 
于 2009-09-10T05:04:43.640 回答
18

不是真正的隐藏功能,但使用 WPF/XAML 你会得到Bea StollnitzJosh Smith。WPF/XAML 编程的女王和王者。

于 2009-07-14T14:33:46.043 回答
18

标记扩展和附加属性是我最喜欢的功能,它们使您能够以非常优雅的方式扩展 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.ClickOrtus 提到的事件)

于 2009-08-24T12:29:20.373 回答
15

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

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

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

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

此语法未在 MSDN 上记录,并且不受官方支持。有人在 MSDN 论坛上询问过,显然它破坏了 VS2010 的 WPF Designer。它已在 Microsoft Connect 上进行了报道。

于 2011-01-12T19:08:05.337 回答
14

网格大小共享(这是一个很好的例子)。长话短说,您可以让网格列和行共享大小,甚至跨不同的网格。这对于所有使用 DataGrids 而无需就地编辑数据的人来说将是无价的。

于 2009-07-14T14:07:39.000 回答
11

优先绑定。允许您以“先到先显示”的顺序使用异步绑定:

<TextBlock.Text>
      <PriorityBinding FallbackValue="defaultvalue">
        <Binding Path="SlowestDP" IsAsync="True"/>
        <Binding Path="SlowerDP" IsAsync="True"/>
        <Binding Path="FastDP" />
      </PriorityBinding>
</TextBlock.Text>
于 2010-03-05T21:27:45.127 回答
10

通过 x:FactoryMethod 使用静态工厂方法

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

<!-- XAML 2006 -->
Guid id = Guid.NewGuid();

<!-- XAML 2009 -->
<Guid x:FactoryMethod="Guid.NewGuid" />
于 2009-09-10T12:01:44.073 回答
7

高级“标题”属性

还有一点不是很清楚,就是我们习惯的一些属性的内容只包含文本。如果 GUI 元素的属性是 Object 类型,则很可能您可以添加一个包含一组控件的面板,而不仅仅是设置文本。

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

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

<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>
于 2009-07-22T11:06:58.320 回答
7

XAML 转换器

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

Adobe Illustrator XAML 导出插件

Adobe Photoshop 到 XAML 转换器

Blender XAML 导出插件

Lightwave XAML 导出插件

Visio XAML 导出

3D Studio Max 到 XAML 转换器

Maya 到 XAML 转换器

Flash 到 XAML 转换器

SVG 到 XAML 转换器

WMF/EMF 到 XAML 转换器

于 2009-09-10T12:29:59.763 回答
6

系统颜色使用

<Border Background="{DynamicResource {x:Static SystemColors.InactiveBorderBrushKey}}"/>
于 2010-06-15T04:20:17.303 回答
6

内置类型

如果您想将简单类型的对象(如 string 或 double)添加到资源字典中,则需要将所需的 clr-namespaces 映射到 XML 命名空间。在 XAML 2009 中,我们在 XAML 语言中包含了很多简单类型。

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

<!-- XAML 2009 -->
<x:String>Test</x:String>

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/> 
于 2009-09-10T11:59:51.957 回答
6

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

如果您今天想创建一个对象引用,您需要进行数据绑定并使用 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" />
于 2009-09-10T12:09:04.617 回答
3

支持任意字典键

在 XAML 2006 中,所有显式 x:Key 值都被视为字符串。在 XAML 2009 中,您可以通过在 ElementSyntax 中编写键来定义您喜欢的任何类型的键。

<!-- 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>
于 2009-09-10T12:03:56.440 回答
2

通过代码设置 ValidationError

BindingExpression 中的 ValidatioRule 仅在绑定的目标端发生更改时触发。如果要通过代码设置验证错误,可以使用以下代码段。

设置验证错误

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.ClearInvalid(textBox.GetBindingExpression(TextBox.TextProperty));
于 2009-09-10T12:21:04.753 回答
2

将 UIElement(s) 填充到 TextBlock 中的能力

我不知道这是多么有用(虽然它有资格被隐藏)......但当我第一次遇到它时它确实让我措手不及:

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

您可能会争辩说以下 xaml 可能有用(即在某些文本的末尾放置一个图形):

<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 Z M 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 呈现如下:

你好世界

于 2011-01-12T22:18:20.153 回答
1

调试动画

常见错误

如果您收到以下错误:Cannot animate '(0).(1)' on an immutable object instance。可能是您遇到了以下限制之一:

  • 您正在为依赖属性设置动画而不设置本地值
  • 您正在为一个依赖属性设置动画,该属性的当前值是在另一个未合并到资源字典中的程序集中定义的。
  • 您正在为当前数据绑定的值设置动画
于 2009-09-10T12:41:18.593 回答
1

没有 INotifyPropertyChanged 或 DependencyProperties 的绑定

正如这里所讨论的,您可以在没有 INotifyPropertyChanged 的​​情况下绑定一个普通的 CLR 对象属性,并且它可以正常工作

这是我指的论坛帖子。

引用:

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

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

这是关于该主题的另一篇精彩而详细的文章

请注意,这仅在使用 binding 时有效。如果您从代码更新值,则不会通知更改。[...]

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

于 2011-10-14T12:11:29.020 回答