C# richtextbox不会立即追加文本
当我点击按钮时,我开始模拟 在模拟过程中,我希望附加到C# richtextbox不会立即追加文本,c#,winforms,C#,Winforms,当我点击按钮时,我开始模拟 在模拟过程中,我希望附加到richTextBox项。循环看起来像这样。(Output是一个RichTextBox) 顺便说一句,当我使用多行textbox时,它工作正常。显然,主要问题是您在UI线程中运行此循环,阻止任何UI逻辑运行。在Winforms和几乎所有其他主流GUI平台中,这是一个巨大的“不要那样做” 在UI线程中执行的代码应该做得很少而且非常快。您不应该在UI线程中阻塞(例如调用thread.Sleep()),并且应该将任何长时间运行的代码执行移动到单独的
richTextBox
项。循环看起来像这样。(Output
是一个RichTextBox
)
顺便说一句,当我使用多行
textbox
时,它工作正常。显然,主要问题是您在UI线程中运行此循环,阻止任何UI逻辑运行。在Winforms和几乎所有其他主流GUI平台中,这是一个巨大的“不要那样做”
在UI线程中执行的代码应该做得很少而且非常快。您不应该在UI线程中阻塞(例如调用thread.Sleep()
),并且应该将任何长时间运行的代码执行移动到单独的线程中
我强烈建议不要使用Control.Refresh()
方法。这只是一种解决代码设计中更基本问题的技巧
如果没有清楚地说明您的场景,就不可能知道最佳解决方案是什么。但是假设您使用的是最新版本的.NET和C#,并且假设BattleExchange()
方法本身执行得相当快,我能想到的最简单的修复方法是将您的SimulateBattle()
方法设置为async
方法并使用Task.Delay()在循环中间的一秒延迟:< /p>
async void SimulateBattle()
{
while (!battleEnded)
{
BattleExchange(bh, Left, Right, System.Drawing.Color.Red);
if (Right.Health <= 0)
{
Right.Health = 0;
Output.AppendText(String.Format(Announcements.PERSON_DIED, Right.Name));
break;
}
await Task.Delay(1000);
BattleExchange(bh, Right, Left, System.Drawing.Color.Blue);
if (Left.Health <= 0)
{
Left.Health = 0;
Output.AppendText(String.Format(Announcements.PERSON_DIED, Left.Name));
}
....
}
}
async void SimulateBattle()
{
而(!战斗结束)
{
战场交换(bh,左,右,系统。绘图。颜色。红色);
if(Right.Health)为什么要插入这个延迟:System.Threading.Thread.Sleep(1000);?UI线程被阻塞。你需要在另一个线程中剥离这些内容。@AlexBell,因为我想每秒添加一次消息(因为它会很快结束),所以这就是“richtextbox不会立即追加文本”的原因(请参阅Thread.Sleep(1000)之后的第二个BattleExchange();似乎您有意插入了这样的延迟,从而阻止了执行。请澄清您的业务逻辑。在Thread.Sleep(1000)期间,向您表示感谢和问候
UI线程中不会发生任何事情。请确保插入输出。在点击睡眠按钮之前刷新!
richTextBox1.Clear();
fight.SimulateBattle();
async void SimulateBattle()
{
while (!battleEnded)
{
BattleExchange(bh, Left, Right, System.Drawing.Color.Red);
if (Right.Health <= 0)
{
Right.Health = 0;
Output.AppendText(String.Format(Announcements.PERSON_DIED, Right.Name));
break;
}
await Task.Delay(1000);
BattleExchange(bh, Right, Left, System.Drawing.Color.Blue);
if (Left.Health <= 0)
{
Left.Health = 0;
Output.AppendText(String.Format(Announcements.PERSON_DIED, Left.Name));
}
....
}
}