用户设置读取错误的双精度值

本文关键字:双精度 取错误 设置 读取 用户 | 更新日期: 2023-09-27 18:03:32

我正在尝试制作一个用于编辑用户设置的应用程序,并遇到一个奇怪的问题。我正在使用用户设置读写,它不能读取其中一个变量。

    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设置编辑器inputt1设置为double, input2设置为int。两个作用域都设置为user。

问题是,只有滑块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没有帮助。

用户设置读取错误的双精度值

问题是input1的最小值非零,而valuechange在XAML中被设置。当滑块被创建时,它们的默认值为0,然后事件被连接起来,然后它们被调整为最小和最大。

这意味着input1的值变为1,然后事件触发并将值保存到设置中。这一切都发生在InitializeComponent期间,因此发生在您尝试分配input1之前。

选项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文件中有Settings键可用。您需要将名称空间添加到应用程序节点属性中,xmlns:properties="clr-namespace:WpfApplication1 "。属性"和应用程序内部。资源节点添加属性节点。下面是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>

现在回到主窗口。xaml,删除ValueChanged(如上面的例子),并添加一个Value属性将其绑定到settings 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="MainWindow_Closing"属性到MainWindow。

我喜欢选项2,因为它只保存一次,即使设置。默认值总是基于滑块的值,你只需要保存它,以便下次启动时可用。

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