나는 이런 종류의 일을 너무 자주 본다:
transform.position = Vector3.Lerp(startPos, endPos, Time.deltaTime);
그것을 게시하는 사람은 일반적으로 그것이 Vector3.Lerp“깨졌다”고 확신하지만 실제 문제는 그들이 그것을 올바르게 사용하지 않는다는 것입니다.
“선형 보간”의 약어인 Lerp는 매우 간단한 작업을 수행합니다. 두 값이 주어지면 두 값 x사이 의 백분율 y값을 반환합니다 . t출력이 변경될 것으로 예상되는 경우 전달하는 인수에 이를 반영해야 합니다!
Time.deltaTime위의 예에서는 가장 최근 프레임 동안 경과한 시간만 전달하므로 를 전달하는 것은 의미가 없습니다 . 게임이 일정한 50fps로 실행되는 경우 항상0.02 .
해당 타이머가 여러 프레임에 걸쳐 누적되도록 하면 더 나은 결과를 얻을 수 있습니다.
이와 같은 내용이 요점을 전달해야 합니다.
public class LerpExample : MonoBehaviour {
float lerpTime = 1f;
float currentLerpTime;
float moveDistance = 10f;
Vector3 startPos;
Vector3 endPos;
protected void Start() {
startPos = transform.position;
endPos = transform.position + transform.up * moveDistance;
}
protected void Update() {
//reset when we press spacebar
if (Input.GetKeyDown(KeyCode.Space)) {
currentLerpTime = 0f;
}
//increment timer once per frame
currentLerpTime += Time.deltaTime;
if (currentLerpTime > lerpTime) {
currentLerpTime = lerpTime;
}
//lerp!
float perc = currentLerpTime / lerpTime;
transform.position = Vector3.Lerp(startPos, endPos, perc);
}
}
빈 장면을 만들고, 큐브에 놓고, 이 스크립트를 첨부하고, 실제로 작동하는 모습을 볼 수 있습니다.
변수는 원래 있던 perc곳에 사용됩니다 . Time.deltaTime무엇입니까 perc? 이는 Lerp를 통한 진행 상황을 나타내는 0와 사이의 숫자입니다 .1
궁금하신 분들은 lerpTime또는 변경하면 결과를 확인해보세요 moveDistance.
모든 것을 Lerp
Unity는 다양한 값을 보간하기 위한 도우미 함수를 제공합니다.
Mathf.LerpVector3.LerpColor.Lerp
하지만 결국에는 Mathf.Lerp 만 있으면 됩니다. 다른 것들은 단지 편의를 위한 방법일 뿐입니다. 보간해야 할 클래스나 데이터에 대해 자체 Lerp 함수를 작성하는 것은 충분히 쉽습니다.
Unity가 회전을 표현하기 위해 사용하는 쿼터니언의 특정 경우에는 Slerp 또는 “Spherical Lerp”도 있습니다.
두 개의 값이 있고 두 값 사이를 원활하게 전환하고 싶으십니까? 보간은 당신의 친구입니다!
Lerp 너머
만약 우리가 t단순한 백분율이 아닌 Lerp a를 통과한다면 어떻게 될까요? 두 점 사이에 그래프로 표시된 직선 대신 일종의 곡선을 원하면 어떻게 될까요? 0입력은 과 사이에 있어야 1하지만 이를 수행하는 기능이 많이 있습니다.
예를 들어, sinerp를 사용하여 “완화”할 수 있습니다.
float t = currentLerpTime / lerpTime; t = Mathf.Sin(t * Mathf.PI * 0.5f);

또는 coserp를 사용하여 “편안하게” 할 수도 있습니다.
t = 1f - Mathf.Cos(t * Mathf.PI * 0.5f)

기하급수적인 움직임을 만들 수도 있습니다.
t = t*t

그 자체를 곱하는 것에 는 흥미로운 특징이 있습니다. 과 사이에 있는 t한 , 그 자체를 여러 번 곱하면 항상 와 사이에 있는 숫자가 생성됩니다 .t01t01
스무스스텝
위에서 언급한 곱셈 속성은 유명한 “스무스 스텝” 공식 과 같이 이지 인(Ease In) 및 이지 아웃(Ease Out)하는 일부 보간 방법의 핵심 개념입니다 .
t = t*t * (3f - 2f*t)

