C# 每秒锁定帧数至60fps

C# 每秒锁定帧数至60fps,c#,winforms,gdi,frame-rate,C#,Winforms,Gdi,Frame Rate,我从FPS的额外积分中看到了这一集,他们提到,通常应该将FPS锁定为30的倍数,因为它与监视器的刷新率相匹配,并减少了伪影。我的代码以60帧/秒的速度运行,但我仍然在运动中得到一个非常微妙的工件 它在Windows窗体中,所以可能真的没有什么可以做的 我的渲染循环如下所示: private void Render() { Update(); if (RenderDelegate != null) RenderDelegate(_renderFunctions);

我从FPS的额外积分中看到了这一集,他们提到,通常应该将FPS锁定为30的倍数,因为它与监视器的刷新率相匹配,并减少了伪影。我的代码以60帧/秒的速度运行,但我仍然在运动中得到一个非常微妙的工件

它在Windows窗体中,所以可能真的没有什么可以做的

我的渲染循环如下所示:

private void Render() {
    Update();
    if (RenderDelegate != null)
        RenderDelegate(_renderFunctions);
    var msPause = 1000 / (double)FpsLimit - _gameTime.DeltaTime;
    if (msPause > 0)
        System.Threading.Thread.Sleep((int)msPause);
    _attachedSystem.NextFrame(); // Will call Invalidate();
}
WinForms控件中的实现

protected void FormOnPaint(object sender, PaintEventArgs paintEventArgs) {
    _graphic = paintEventArgs.Graphics;
    _render();
}
void IGameMessages.DrawImage(Image image, Rectangle rect) {
    _graphic.DrawImage(image, rect);
}
void IGameMessages.NextFrame() {
    Control.Invalidate();
}

我猜按动态值睡眠不是首选方式,因为它可能与监视器刷新率不同步1%或其他什么?fps输出在58到63 fps之间波动(DeltaTime计算可能也有问题)

WinForm不理想。原因是屏幕更新并不取决于你的应用程序。WinForms中没有屏幕中断

我保留了一个计时器,从左向右移动了一个对象,800像素,这个类似“精灵”的对象有一个开始计数器整数。取决于一个新职位过去的时间

if(!x.AtEnd) {
    X.DeltaTime = X.Startime-currentTime;
    int x = myStartTime - currentTime;
    x.position = X.DeltaTime % 430; //time was in ms and 430 just a number 

    if (x.postion > x.end) {
        x.position=x.end;
        x.AtEnd=true;
    }
}

这在一定程度上取决于它的移动速度和外观(这也取决于计算机的速度,因为速度较慢的计算机在其他线程上执行时也需要更多的时间)。使用上面的方法,我得到了一个合理的平滑移动对象,不像在游戏中那样平滑,但是它工作得很好,并且没有阻塞(延迟)代码(因为我尝试了线程延迟,所以每个移动花费了相等的时间,但也没有平滑,屏幕更新太随机了)

还有一条免责声明:我已经将这一行放在SetStyle(ControlStyles.AllPaintingInWmPaint | ControlStyles.不透明| ControlStyles.DoubleBuffer,true)的表单中;我得到的人工制品非常微妙。在Winforms中制作一个每秒60帧的游戏已经是一场失败的战斗。在你进入视频谈论的每秒60帧之前,你还有很多事情要担心。你真的应该使用一个设计用来做游戏开发的框架,而不是把它强加给winforms,你会得到很多好处,比如硬件加速。winforms也不是我个人的选择。我正在做一个10年的项目,老板想在应用程序中嵌入一个小游戏。但我敢打赌团结。也许正确的答案是替代方案?有一些要求。第一:应用程序托管在windows窗体内(不一定由绘制)。第二:我不能在客户机上安装任何软件,但我可以使用任意数量的dll。唉,与监视器同步根本不是winforms内置的。WPF将开箱即用。直接访问视频适配器,从而导致撕裂伪影,在过去10年中已经结束。现在渲染到内存中的曲面,DWM将其合成到屏幕上。我已经很久没有看到有人抱怨撕裂了,这是一个XP问题吗?我离开那家公司已经很久了,不过还是谢谢你的回答。2年后,我认识到我应该使用框架提供的回调或线程锁,这可能是硬件提供的。