플레이어 객체를 다룰 때 언제 속도 대 addForce를 사용해야합니까?


18

Unity 프레임 워크 에서이 두 가지 방법에 대해 혼란 스럽습니다. 둘 다 플레이어 객체를 움직이고, 멈추고, 방향을 바꾸는 등의 일을합니다. 하나는 언제 다른 것 위에 사용해야합니까?



@ Byte56 두 질문 모두 다른 것들에 대해 묻습니다
Robert

1
다르지만 관련이 있습니다. 그렇기 때문에 그들은 단지 연결되어 있고 중복되지 않습니다. 오른쪽의 연결된 열에 표시됩니다.
MichaelHouse

답변:


13

당신이 사용하는 것 velocity(예를 들어 총알을) 일정한 속도로 개체를 이동하고 AddForce()(예를 우주선 스러 스터를위한) 움직임을 추가 할 수 있습니다. 또한 운동에는 두 가지 "유형"이 있습니다. 힘과 충동. 우주선 추진기의 경우 충동을 사용합니다.


4
우주선 추진기에 충동을 선호하는 이유를 설명 할 수 있습니까? 무기의 충격과 같은 것들로 인한 순간적인 운동량 변화보다는 시간이 지남에 따라 점진적인 가속을 적용하는 경우 실제로 이것은 적합하지 않을 수 있습니다. 시간 창에 적용하면 일반적으로 힘 (또는 질량이 요인이 아닌 경우 가속)을 원하지만 순간적으로 임펄스 (또는 그에 따라 velocityChange)를 사용합니다.
DMGregory

@DMGregory 네, 추가하려는 힘의 종류에 따라 다릅니다. 우주선 추진기의 나의 예에서, 순간 에너지 파열 인 임펄스가 올바른 선택입니다.
trojanfoe

2
태도 제트기의 짧은 발사 또는 주 엔진의 연속 연소를 의미했는지 여부는 즉시 명확하지 않았으므로 ( "추력기"는 공상 과학에서 약간 사용됨) 누군가가 시도하지 않도록 명확히해야한다고 생각했습니다. 로켓 부스터에 임펄스를 사용합니다. ;)
DMGregory

@DMGregory 실제로; 내 우주 기술 용어는 주로 영화를 기반으로합니다 :)
trojanfoe

@trojanfoe Go는 KSP를한다. 지금처럼
user253751

21

이미 받아 들여진 답변이 있지만 추가 가치가있는 부분이 있다고 생각합니다.

속도 사용

속도를 설정하면 해당 객체의 움직임에 영향을 줄 수있는 다른 모든 것을 절대적으로 무시합니다. 트로이 포아의 예에서와 같이, 발사되는 순간 총알의 초기 속도를 설정하는 것과 같은 일부 상황에서는 바람직합니다. 잘못된 상황에서 사용하면 문제가 발생할 수 있으므로주의하십시오.

  • 여러 소스 / 스크립트가 동일한 Rigidbody의 속도를 직접 설정하여 (예 :) 수정하려고하면 body.velocity = foo마지막 승리는 실행되고 다른 하나는 효과가 없습니다. 이로 인해 업데이트 버그가 발생할 수 있습니다. 특히 개체가 움직이거나 느려지는 경우 (중력으로 인한 가속이 누적되기 전에 재정의되기 때문에)

  • 프레임마다 속도를 설정하면 다른 객체와의 충돌이 약간 이상 할 수 있습니다. 마치 무한한 토크로 엔진에 의해 물체가 추진되는 것처럼 보입니다. 충격에서 얼마나 많은 속도를 잃어도 다음 물리 단계에서 최고 속도로 돌아오고 속도가 충격에서 벗어나지 않습니다. . 이로 인해 충돌하는 물체가 시작되거나 작은 물체가 생각보다 큰 물체를 훨씬 더 쉽게 밀 수 있거나 물체가 튕겨 나가는 대신 정적 장벽을 따라 천천히 미끄러 져 움직일 수 있습니다.

