我正在为学校项目编写聊天应用程序。我有一种形式是“联系人”表单,我从中打开了不同的SingleDialogue表单(它们是1对1的聊天记录)。我想这样做,当我关闭Contacts表单时,它会关闭我打开的所有SingleDialogue表单。
为此,我这样做,以便Contacts_FormClosing事件触发客户端对象中的Disconnected事件,并在Contacts表单中创建了一个方法:
private void On_ImDisconnected(object sender, EventArgs e)
{
foreach (SingleDialogue sd in singleChats)
sd.Close();
}
singleChats是从“联系人”表单打开的SingleDialogue表单列表的名称。每次我打开另一个SingleDialogue时,都会将其添加到singleChats中。 在构造函数中,我将它订阅到客户端对象中的Disconnected事件:
im.Disconnected += new EventHandler(On_ImDisconnected);
到目前为止,当我在客户端对象On_ImDisconnected中触发Disconnected事件时,会触发并关闭所有SingleDialogues,对吗?
但我得到一个例外,说#34;跨线程操作无效:Control' SingleDialogue'从在"上创建的线程以外的线程访问。
好吧,然后我改变了On_ImDisconnected:
private void On_ImDisconnected(object sender, EventArgs e)
{
this.BeginInvoke(new MethodInvoker(delegate
{
foreach (SingleDialogue sd in singleChats)
sd.Close();
}));
}
但现在没有任何反应。你能帮助我解决这个问题吗?
编辑:
清单声明:
List<SingleDialogue> singleChats = new List<SingleDialogue>();
添加新成员:
private void chatButton_Click(object sender, EventArgs e)
{
SingleDialogue sd = new SingleDialogue(im, chatTextBox.Text);
singleChats.Add(sd);
chatTextBox.Text = "";
sd.Show();
}
答案 0 :(得分:1)
我要说完全跳过列表。在#include <vector>
#include <string>
#include <iostream>
namespace DataWorld {
using DataType = int;
// It is a data. Holder struct will hold this data. But holder has it's id
struct Data {
DataType storage[5];
void Show() {
std::cout << "my_holder_index" << " "; // here the data has to know the id of the holder that holds this data
for(auto elem : storage) {
std::cout << elem << " ";
}
std::cout << std::endl;
}
};
struct DataHolder {
Data my_data;
std::string my_holder_index;
DataHolder(Data my_data, std::string my_holder_index)
: my_data(my_data)
, my_holder_index(my_holder_index) {}
void Show() {
// Do not show holder id here! It is the data that has to know it.
my_data.Show();
}
};
}
int main() {
using namespace DataWorld;
DataHolder dhs[] = {
{ {1, 2, 3, 4, 5}, "nat" },
{ {1, 3, 5, 7, 9}, "even" },
{ {2, 4, 6, 8, 10}, "odd" }
};
for(auto dh : dhs) {
dh.Show();
}
}
表单的构造函数中,您可以在传递的父级断开连接时添加处理程序,然后从其自身内部关闭SingleDialogue
。
因此,如果我不得不猜测构造函数的样子,你可以这样做:
SingleDialogue
请注意,我不是本地C#开发人员,所以如果我做错了请告诉我。 :)
答案 1 :(得分:0)
据我了解情景,您在联系表单中保留了一个表单列表,并希望将其关闭。
当您将每个表单订阅到Disconnected
事件时,我认为您的方法是错误的。为什么不从它内部关闭事件触发器上的表单?
您只需要在每个SingleDialogue
实例中使用此代码:
//subscribe to event handler, most probably in constructor
im.Disconnected += new EventHandler(On_ImDisconnected);
//close on event fire
private void On_ImDisconnected(object sender, EventArgs e)
{
this.Close();
}
您无需浏览list
并关闭父表单中的表单。
如果我的问题出错了,请纠正我。