Windows 窗体文本框字体颜色限时更改

Posted

技术标签:

【中文标题】Windows 窗体文本框字体颜色限时更改【英文标题】:Windows forms textbox font color change for a limited time 【发布时间】:2021-05-07 16:33:08 【问题描述】:

我是 C# 和 Windows 窗体的新手,但这里有一件事: 如果我的布尔函数返回 false,我想将名为 NameField 的文本框中的文本颜色更改为红色;

我尝试使用NameField.ForeColor = System.Drawing.Color.Red;,但它永远将其更改为红色,但我只想要几秒钟。有可能吗?

【问题讨论】:

你可以使用计时器来做到这一点。 你已经有几个选项了,但是你从哪里检查布尔函数? @Idle_Mind,在我的 Form1 类中有一个检查 TextBoxes 的布尔函数 好的,但是该布尔函数是如何以及何时被调用的?从一个事件?一根线?计时器? ……还有什么? 【参考方案1】:

最简单的方法是使用Task.Delay。假设您想在单击按钮时执行此操作:

private async void button1_Click(object sender, EventArgs e)
    try
        NameField.ForeColor = System.Drawing.Color.Red;
        await Task.Delay(1000); // 1s
        NameField.ForeColor = System.Drawing.Color.Blue;
    
     catch(Exception e)
          // handle exception
      

计时器是另一种选择,但如果您只想触发一次,则需要在事件处理程序中禁用计时器。 Task.Delay 或多或少做同样的事情,但更简洁一些。

请记住 try/catch,每当您使用 async void 时,您都希望捕获任何异常以确保它们不会丢失。

您可能还需要考虑重复按下按钮。要么禁用按钮,要么增加一些字段,并且仅当字段具有与设置颜色时相同的值时才重置颜色。

【讨论】:

private async Task MyMethod() 。您还应该说明调用此方法的方式/时间/地点。【参考方案2】:

在您的面向对象类中,您了解到,如果您想要一个类与另一个类几乎相同,但只有一点功能不同,那么您应该派生该类。

所以让我们创建一个类,派生自按钮,它会改变颜色并在一段时间后自动恢复为默认颜色。

按钮会有一个 Flash 方法,它会改变按钮的颜色。在指定的时间后,该按钮将不闪烁。

为此,该类具有指定前景/背景颜色以及闪烁时间的属性。

public class FlashOnceButton : Button

    private readonly Timer flashTimer
    private Color preFlashForeColor;
    private Color preFlashBackColor;

    public FlashOnceButton()
    
         this.flashTimer = new Timer
         
             AutoReset = false,
         ;
         this.flashTime.Elapsed += FlashTimer_Elapsed;
    

    public Color FlashBackColor get; set; = Color.Red;
    public Color FlashForeColor get; set; = base.ForeColor;
    public TimeSpan FlashTime get; set; = TimeSpan.FromSeconds(1);

    public bool IsInFlashState => this.Timer.Enabled;

    public void StartFlash()
    
        // if already flashing, do nothing            
        if (this.IsInFlashState) return;

        // before changing the colors remember the current fore/back colors
        this.preFlashForeColor = this.ForeColor;
        this.preFlashBackcolor = this.BackColor;
        this.ForeColor = this.FlashForeColor;
        this.BackColor = this.FlashBackColor;

        this.Timer.Interval = this.FlashTime.TotalMilliseconds;
        this.Timer.Enabled = true;
    
        
    private void FlashTimer_Elapsed(object sender, ElapsedEventArgs e)
    
        // restore the colors:
        this.ForeColor = this.preFlashForeColor;
        this.BackColor = this.preFlashBackColor;
        this.flashTimer.Enabled = false;
    

用法:编译后你应该在visual studio Toolbox中找到这个类。因此,您可以使用 Visual Studio 设计器添加它并设置属性。

您会在 InitializeComponent 中找到它。或者,您可以在构造函数中设置它

