用户设置读取错误的双重类型值

时间:2016-08-22 18:28:56

标签: c# wpf settings

我正在尝试创建一个用于编辑用户设置的应用程序并遇到一个奇怪的问题。我正在使用user settings编写和阅读,但它无法读取其中一个变量。

    public MainWindow()
    {
        InitializeComponent();

        input1.Value = Properties.Settings.Default.input1Setting;
        input2.Value = Properties.Settings.Default.input2Setting;
    }


    private void input1_ValueChanged(object sender, RoutedPropertyChangedEventArgs<double> e)
    {
        Properties.Settings.Default.input1Setting = Convert.ToDouble(input1.Value);
        Properties.Settings.Default.Save();
    }

    private void input2_ValueChanged(object sender, RoutedPropertyChangedEventArgs<double> e)
    {
        Properties.Settings.Default.input2Setting = Convert.ToInt16(input2.Value);
        Properties.Settings.Default.Save();
    }

    private void OnlyNumberValidation(object sender, TextCompositionEventArgs e)
    {
        Regex regex = new Regex("[^0-9]+");
        e.Handled = regex.IsMatch(e.Text);
    }

和xaml滑块

<Slider ValueChanged="input1_ValueChanged" IsSnapToTickEnabled="True" TickFrequency="0.25" Minimum="1" Maximum="50" Name="input1" PreviewTextInput="OnlyNumberValidation"/>
<Slider ValueChanged="input2_ValueChanged" IsSnapToTickEnabled="True" TickFrequency="1" Maximum="2000" Minimum="0" Name="input2" PreviewTextInput="OnlyNumberValidation"/>

在visual studio设置中,编辑器input1设置为double,input2设置为int。 Botch范围设置为用户。

问题是,只有滑块input2得到正确的值。 input1始终设置为1。

我尝试添加MessageBox.Show(Properties.Settings.Default.input1Setting.ToString()) 在启动时,它仍然显示1,但app.config中的input1的值(project / bin / debug /文件夹中的一个,local / company / project / 1.0.0 /和visual studio app.config中的一个是4)

upd1 更改4到4.0没有帮助。仍然改为1。

1 个答案:

答案 0 :(得分:0)

问题是input1的最小值为非零,并且在XAML中设置了ValueChanged。创建滑块时,默认值为零,然后将事件连接起来,然后将它们调整到最小值和最大值。

这意味着input1上的值更改为1,然后事件将触发并将值保存到设置中。这一切都发生在InitializeComponent期间,因此在您尝试在MainWindow的构造函数中分配input1.Value之前发生。

选项1

有几个选项,首先是对现有代码的更改较少。从XAML中删除ValueChanged绑定。

<Slider IsSnapToTickEnabled="True" TickFrequency="0.25" Minimum="1" Maximum="50" Name="input1" PreviewTextInput="OnlyNumberValidation"/>
<Slider IsSnapToTickEnabled="True" TickFrequency="1" Maximum="2000" Minimum="0" Name="input2" PreviewTextInput="OnlyNumberValidation"/>

在InitializeComponent之后添加它们,甚至在设置值后更好地添加它们,这样你就不会重新保存现有值:

  input1.ValueChanged += input1_ValueChanged;
  input2.ValueChanged += input2_ValueChanged;

选项2

但根据您的观察方式,可能更好的选择是将控件直接绑定到设置,然后仅在关闭表单时调用save。

将其放在app.xaml文件中,确保您可以使用“设置”键。您需要将命名空间添加到Application节点属性, xmlns:properties =&#34; clr-namespace:WpfApplication1.Properties&#34; 和Inside Application.Resourses节点添加属性节点。下面是app.xaml的外观示例(使用通用名称空间):

<Application x:Class="WpfApplication1.App"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:local="clr-namespace:WpfApplication1"
             xmlns:properties="clr-namespace:WpfApplication1.Properties"
             StartupUri="MainWindow.xaml">
  <Application.Resources>
    <properties:Settings x:Key="Settings" />
  </Application.Resources>
</Application>

现在返回MainWindow.xaml,删除ValueChanged(如上例所示)并添加一个Value属性,将其绑定到设置值:

<Slider IsSnapToTickEnabled="True" TickFrequency="0.25" Minimum="1" Maximum="50" Name="input1" Value="{Binding Source={StaticResource Settings}, Path=Default.input1Setting}" PreviewTextInput="OnlyNumberValidation"/>
<Slider IsSnapToTickEnabled="True" TickFrequency="1" Maximum="2000" Minimum="0" Name="input2" Value="{Binding Source={StaticResource Settings}, Path=Default.input2Setting}" PreviewTextInput="OnlyNumberValidation"/>

在MainWindow.xaml.cs文件中,您将其修改为如下所示:

public MainWindow()
{
  InitializeComponent();
  Closing += MainWindow_Closing;
}

private void MainWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
  Properties.Settings.Default.Save();
}

private void OnlyNumberValidation(object sender, TextCompositionEventArgs e)
{
  Regex regex = new Regex("[^0-9]+");
  e.Handled = regex.IsMatch(e.Text);
}

当然,如果您希望在XAML中连接事件,则可以跳过Closing + = MainWindow_Closing;在MainWindow.xaml.cs文件中,将这个,Closing =&#34; MainWindow_Closing&#34;,属性添加到MainWindow.xaml的Window节点。

我喜欢选项2,因为它只保存一次,即使Settings.Default值始终基于滑块值可用,您只需要保存它以便下次启动时可用。

尝试这些,看看你更喜欢哪一个。