我刚刚从物理学开始,所以我并不总是确定我在做什么。这是一个2D项目,但我正在使用像SphereCollider等3D物理对象。
我有什么:
物体漂浮在太空中并通过重力相互影响:
protected virtual IEnumerator OnTriggerStay(Collider other) {
yield return new WaitForFixedUpdate();
if(other.attachedRigidbody) {
Vector3 offsetVector = this.transform.position - other.transform.position;
float distance = offsetVector.magnitude;
float gravityForce = (other.rigidbody.mass * mass) / Mathf.Pow(distance, 2);
// Clamp gravity.
if(gravityForce > 1.0F) {
gravityForce = 1.0F;
}
other.attachedRigidbody.constantForce.force = offsetVector.normalized * gravityForce;
}
}
有可控制的物体,玩家可以在上面点击并拖动一条线远离物体,以便向相反方向施加力(射击)。
我想要实现的目标:
玩家应该在瞄准时看到粗略的预测方式。这意味着方式预测需要考虑当前速度,当玩家释放鼠标按钮时应用的力和周围物体的重力。
到目前为止我尝试了什么:
出于测试目的,我只是将计算/预测位置保存在数组中,并在OnDrawGizmos()中绘制这些位置。
我写了一个方法,它返回一个名为computeGravityForPosition(Vector3 position)的某个位置的重力影响。
这就是我如何计算位置:
private void drawWayPrediction() {
Vector3 pos = this.transform.position;
// The offsetVector for the shooting action.
Vector3 forceVector = pos - Camera.main.ScreenToWorldPoint(Input.mousePosition);
forceVector.z = 0.0F;
// The predicted momentum scaled up to increase the strength.
Vector3 force = (forceVector.normalized * forceVector.magnitude);
// 1. I guess that this is wrong, but don't know how to do it properly.
momentum = this.rigidbody.velocity + force;
for(int i = 0; i < predictionPoints.Length; i++) {
float t = i * Time.fixedDeltaTime;
momentum += computeGravityForPosition(pos);
pos += momentum * t * t;
predictionPoints[i] = pos;
}
}
一开始,当物体慢慢接近彼此时看起来没问题。第一次拍摄后,预测完全错误。我想这是因为代码中的1.只是将力加到速度上可能是错误的。
非常感谢你的时间。
修改
我删除了看似无关紧要的部分。
我仍然认为主要问题在于代码中的1.。我只是不知道如何混淆对象的当前运动(据我知道统一的物理引擎我只有当前的速度)和新创建的力:
Vector3 forceVector = pos - Camera.main.ScreenToWorldPoint(Input.mousePosition); Vector3 force =(forceVector.normalized * forceVector.magnitude);
答案 0 :(得分:3)
因此,如果您使用的统一版本可能在2018年以上,则可以使用不错的方法
Physics.Simulate(dt); // delta time, dt, is the amount of time to simulate.
使用此功能,您可以手动进行仿真。 此方法应应用于不同的物理场景。 因此,我建议单击时将模拟一些物理步骤(模拟的次数越多,玩家得到的指示越准确), 每一步都存储对象的位置,完成模拟后,在所有点之间画一条线。 我认为,如果操作正确,它应该运行得很快。
代码应如下所示:
public PhysicsScene physicsScene;
GameObject actualBall;
GameObject simulatedBall;
OnClick() {
simulatedBall.SetPosition(actualBall.transform.position);
if (!physicsScene.IsValid())
return; // do nothing if the physics Scene is not valid.
for (int i=0; i < 10; i++) {
physicsScene.Simulate(Time.fixedDeltaTime);
// store the position.
myPoints.append(simulatedBall.rb.position);
}
// draw a line from the stored points.
}
此外,我希望有此视频对您有所帮助 https://www.youtube.com/watch?v=GLu1T5Y2SSc
我希望我回答了你的问题,如果不告诉我:)
答案 1 :(得分:1)
免责声明:不幸的是,我在数学方面很糟糕,因此无法提供任何计算代码。
现在合法的东西已经不在了:)
在我看来,你看这一切都错了。您需要的是计算曲线(物体轨迹的路径),然后使用线渲染器在OnDrawGizmos中绘制曲线。
您不需要模拟对象的行为。这不仅速度快,而且在TimeScale恶作剧方面也更简单。通过更改TimeScale,您还会影响轨迹模拟的TimeScale,这很可能看起来很奇怪。
通过进行基本轨迹计算,您将不会遇到此问题。
PS:这link可能会有所帮助。