1. 벡터란?
벡터는 방향과 크기를 갖는 데이터 타입이다.
Unity에서는 주로 위치나 속도를 표현할때 사용된다.
2. 벡터 연산
2.1. 덧셈
한 위치에서 순차적으로 이동하는 것을 표현
식 :
C = A + B (처음 위치 A에서 B만큼 이동한 위치)
2.2. 벡터의 뺄셈
두 위치간의 방향과 거리를 계산
식 :
C = A - B (A 위치에서 B 위치까지 가는 방향과 거리)
2.3. 내적 (Dot Product)
두 벡터 사이의 각도 관계를 스칼라 값으로 표현
같은 방향일 때 최대(1), 수직일때 0, 반대 방향일때 최소값(-1)을 갖는다.
식 :
a·b = |a||b|cosθ = ax×bx + ay×by + az×bz
반지름이 1인 원에서 내적값은 cosθ값과 같다.
유니티에서의 활용 :
- Vector3.Dot(a, b);
- 대상이 캐릭터의 정면에 있는지 체크
- 캐릭터의 시야각 계산
ex)
적이 플레이어를 정면으로 바라보고있는지 체크
bool IsEnemyLookingPlayer()
{
// 적의 위치에서 플레이어 방향으로의 단위벡터를 계산
Vector3 enemyToPlayer = (playerPos - transform.position).normalized;
// 내적값이 1에 가까울수록 적이 플레이어를 정면으로 바라보고 있음
float lookAmount = Vector3.Dot(transform.forward, enemyToPlayer);
// 0.7은 약 45도의 코사인값
return lookAmount > 0.7f;
}
2.4. 외적(Cross Product)
두 벡터가 이루는 평면의 수직방향 벡터를 생성 (노말벡터)
벡터의 크기는 두 벡터가 이루는 평행사변형의 면적
두 벡터가 평행하면 외적의 결과는 0
식 :
|a×b| = |a||b|sinθ
= (
ay×bz - az×by,
az×bx - ax×bz,
ax×by - ay×bx
)
외적의 결과는 A, B 벡터가 이루는 평면에 수직인 벡터이다.
유니티에서의 활용 :
- Vector3.Cross(a, b);
- 대상이 캐릭터의 왼쪽인지 오른쪽에 있는지 체크
- 카메라 방향 설정
ex)
회전 방향 결정
void Rotation()
{
Vector3 forward = transform.forward;
Vector3 toTarget = (targetPos - transform.position).normalized;
// 외적의 결과값으로 출력되는 벡터를 회전축으로 사용
Vector3 rotationAxis = Vector3.Cross(forward, toTarget);
// 회전 방향 결정
// - y가 양수: 시계 반대 방향 회전 (rotationDirection = 1)
// - y가 음수: 시계 방향 회전 (rotationDirection = -1)
float rotationDirection = (rotationAxis.y > 0) ? 1f : -1f;
transform.Rotate(Vector3.up * rotationSpeed * rotationDirection * Time.deltaTime);
}
3. 벡터 관련 메서드
3.1. 정규화 (Normalize)
벡터의 방향은 유지하고 크기를 1로 만든다.
유니티에서의 활용 :
- Vector.normalized;
- 크기가 필요 없는 방향 벡터만 필요할 때 사용
ex)
플레이어 이동시 대각선방향 속도를 보정
// 플레이어 이동
void Move(float speed)
{
// 입력 받기
float horizontal = Input.GetAxis("Horizontal");
float vertical = Input.GetAxis("Vertical");
// 이동 벡터 계산
Vector3 movement = new Vector3(horizontal, 0f, vertical);
// 정규화로 대각선 이동 속도 보정
movement = movement.normalized * speed * Time.deltaTime;
// 이동 적용
transform.position += movement;
}
3.2. 크기 (Magnitude)
벡터의 길이(크기)를 계산
유니티에서의 활용 :
- Vector3.magnitude;
- 속도의 크기 측정
ex)
Vector3 playerPos = transform.position;
Vector3 targetPos = target.position;
// 방향 구하기
Vector3 direction = (targetPos - playerPos).normalized;
// 거리 구하기
float distance = Vector3.magnitude(targetPos - playerPos);
// 적이 플레이어의 시야에 있는지 확인
float dotProduct = Vector3.Dot(transform.forward, direction);
if(dotProduct > 0.5f) // 60도 이내
{
Debug.Log("적이 시야 내에 있음");
}
'Unity' 카테고리의 다른 글
Delegate, Action, Event (1) | 2024.11.07 |
---|---|
Null 관련 연산자 (3) | 2024.10.31 |
비동기 프로그래밍 (0) | 2024.09.08 |
Rigidbody.velocity 천천히 떨어지는 문제 (0) | 2024.04.21 |