C#线程安全的RichTextBox事件日志的方法? [英] C#: Thread safe richtextbox event logging method?

查看:396
本文介绍了C#线程安全的RichTextBox事件日志的方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有,是为了显示在表单中的一个RichTextBox输出的方法。

I have a method that is meant to display output on a RichTextBox in a form.

    public void LogTextEvent(RichTextBox TextEventLog, Color TextColor, string EventText)
    {
        string nDateTime = DateTime.Now.ToString("hh:mm:ss tt") + " - ";

        // color text.
        TextEventLog.SelectionStart = TextEventLog.Text.Length;
        TextEventLog.SelectionColor = TextColor;

        // newline if first line, append if else.
        if (TextEventLog.Lines.Length == 0)
        {
            TextEventLog.AppendText(nDateTime + EventText);
            TextEventLog.ScrollToCaret();
            TextEventLog.AppendText(System.Environment.NewLine);
        }
        else
        {
            TextEventLog.AppendText(nDateTime + EventText + System.Environment.NewLine);
            TextEventLog.ScrollToCaret();
        }
    }

当我从另一个调用LogEventText()问题出现方法的线程中运行:

The problem arises when I call LogEventText() from another method running inside a thread:

            Thread thListening = new Thread(new ThreadStart(StartListening));
            thListening.Start();

在StartListening方法(这是创建一个线程来处理客户端上创建新的TCP套接字一个小的HTTP服务器主监听套接字),我利用LogTextEvent来记录一些数据,但我收到一个InvalidOperationException是在第2行中的LogTextEvent方法未处理的错误,TextEventLog.SelectionStart = TextEventLog.Text.Length;

Inside the StartListening method (it is a thread created that handles new tcp sockets to be created for clients on a main listening socket for a small http server), I make use of LogTextEvent to log some data, but I receive an InvalidOperationException was unhandled error in the LogTextEvent method at the 2nd line, TextEventLog.SelectionStart = TextEventLog.Text.Length;

错误读取,跨线程操作无效:控制'rchEventLog从比它创建的线程以外的线程访问

The error reads, Cross-thread operation not valid: Control 'rchEventLog' accessed from a thread other than the thread it was created on.

谁能帮助打破这是怎么回事,为什么,以及错误如何修复?

Can anyone help break down what's going on, why, and how the error could be fixed?

推荐答案

尝试是这样的:

public void LogTextEvent(RichTextBox TextEventLog, Color TextColor, string EventText)
{
    if (TextEventLog.InvokeRequired)
    {
        TextEventLog.BeginInvoke(new Action(delegate {
            LogTextEvent(TextEventLog, TextColor, EventText);
        }));
        return;
    }

    string nDateTime = DateTime.Now.ToString("hh:mm:ss tt") + " - ";

    // color text.
    TextEventLog.SelectionStart = TextEventLog.Text.Length;
    TextEventLog.SelectionColor = TextColor;

    // newline if first line, append if else.
    if (TextEventLog.Lines.Length == 0)
    {
        TextEventLog.AppendText(nDateTime + EventText);
        TextEventLog.ScrollToCaret();
        TextEventLog.AppendText(System.Environment.NewLine);
    }
    else
    {
        TextEventLog.AppendText(nDateTime + EventText + System.Environment.NewLine);
        TextEventLog.ScrollToCaret();
    }
}

如果该LogTextEvent方法是从以外的线程调用丰富的文本框的UI线程,它会发布一个消息给UI线程,这将导致该线程被称为LogTextEvent方法。

If the LogTextEvent method is called from a thread other than the rich text box's UI thread, it will post a message to the UI thread which will cause the LogTextEvent method to be called in that thread.

使用的BeginInvoke,而不是调用,它是异步发布,这意味着它会立即返回给调用者,而不是等待被其他线程上执行的方法。对于这样的记录的情况下,这可能是你想要的。如果你需要从一个控件或东西的价值,你可能会需要使用调用来代替。

By using BeginInvoke instead of Invoke, it is posted asynchronously which means that it returns immediately to the caller instead of waiting for the method to be executed on the other thread. For a logging scenario like this, this is probably what you want. If you needed to get a value from a control or something you would probably need to use Invoke instead.

这篇关于C#线程安全的RichTextBox事件日志的方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