回答:
Unity物理エンジンの重力は一方向にのみ移動し、[編集]-> [プロジェクト設定]メニューの[物理]メニューで制御されます。
それ以外のことをしたい場合は、独自の重力を実装する必要があります。
基本的に、重心にしたいオブジェクトに球体コライダーを追加できます。コライダーは、オブジェクトがそのオブジェクトの重力の影響を受ける領域全体を囲む必要があります。オブジェクトがこの「影響範囲」と衝突するたびに、力を適用します。影響範囲内にある限り、力を加え続けます。
使用する重力定数は微調整できますが、実際の世界での計算に使用される標準的な定数は次のとおりです。
F = Gm1m2 / r2
綴りは次のとおりです。
力= 重力定数 *オブジェクト1の質量*オブジェクト2の質量/ 2つのオブジェクト間の距離の2乗。
重力定数は9.81ではないことに注意してください。それは地球の表面の重力によって引き起こされる加速です。
重力方程式に頼る必要はありません。重力による加速度は質量に関係なく一定です。したがって、あなたがしたいことは、小さなオブジェクトを各フレームの大きなオブジェクトに向かって加速することだけです。
コードは次のようになります。
public void FixedUpdate()
{
rigidbody.velocity += gravitationalAcceleration * Time.fixedTime * (largeObject.transform.position - transform.position);
}
実際、私は現在重力に基づいたゲームに取り組んでいます。単純に、星を配置して楕円軌道とパチンコ効果でプレーヤーを動かします。重力を無効にして、次のコードを使用しました。
using UnityEngine;
using System.Collections;
public class PlanetGrav : MonoBehaviour {
//Declare Variables:
//Strength of attraction from your sphere (obviously, it can be any type of game-object)
public float StrengthOfAttraction;
//Obviously, you won't be using planets, so change this variable to whatever you want
GameObject planet;
//Initialise code:
void Start ()
{
//Again, you can change the tag to whatever you want.
planet = GameObject.FindGameObjectWithTag("Planet");
}
//Use FixedUpdate because we are controlling the orbit with physics
void FixedUpdate () {
//Declare Variables:
//magsqr will be the offset squared between the object and the planet
float magsqr;
//offset is the distance to the planet
Vector3 offset;
//get offset between each planet and the player
offset = planet.transform.position - transform.position;
//My game is 2D, so I set the offset on the Z axis to 0
offset.z = 0;
//Offset Squared:
magsqr = offset.sqrMagnitude;
//Check distance is more than 0 to prevent division by 0
if (magsqr > 0.0001f)
{
//Create the gravity- make it realistic through division by the "magsqr" variable
rigidbody2D.AddForce((StrengthOfAttraction * offset.normalized / magsqr) * rigidbody2D.mass);
}
}
}
}
PS元々はすべての惑星の配列をループしていたコード:これは編集されているため、完全に正しいとは限りません。でも大丈夫なはずです。
私はZero-Gに基づいた同様のプロジェクトに取り組んでおり、すべてのゲームオブジェクトが、体積、密度、質量、エネルギー、伝導率に基づいて重力と電磁力の両方を生成し、それらに反応する必要があります。私はスクリプト作成は比較的初心者ですが、上記のスクリプトにいくつかの変更を加えて、3D空間で動作するようにしました(重力に関する限り...ほとんど...):
using UnityEngine;
using System.Collections;
public class DynamicWeightAnalysis : MonoBehaviour {
//Declare Variables:
//BBB adding volume calculations
//NOPE
//BBB adding density (...does nothing yet...)
public float density;
//BBB NOPE!
//Strength of attraction from your game-object, ideally this will be derived from a calculation involving the objects volume and density, but for now it's entered from the inspector)
public float RelativeWeight;
//BBB Here, we name our target object (s)
GameObject blockALPHA;
//Initialise code:
void Start ()
{
//BBB here, we define our target object by searching for its tag (setup in editor)
blockALPHA = GameObject.FindGameObjectWithTag("Block ALPHA");
}
//Use FixedUpdate because we are controlling the orbit with physics
void FixedUpdate () {
//Declare Variables:
//magsqr will be the offset squared between the object and the planet
float magsqr;
//offset is the distance to the planet
Vector3 offset;
//get offset between each planet and the player
offset = blockALPHA.transform.position - transform.position;
//Offset Squared:
magsqr = offset.sqrMagnitude;
//Check distance is more than 1 to prevent division by 0 (because my blocks are all 1x1x1 so, any closer than 1 and they'd be intersecting)
if (magsqr > 1f)
{
//Create the gravity- make it realistic through division by the "magsqr" variable
GetComponent<Rigidbody>().AddForce((RelativeWeight * offset.normalized / magsqr) * GetComponent<Rigidbody>().mass);
}
}
}
ご覧のとおり、私はまだ作業中です。基本的に、これまでに追加された「BBB」という注釈が付いたものは、まだ希望どおりに機能していません。しかし、現状では、私の「ブロックアルファ」オブジェクトは、かなり予測可能な方法で3Dで他の「ブロックアルファ」オブジェクトと重力的に相互作用することができます。(ただし、2つ以上のブロックを配置する場合、最後のブロックは常に「アトラクタ」であり、衝突が発生するまで静止したままになります。作業中です...感謝します:))