이 두 가지 효과 모두 때때로 필요할 수 있습니다. 예를 들어 Kinect 게임을 제작할 때 플레이어의 가상 아바타 팔다리가 물리 장면과 상호 작용할 수있게하려면 일반적으로 직접 속도 설정을 사용하여 해당 바디를 이동합니다. 플레이어의 실제 손은 알려진 장소에 있고 가상 객체와의 충돌로 인해 느려지지 않았으므로, 가상 손은 정렬 상태를 유지하기 위해 동일한 작업을 수행해야하므로이 경우 실제로 원합니다. 다른 모든 물리 효과를 재정의 합니다. 가져와

애드 포스와 친구들

이와 대조적으로 AddForce 및 이와 유사한 도우미 기능은 물리 세계에서 진행되는 다른 모든 작업에 협력하도록 만들어졌습니다. Rigidbody에 여러 소스 / 스크립트 AddForce가있는 경우 이러한 모든 효과가 함께 추가되어 객체의 움직임에 순 변화가 발생합니다 (계산 방법에 따라 순서에 독립적 일 수도 있음). 이를 통해 하나의 스크립트가 다른 물리 효과를 완전히 밟지 않도록 할 수 있습니다.

AddForce는 옵션 ForceMode 매개 변수 를 지정하여 다음과 같은 네 가지 방식으로 제공됩니다 .

ForceMode       |   Use
-----------------------------------------------------------------------
Force (default) |   Accelerate an object over 1 time step, based on its mass.
                |   Units: Newtons = kg * m/s^2
                |
Acceleration    |   Accelerate an object over 1 time step, ignoring its mass. (like gravity)
                |   Units: m/s^2
                |
Impulse         |   Instantaneously propel an object, based on its mass
                |   Units: N * s = kg * m/s
                |
VelocityChange  |   Instantaneously propel an object, ignoring its mass
                |   (like body.velocity = foo, except multiple scripts can stack)
                |   Units:  m/s

자동차 운전이나 로켓 연소 또는 중력을 잘 당기는 것과 같이 시간이 지남에 따라 연속적인 푸시 (예 : 모든 FixedUpdate를 적용하는 것)를 모델링하려는 경우 Force 또는 Acceleration이 필요합니다. (무거운 물체가 더 느리게 가속되기를 원하는지에 따라)

총알 발사, 폭발로 인한 반동 또는 장벽을 튀어 오르는 것과 같이 갑자기 급격한 움직임의 변화를 모델링하는 경우 임펄스 또는 속도 변경이 필요할 수 있습니다.

AddForce를 사용하면보다 실감 나는 현실감을 얻을 수 있지만 행동의 물리학을 생각하는 데 더 많은 시간을 소비해야 할 수도 있습니다. 예를 들어, 신체가 목표 속도까지 유한 한 가속을 갖도록하려면 매 프레임마다 속도를 설정하는 것보다 충돌에보다 사실적으로 반응하도록하려면이 도우미 함수와 비슷한 계산이 필요할 것입니다.

public static void AccelerateTo(this Rigidbody body, Vector3 targetVelocity, float maxAccel)
{
    Vector3 deltaV = targetVelocity - body.velocity;
    Vector3 accel = deltaV/Time.deltaTime;

    if(accel.sqrMagnitude > maxAccel * maxAccel)
        accel = accel.normalized * maxAccel;

    body.AddForce(accel, ForceMode.Acceleration);
}

이 "도우미 함수"를 모두 호출하는 이유는 기술적으로 다음과 같은 목적을 달성 할 수 있기 때문입니다.

 body.velocity += suitablyCalculatedDeltaV;

( 제 생각에 . AddForce를 통한 Unity의 PhysX / Box2D 기반 물리 솔버 버퍼 변경은 개별적으로 가능하지만, 이것의 명백한 결과는 보지 못했다)

하루가 끝날 무렵,이 함수들이 실제로 우리에게주는 것은 의도의 명확성입니다 . 점진적인 힘을 적용하고 싶을 때 deltaV에 Time.deltaTime을 곱하고 질량으로 나누는 것을 기억할 필요가 없습니다. ForceMode.Force를 원한다고 말하면 정확하고 일관된 방식으로 처리됩니다. 그리고 나 또는 다른 사람이 나중에 내 코드를 반복 할 때 시간과 질량 계산을 해독하지 않고도 내가 의미하는 바를 즉시 알 수 있습니다.