如果我的布尔函数返回 false,我想将名为 NameField 的文本框中的文本颜色更改为红色;

public void OnBooleanChangedFalse()

    this.flashOnceButton1.StartFlash();

就是这样!

有一个怪癖:Timer 类实现了 IDisposable,所以如果你停止你的表单,你应该 Dispose 它。

public class FlashOnceButton : Button

    protected override void Dispose(bool disposing)
    
        if (disposing)
        
            this.flashTimer.Dispose();
        
    

确保在释放表单时释放按钮的最简单方法是将其移至表单的组件字段:

public void MyForm()

    InitializeComponent();   // this will create flashOnceButton1

    // make sure that the button is disposed when the Form is disposed:
    this.components.Add(this.flashOnceButton1);

【讨论】:

你应该设置那个定时器的SynchronizingObject,否则它的Elapsed事件是在线程池线程中引发的。为什么不简单地使用 System.Windows.Forms.Timer?【参考方案3】:

我为您提供了解决方案,但是它的效率有点低。请检查并告诉我。

        int counter = 1;
        Timer timer1 = new TimerInterval = 5000;
        private void button1_Click(object sender, EventArgs e)
        
            timer1.Enabled = true;

            if (myBoolMethod(counter))
             
                textBox1.ForeColor = System.Drawing.Color.Red;
                timer1.Tick += OnTimerEvent;
            
            
            if (counter == 1)
                counter = 2;
            else
                counter = 1;
        

        private void OnTimerEvent(object sender, EventArgs e)
        
            textBox1.ForeColor = System.Drawing.Color.Black;
            timer1.Tick -= OnTimerEvent;
        


        bool myBoolMethod(int param)
        
           if(param % 2 == 0)
            
                return true;
            
            else
            
                return false;
            
        

【讨论】:

【参考方案4】:

有几种方法可以处理这个问题。最直接的方法是使用Timer。如果您想在一段时间内保持颜色更改,则可以使用Stopwatch 来捕获经过的时间。

    public partial class Form1 : Form
    
        public Form1()
        
            InitializeComponent();
        

        private Timer _colorTimer; // Create a timer as a private field to capture the ticks
        private Stopwatch _swColor; // Create a stopwatch to determine how long you want the color to change
        private void Form1_Load(object sender, EventArgs e)
        
            // Initialize fields
            _colorTimer = new Timer();
            _colorTimer.Interval = 10; // in milliseconds
            _colorTimer.Tick += ColorTimer_Tick; // create handler for timers tick event
            _swColor = new Stopwatch();

            NameField.Text = "Person Name"; // For testing purposes
        

        // the timer will run on a background thread (not stopping UI), but will return to the UI context when handling the tick event
        private void ColorTimer_Tick(object sender, EventArgs e)
        
            if(_swColor.ElapsedMilliseconds < 1000) // check elapsed time - while this is true the color will be changed
            
                if(NameField.ForeColor != Color.Red)
                
                    NameField.ForeColor = Color.Red;
                
             
            else
            
                // reset the controls color, stop the stopwatch and disable the timer (GC will handle disposal on form close)
                NameField.ForeColor = Color.Black;
                _swColor.Stop();
                _swColor.Reset();
                _colorTimer.Enabled = false;
            
        

        private void btnChangeColor_Click(object sender, EventArgs e)
        
            // on button click start the timer and stopwatch
            _colorTimer.Start();
            _swColor.Start();
        
    

【讨论】:

以上是关于Windows 窗体文本框字体颜色限时更改的主要内容,如果未能解决你的问题,请参考以下文章

Libre office Draw如何更改pdf表单可填写文本框的字体颜色

如何修改PPT中的超链接字体颜色

webstorm怎么设置背景颜色

MFC文本框字体颜色设置

animate+cc为啥编辑器字体颜色更改不了?

对话框控件 MessageBox.Show()用法补充 打开新窗体的3中模式