我正在寻找一些很好的参考资料来学习如何在游戏中建模2d物理.我不是在找图书馆为我做这件事 - 我想思考和学习,而不是盲目地利用别人的工作.
我已经做了很多谷歌搜索,虽然我已经在GameDev上找到了一些教程等,但是我发现他们的教程难以理解,因为它们要么写得不好,要么假设我不懂数学水平.但还是拥有.
具体而言 - 我正在寻找如何模拟自上而下的2D游戏,有点像坦克战斗游戏 - 我想准确地模拟(除其他外)加速度和速度,'组件的热量积累'之间的碰撞模型和等级界限,以及导弹型武器.
网站,推荐书籍,博客,代码示例 - 如果有助于理解,欢迎所有人.我正在考虑使用C#和F#来构建我的游戏,所以这两种语言中的代码示例都会很棒 - 但是不要让语言阻止你发布一个好的链接.=)
编辑:我不是说我不理解数学 - 更多的情况是我不知道我需要知道什么才能理解所涉及的系统,并且不知道如何找到资源会以一种可以理解的方式教我.
我写了一个简单的物理建模器,它允许我在屏幕周围弹跳球.您可以单击并拖动以启动球,或者您可以一次生成数百个球并观察它们彼此交互.
alt text http://i41.tinypic.com/2zr0oic.png
[链接到更大的版本]
这是一个很有趣的小程序,如果可以的话,我想进一步研究它.我知道他们说早熟优化是所有邪恶的根源,但我开始遇到实际的性能障碍,我想知道是否有任何有游戏/模拟器开发经验的人可以帮助我.
问题:
现在,如果你添加太多球(我的机器上似乎无法处理超过800个),我的程序就会窒息.如果这样做,模拟不再现实,并且所有球在底部彼此重叠.
问题在于碰撞检测.在最天真的情况下,碰撞检测是O(N ^ 2)问题.每个球都会检查每一个球.这很快就会导致性能下降(即使在100个球之后,你也会在每个循环周期进行10k次碰撞检查).
如果你看这里,你可以看到我添加了几百个球的截图.模拟器无法跟上,它们开始相互重叠.
alt text http://i41.tinypic.com/2nsnuqd.png
[链接到更大的版本]
目前,我通过寻找重叠球来检测碰撞.如果我找到两个重叠的球,我将它们按最小平移距离(MTD)分开,或将它们分开.然后,我使用一个简单的物理方程来调整它们的脉冲矢量,然后在碰撞后它们向不同的方向移动.
它的效果很好,除非有太多的球,最小的平移距离变得明显.它们开始大量重叠并且不断地在底部互相挤压.我越是"增加"引力就越糟糕.它们上的压力增加,它们被压缩/相互重叠的量增加.
再说一次,我没有问题,直到我击中了相当数量的N球.
当前优化方法:
碰撞检测 -
扫描和修剪 - (又称排序和扫描)
我在我的球上使用插入排序,每个循环沿x轴循环.由于插入排序的性质,我可以利用我的模拟器的时间一致性.框架到框架,球的位置只是稍微改变,因此排序没有太多工作要做.这使得线性分类分摊运行时间为O(N)或线性而不是其平均运行时间O(N ^ 2).
由于球是排序的,我在检查碰撞之前在第二个循环中做了几次预检查.现在我只需要检查彼此附近的球(因为它们沿着x轴排序),并且当我检查球与另一个球的xmin大于当前球的xmax时,我会突破第二个循环.所以它跳过了成千上万的支票.
当我实现这一点时,它带来了巨大的速度提升.但是,我仍然希望能够处理超过600-800个球.我已经阅读过物理引擎,可以轻松地同时处理10k个物体之间的碰撞检测,所以我想我可以通过一点点工作达到1-2k.
在运行了一个分析器之后,碰巧检测器占用了大约55%的时间,而渲染器占用了大约45%.所以,这是我最昂贵的两个成本.
题:
你能想到任何更好的算法或技术,让我的模拟器能够处理更多的球吗?
相关守则:
整个项目:
svn checkout http://simucal-projects.googlecode.com/svn/ballbounce/trunk/
或者,单击此处在浏览器中手动浏览文件.
感兴趣的部分:
我正在研究2D游戏,我正在尝试使用一些基本的物理代码将对象加速到最高速度.
这是它的伪代码:
const float acceleration = 0.02f;
const float friction = 0.8f; // value is always 0.0..1.0
float velocity = 0;
float position = 0;
move()
{
velocity += acceleration;
velocity *= friction;
position += velocity;
}
Run Code Online (Sandbox Code Playgroud)
这是一种非常简化的方法,不依赖于质量或实际摩擦(代码内摩擦只是一种阻止运动的通用力).它的效果很好,因为"速度*=摩擦力"; 部分保持速度不超过某一点.然而,正是这种最高速度及其与加速和摩擦的关系,我有点迷失.
我想要做的是设置一个最高速度,以及达到它所需的时间,然后使用它们来获得加速度和摩擦值.
即
const float max_velocity = 2.0;
const int ticks; = 120; // If my game runs at 60 FPS, I'd like a
// moving object to reach max_velocity in
// exactly 2 seconds.
const float acceleration = ?
const float …Run Code Online (Sandbox Code Playgroud) Box2d 中刚体的定义是
一块物质非常强大,以至于块上任何两个物质之间的距离是完全恒定的.
这正是我不想要的,因为我想制作2D(最终可能是3D),弹性,可变形,易碎,甚至是粘稠的物体.
我希望离开这个社区的是资源,它教会我如何弯曲,破坏和互动对象.我不关心这些物体的分子或化学性质,当我试图寻找如何计算一块木头,金属,橡胶,粘性物质,液体,有机物质等时,我常常发现这一切.在施加力之后可能看起来像.
此外,我是一个非常直观的人,因此图表等对我来说非常有帮助.
================================================== ==============================
忽略这些问题,它们已经过时了,我只是为了上下文的目的而将它们保留在这里
这里有没有简单的2D软体物理引擎?
最好是免费还是开源?
如果不花费数年时间就可以自己创作吗?
3.我可以使用像bullet和box2d这样的现有引擎作为开始并简单地转换他们的代码,或者考虑到我1年的编程经验和子弹是3D,这会导致更多的问题吗?
4.最后,如果我要转换另一个库,那么它是最好的改变box2D已经是2d代码,Bullet已经是软代码,还是混合了两个源代码?
谢谢!
我有兴趣做一个"太阳系"模拟器,它可以让我模拟行星和恒星的旋转和重力.
我想能够说,模拟我们的太阳系,并以不同的速度模拟它(即,观察地球和其他行星在太阳,几年等周围绕太阳旋转).我希望能够添加行星并改变行星质量等,以了解它将如何影响系统.
有没有人有任何资源可以指出我正确的方向来编写这种模拟器?
是否有为此目的设计的现有物理引擎?
我使用bodyWithPolygonFromPath来定义物理体的体积,并使用
http://dazchong.com/spritekit/
获得所需的路径.但路径似乎不正确,我希望看到物理体路径的边界,看看形状是否正确.
有没有办法看到物理学家的卷大纲?
我尝试了以下代码,但它不起作用.
ship = [SKSpriteNode spriteNodeWithImageNamed:@"Spaceship"];
CGFloat offsetX = ship.frame.size.width * ship.anchorPoint.x;
CGFloat offsetY = ship.frame.size.height * ship.anchorPoint.y;
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, NULL, 50 - offsetX, 110 - offsetY);
CGPathAddLineToPoint(path, NULL, 18 - offsetX, 16 - offsetY);
CGPathAddLineToPoint(path, NULL, 140 - offsetX, 15 - offsetY);
CGPathCloseSubpath(path);
SKShapeNode *yourline = [SKShapeNode node];
yourline.name = @"yourline";
yourline.path = path;
[yourline setStrokeColor:[UIColor redColor]];
[self addChild:yourline];
ship.physicsBody = [SKPhysicsBody bodyWithPolygonFromPath:path];
//[ship setScale:0.5];
ship.zRotation = - M_PI / 2;
Run Code Online (Sandbox Code Playgroud) 我正在构建一个2D物理引擎,我想添加宽相碰撞检测,但我只知道2或3种类型:
但肯定还有更多选择吗?这些是什么?并且可以提供每个的基本描述或链接到描述吗?
我已经看到了这个,但我要求提供一系列可用的算法,而不是最符合我需求的算法.
在这种情况下,"广泛相位碰撞检测"是物理引擎用来确定模拟中哪些物体足够接近以保证进一步调查和可能的碰撞解决的方法.
我正试图制作一个自上而下的太空飞船游戏,我希望这个运动有点逼真.360度惯性,重力等
我的问题是我可以让船在惯性运动的情况下360°运行没有问题,但我需要做的是对发动机的运行速度施加限制,同时不限制推/拉船的其他力.
因此,如果发动机转速最大为500且船舶从重力井转向1000,那么当它的发动机打开时,该船不会进入1500,但是如果指向远离角度的话,那么它可能会变慢下.
对于它的价值,我正在使用Construct,而我所需要的只是数学.
感谢您的帮助,我想要解决这个问题.
下面是我最里面的循环,运行几千次,输入大小为20 - 1000或更多.这段代码占用了99-99.5%的执行时间.我能做些什么来帮助挤出更多的表现吗?
我不打算将此代码移动到类似于使用树代码(Barnes-Hut)的东西,而是为了优化内部发生的实际计算,因为在Barnes-Hut算法中进行相同的计算.
任何帮助表示赞赏!
编辑:我在Core 2 Duo T5850(2.16 GHz)上使用Visual Studio 2008版本运行Windows 7 64位
typedef double real;
struct Particle
{
Vector pos, vel, acc, jerk;
Vector oldPos, oldVel, oldAcc, oldJerk;
real mass;
};
class Vector
{
private:
real vec[3];
public:
// Operators defined here
};
real Gravity::interact(Particle *p, size_t numParticles)
{
PROFILE_FUNC();
real tau_q = 1e300;
for (size_t i = 0; i < numParticles; i++)
{
p[i].jerk = 0;
p[i].acc = 0;
}
for (size_t i = 0; i < …Run Code Online (Sandbox Code Playgroud) 我正在尝试像javascript一样做一个小小的翅膀.
我第一次看到使用Box2D的技术,我正在使用closure-web版本(因为内存泄漏修复).
简而言之,我将曲线分解为多边形,因此它看起来像这样:

我也试过过Chipmunk-js,我用段形来模拟我的地面:

在这两种情况下,当圆形滚动时,我在多边形或线段之间的公共点处遇到一些"崩溃"或"颠簸".
我询问了Chipmunk,作者说他为段实现了radius属性以减少这种行为.我试过,它确实做了诀窍,但它并不完美.我仍然有一些颠簸(我必须设置为30px的半径才能获得正面效果).
"凸起"附加在两个多边形之间的共享点上:

正如伊兰德里尔向我建议的那样使用边缘技术 (他只测试了多边形 - 多边形接触)以避免圆圈在边缘上崩溃:

还试图像Luc建议的那样添加子弹选项,似乎没有任何改变.
这里是问题的演示.
您可以尝试更改要检查的值:
(仅在最新的开发Chrome上测试)
耐心(或改变水平重力),你会明白我的意思.
这里的感兴趣的回购.
physics ×10
math ×3
2d ×2
algorithm ×2
optimization ×2
astronomy ×1
box2d ×1
broad-phase ×1
c# ×1
c++ ×1
chipmunk ×1
curve ×1
f# ×1
game-physics ×1
javascript ×1
loops ×1
rigid-bodies ×1
simulation ×1
sprite ×1
sprite-kit ×1