6

이외에 Trojanfoe의 답변 Angry Birds vs Car Racing. 이 방법들에 대한 두 가지 주요한 예 AddForcevelocity각각 다른 예 . 예를 들어, Angry Birds에서는 속도를 사용하는 것이 조금 더 어렵습니다.

Angry Birds에서 AddForce를 사용하면

_birdRigidbody.AddForce(new Vector2(5,5));

속도를 사용하면 궤적을 사용하여

x = v*t*Cos(theta) y = v*t*Sin(theta) - 0.5 * g * t *t

또는 이와 같은 것.

Car Racing 게임을하는 동안 Angry Birds, 즉 Shoot와 같은 것이 아니라 항상 속도를 제어해야합니다. 그 시나리오에서velocity 은보다 유용합니다 AddForce.

이해하시기 바랍니다. 최소한 조금.


1
AngryBirds 예제는 슬링 샷이 해제 될 때 시간 창에서 그 효과를 시뮬레이트하는 기본 ForceMode.Force가 아니라 순간적으로 운동량 (예 : Impulse 또는 VelocityChange)을 사용해야합니다. 두 접근 방식 중 하나에서 동등한 동작을 얻도록 숫자를 조정할 수 있지만 고정 시간 간격을 변경하면 힘 솔루션이 다른 출력을 갖습니다 (길이가 짧거나 짧은 시간 간격에 힘을 통합하기 때문에). 그것은 단지 방출 순간을 나타 내기 때문에 바람직하다.
DMGregory

0

Rigidbody Velocity와 Rigidbody Addforce는 Unity 3D의 두 가지 혼란스러운 기능이며 초보자는 종종 차이점을 이해하지 못합니다. 이 기사에서는 RigidBody.velocity와 RigidBody.addforce의 차이점에 대해 설명합니다.

두 경우 모두 애드 포스 함수이든 속도 함수이든 관계없이 힘이라는 용어를 사용합니다.

Rigidbody.velocity를 사용하는 경우,이 경우 객체에 힘을 추가하지만이 힘은 계속해서 힘을 가하지 않으면 객체를 움직입니다.

예를 들어

body.velocity = 새로운 Vector3 (0,0,5);

z 위치에 5f를 추가했다고 가정하면 W 키를 누르면 그 힘이 추가됩니다. 따라서 W 키를 누르면 객체가 즉시 5의 속도로 시작합니다. 자동차에서이 기능을 사용하여 힘을 추가하는 경우와 동일합니다. 그 자동차는 5의 속도로 시작합니다.

body.velocity = 새로운 Vector3 (0,0,200);

그리고 값을 200으로 변경 한 다음 W를 저장 한 후 W를 누르면, 자동차는 시작부터 200의 속도로 달리기 시작합니다. 실제 세계에서는 불가능합니다.

이제 Rigidbody에 대해 이야기하면

우리의 자동차 예제를 계속함으로써. 차에 200의 힘을 가하면

body.addforce (0,0,200);

W 키를 누르면 Car가 200의 속도로 움직이기 시작하지 않지만 천천히 시작하여 Drag 값에 따라 속도를 높이고 멈 춥니 다.

Rigidbody.addforce는 느린 테이블을 드래그하는 것처럼 느리게 시작한 다음 속도를 높입니다. 먼저 테이블을 밀기 시작하면 테이블이 약간 움직이기 시작하지만 테이블을 계속 밀면 이동 & 해당 테이블을 떠나면 표면에 따라 약간의 거리가 적용되며 동일한 rigidbody입니다.

Rigidbody.velocity를 사용하면 플레이어 점프처럼 즉시 반응하도록 개체를 이동하고 점프 후 바로 그 힘의 결과가 사라지고 느린 시작이 필요한 곳에서 Rigidbody.addforce를 사용할 수 있습니다. 로켓. 점프에서 Rigidbody.addforce를 사용하면 플레이어 / 오브젝트는 잠시 동안 공간에 남아있다가 다시 지상으로 돌아옵니다.

(출처)


최소한 스택 교환 답변 형식으로 게시물을 수정하고 수정해야합니다. :)
Vaillancourt
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.