繁体   English   中英

WPF自定义控件的依赖项属性意外影响其他控件

[英]WPF Custom Control's Dependency Property unintentionally affecting other controls

我正在制作一个应该记录鼠标位置的窗口。 我创建了一个用户控件,该控件应该显示该位置标签的当前坐标,并允许用户更改它们。
在此处输入图片说明

它的工作原理很不错,除了更新时它们都会改变。

认为这与依赖项属性是静态注册的事实有关。 它们必须是依赖项属性,因为我需要能够将它们从xaml绑定到我的模型。

如何使用户控件彼此独立?

<UserControl x:Class="SapFormFiller.SerializableMouseEditorControl"
         ...
         DataContext="{Binding RelativeSource={RelativeSource Self}}">
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="60*"/>
        ...
        <ColumnDefinition Width="20*"/>            
    </Grid.ColumnDefinitions>
    <Label Content="{Binding LabelText}"></Label>
    <Label Grid.Column="1" Content="{Binding SerializableMouseKeyboardEventArgs.X}"/>
    <Label Grid.Column="2" Content="{Binding SerializableMouseKeyboardEventArgs.Y}"/>
    <Button Grid.Column="3" Margin="0,0,0.4,0" Click="ButtonBase_OnClick">Edit</Button>
</Grid>

CS:

public partial class SerializableMouseEditorControl : UserControl
{
    public static DependencyProperty LabelTextProperty = DependencyProperty.Register(
        "LabelText", typeof (string), typeof (SerializableMouseEditorControl), new PropertyMetadata(default(string)));

    public string LabelText
    {
        get { return (string) GetValue(LabelTextProperty); }
        set { SetValue(LabelTextProperty, value); }
    }
    public static DependencyProperty SerializableMouseKeyboardEventArgsProperty = DependencyProperty.Register(
        "SerializableMouseKeyboardEventArgs", typeof (SerializableMouseKeyboardEventArgs), typeof (SerializableMouseEditorControl), new PropertyMetadata(new SerializableMouseKeyboardEventArgs()));

    public SerializableMouseKeyboardEventArgs SerializableMouseKeyboardEventArgs
    {
        get { return (SerializableMouseKeyboardEventArgs) GetValue(SerializableMouseKeyboardEventArgsProperty); }
        set { SetValue(SerializableMouseKeyboardEventArgsProperty, value); }
    }
    public SerializableMouseEditorControl()
    {
        InitializeComponent();
        SerializableMouseKeyboardEventArgs = new SerializableMouseKeyboardEventArgs();
    }

    private void ButtonBase_OnClick(object sender, RoutedEventArgs e)
    {
        SerializableMouseKeyboardEventArgs.Update();
    }
}

SerializableMouseKeyboardEventArgs:

public class SerializableMouseKeyboardEventArgs : INotifyPropertyChanged
{
    public int X
    {
        get { return _x; }
        set
        {
            _x = value; 
            OnPropertyChanged("X");
        }
    }

    public int Y
    {
        get { return _y; }
        set
        {
            _y = value;
            OnPropertyChanged("Y");

        }
    }
    ...
    IKeyboardMouseEvents gkme;        
    private int _x = 0;
    private int _y=0;

    public override string ToString(){...}
    public SerializableMouseKeyboardEventArgs()
    {
        gkme = Hook.GlobalEvents();
    }
    public void Update()
    {
        IsEditing = true;
        gkme.MouseClick += Gkme_MouseClick;
    }

    private void Gkme_MouseClick(object sender, MouseEventArgs e)
    {
        if(e.Button==MouseButtons.Left)
        {
            this.X = e.X;
            this.Y = e.Y;
        }
        else if (e.Button == MouseButtons.Right)
        {
            gkme.MouseClick -= Gkme_MouseClick;
            IsEditing = false;
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    [NotifyPropertyChangedInvocator]
    protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}

这条线

new PropertyMetadata(new SerializableMouseKeyboardEventArgs()));

看起来可能会导致您出现问题。 我当时处于使用new关键字声明默认值的情况,导致UserControl的一个实例与另一个实例共享该属性值。

尝试在构造函数中初始化任何此类属性,它可能会起作用。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM