Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/333.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 刚体圆周运动_C#_Unity3d - Fatal编程技术网

C# 刚体圆周运动

C# 刚体圆周运动,c#,unity3d,C#,Unity3d,我有一个2D球,它有一个力,在不确定的方向上移动,当用户触摸屏幕时,我需要使球相对于当前方向向右或向左循环移动,而不改变速度。我该怎么做 我尝试了这个代码,但其他物理无法影响球,因为我们正在直接更改变换: float angle = 0; float radius = 1; void FixedUpdate() { angle += speed * Time.deltaTime; float x = center.x + Mathf.Cos(angle) * radius;

我有一个2D球,它有一个力,在不确定的方向上移动,当用户触摸屏幕时,我需要使球相对于当前方向向右或向左循环移动,而不改变速度。我该怎么做

我尝试了这个代码,但其他物理无法影响球,因为我们正在直接更改变换:

float angle = 0;
float radius = 1;

void FixedUpdate()
{
    angle += speed * Time.deltaTime;
    float x = center.x + Mathf.Cos(angle) * radius;
    float y = center.y + Mathf.Sin(angle) * radius;

    rigidbody.transform.position = new Vector3(x, y, 3);
}

如果你不让它在自己的轴上移动,你必须把它连接到另一个物体上,但一定要把球放在与球相同的位置。然后,可以在自动旋转时隐藏实体,使其移动隐藏实体的轴。这是实现这一点的最佳方法,无需额外编码或面对四元数问题

如果你不让它沿着自己的轴移动,你必须将它连接到另一个物体上,但一定要将球放在与球相同的位置。然后,可以在自动旋转时隐藏实体,使其移动隐藏实体的轴。这是实现这一点的最佳方法,无需额外编码或面对四元数问题

就像物理学那样:

你的触摸位置有点像重力中心&向右箭头;使用相同的幅值连续指定一个新方向,但该方向与从中心到移动对象和旋转轴的矢量成90°角

在代码中,这可能看起来像

public class Example : MonoBehaviour
{
    [SerializeField] private Rigidbody2D rb;
    [SerializeField] private Camera _camera;

    [SerializeField] private Vector2 initialVelocity;    

    private bool doGravitation;
    private Vector2 centerPos;

    private void Awake()
    {
        if(!rb) rb = GetComponent<Rigidbody2D>();
        if(!_camera) _camera = Camera.main;

        rb.velocity = initialVelocity;
    }

    private void Update()
    {
        // check for touch support otherwise use mouse as fallback
        // (for debugging on PC)
        if (Input.touchSupported)
        {
            // not touching or too many -> do nothing
            if (Input.touchCount != 1)
            {
                doGravitation = false;
                return;
            }

            var touchPosition = Input.GetTouch(0).position;
            centerPos = _camera.ScreenToWorldPoint(touchPosition);
            doGravitation = true;
        }
        else
        {
            // mouse not pressed -> do nothing
            if (!Input.GetMouseButton(0))
            {
                doGravitation = false;
                return;
            }

            centerPos = _camera.ScreenToWorldPoint(Input.mousePosition);
            doGravitation = true;
        }
    }

    private void FixedUpdate()
    {
        if(!doGravitation) return;

        // get current magnitude
        var magnitude = rb.velocity.magnitude;

        // get vector center <- obj
        var gravityVector = centerPos - rb.position;

        // check whether left or right of target
        var left = Vector2.SignedAngle(rb.velocity, gravityVector) > 0;

        // get new vector which is 90° on gravityDirection 
        // and world Z (since 2D game)
        // normalize so it has magnitude = 1
        var newDirection = Vector3.Cross(gravityVector, Vector3.forward).normalized;

        // invert the newDirection in case user is touching right of movement direction
        if (!left) newDirection *= -1;

        // set new direction but keep speed(previously stored magnitude)
        rb.velocity = newDirection * magnitude;
    }
}
另见:


请注意,这有时看起来很奇怪,尤其是在触球前方时,因为我们将球推到一条可能与当前运动有奇怪角度的圆曲线上。你可以让它平静下来,但这取决于你

就像物理学那样:

你的触摸位置有点像重力中心&向右箭头;使用相同的幅值连续指定一个新方向,但该方向与从中心到移动对象和旋转轴的矢量成90°角

在代码中,这可能看起来像

public class Example : MonoBehaviour
{
    [SerializeField] private Rigidbody2D rb;
    [SerializeField] private Camera _camera;

    [SerializeField] private Vector2 initialVelocity;    

    private bool doGravitation;
    private Vector2 centerPos;

    private void Awake()
    {
        if(!rb) rb = GetComponent<Rigidbody2D>();
        if(!_camera) _camera = Camera.main;

        rb.velocity = initialVelocity;
    }

    private void Update()
    {
        // check for touch support otherwise use mouse as fallback
        // (for debugging on PC)
        if (Input.touchSupported)
        {
            // not touching or too many -> do nothing
            if (Input.touchCount != 1)
            {
                doGravitation = false;
                return;
            }

            var touchPosition = Input.GetTouch(0).position;
            centerPos = _camera.ScreenToWorldPoint(touchPosition);
            doGravitation = true;
        }
        else
        {
            // mouse not pressed -> do nothing
            if (!Input.GetMouseButton(0))
            {
                doGravitation = false;
                return;
            }

            centerPos = _camera.ScreenToWorldPoint(Input.mousePosition);
            doGravitation = true;
        }
    }

    private void FixedUpdate()
    {
        if(!doGravitation) return;

        // get current magnitude
        var magnitude = rb.velocity.magnitude;

        // get vector center <- obj
        var gravityVector = centerPos - rb.position;

        // check whether left or right of target
        var left = Vector2.SignedAngle(rb.velocity, gravityVector) > 0;

        // get new vector which is 90° on gravityDirection 
        // and world Z (since 2D game)
        // normalize so it has magnitude = 1
        var newDirection = Vector3.Cross(gravityVector, Vector3.forward).normalized;

        // invert the newDirection in case user is touching right of movement direction
        if (!left) newDirection *= -1;

        // set new direction but keep speed(previously stored magnitude)
        rb.velocity = newDirection * magnitude;
    }
}
另见:


请注意,这有时看起来很奇怪,尤其是在触球前方时,因为我们将球推到一条可能与当前运动有奇怪角度的圆曲线上。你可以让它平静下来,但这取决于你

谢谢@derHugo!如此完美的答案!你是职业选手!但有一个问题,当我继续接触时,重力半径平稳增加,你能解释为什么吗?在FixedUpdate上获取输入会导致错误,除非它与更新完全同步,否则它永远不应该是可靠的,因为这违背了目的。-还有,在这种只支持单次触摸的情况下,不需要区分触摸和鼠标输入。单靠鼠标操作就可以了。谢谢@derHugo!如此完美的答案!你是职业选手!但有一个问题,当我继续接触时,重力半径平稳增加,你能解释为什么吗?在FixedUpdate上获取输入会导致错误,除非它与更新完全同步,否则它永远不应该是可靠的,因为这违背了目的。-还有,在这种只支持单次触摸的情况下,不需要区分触摸和鼠标输入。只需鼠标操作就可以了。