微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

在单独的线程中更新物理引擎,这明智吗?

如何解决在单独的线程中更新物理引擎,这明智吗?

| 我是线程技术的100%新手,一开始,我已经决定要考虑使用它在单独的线程中更新物理特性。我正在使用名为Farseer的第三方物理引擎,这是我正在做的事情:
// class level declarations
System.Threading.Thread thread;
Stopwatch threadUpdate = new Stopwatch();

//In the constructor:
PhysicsEngine()
{
(...)

            thread = new System.Threading.Thread(
                        new System.Threading.ThreadStart(PhysicsThread));
            threadUpdate.Start();

            thread.Start();
}


        public void PhysicsThread()
        {
            int milliseconds = TimeSpan.FromTicks(111111).Milliseconds;
            while(true)
            {
                if (threadUpdate.Elapsed.Milliseconds > milliseconds)
                {
                    world.Step(threadUpdate.Elapsed.Milliseconds / 1000.0f);
                    threadUpdate.Stop();
                    threadUpdate.Reset();
                    threadUpdate.Start();
                }
            }
        }
这是更新物理的一种好的方法,还是应该寻找一些东西?     

解决方法

在游戏中,您需要将物理更新同步到游戏的帧频。这是因为您的渲染和游戏玩法将取决于物理引擎每帧的输出。而且您的物理引擎将取决于每个帧的用户输入和游戏事件。 这意味着在单独的线程上计算物理量的唯一优势是,它可以在其他游戏逻辑和渲染的单独CPU内核上运行。 (这些天对PC来说已经相当安全了,移动领域才刚刚开始使用双核。) 这允许他们同时进行物理操作和游戏/渲染-但是缺点是您需要某种机制来防止一个线程修改数据而另一个线程正在使用该数据。通常这很难实现。 当然,如果您的物理学不依赖于用户输入(例如《愤怒的小鸟》或《不可思议的机器》(例如:用户按下\“ play \”并且模拟运行)–在这种情况下,您可以预先计算物理模拟,记录其输出以进行回放。但是,除了阻塞主线程之外,您还可以将此耗时的操作移至后台线程-这是一个众所周知的问题。您甚至可以走到尽头,甚至在记录结束之前就开始在主线程中播放记录!     ,一般而言,您的方法没有错。将耗时的操作(例如物理引擎计算)移动到单独的线程通常是个好主意。但是,我假设您的应用程序在UI中包含某种物理对象的视觉表示?如果是这种情况,您将遇到问题。 Silverlight中的UI控件具有线程关联性,即,您不能从以上示例中创建的线程中更新其状态。为了更新其状态,您将必须通过Dispatcher进行调用,例如TextBox.Dispatcher.Invoke(...)。 另一种选择是使用Silverlight BackgroundWorker。这是一个有用的小类,可让您完成耗时的工作。它将您的工作移至后台线程,而无需创建自己的
System.Threading.Thread
。它还将为您提供将结果编组回UI线程的事件。 简单得多!     

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。