我正在创建一个改变Button的ControlTemplate的样式(它实际上在右边添加了箭头,因此按钮看起来像下拉按钮(在wpf中缺少)).
在模板内部,我放了实际按钮(因为我需要结果仍然像按钮 - 我只能更改ContentTemplate,但我需要与箭头一起显示实际内容,并将ContentPresenter放在ContentTemplate中产生堆栈溢出 - wpf just将模板扩展到演示者并继续和箭头一起继续.
我的问题是我希望用户能够更改按钮的背景,所以我需要绑定Background="{TemplateBinding Background}".有了这个,用户必须始终提供背景,否则它将为null.为了防止这种情况,我理解我需要为后台提供默认值,所以我补充说<Setter Property="Background" Value="default Background goes here"/>
问题是,这个二传手应该是什么价值?我假设wpf的内置样式是为每个应用程序自动加载的,我已经查看了aero.normalcolor.xaml,它们提供了ButtonNormalBackground样式,后来将它用作默认按钮样式<Setter Property="Background" Value="{StaticResource ButtonNormalBackground}"/>(aero.normalcolor.xaml,第47行).
正是我想要的,但是,当我使用这个setter时,找不到静态资源.然后我将其更改为DynamicResource,但在这种情况下,按钮的背景保持透明 - 不使用ButtonNormalBackground!
我应该如何提供系统的按钮外观作为默认值?谢谢!
PS:对于BorderBrush,BorderThickness - geez的dtto,似乎我不允许WPF作者一直使用的技巧:/
我的风格:
<Style TargetType="{x:Type ToggleButton}" x:Key="DropDownArrowStyle">
<Setter Property="Background" Value="{StaticResource ButtonNormalBackground}"/>
<Setter Property="ToggleButton.Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<ToggleButton
x:Name="PART_ToggleButton"
Margin="{TemplateBinding Margin}"
Padding="{TemplateBinding Padding}"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
IsEnabled="{TemplateBinding IsEnabled}"
IsChecked="{Binding IsChecked, RelativeSource={RelativeSource TemplatedParent}, Mode=TwoWay}"
ContextMenu="{TemplateBinding ContextMenu}"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
Foreground="{TemplateBinding Foreground}"
FocusVisualStyle="{TemplateBinding FocusVisualStyle}"
ClickMode="{TemplateBinding ClickMode}" …Run Code Online (Sandbox Code Playgroud) 如何以编程方式设置按钮的模板?
Polygon buttonPolygon = new Polygon();
buttonPolygon.Points = buttonPointCollection;
buttonPolygon.Stroke = Brushes.Yellow;
buttonPolygon.StrokeThickness = 2;
// create ControlTemplate based on polygon
ControlTemplate template = new ControlTemplate();
template.Childeren.Add(buttonPolygon); // This does not work! What's the right way?
//create button based on controltemplate
Button button = new Button();
button.Template = template;
Run Code Online (Sandbox Code Playgroud)
所以我需要一种方法将我的Polygon设置为按钮的模板.建议?
谢谢.
正如我所看到的,很多人遇到了这个确切的问题,但我无法理解为什么我的情况不起作用而且它开始让我发疯.
上下文:我有一个DataGrid根据每个单元格的值着色的.因此,我有一个动态样式解析用于每个单元格的实际模板.背景现在相应地起作用.
新问题:当我有一个深色背景时,我希望字体颜色为白色,字体粗细为粗体,以便文本可以正确读取.而且......我无法正确设计它.
我读了一些关于它的Stackoverflow帖子:
这个适合我的问题,但没有提供任何工作解决方案 这一个也很清楚,细节但是...... 这个问题和我几乎一样但是......解决方案不起作用
这是我到目前为止尝试的内容:
<!-- Green template-->
<ControlTemplate x:Key="Green" TargetType="{x:Type tk:DataGridCell}">
<Grid Background="Green">
<ContentPresenter
HorizontalAlignment="Center"
VerticalAlignment="Center">
<ContentPresenter.Resources>
<Style BasedOn="{StaticResource BoldCellStyle}" TargetType="{x:Type TextBlock}" />
</ContentPresenter.Resources>
</ContentPresenter>
</Grid>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud)
不行.背景为绿色,但文字保持黑色而不是粗体.
BTW,BoldCellStyle尽可能简单:
<Style x:Key="BoldCellStyle" TargetType="{x:Type TextBlock}">
<Setter Property="FontWeight" Value="Bold"/>
<Setter Property="Foreground" Value="White" />
</Style>
Run Code Online (Sandbox Code Playgroud)
好的.第二次尝试(这是一个真正的愚蠢但很好......)
<!-- Green template -->
<ControlTemplate x:Key="Green" TargetType="{x:Type tk:DataGridCell}">
<Grid Background="Green">
<ContentPresenter
HorizontalAlignment="Center"
VerticalAlignment="Center">
<ContentPresenter.Resources>
<Style x:Key="BoldCellStyle" TargetType="{x:Type TextBlock}">
<Setter Property="FontWeight" Value="Bold"/>
<Setter Property="Foreground" Value="White" />
</Style>
</ContentPresenter.Resources>
</ContentPresenter>
</Grid>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud)
也不起作用.
然后,我试着玩这个 …
我正在尝试编写一个自定义控件,该控件在模板中具有一个TextBox和一个ListBox。但是我发现,当我在TextBox中输入文本时(因此TextBox具有焦点),ListBox显得未聚焦。这使我的控件看起来像两个不同的控件。
我在MSDN上读到过,在WPF中有一个叫做FocusScope的东西,但是我没有成功。
所以我的问题是,当其中之一具有键盘焦点时,如何使ListBox和TextBox控件都显示为焦点?
有什么区别
我在网格中有一个BindingGroup:
<Grid x:Name="?????????????" DataContext="{Binding Source={StaticResource ????????}}"
Grid.RowSpan="1" Grid.Row="1" HorizontalAlignment="Center">
<Grid.BindingGroup>
<BindingGroup NotifyOnValidationError="True">
<BindingGroup.ValidationRules>
<??:??????????? ValidationStep="ConvertedProposedValue" />
</BindingGroup.ValidationRules>
</BindingGroup>
</Grid.BindingGroup>
<Grid.Style>
<Style>
<Setter Property="Validation.ErrorTemplate" Value="{StaticResource BindingGroup??????}" />
</Style>
</Grid.Style>
...
Run Code Online (Sandbox Code Playgroud)
我的网格有一个ErrorTemplate:
<ControlTemplate x:Key="BindingGroup??????">
<Border BorderBrush="Blue" BorderThickness="2">
<StackPanel>
<Label Content="My BindingGroup Error should be here!"></Label>
<AdornedElementPlaceholder />
</StackPanel>
</Border>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud)
我想从我的ControlTemplate访问Validation.Errors [0] .ErrorContent以在我的标签中显示它。可能吗?请你帮助我好吗?
ControlTemplate如何处理datacontext?
使用以下模板
<ControlTemplate x:Key="ToolbarButtonHover" TargetType="Button">
<Grid Name="backgroundGrid">
<Image Source="{DynamicResource ResourceKey=Img}" Width="{TemplateBinding Width}" Height="{TemplateBinding Height}"></Image>
</Grid>
<ControlTemplate.Triggers>
<DataTrigger Binding="{Binding Path=DataContext.ToolSelected, RelativeSource={RelativeSource TemplatedParent}}" Value="Unlink">
<Setter TargetName="backgroundGrid" Property="Background" Value="Red" />
</DataTrigger>
</ControlTemplate.Triggers>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud)
与控制
<Button Content="Button"
Template="{StaticResource ResourceKey=ToolbarButtonHover}"
Height="24" Width="24" Background="Red">
<Button.Resources>
<ImageSource x:Key="Img">Resources/Icons/toolSelect.png</ImageSource>
</Button.Resources>
</Button>
Run Code Online (Sandbox Code Playgroud)
但这并没有使背景变红.我已经验证了ToolbarViewModel属性的值ToolSelected实际上是通过在控件<Label Content="{Binding ToolSelected}"/>旁边使用Unlink 来实现的.所以我认为问题是模板没有使用正确的DataContext,但我不确定.这就是我向你求助的原因.
控制在于自定义用户控件,并ToolbarViewModel设置为背景的这一切,就像这样.
<UserControl.DataContext>
<local:ToolboxView/>
</UserControl.DataContext>
Run Code Online (Sandbox Code Playgroud) 在绑定到ControlTemplate中的Effect的Color属性时,我看到了一些奇怪的行为.直接设置值时,我可以将颜色定义为字符串(例如"Red")或Hex值(例如#FFFF0000).
但是,当使用绑定时,它仅在颜色被定义为String时才有效,这是ControlTemplate样式中的一个问题,因为我想使用TemplateParent属性的颜色,这些颜色被绑定为Hex值.
例如.看看下面的XAML(对不起,我知道它很长但我想展示所有情况):
<Window x:Class="EffectTest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<!--
STYLE 1
This works, as the Color is hard coded, but note that the hard
coded value is identicle to the value in Style 2 (which doesn't work).
-->
<Style x:Key="Style1" TargetType="{x:Type Button}">
<Style.Setters>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border Width="{TemplateBinding Width}"
Height="{TemplateBinding Height}"
Background="{TemplateBinding Foreground}">
<Border.Effect>
<DropShadowEffect Color="#FFFF0000"/>
</Border.Effect>
<TextBlock Foreground="White" Text="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=Background}"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style.Setters>
</Style>
<!--
STYLE 2
This fails …Run Code Online (Sandbox Code Playgroud) ComboBox有一个用于选择项目的按钮.我需要第二个按钮,我的自定义方法靠近第一个按钮.如何在没有UserControl的情况下添加它?
有时当我正在编辑控件原始模板的副本时,我不需要更改原始样式和颜色,并且希望直接引用原始样式和颜色.
例如,我想更改ComboBox模板以在下拉列表中添加一些过滤按钮,其切换按钮指的是也复制到文件中的样式.我想参考原始风格,所以我XAML不会过于凌乱.
编辑:因此,这是您选择编辑副本时创建的XAML代码的一部分.ControlTemplate是我想要改变的,但我不需要ComboBoxToggleButton样式,因此对于toggleButton,我想将它的样式设置为从中复制ComboBoxToggleButton样式的样式.是否存在一些名称空间,它们都存储在其中,或者它们是否无法访问?
<Style x:Key="ComboBoxToggleButton" TargetType="{x:Type ToggleButton}">
...
</Style>
<ControlTemplate x:Key="ComboBoxTemplate" TargetType="{x:Type ComboBox}">
<Grid x:Name="templateRoot" SnapsToDevicePixels="true">
...
<ToggleButton x:Name="toggleButton" ... Style="{StaticResource ResourceKey=ComboBoxToggleButton}"/>
</Grid>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud)
而且大约是我喜欢它的样子
<Window xmlns:baseStyles="{namespace/url to the default wpf styles}">
<ControlTemplate x:Key="ComboBoxTemplate" TargetType="{x:Type ComboBox}">
<Grid x:Name="templateRoot" SnapsToDevicePixels="true">
...
<ToggleButton x:Name="toggleButton" ... Style="{StaticResource ResourceKey=baseStyles:ComboBoxToggleButton}"/>
</Grid>
<ControlTemplate.Triggers>
...
</ControlTemplate.Triggers>
</ControlTemplate>
Run Code Online (Sandbox Code Playgroud) controltemplate ×10
wpf ×10
c# ×3
xaml ×3
datatemplate ×2
aero ×1
binding ×1
code-behind ×1
combobox ×1
datacontext ×1
datagrid ×1
default ×1
itemtemplate ×1
validation ×1
wpf-controls ×1