C# InotifyProperty已更改为2个窗口

C# InotifyProperty已更改为2个窗口,c#,wpf,xaml,C#,Wpf,Xaml,我有一个简单的WPF应用程序,有两个窗口。 当用户在子窗口中输入内容时,我试图更新主窗口上的文本块和复选框 我设置了两个变量在窗口之间传递值 Properties.Settings.Default.strText Properties.Settings.Default.isChecked MainWindow.xaml <Window x:Class="PropertyChangedExample.MainWindow" xmlns="http://schemas.mic

我有一个简单的WPF应用程序,有两个窗口。 当用户在子窗口中输入内容时,我试图更新主窗口上的文本块和复选框

我设置了两个变量在窗口之间传递值

Properties.Settings.Default.strText
Properties.Settings.Default.isChecked
MainWindow.xaml

<Window x:Class="PropertyChangedExample.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:PropertyChangedExample"
        mc:Ignorable="d"
        Title="MainWindow" Height="400" Width="400"
        Focusable="False">
    <Grid>
        <TextBlock x:Name="TxtBlock" Text="{Binding TxtBinding}" Width="200" Height="30" Margin="0,100,0,0"/>
        <CheckBox IsChecked="{Binding IsChecked}" Width="25" Height="25" />
    </Grid>
</Window>
<Window x:Class="PropertyChangedExample.SubWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:PropertyChangedExample"
        mc:Ignorable="d"
        Title="SubWindow" Height="100" Width="250">
    <Grid>
        <TextBox KeyUp="Window_KeyUp" x:Name="TxtBox" Width="200" Height="30" />
    </Grid>
</Window>
MainWindow.xaml.cs

using System.ComponentModel;
using System.Windows;

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

            SubWindow subWindow = new SubWindow();
            subWindow.Show();

            DataContext = new DataContextExample();
        }
    }

    public class DataContextExample : INotifyPropertyChanged
    {
        public string TxtBinding
        {
            get { return Properties.Settings.Default.strText; }
            set
            {
                Properties.Settings.Default.strText = value;
                OnPropertyChanged(nameof(TxtBinding));
            }
        }

        public bool IsChecked
        {
            get { return Properties.Settings.Default.isChecked; }
            set
            {
                Properties.Settings.Default.isChecked = value;
                OnPropertyChanged(nameof(IsChecked));
            }
        }

        private void OnPropertyChanged(string propertyName)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }

        public event PropertyChangedEventHandler PropertyChanged;
    }
}
using System.Windows;
using System.Windows.Input;

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

        private void Window_KeyUp(object sender, KeyEventArgs e)
        {
            if (e.Key == Key.Enter)
            {
                Properties.Settings.Default.strText = TxtBox.Text;
            }
            else if (e.Key == Key.LeftCtrl)
            {
                Properties.Settings.Default.isChecked = true;
            }
            else if (e.Key == Key.LeftShift)
            {
                Properties.Settings.Default.isChecked = false;
            }

        }
    }
}
SubWindow.xaml

<Window x:Class="PropertyChangedExample.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:PropertyChangedExample"
        mc:Ignorable="d"
        Title="MainWindow" Height="400" Width="400"
        Focusable="False">
    <Grid>
        <TextBlock x:Name="TxtBlock" Text="{Binding TxtBinding}" Width="200" Height="30" Margin="0,100,0,0"/>
        <CheckBox IsChecked="{Binding IsChecked}" Width="25" Height="25" />
    </Grid>
</Window>
<Window x:Class="PropertyChangedExample.SubWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:PropertyChangedExample"
        mc:Ignorable="d"
        Title="SubWindow" Height="100" Width="250">
    <Grid>
        <TextBox KeyUp="Window_KeyUp" x:Name="TxtBox" Width="200" Height="30" />
    </Grid>
</Window>
SubWindow.xaml.cs

using System.ComponentModel;
using System.Windows;

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

            SubWindow subWindow = new SubWindow();
            subWindow.Show();

            DataContext = new DataContextExample();
        }
    }

    public class DataContextExample : INotifyPropertyChanged
    {
        public string TxtBinding
        {
            get { return Properties.Settings.Default.strText; }
            set
            {
                Properties.Settings.Default.strText = value;
                OnPropertyChanged(nameof(TxtBinding));
            }
        }

        public bool IsChecked
        {
            get { return Properties.Settings.Default.isChecked; }
            set
            {
                Properties.Settings.Default.isChecked = value;
                OnPropertyChanged(nameof(IsChecked));
            }
        }

        private void OnPropertyChanged(string propertyName)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }

        public event PropertyChangedEventHandler PropertyChanged;
    }
}
using System.Windows;
using System.Windows.Input;

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

        private void Window_KeyUp(object sender, KeyEventArgs e)
        {
            if (e.Key == Key.Enter)
            {
                Properties.Settings.Default.strText = TxtBox.Text;
            }
            else if (e.Key == Key.LeftCtrl)
            {
                Properties.Settings.Default.isChecked = true;
            }
            else if (e.Key == Key.LeftShift)
            {
                Properties.Settings.Default.isChecked = false;
            }

        }
    }
}

当用户在子窗口的文本框中输入任何内容时,主窗口上的文本块应该更新。此外,如果用户按左ctrl键或shift键,则应选中和取消选中该复选框。到目前为止,什么也没有发生。这里缺少什么?

您需要将DataContext传递到第二个窗口,否则它无法知道主窗口中使用的数据。这可以在第二个窗口的构造函数中完成

DataContextExample myContext;
public SubWindow(DataContextExample context)
{
    myContext = context;
    DataContext = myContext;
    InitializeComponent();
}
然后从主窗口像这样调用它

另外,在第二个窗口中,您直接更改Properties.Setting.Default值,但需要更改DataContext值


您需要将DataContext传递到第二个窗口,否则它无法知道主窗口中使用的数据。这可以在第二个窗口的构造函数中完成

DataContextExample myContext;
public SubWindow(DataContextExample context)
{
    myContext = context;
    DataContext = myContext;
    InitializeComponent();
}
然后从主窗口像这样调用它

另外,在第二个窗口中,您直接更改Properties.Setting.Default值,但需要更改DataContext值


对于这种情况,我能看到的最好的解决方案是messagin或所谓的发布者/订阅者模式,在您的子窗口中创建一个事件并将其发布到任何lessner订阅者。下面是一个简单的例子:

对于这种情况,我能看到的最佳解决方案是messagin或所谓的发布者/订阅者模式,在您的子窗口中创建一个事件,并将其发布到其他订阅者。下面是一个简单的例子:

我按照您的建议更改了代码,但仍然一无所获……您不是在第二个窗口中更新datacontext,而是直接更新属性。查看我对第二个窗口构造函数和键启动事件的编辑;对于myContext.TxtBinding=TxtBox.Text;,但它现在工作得很好。多谢各位@TronaldI按照您的建议更改了代码,但我仍然一无所获……您不是在第二个窗口中更新datacontext,而是直接更新属性。查看我对第二个窗口构造函数和键启动事件的编辑;对于myContext.TxtBinding=TxtBox.Text;,但它现在工作得很好。多谢各位@请看我编辑过的答案。由于某些原因,我现在无法标记您。请参阅我编辑的答案。由于某些原因,我现在不能给你贴标签。