Silverlight模板化按钮控件中的命令数据绑定

时间:2012-04-18 15:34:58

标签: silverlight data-binding controltemplate

我正在尝试使用数据绑定为可见性,工具提示和命令创建模板化按钮控件。可见性绑定与工具提示一样,但命令不起作用。另一个进程负责注入视图模型并将其与View关联,其他数据绑定正在工作,因此我非常有信心它正常工作。

在资源词典中:

<Converters:BoolToVisibilityConverter x:Key="boolVisibilityConverter" />

<Style TargetType="local:ImageButton">
    <Setter Property="Visibility" Value="{Binding FallbackValue=Visible, Path=ToolIsAvailable, Converter={StaticResource boolVisibilityConverter} }"/>
    <Setter Property="Command" Value="{Binding ButtonCommand}"/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="local:ImageButton">
                <Grid>
                <Image Source="{TemplateBinding Image}" 
                       ToolTipService.ToolTip="{Binding ToolName}"  />
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

模板化对照

public class MyButton: ImageButton
{
    public MyButton(MyCommandViewModel viewmodel)
    {
        this.DefaultStyleKey = typeof(ImageButton);
        this.Image = new BitmapImage(new Uri("/MyProject;component/Themes/myimage.png", UriKind.Relative));
                this.DataContext = viewmodel;
    }

}

并在视图模型中

public MyCommandViewModel()
        : base("My Tool", true)
    {
    }


    public class CommandViewModel
    {
    public CommandViewModel(string toolName, bool isAvailable)
    {
                    ToolIsAvailable = isAvailable;
                    ToolName = toolName;
        _buttoncommand = new DelegateCommand(() =>
        {
            ExecuteCommand();
        },
        () => { return CanExecute; });
    }

    private bool _canExecute = true;
    public bool CanExecute
    {
        get { return _canExecute; }
        set 
        { 
            _canExecute = value; 
            OnPropertyChanged("CanExecute");  
            if (_command != null) _command.RaiseCanExecuteChanged();  
        }
    }

    private DelegateCommand _buttoncommand;
    public ICommand ButtonCommand
    {
        get { return _buttoncommand; }
    }
    protected virtual void ExecuteCommand()
    {
    }
    public bool ToolIsAvailable
    {
        get { return _toolIsReady; }
        set { _toolIsReady = value; OnPropertyChanged("ToolIsAvailable"); }
    }
    public string ToolName
    {
        get { return _toolName; }
        set { _toolName = value; OnPropertyChanged("ToolName"); }
    }
         }

为什么其他数据绑定功能正常但命令数据绑定不正常。我发现了这个类似的帖子 Overriding a templated Button's Command in WPF 我是否需要模板化网格控件并使用RoutedCommands?我不确定我理解为什么Silverlight将Command绑定与其他绑定区别对待,所以我怀疑我的代码中只有一个错误。

2 个答案:

答案 0 :(得分:0)

是否专门寻找datacontext工作?

Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Path=DataContext.ButtonCommand}"

答案 1 :(得分:0)

这是我的解决方案。使用与上面相同的commandviewmodel和相同的MyCommandViewModel

<Style TargetType="local:ImageButton">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="local:ImageButton">
                <Grid>
                <Image Source="{TemplateBinding Image}" />
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

数据绑定现在在用户控件

中完成
<UserControl x:Class="SilverlightApplication11.Test"
...
   >
    <UserControl.Resources>
        <Converters:BoolToVisibilityConverter x:Key="boolVisibilityConverter" />
    </UserControl.Resources>
    <Grid>
      <local:ImageButton Image="/SilverlightApplication11;component/Themes/hand.png" Command="{Binding ButtonCommand}" Visibility="{Binding FallbackValue=Visible, Path=ToolIsAvailable, Converter={StaticResource boolVisibilityConverter} }"/>
    </Grid>
</UserControl>

和背后的代码

    public Test(TestCommandViewModel vm)
    {
        InitializeComponent();

        this.Loaded += (o, e) => this.DataContext = vm;
    }