使用c#与另一个人交流或访问父母

我似乎在一个简单的问题上遇到了很多麻烦。 是的,我是c#的新手,但是我试着去学习我能做什么而不跳过问题。 在这种情况下,我只是觉得我没有问正确的问题。

没有代码示例在这里会有所帮助,因为我在谈论基础知识(实现)。 我还没有真正编码任何东西,只需使用可视化构建器来创建我的窗体和菜单。

我遇到的问题是当我选择一个菜单项(称之为:设置路径)时,我希望我的主表单上的列表视图从我在form2上点击确定时选择的路径加载。 所以我做了一个简单的查找文件夹对话框,我将新路径存储在form2的文本框中。 当我在那个form2上点击确定时,我希望我的listview form1能够填充。 我知道怎么做所有这些,但我不能为我的生活从form2访问form1,反之亦然。

我尝试了一个回调函数但我得到的非静态变量无法引用…错误,因为我的form1是静态的,所以我不能创建任何非静态方法。 我查看了EventArgs,但对于这样一个常见请求来说,这似乎是一种过度杀戮。

那么通常的做法是什么?

罗伯特的回答是正确的,只要访问另一种forms的成员。 但是,通常您应该将应用程序的状态(称为“模型”) 用户界面的状态分开存储 (称之为“视图”)。 当您的应用程序超出一两个交互时,这变得非常重要。 关于如何将两者结合在一起有几种哲学或模式(例如谷歌“模型 – 视图 – 控制器”(MVC)和“模型 – 视图 – 视图模型”(MVVM)),如果你真的想要正确地做到这一点我会建议学习这些。 我更喜欢MVVM方法,即使它是在考虑WPF应用程序的情况下设计的,您也可以使用Windows Forms轻松完成。

在.NET中,您应该用来实现viewmodel和视图之间连接的基本代码是一个名为INotifyPropertyChanged的接口。 您创建了一个实现此接口的类,并在属性更改时发送通知,因此例如对于您的路径属性,您将创建此类:

class ViewModel : INotifyPropertyChanged { private string path; public string Path { get { return path; } set { if (value != path) { path = value; NotifyPropertyChanged(); } } } // This event gets triggered whenever a property changes. public event PropertyChangedEventHandler PropertyChanged; // This will cause the event to actually be triggered. It automatically determines the name of the property that triggered it using the [CallerMemberName] attribute - just a bit of .NET 4.5 sweetness. :) private void NotifyPropertyChanged([CallerMemberName] String propertyName = "") { if (PropertyChanged != null) { PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); } } } 

这可能看起来很多工作,但现在在您的form1中,您可以创建一个新的“ViewModel”实例,订阅该事件,然后将该实例传递给form2。 只要用户选择不同的路径,form2就会更新viewmodel实例上的Path属性。

因此,Form1需要靠近顶部的代码:

 private ViewModel viewmodel = new ViewModel(); 

这是在Form1构造函数中:

 viewmodel.PropertyChanged += new EventHandler(OnPathChanged); 

当你创建/ show form2时:

 var form2 = new Form2(viewmodel); // Note, the viewmodel instance is being passed to the form2 constructor form2.Show(); 

然后,form2构造函数将自己的引用存储到“viewmodel”实例,并在用户更改路径时设置Path属性。

 private ViewModel viewmodel; public Form2(ViewModel viewmodel) { this.viewmodel = viewmodel; ... // Other stuff to set up your controls etc. goes here } private void PathChanged(object sender, EventArgs e) // This may be named differently in your code; it's the event handler that gets called when the path changes { // This will automatically notify the event handler in Form1! It's super-elegant and flexible. this.viewmodel.Path = txtPath.Text; // Assuming you have a textbox called txtPath } 

最后是Form1中的事件处理程序:

 private void OnPathChanged(object sender, EventArgs e) { var newPath = viewmodel.Path; // Get the updated path back from the viewmodel //TODO: Whatever you want to do when the path changes. } 

这里是使用Windows Forms的一个非常好的MVVM简介的链接,它使用了两个表单,就像你在你的例子中一样。 Windows窗体应用程序的MVVM(Model-View-ViewModel)模式,使用C#

如果您需要访问其他表单上的内容,只需在第一个表单中保留对它的引用,如下所示:

 form2 = new Form2(); form2.Show(); form2.WhateverYouWantToAccess 

也就是说,如果您只想从用户那里获取文件路径,则需要使用OpenFileDialog类。

 private void button1_Click(object sender, System.EventArgs e) { Stream myStream = null; OpenFileDialog openFileDialog1 = new OpenFileDialog(); openFileDialog1.InitialDirectory = "c:\\" ; openFileDialog1.Filter = "txt files (*.txt)|*.txt|All files (*.*)|*.*" ; openFileDialog1.FilterIndex = 2 ; openFileDialog1.RestoreDirectory = true ; if(openFileDialog1.ShowDialog() == DialogResult.OK) { try { if ((myStream = openFileDialog1.OpenFile()) != null) { using (myStream) { // Insert code to read the stream here. } } } catch (Exception ex) { MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message); } } }