2017-01-10 28 views
0

我一直在努力一段时间,如何在WinRT/UWP应用程序中与绑定级别上的设置进行最佳“交互”。我一直在寻找有关这方面的最佳做法,但我没有找到明确的答案。到目前为止,我在我的应用程序中完成的工作如下:绑定最佳实践的应用程序设置

  1. 定义一个实现INotifyPropertyChanged的BindableBase。
  2. 创建从BindableBase继承,看起来有点像这样一个的AppSettings类:

    public class AppSettings : BindableBase 
    { 
        ApplicationDataContainer localSettings = ApplicationData.Current.LocalSettings; 
    
        public string MySetting 
        { 
         get 
         { 
          if (!localSettings.Values.ContainsKey("MySetting")) 
           localSettings.Values["MySetting"] = "Some default value"; 
    
          return localSettings.Values["MySetting"].ToString(); 
         } 
         set 
         { 
          localSettings.Values["MySetting"] = value; 
          RaisePropertyChanged(); 
         } 
        } 
    } 
    
  3. 定义视图模型具有的AppSettings属性:

    public class SettingsViewModel 
    { 
        public AppSettings Settings { get; set; } = new AppSettings(); 
    } 
    
  4. 绑定到设置属性在视图中:

    <TextBlock Text="{Binding Settings.MySetting, Mode=TwoWay}"> 
    

我以前见过并使用过具有设置服务的实现,但这些应用程序不需要设置更改即可立即生效。所以我基本上要问的是:如果设置的更改应该立即生效,上述实现是绑定到设置的好方法吗?如果不是,你推荐什么?

+1

相关:[最佳实践僵尸](http://meta.stackexchange.com/a/142354/1228)此外,可以使用你的意思*去实际的说明*。你的意思是立即保存吗?我知道在WPF中,框架中没有任何东西可以为你做任何事情。你似乎已经有了应该工作的东西(ish?)。如果它没有做你所需要的,那就改变它的代码。 – Will

+0

我认为你的实施是好的,并按照你的情况工作。如果您需要立即应用每个设置(而不是单击保存按钮),则必须在属性集中分配新值(如您所用)。任何订阅的监听器都将在此时触发属性集中的更改。 –

+0

@我并不是在寻找最佳实践,但是如果我的实施出现问题,因为我觉得它在性能方面效率不高。 – Abdousamad

回答

1

这在一般情况下似乎很好。我会改变的唯一事情是只提高了通知,如果数据实际上改变:

set 
{ 
    if (MySetting != value) 
    { 
     localSettings.Values["MySetting"] = value; 
     RaisePropertyChanged(); 
    } 
} 

这将避免不必要地提高的通知。
根据读取值的频率,您可能希望将自己的设置值保存在私有字段中,而不是每次都从容器中读取它们。

+0

将值存储在专用字段中,并且仅在更改了ApplicationData时才更改ApplicationData,但实际上性能可能会更好一些。至于我的RaisePropertyChanged实现,如果我没有记错,它已经检查一个设置是否已经改变,但我会检查确认。 – Abdousamad

0

我非常喜欢这篇文章,所以我想出了一些更优雅的东西,以避免复制和粘贴属性名称(键)很多次。我用的是以下几点:

public class SettingsViewModel : BindableBase 
{ 
    public string MyProperty 
    { 
     get 
     { 
      return Get("MyProperty", "SomeDefaultValue"); 
     } 
     set 
     { 
      Set("MyProperty", value); 
     } 
    } 

    public T Get<T>(string PropertyName, T DefaultValue) 
    { 
     //If setting doesn't exist, create it. 
     if (!App.Settings.ContainsKey(PropertyName)) 
      App.Settings[PropertyName] = DefaultValue; 

     return (T)App.Settings[PropertyName]; 
    } 

    public void Set<T>(string PropertyName, T Value) 
    { 
     //If setting doesn't exist or the value is different, create the setting or set new value, respectively. 
     if (!App.Settings.ContainsKey(PropertyName) || !((T)App.Settings[PropertyName]).Equals(Value)) 
     { 
      App.Settings[PropertyName] = Value; 
      OnPropertyChanged(PropertyName); 
     } 
    } 
} 

假设你App类定义了以下属性:

public static IPropertySet Settings 
{ 
    get 
    { 
     return Windows.Storage.ApplicationData.Current.LocalSettings.Values; 
    } 
} 

后者比写作更方便,

ApplicationData.Current.LocalSettings.Values 

而且仍然可以全局访问。

相关问题