我一直在尝试让这个小小的IRC程序正常工作但由于某种原因我遇到了VS和交叉线程的问题。我不确定我是不是以正确的方式做什么。以下是导致问题的部分。
主线程:
public partial class MainUI : Form
{
private static IRC irc = new IRC();
public MainUI()
{
InitializeComponent();
}
public static void StartIRC()
{
irc.Start();
}
}
IRC主题:
class IRC
{
private Thread ircThread;
private bool _running = true;
private NetworkStream stream;
private StreamWriter writer;
private StreamReader reader;
private TcpClient irc;
public IRC(){
ircThread = new Thread(new ThreadStart(Run));
ircThread.IsBackground = true;
}
public void Run(){
while (_running) {
parseInStream(reader.ReadLine());
}
}
public void Start()
{
ircThread.Start();
}
private void parseInStream(String inText)
{
String[] text = inText.Split(' ');
String name;
String message;
if (text[1].Equals("PRIVMSG")) {
name = capsFirstChar(getUser(inText));
message = inText.Substring(inText.IndexOf(":", 1) + 1);
sendToChatBox(capsFirstChar(name) + ": " + message, Color.Black);
}
else if (text[1].Equals("JOIN")) {
name = getUser(inText);
sendToChatBox(capsFirstChar(name) + " has joined the channel.", Color.LimeGreen);
}
else if (text[1].Equals("PART")) {
name = getUser(inText);
sendToChatBox(capsFirstChar(name) + " has left the channel.", Color.Red);
}
}
public void sendToChatBox(String text, Color color)
{
//Trying to send the text to the chatbox on the MainUI
//Works if the MainUI.Designer.cs file has it set to static
if (MainUI.txtMainChat.InvokeRequired) {
MainUI.txtMainChat.Invoke((MethodInvoker)delegate() {
sendToChatBox(text, color);
});
}
else {
MainUI.txtMainChat.SelectionColor = color;
MainUI.txtMainChat.AppendText(text);
}
}
private String getUser(String msg)
{
String[] split = msg.Split('!');
user = split[0].Substring(1);
return capsFirstChar(user);
}
private String capsFirstChar(String text)
{
return char.ToUpper(text[0]) + text.Substring(1).ToLower();
}
}
我能够让它工作的唯一方法是,如果我输入MainUI.Designer.cs文件并将文本框更改为静态,然后将此内容从this.txtMainChat更改为MainUI.txtMainChat。
我的主要问题是,当我在视觉方面进行任何更改时,所有标记为静态的内容或名为MainUI的内容都将被删除。我正在试图弄清楚我需要做些什么来防止这种情况发生。我是以正确的方式做到的,还是有更好的方法?我尝试使用后台工作程序,但出于某种原因,它使用了大量处理能力以这种方式工作。
我环顾网络,似乎无法找出与我的设置有什么关系。我看到人们从主线程中调用一个线程,然后将事物从主线程发送到它调用的线程,但不是相反。没有任何其他内容写入文本框,因此两个线程同时使用它不会有问题。
答案 0 :(得分:1)
每次在设计器中更改UI时,都会重建您的设计器文件。
您需要将您的MainUi传递给您的IRC类,或者使用接口(最佳选项)将其抽象化。
public interface IMainUI
{
void AddText(string text, Color color);
void UiThread(Action code);
}
public class MainUI : IMainUI
{
// Whatever else
public void AddText(string text, Color color)
{
UiThread( () =>
{
// Same code that was in your Irc.SendToChatBox method.
});
}
public void UiThread(Action code)
{
if (InvokeRequired)
{
BeginInvoke(code);
return;
}
code.Invoke();
}
}
public class IRC
{
IMainUI _mainUi;
//Other properties, and fields
public IRC(IMainUI mainUi)
{
this._mainUi = mainUi;
// Other constructor stuff.
}
// Other logic and methods
}
答案 1 :(得分:1)
在我的主要UI线程中,我传入了#34;这个"所以我可以从我的IRC类中引用主窗口。 MainUI.txtMainChat
irc = new IRC(this);
然后在我的IRC课程中
MainUI main;
public IRC(MainUI main){
this.main = main;
ircThread = new Thread(new ThreadStart(Run));
ircThread.IsBackground = true;
}
然后我能够改变
//MainUI.txtMainChat to
main.txtMainChat
像卡梅隆说的那样,虽然我知道我被告知这不是最好的办法让我开始。