如何在无模式 WPF 应用 window 中立即将 child 数据发送到 parent

How to send child data to parent instantly in modeless WPF app window

使用 VS2019 - WPF 应用程序:我的目标是通过编辑无模式 child window 文本框来创建 parent window ListBox 的 live-update,是可能吗?

假设一个应用有一个用户列表,您可以向其中添加、删除、编辑和查看。添加和编辑通过一种模式 window 使用不同的方法工作。 View 必须是无模式的 window(所以我做了另一个 class)并且它必须实时更新 ListBox 中的用户数据。

MainWindow.cs:

public UserDlg userDlg; //modal window (it has OK/cancel buttons)
public UserView userView; //modeless window (it has only Close button)
public List<User> users = new List<User>(); // a distinct user class that also has a method .getUser() that prints user data to String.

private void View(object sender, RoutedEventArgs e) { //view button
        userView.Show();
        userView.openEdition(users[sel].fName, users[sel].lName, users[sel].eMail);// it passes ListBox selected user data to new window (works)
        }

private void UsersList_SelectionChanged(object sender, SelectionChangedEventArgs e){ //ListBox changes here

        ...if (userView != null && userView.IsVisible)
            {
                userView.openEdition(users[sel].fName, users[sel].lName, users[sel].eMail); // this updates selection in modeless window (works)
            }

UserView.cs:

public void FName1_TextChanged(object sender, TextChangedEventArgs e)
        {
            Console.WriteLine(fName1.Text + " / " + lName1.Text + " / " + eMail1.Text); //this part is to show me that every character written/removed works fine
            user.setUserData(getFirstName(), getLastName(), getMailAddress());
            string dataToPass = user.getUser(); // - here I tried with RoutedEventHandler (something I found on web) but I managed to only send preinitialized string with a button - not a real-time text changed from textbox
        }
public void openEdition(string fName, string lName, string eMail)
        {
            user = new User(fName, lName, eMail);
            fName1.Text = fName;
            lName1.Text = lName;
            eMail1.Text = eMail;
        }

我希望通过更改无模式 child 中的文本框来实时更改 parent 中的数据。有什么想法吗?

编辑:我猜我使用了 Java 的(一些错误的)知识..我想用 MainWindow window 作为参数创建 UserView .. 作为 parent,它起作用了我相信它以某种方式设法解决了我的问题? - 立即测试(我希望 10-15 分钟后返回这里。)>> UserView.cs:

MainWindow window;
public UserView(MainWindow window){ this.window = window; ... }

现在我可以简单地调用 window.usersList.Items.Add("Test");例如。

如果您想使用 "best practice" 在 WPF 上创建应用程序,则需要阅读 WPF 上的 MVVM。

但在这种情况下,您需要了解 (DataContext, ItemsSource),因为在 WPF 上,数据在大多数情况下是通过绑定和 ViewModel 移动的。

1 种方法。 - 使用绑定到通用 ViewModel。

更新

如果您的 ViewParent 绑定到 ViewModel 上的字段并且 ViewChild 绑定到 ViewModel,那么如果您更改 ViewParent 中的数据,则 ViewModel 中的数据将更改,并且 ViewChild 上的数据也会更改(因为它绑定到 ViewModel)

2 方法

绑定到另一个视图。 它像上面那样绑定,但是你创建绑定到 View 和 View 上的字段。

关键字:绑定、数据绑定、mvvm、INPC。

好links。我认为这对你有帮助 MVVM: Tutorial from start to finish?

编辑(更新):它在 wpf 上的错误位置。如果你不会使用绑定,你将 wpf 转换为 winforms,你将关闭 WPF 的 90% 功能。

您可以为此使用 WinForms,它比 wpf 更容易,并且具有您尝试做的功能(将 link 发送到父视图等)

好的,使用了我自己找到的解决方案 - 经过测试,它只工作 "good enough"。我做了什么 : MainWindow.cs:

private void View(object sender, RoutedEventArgs e)
        {
            userView = new UserView(this);
            userView.Show();
            userView.openEdition(users[sel].fName, users[sel].lName, users[sel].eMail);
        }

UserView.cs:

public UserView(MainWindow window)
        {
            this.window = window;
            InitializeComponent();
        }
public void FName1_TextChanged(object sender, TextChangedEventArgs e)
        {
            wasEdited = true;
            user.setUserData(getFirstName(), getLastName(), getMailAddress());
            string dataToPass = user.getUser();
        }
private void Close(object sender, RoutedEventArgs e) // Close button
        {
            closeEdition();
            Close();
        }
public void closeEdition()
        {
            if (wasEdited)
            {
                window.users[window.sel].fName = user.fName;
                window.users[window.sel].lName = user.lName;
                window.users[window.sel].eMail = user.eMail;
                window.usersList.Items.Insert(window.usersList.SelectedIndex, user.getUser());
                window.usersList.Items.Remove(window.usersList.SelectedItem);
            }
            window.usersList.Items.Refresh();
        }

假设任何文本框的文本已更改,则 wasEdited 布尔值为真。