经过一段时间的休息后,我设法进一步使用了我的只读复选框,现在以相当优雅的形式拥有了我想要的功能。问题是我使用了一些技巧来使它工作,虽然这不是一场灾难,但做得更好会很好。
回顾一下:我想要一个常规外观的复选框,它在单击时不会自检,而是单击事件触发后台工作人员,该工作人员稍后会导致变量被更新。此变量绑定到 checkbox.ischecked,然后使用新值进行更新。
我想根据这里的想法使用一个控制模板:
我已经对此进行了修改并删除了我认为不需要的东西(也许是不明智的)并最终得到:
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:Microsoft_Windows_Themes="clr-namespace:Microsoft.Windows.Themes;assembly=PresentationFramework.Aero">
<!-- -->
<Style x:Key="ReadOnlyCheckBoxStyle" TargetType="{x:Type CheckBox}" >
<Setter Property="Control.Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type CheckBox}">
<BulletDecorator SnapsToDevicePixels="true" Background="Transparent">
<BulletDecorator.Bullet>
<Microsoft_Windows_Themes:BulletChrome Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
RenderMouseOver="{TemplateBinding IsMouseOver}"
IsChecked="{TemplateBinding Tag}">
</Microsoft_Windows_Themes:BulletChrome>
</BulletDecorator.Bullet>
<ContentPresenter SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
Margin="{TemplateBinding Padding}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
RecognizesAccessKey="True" />
</BulletDecorator>
<ControlTemplate.Triggers>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="{StaticResource {x:Static SystemColors.GrayTextBrushKey}}" />
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
这个复选框的工作原理如上所述,我这样称呼它:
<CheckBox x:Name="uiComboBox" Content="Does not set the backing property, but responds to it."
Style="{StaticResource ReadOnlyCheckBoxStyle}" Tag="{Binding MyBoolean}" Click="uiComboBox_Click"/>
我所做的 hack 是使用“标记”DependencyProperty 将数据绑定携带到控件模板中。这绕过了通常导致复选框自检的任何机制。要恢复为正常的复选框,只需将绑定到 Tag 更改为绑定到 IsChecked 并在 BulletDecorator 内部将 TemplateBinding 设置为 IsChecked 而不是 Tag。
所以我想我的问题是:
- 我弄错了棍子的一端吗?有没有一个地方我可以覆盖导致盒子自检的任何机制?也许在 ControlTemplate 触发器中?
- 消除我认为只是从默认 CheckBox 引入的任何备用 XAML 是一个好主意,还是应该尝试完全替换所有样式?
- 如果我正在做的事情不是太疯狂,我可以在 XAML 中添加一个依赖属性,这样我就不必使用 Tag 属性了吗?
- 我还想到,也许我真正想要的是一个看起来像复选框的按钮控件,也许是一个不可见的按钮,顶部带有通常的动画复选框,我将数据绑定到其图形。对该计划的任何想法也将非常受欢迎。
非常感谢
埃德