我希望我的程序不断更改字体背景颜色,但我希望它顺利进行,所以我尝试修改颜色变量颜色自定义;并将其用于表单背景颜色this.BackColor = custom;但它不起作用,我不知道如何使它工作,这里是完整的代码:
private void Principal_Load(object sender,EventArgs e) { Color custom; int contr = 0,contg = 0,contb = 0; do { while (contr < 255 && contg == 0) { if (contb != 0) { contb--; } contr++; while (contg < 255 && contb == 0) { if (contr != 0) { contr--; } contg++; while (contb < 255 && contr == 0) { if (contg != 0) { contg--; } contb++; } } } custom = Color.FromArgb(contr,contg,contb); this.BackColor = custom; } while (true); }
解决方法
首先,您当前的代码不起作用,但不是因为任何线程问题(尽管确实需要解决).
问题是这些线永远不会被击中:
custom = Color.FromArgb(contr,contb); this.BackColor = custom;
你的while循环中的逻辑不起作用.
您生成的值是以下集合:
(0,1),(0,2) ... (0,255),254,253,1,254)
然后它只是重复尝试产生这些值,但永远不会突然出现(contr< 255&& contg == 0)循环. 现在,假设这实际上是您想要的,那么我建议最好的方法是使用Microsoft的Reactive Framework.只需NugGet“Rx-WinForms”然后你就可以编写这段代码了:
var ranges = new[] { Observable.Range(1,255).Select(x => Color.FromArgb(0,x)),Observable.Range(1,254).Select(x => Color.FromArgb(0,255 - x,}; var query = ranges .Concat() .Zip(Observable.Interval(TimeSpan.FromMilliseconds(100.0)),(x,i) => x) .Repeat() .ObserveOn(this); var subscription = query.Subscribe(c => this.BackColor = c);
因此范围是IObservable< Color>的数组.在范围上调用.Concat()会将其从IObservable< Color> []转换为IObservable< Color>. .Zip将每个值绑定到以10ms为增量计数的计时器(如果需要,可以更改该值).调用.Repeat()只是连续重复循环 – 有点像while(true).然后.ObserveOn(this)强制可观察的订阅在UI线程上运行.
最后,.Subscribe(…)实际上运行了observable并更新了表单的BackColor.
关于这一点的好处是你可以通过在订阅上调用.Dispose()来随时停止订阅:
subscription.Dispose();
这清理了所有的线程和计时器.这是一个非常巧妙的解决方案.