我知道有点长但都是有联系的。
在form1 top中,我创建了这个类:
public class SettingControlPair
{
public string Key { get; set; }
public object Value { get; set; }
public Control Control { get; set; }
}
字符串
然后为configurationhelper类创建了这个列表变量和一个变量:
private List<SettingControlPair> settingControlPairs = new List<SettingControlPair>();
private ConfigurationHelper configurationHelper;
型
在form1构造函数中,我初始化了configurationhelper并调用了configurationLoading方法:
public Form1()
{
InitializeComponent();
// Initialize your module classes here
selectedImagePath = string.Empty;
imageProcessor = new ImageProcessor(selectedImagePath);
fileHandler = new FileHandler();
configurationHelper = new ConfigurationHelper(settingControlPairs);
if (textBoxLensSize.Text == string.Empty)
{
LensCropRectWidth = 10;
}
InitializeUI();
configurationHelper.LoadConfiguration();
}
型
我如何使用它来保存的示例:
private void textBoxLensSize_TextChanged(object sender, EventArgs e)
{
// Perform real-time input validation
if (int.TryParse(textBoxLensSize.Text, out int width))
{
// Valid integer input
if (width >= 10)
{
LensCropRectWidth = width; // Update the property
labelCroppedImagesCount.Focus();
configurationHelper.SaveConfiguration("LensSize", width, textBoxLensSize);
}
else
{
// Show a message if the value is less than 10
MessageBox.Show("Please enter a value greater than or equal to 10.");
textBoxLensSize.Text = 10.ToString(); // Revert to the previous value
labelCroppedImagesCount.Focus();
}
}
}
型
这是储蓄线:
configurationHelper.SaveConfiguration("LensSize", width, textBoxLensSize);
型
最后是ExclusionHelper类代码:
using System;
using System.Collections.Generic;
using System.Windows.Forms;
using static Images_Cropping.Form1;
namespace Images_Cropping
{
public class ConfigurationHelper
{
private List<SettingControlPair> settingControlPairs;
public ConfigurationHelper(List<SettingControlPair> settingControlPairs)
{
this.settingControlPairs = settingControlPairs;
}
public void LoadConfiguration()
{
foreach (var pair in settingControlPairs)
{
var value = Properties.Settings.Default[pair.Key];
if (value != null)
{
pair.Value = value;
if (pair.Control is TextBox textBox)
{
textBox.Text = value.ToString();
}
else if (pair.Control is CheckBox checkBox)
{
if (bool.TryParse(value.ToString(), out bool isChecked))
{
checkBox.Checked = isChecked;
}
}
else if (pair.Control is NumericUpDown numericUpDown)
{
if (decimal.TryParse(value.ToString(), out decimal numericValue))
{
numericUpDown.Value = numericValue;
}
}
else if (pair.Control is ComboBox comboBox)
{
comboBox.SelectedItem = value;
}
else if (pair.Control is TrackBar trackBar)
{
if (int.TryParse(value.ToString(), out int trackBarValue))
{
trackBar.Value = trackBarValue;
}
}
}
}
}
public bool SaveConfiguration(string key, object value, Control control)
{
try
{
// Save the configuration setting
Properties.Settings.Default[key] = value;
// Add the key, object value, and control to the list
settingControlPairs.Add(new SettingControlPair
{
Key = key,
Value = value,
Control = control
});
Properties.Settings.Default.Save();
return true; // Save operation succeeded
}
catch (Exception ex)
{
// Handle any exceptions related to saving the configuration
Console.WriteLine("Error saving configuration: " + ex.Message);
return false; // Save operation failed
}
}
}
}
型
问题是List settingControlPairs是空的。然后当试图在LoadConfiguration方法中循环列表时,ir什么也不做,因为List是空的。
列表为空的原因是因为我用列表初始化了form1构造函数中的configurationHelper,但列表为空:
configurationHelper = new ConfigurationHelper(settingControlPairs);
型
列表settingControlPairs为空,因此在LoadingConfiguration方法中也为空。
我怎样才能解决这个逻辑问题,列表不会是空的?
2条答案
按热度按时间pobjuy321#
当从配置中读取字符串时,它可能只是空的而不是null。因此,为了解决这个问题,在if块(位于load方法的foreach循环中)中进行以下检查之一应该会有所帮助:
字符串
或者,您可以使用:用途:
型
例如:
型
k5ifujac2#
查看您的代码,可以解释此行为的一件事是,在
InitializeComponent
中,如果在设置控件的 initial 值之前订阅了像TextBox.TextChanged
这样的事件,因为这些初始(空白)值可能会保存到配置中,然后当您加载配置时,您将什么也得不到。因此,例如,如果您有一个包含这些控件的表单,并希望在下次应用程序启动时使用相同的值填充它,那么您可以使用一种方法来解决您遇到的所有问题。
的数据
我认为你写一个JSON文件的想法(到用户的AppData文件夹)是一个很好的想法。为了安全起见,试着按照这个顺序做:
字符串
从Json文件加载配置
型
订阅更改事件
确保浏览Designer.cs文件。要么完全删除
TextChanged
或SelectionIndexChanged
等控制更改事件的现有处理程序,* 或者 * 至少浏览这些处理程序,确保它们不会对配置文件进行任何写入。这些处理程序有真实的可能导致竞争条件,从而导致您看到的问题。* 需要明确的是,将一个事件多次订阅到多个处理程序是完全可以的。如果你选择保留现有的处理程序,不要让它们写入你的SaveConfiguration
方法。*在配置已经加载之后,改为以这种方式订阅事件:
型
保存单个控件更改
当发生更改时,只需序列化字典。就像写的那样,它不是非常有效。任何文本框中的每个字符串都会写入整个文件。因此,通过等待更改解决,异步写入配置文件,甚至在应用程序关闭时执行配置文件来优化。
型