我有一个在动画画布上绘制大量像素的算法。但是我无法控制动画的速度,而且绘制速度非常快,所以我添加了一个Thread.Sleep(1),但是当绘制数千个像素时,它太慢了。我已经尝试了Storyboard方法,但最终速度非常慢。
那么有没有替代Thread.sleep的方法来降低我的循环速度呢?
void DrawGasket(object sender, DoWorkEventArgs e)
    {
        Random rnd = new Random();
        Color color = Colors.White;
        while (Counter <= noOfPx)
        {
            switch (rnd.Next(3))
            {
                case 0:
                    m_lastPoint.X = (m_top.X + m_lastPoint.X)/2;
                    m_lastPoint.Y = (m_top.Y + m_lastPoint.Y)/2;
                    color = Colors.White;
                    break;
                case 1:
                    m_lastPoint.X = (m_left.X + m_lastPoint.X)/2;
                    m_lastPoint.Y = (m_left.Y + m_lastPoint.Y)/2;
                    color = Colors.Orange;
                    break;
                case 2:
                    m_lastPoint.X = (m_right.X + m_lastPoint.X)/2;
                    m_lastPoint.Y = (m_right.Y + m_lastPoint.Y)/2;
                    color = Colors.Purple;
                    break;
            }
            Dispatcher.BeginInvoke(() =>
            {
                var px = new Rectangle { 
                                       Height = m_pxSize, 
                                       Width = m_pxSize,
                                       Fill = new SolidColorBrush(color) 
                                       };
                Canvas.SetTop(px, m_lastPoint.Y);
                Canvas.SetLeft(px, m_lastPoint.X);
                can.Children.Add(px);
                lblCounter.Text = Counter.ToString();
            });
            Counter++;
            Thread.Sleep(1);
        }
    }发布于 2009-07-21 18:09:27
难道你不能在循环中每N次迭代休眠一次,而不是每一次迭代吗?
发布于 2009-07-21 18:09:32
下面是一个简单的方法:您希望它在一个特定的time...during处绘制每个循环,让它查看时间。如果是你确定的“时间”(不管是什么)速率,那么绘制/更新。否则,只需循环。(例如,如果您希望每秒更新10次,而您刚刚进行了更新,则将当前时间存储在variable...and中,然后与该变量进行比较。直到十分之一秒后,不要重画,只需循环。)
这不是很糟糕,只要你能在这个循环中做任何你需要做的事情。但是,如果这个循环必须在任何其他事情发生之前完成,那么您将只会在等待时消耗大量cpu周期。
如果你想变得花哨,并正确地做这件事,你可以让它看到多少时间过去了,然后按正确的量更新视觉效果。所以,举个例子,如果你想让你的对象每秒移动30个像素,你只需要更新它的精确位置(例如,如果.0047秒已经过去了,它应该移动.141个像素)。您可以存储该值。当然,从视觉上看,在另一轮循环之前,它根本不会移动,但它移动的确切时间和距离将由时间决定,而不是由计算机的速度决定。这样你就可以让它每秒移动30个像素,而不管machine...it的速度如何,在速度较慢的机器上会更快一些。
发布于 2009-07-21 18:23:50
每次Silverlight绘制框架时都会触发CompositionTarget.Rendering事件,这是编写任何自定义绘制代码的好地方。您可以使用一些其他机制,如计时器,来跟踪您的“游戏时间”,并在绘图代码之外的单独线程(或至少单独的执行路径)上适当地调整模型。这样,当需要绘制UI时,不需要执行计算,只需绘制模型的当前状态即可。基本上,只需将Dispatcher.BeginInvoke中的代码移到CompositionTarget.Rendering的事件处理程序中,我相信您会做得很好。
https://stackoverflow.com/questions/1160762
复制相似问题