【发布时间】:2017-02-27 14:59:59
【问题描述】:
我想更改 CustomControl 中的 DependcyProperty(命名为 MessageTemplateProperty),类型为 Controltemplate。
但我无法使用 datatrigger 为其设置值
但是可以使用datatrigger设置CustomControl中的另一个DependcyProperty(命名为IsShowMessageProperty),类型为bool。
谁能解释它、为什么以及如何解决它。
自定义代码如下:
public class MessageOverLay : ContentControl
{
static MessageOverLay()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(MessageOverLay),
new FrameworkPropertyMetadata(typeof(MessageOverLay)));
}
#region DependcyProperties
// Template attached property
public static readonly DependencyProperty MessageTemplateProperty =
DependencyProperty.Register("MessageTemplate", typeof(ControlTemplate), typeof(MessageOverLay),
new FrameworkPropertyMetadata(MessageTemplateChanged));
public ControlTemplate MessageTemplate
{
set{SetValue(MessageTemplateProperty, value);}
get{return (ControlTemplate)GetValue(MessageTemplateProperty);}
}
// IsVisible attached property
public static readonly DependencyProperty IsShowMessageProperty =
DependencyProperty.Register("IsShowMessage", typeof(bool), typeof(MessageOverLay),
new PropertyMetadata(IsShowMessageChanged));
public bool IsShowMessage
{
get{return (bool)GetValue(IsShowMessageProperty);}
set{SetValue(IsShowMessageProperty, value);}
}
#endregion DependcyProperties
}
自定义默认主题 Generic.xaml
<Style TargetType="{x:Type controls:MessageOverLay}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="controls:MessageOverLay">
<AdornerDecorator>
<Grid>
<ContentPresenter x:Name="PART_Conent"
VerticalAlignment="Stretch"
HorizontalAlignment="Stretch"
Content="{TemplateBinding Content}" />
<Control x:Name="Part_MessageControl" Template="{TemplateBinding MessageTemplate}"
Visibility="{TemplateBinding IsShowMessage,Converter={StaticResource BooleanToVisibilityConverter}}" />
</Grid>
</AdornerDecorator>
</ControlTemplate>
</Setter.Value>
</Setter>
<Setter Property="MessageTemplate">
<Setter.Value>
<ControlTemplate>
<Grid HorizontalAlignment="Left" VerticalAlignment="Bottom">
<Grid Width="150" Height="100" Margin="5 0 0 10">
<Rectangle Stroke="Black" Fill="Yellow" RadiusX="6" RadiusY="6" Margin="0 20 0 0" />
<TextBlock Text="What are you doing?" Margin="5 25 0 0" />
<Button Content="Cancel" Margin="5" VerticalAlignment="Bottom" HorizontalAlignment="Right" />
<Button Content="OK" Margin="5" VerticalAlignment="Bottom" HorizontalAlignment="Left" />
</Grid>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
我想按如下方式使用:
演示 XAML:
<Window ...>
<Window.Resources>
<ControlTemplate x:Key="GenderPopupTemplate">
<Grid HorizontalAlignment="Left" VerticalAlignment="Bottom">
<Grid Width="200" Height="100" Margin=" 5 0 0 10">
<TextBlock Text="Please Select Gender " Margin="5 25 0 0" />
<Button Content="Male" Margin="5" VerticalAlignment="Bottom" HorizontalAlignment="Left"
Command="{Binding SelectedGenderCommand}" />
<Button Content="FeMale" Margin="5" VerticalAlignment="Bottom" HorizontalAlignment="Right"
Command="{Binding SelectedGenderCommand}" />
</Grid>
</Grid>
</ControlTemplate>
<ControlTemplate x:Key="FacePopupTemplate">
<Grid HorizontalAlignment="Left" VerticalAlignment="Bottom">
<Grid Width="200" Height="100" Margin="5 10 0 0">
<TextBlock Text="Do you like your Face,Now?" Margin="5 25 0 0" />
<Button Content="OK" Margin="5" VerticalAlignment="Bottom" HorizontalAlignment="Left"
Command="{Binding OKCommand}" />
</Grid>
</Grid>
</ControlTemplate>
</Window.Resources>
<controls:MessageOverLay HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
MessageTemplate="{StaticResource GenderPopupTemplate}"
IsShowMessage="True">
<controls:MessageOverLay.Style>
<Style TargetType="{x:Type controls:MessageOverLay}">
<Style.Triggers>
<DataTrigger Binding="{Binding MessageBoxType}" Value="{x:Static viewModels:MessageBoxTypes.SelectView}">
<Setter Property="MessageTemplate" Value="{StaticResource GenderPopupTemplate}"></Setter>
<Setter Property="Height" Value="350"/>
</DataTrigger>
<DataTrigger Binding="{Binding MessageBoxType}" Value="{x:Static viewModels:MessageBoxTypes.MessageView}">
<Setter Property="MessageTemplate" Value="{StaticResource FacePopupTemplate}"></Setter>
<Setter Property="Height" Value="150"/>
</DataTrigger>
</Style.Triggers>
</Style>
</controls:MessageOverLay.Style>
<Grid Background="SeaGreen"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch">
<TextBlock Text="Content"/>
</Grid>
</controls:MessageOverLay>
当MainWindowViewModel 的Propery MessageBoxType 发生更改时,我想更改MessageTemplate。
但我无法存档。
其他相关代码
演示 C# 代码:
public class MainWindowViewModel : BindableBase
{
public ICommand SelectedGenderCommand { get; }
public ICommand OKCommand { get; }
private MessageBoxTypes _messageBoxType;
public MessageBoxTypes MessageBoxType
{
get { return _messageBoxType; }
set { SetProperty(ref _messageBoxType, value); }
}
private string _title = "Prism Unity Application";
public string Title
{
get { return _title; }
set { SetProperty(ref _title, value); }
}
public MainWindowViewModel()
{
MessageBoxType = MessageBoxTypes.SelectView;
SelectedGenderCommand = new DelegateCommand<object>(SelectedGender);
OKCommand = new DelegateCommand<object>(OK);
}
private void OK(object obj)
{
MessageBoxType = MessageBoxTypes.SelectView;
}
private void SelectedGender(object obj)
{
MessageBoxType = MessageBoxTypes.MessageView;
}
}
public enum MessageBoxTypes
{
SelectView,
MessageView,
ConfirmView
}
更新:
Here是github中的完整demo代码,请查看。
【问题讨论】:
-
您已经使用静态 getter 和 setter 方法声明了依赖属性,同时应该有一个 CLR 属性包装器(例如
MessageTemplate属性)。除此之外,尚不清楚您的控件如何实际使用(或打算使用) MessageTemplate 属性。 -
@Clemens no ,我还没有实现 CLR 属性包装器(例如 MessageTemplate 属性)。但是
IsShowMessageProperty与MessageTemplateProperty相同 -
当然,你为什么不这样做?
-
@我只是在 XAML 中使用这些属性,而不是在 C# 代码中。
-
没关系。有效的依赖属性声明需要 CLR 包装器。同样,尚不清楚您的控件如何实际使用(或打算使用) MessageTemplate 属性。
标签: c# wpf custom-controls controltemplate datatrigger