【问题标题】:Saving state of Child windows in WPF C#在 WPF C# 中保存子窗口的状态
【发布时间】:2013-07-10 18:02:40
【问题描述】:

我有一个允许用户打开选项菜单的 WPF GUI。选项菜单在新窗口中打开,并充满了复选框。当用户按下“确定”按钮时,窗口关闭。但是,它不记得打开备份时选中了哪些复选框。如何确保程序能够记住哪些框被选中,哪些没有被选中?

只是为了说明:我只需要记住在程序运行期间选中了哪些框。整个程序退出后程序不需要记住。

谢谢!

这是我在主窗口 Window1.XAML.CS 下的代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace CartToolsPrototype1
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Window1 : Window
    {
        public Window1()
        {
            InitializeComponent();
        }

        //Exit
        private void Exit_Click(object sender, RoutedEventArgs e)
        {
            System.Environment.Exit(0);
        }

        //Options
        private void Options_Click(object sender, RoutedEventArgs e)
        {
            var newWindow = new Options();
            newWindow.Show();
        }
    }
}

这是我在子 Window Options.XAML.CS 下的代码。这是基于第一个答案。我已经阅读了您发布的link,这是有道理的。我的设置文件中有条件,当用户选中我的复选框时我会更改这些条件。然后我有一个条件确定是否根据设置文件选中该框,但它似乎没有反映任何更改...

public partial class Options_Window : Window
    {
        public Options_Window()
        {
            InitializeComponent();

            //Checkbox1
            if (Properties.Settings.Default.OptionsBox1 == true)
                checkBox1.IsChecked = true;
            else
                checkBox1.IsChecked = false;
        }

        //Close Window
        private void button1_Click(object sender, RoutedEventArgs e)
        {
            this.Close();
        }

        //Ask before downloading... - CHECKED
        private void checkBox1_Checked(object sender, RoutedEventArgs e)
        {
            Properties.Settings.Default.OptionsBox1 = true;
        }

        //Ask before downloading... - UNCHECKED
        private void checkBox1_Unchecked(object sender, RoutedEventArgs e)
        {
            Properties.Settings.Default.OptionsBox1 = false;
        }

【问题讨论】:

  • 您是否考虑过将复选框绑定到 ViewModel 中的布尔属性?如果您的意思是主窗口关闭,则需要以某种方式保留这些状态;也许是一个 xml 文件。
  • 为了清楚起见,即使在重新启动整个程序后,您是否仍试图保持这种持久性?如果是这种情况,我会将其保存到您的 APPDATA 文件夹中的 XML 文件中。
  • 就在程序运行期间。如果用户再次打开选项窗口,我希望选中相同的复选框。
  • 您还可以在应用程序运行期间使用设置保存数据。
  • 我该怎么做呢?

标签: c# wpf childwindow


【解决方案1】:

您可以使用Settings在不同的Windows/控件之间共享数据,甚至在关闭/启动应用程序时保存应用程序数据。

.NET Framework 允许您创建和访问以下值 在应用程序执行会话之间持续存在。这些值是 称为设置。设置可以代表用户偏好,或有价值的 应用程序需要使用的信息。例如,您可能 创建一系列设置来存储用户对颜色的偏好 应用程序的方案。或者您可以存储连接字符串 指定您的应用程序使用的数据库。设置允许 您都可以保留对应用程序至关重要的信息 在代码之外,并创建存储偏好的配置文件 个人用户。

您可以在任何窗口中保存设置:

Properties.Settings.Default.mySetting = true;
Properties.Settings.Default.Save();

您可以在任何窗口中读取/使用设置:

this.Property = Properties.Settings.Default.mySetting;

【讨论】:

  • 嘿,这很有意义,但我的程序似乎没有注意到 settings.settings 文件中的任何变化。我已经根据您的解决方案编辑了我的帖子,请看一下,我想我已经接近了。
  • 别忘了Properties.Settings.Default.Save();
  • 它到底应该去哪里?我把它放在this.close(); 之前
  • 没关系。您是否将设置范围(属性 -> 设置中的第三列)定义为用户?
  • 是的,所有设置都属于用户范围。
【解决方案2】:

首先我们需要一个设置对象,它存储我们的属性。记得正确实现 INotifyPropertyChanged

class MySettings : INotifyPropertyChanged
{
    public bool IsSettingSet {get;set;}
}

然后在我们的设置窗口中,只需使用绑定将视图控件绑定到您的设置对象。

<Window 
    x:Class="SettingsWindow"
    ...>
    <CheckBox IsChecked="{Binding IsSettingSet}"/>
</Window>

最后,在您实际打开窗口的位置,您需要将设置对象分配给设置窗口的 DataContext。

class MainWindow
{
    public MainWindow()
    {
        InitializeComponent();
    }
    void OpenSettingsWindow()
    {
        var dlg = new SettingsWindow();
        dlg.DataContext = mGlobalSettings;
        dlg.ShowDialog();
    }

    MySettings mGlobalSettings = new MySettings();
}

现在每次打开窗口时,您的设置都会与上次一样。只要您不关闭应用程序。

【讨论】:

  • 我已经实现了代码,我得到的唯一构建错误与设置窗口的 .XAML 窗口有关。它说Checked="{Binding IsSettingSet}" is not valid. '{Binding IsSettingSet}" is not a valid event handler method name. Only instance methods on the generated or code-behind class are valid.
  • Checked 是一个事件。应该使用 IsChecked 属性来代替绑定。我已经编辑了@dowhilefor 的代码示例,使其更加完整。
  • 在我看来,这是对这个问题的最佳答案,应该被接受。
  • 是的,很抱歉,这是一个错字。
【解决方案3】:

如果只是在运行时,那就很容易了。您可以使用静态类:

public static class MyState
{
    public static bool IsChecked1 { get; set; }
}

或者类的单例实例:

public class MyState   
{
   private static MyState _instance = new MyState();

   public static MyState Instance 
   {
      get { return _instance; }
   }

   private MyState() {}

   public bool IsChecked1 { get; set; }

}

当窗口加载时,从 MyClass 的属性中获取状态。当窗口关闭时,设置 MyClass 的属性。

在 Options.xaml.cs 中:

private void Window_Loaded(object sender, RoutedEventArgs e)
{
    CheckBox1.IsChecked = MyState.IsChecked1;
}

private void Window_Closed(object sender, EventArgs e)
{
    MyState.IsChecked1 = CheckBox1.IsChecked;
}

【讨论】:

  • 如何确保代码专用于我的 Options.xaml 窗口?该代码中似乎没有任何内容会调用该窗口。
  • 这反过来 - 您的 Options.xaml 窗口在加载和关闭时将引用 MyState 中的值。
  • 好的,我已将代码实现到我的 Options.xaml.cs 窗口中,并尝试确保我考虑了所有复选框。但是,编译器说“需要一个 get 或 set 访问器”。在获取和设置之前我需要添加一些东西吗?我已经发布了我的代码,谢谢。
  • 您非常接近...您正在使用我推荐的第二种方法。只需执行 MyState.Instance.IsChecked1
  • 我将MyState.Instance 添加到我认为应该去的每个位置,但是我在任何地方都收到了错误。我已经更新了代码并写下了错误。一定有什么我错过了。谢谢。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-10-04
  • 2015-08-05
  • 1970-01-01
  • 2017-05-06
  • 2022-01-26
  • 1970-01-01
相关资源
最近更新 更多