아니면 제가 개인적으로 좋아하는 “smootherstep”도 있습니다.
t = t*t*t * (t * (6f*t - 15f) + 10f)

정말 매끄러워요! (저항할 수 없었습니다.)
제가 언급한 이러한 추가 공식 중 다수는 Unity에 포함되어 있지 않지만, 이를 통해 찾거나 생성할 수 있는 모든 함수를 자유롭게 사용할 수 있습니다.
숨쉬게 해라
끝나지 않는 Lerp는 어떻습니까?
Robert Yang은 “가끔 사인파로 게임의 모든 것을 애니메이션화할 수 있었으면 좋겠다”고 말한 적이 있습니다 .
일부 게임에서는 플레이어가 실행되는 동안 약간의 “머리 흔들림”이 발생합니다. 다른 게임에서는 메인 메뉴 카메라에 부드러운 밥이 필요합니다. 나는 “코를 고는” 불빛이 점점 희미해졌다가 사라지는 것을 본 적이 있습니다. 어떤 경우이든, 나는 파동 함수가 얼마나 환상적으로 유용할 수 있는지 지적하고 싶습니다. 입력 영역은 무한하므로 끝이 없으며 출력 범위는 좁고 일정하므로 제어하기 쉽습니다.
예를 들어, 다음 스크립트는 사인파에 따라 객체를 천천히 위아래로 움직이게 만듭니다.
public class BreatheSimple : MonoBehaviour {
Vector3 startPos;
protected void Start() {
startPos = transform.position;
}
protected void Update() {
float distance = Mathf.Sin(Time.timeSinceLevelLoad);
transform.position = startPos + Vector3.up * distance;
}
}
사인파를 조정하면 더 많은 제어가 가능해집니다.
public class Breathe : MonoBehaviour {
Vector3 startPos;
public float amplitude = 10f;
public float period = 5f;
protected void Start() {
startPos = transform.position;
}
protected void Update() {
float theta = Time.timeSinceLevelLoad / period;
float distance = amplitude * Mathf.Sin(theta);
transform.position = startPos + Vector3.up * distance;
}
}
진폭은 개체가 이동하는 거리를 제어합니다. period는 얼마나 빨리 수행되는지를 제어합니다.

플레이어의 머리 봅슬레이에는 작은 진폭과 짧은 기간이 필요할 수 있습니다. 메뉴 카메라의 느린 호흡으로 인해 매우 오랜 시간이 걸리거나 다양한 속도로 여러 축에서 움직임이 필요할 수 있습니다.
수학을 정리할 수만 있다면 원하는 동작은 무엇이든 얻을 수 있습니다.
사인파의 절대값만 취하면 어떻게 될까요? 상향 전용 수신 거부.
사인파의 출력을 0과 사이에 고정하면 어떻게 됩니까 1? 바운스 사이에 일시 중지가 있는 위쪽으로만 바운싱합니다. 이유를 알 수 있나요? 고정된 곡선을 직접 그리면 명확해집니다.
0.6해당 웨이브의 출력을 과 사이에 고정하면 어떻게 될까요 1? 일종의 “두근두근” 모션을 얻을 수 있나요? UI에서 경고를 확장하는 데 유용할 수 있습니까?
정말 멋지게 만들고 싶다면 애니메이션 곡선을 사용하여 Lerp 매개변수를 관리할 수도 있습니다.
나는 꽤 난해한 곡선과 파동 함수를 작성했습니다. 그것을 섞는 것을 두려워하지 마십시오.
닫는 중
Lerp는 다양한 응용 프로그램에서 쉽고 강력한 기능입니다.
제가 작성한 첫 번째 플러그인 중 하나는 다양한 줌과 위치 사이를 보간하는 카메라 관리자였습니다. 또한 보간을 사용하여 재료 매개변수, UI 애니메이션, 물리적 힘, 오디오 볼륨, 간단한 컷씬 등을 관리했습니다.
이것은 사용법을 알면 점점 더 자주 등장하는 망치 중 하나입니다.
많은 코드를 작성하고 싶지 않거나 빠르게 시작하고 싶다면 iTween, GoKit 또는 Hotween과 같은 플러그인을 사용하여 Unity에 많은 추가 보간 지원을 추가할 수 있습니다.