【问题标题】:Binding to a property within a static class instance绑定到静态类实例中的属性
【发布时间】:2013-08-25 00:28:14
【问题描述】:

我正在努力实现的目标

我有一个 WPF 应用程序(它只是用于测试),我想将标签的文本(内容)绑定到某处的属性。这个想法是当用户选择不同的语言时,这个属性值将会改变。当属性更改时,我希望标签文本使用新值进行更新。

我的尝试

我尝试为标签值创建一个具有静态属性的静态类。例如:

public static class Language
{
    public static string Name = "Name";
}

然后我可以使用 XAML 将此值绑定到我的标签,如下所示:

Content="{Binding Source={x:Static lang:Language.Name}}"

这对于显示“名称”的初始值效果很好。问题是,当Name 属性更改时,标签值不会更改。

所以,回到绘图板(谷歌)。然后我找到了this answer,这听起来和我需要的完全一样。所以这是我的新尝试:

public class Language
{
    public static Language Instance { get; private set; }
    static Language() { Instance = new Language(); }
    private Language() { }

    private string name = "Name";
    public string Name { get { return name; } set { name = value; } }
}

我的绑定改变了它:

Content="{Binding Source={x:Static lang:Language.Instance}, Path=Name}"

这仍然会导致同样的问题。

问题

我在这里缺少什么?如何在值更改时更新标签?

【问题讨论】:

  • 绑定引擎使用属性。所有代码示例都包含字段名称,而不是属性

标签: c# wpf binding


【解决方案1】:

这根本不是一个属性。试试:

public class Language
{
    public static Language Instance { get; private set; }
    static Language() { Instance = new Language(); }
    private Language() { Name = "Name"; }

    public string Name {get;private set;}
}

或带有更改通知:

public class Language : INotifyPropertyChanged
{
    public static Language Instance { get; private set; }
    static Language() { Instance = new Language(); }
    private Language() { }

    private string name = "Name";
    public string Name
    {
        get { return name; }
        set { SetValue(ref name, value);}
    }
    protected void SetValue<T>(ref T field, T value,
        [CallerMemberName]string propertyName=null)
    {
        if (!EqualityComparer<T>.Default.Equals(field, value))
        {
            field = value;
            OnPropertyChanged(propertyName);
        }
    }
    protected virtual void OnPropertyChanged(
        [CallerMemberName]string propertyName=null)
    {
        var handler = PropertyChanged;
        if (handler != null)
            handler(this, new PropertyChangedEventArgs(propertyName));
    }
    public event PropertyChangedEventHandler PropertyChanged;
}

【讨论】:

  • 好的,我最初只是通过... Name {get;set;} 尝试了这个,正如预期的那样仍然是空白的,但是当我通过“更改语言”选项设置它时,我希望它会改变。通过给它一个默认值(正如你刚才建议的那样)进行测试最初确实有效,但我仍然遇到与原始尝试一样的问题,如何在属性更改时更新标签?
  • @musefan 做你需要实现INotifyPropertyChanged
  • 对不起,我现在改变了我的问题。我的问题具有误导性,因为我在属性尝试中编码错误。我的问题最终是关于财产的变化。如果我有很多不同的标签属性,我对 INotifyPropertyChanged 的​​研究似乎有点让人头疼。所以我一直在寻找一种更简单的方法,这让我达到了现在的水平
  • @musefan 如果你有很多属性,有一个巧妙的技巧 - 我会编辑它
  • 搞定了。我不确定CallerMemberName 是什么(我什至不知道您可以将属性放在参数上),但是没有它似乎可以正常工作……您包含它有什么特别的原因吗?如果没有它,我以后会遇到问题吗?
猜你喜欢
  • 2014-09-10
  • 2014-01-29
  • 1970-01-01
  • 2012-10-15
  • 2013-08-17
  • 1970-01-01
  • 1970-01-01
  • 2013-05-15
  • 2012-06-21
相关资源
最近更新 更多