进度条值与在windows 7中呈现的内容不同步

本文关键字:同步 windows | 更新日期: 2023-09-27 18:09:09

似乎在windows 7中,在设置进度条的值时发生了一些动画。设置值似乎不需要等待动画完成。是否有一种方法可以通知进度条何时完成动画?

我有一个示例程序。请看评论
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Threading;
namespace Testing
{
   static class Program
   {
      [STAThread]
      static void Main()
      {
         Application.EnableVisualStyles();
         Application.SetCompatibleTextRenderingDefault(false);
         var form = new Form1();
         form.Run();
      }
   }
   public partial class Form1 : Form
   {
      public Form1()
      {
         InitializeComponent();
      }
      public void Run()
      {
         Thread thread = new Thread
         (
            delegate()
            {
               ProgressBarMax = 10;
               ProgressValue = 0;
               for (int i = 0; i < 10; i++)
               {
                  Thread.Sleep(1000);
                  ProgressValue++;
               }
            }
         );
         EventHandler show = delegate
         {
            thread.Start();
         };
         Shown += show;
         ShowDialog();
         Shown -= show;
      }
      public int ProgressBarMax
      {
         set
         {
            Invoke
            (
               (MethodInvoker)
               delegate
               {
                  progressBar1.Maximum = value;
               }
            );
         }
      }
      public int ProgressValue
      {
         get
         {
            return progressBar1.Value;
         }
         set
         {
            Invoke
            (
               (MethodInvoker)
               delegate
               {
                  label1.Text = value.ToString();
                  progressBar1.Value = value;
                  // setting the value is not blocking until the
                  // animation is completed. it seems to queue
                  // the animation and as a result a sleep of 1 second
                  // will cause the animation to sync up with the UI
                  // thread.
                  // Thread.Sleep(1000); // this works but is an ugly hack
                  // i need to know if there is a callback to notify me
                  // when the progress bar has finished animating.
                  // then i can wait until that callback is handled 
                  // before continuing.
                  // if not, do i just create my own progress bar?
               }
            );
         }
      }
   }
}

我的google kung foo今天好像死了。谢谢。

进度条值与在windows 7中呈现的内容不同步

最后,这与c#进度条与下载(WebClient类)不同步是相同的问题。

这个问题也类似于Windows窗体中的进度条很慢。这里的解决方案是向前和向后移动值,即progressBar1.Value = value + 1; progressBar1.Value = value;。第一次更新开始动画序列,而第二次更新强制动画序列提前停止。这是一个很好的修复方法,但可能会引入难以复制的问题。这似乎没有一个真正的解决方案。

最后,在Vista Aero上禁用进度条动画建议关闭主题。这似乎是有效的,但进度条失去了它的外观和感觉。最后,最好的办法就是制作我自己的进度条。

微软应该让动画成为一个选项,而不是强迫开发人员重新发明进度条。

这个对我很有用:

if (progressBar1.Value <= progressBar1.Maximum - 2)
{
    progressBar1.Value += 2;
    progressBar1.Value--;
}                    
else if (progressBar1.Value <= progressBar1.Maximum)
{                    
    progressBar1.Maximum--;                   
}   

它更新进度条非常快,并负责最后一步,将其更新到100%。

多亏了LuisG的回答,我注意到ProgressBar中的"填充动画"仅在实际增加值时应用。

这允许我们在不使用几个条件的情况下利用它——我们只需要确保设置期望值的最后一次Value更新是一个减少Value的行为:

var tmp = progress.Maximum;
progress.Maximum = int.MaxValue;
progress.Value = int.MaxValue;
progress.Value = desiredValue;
progress.Maximum = tmp;

以上技巧之所以有效,是因为增加MAX和VALUE会触发动画,所以它不会立即渲染。然后我们立即减小这个值,这样就省略了(尚未执行的)动画并呈现新的状态。巧合的是,这正是我们一开始想要的状态。

以上技巧仅在desiredValue小于int.MaxValue时有效。如果您想要完整的整数范围,您必须使用LuisG的技巧来检测100%的最终情况并执行Maximum--而不是提高值。