2024.10.16 - [게임만들기/UNITY] - [UNITY] 첫 3D 팽이 게임 만들기 - 각저항 분석 후 팽이 '잘'돌리기
0. 개발 목표
1) 필드에 벽을 세우고 팽이가 벽충돌시의 물리 적용하기
- 기존 개발 방식은 Raycast의 거리가 땅을 검사하고 거리가 줄어드면 각 저항을 증가시켜 팽이를 멈춤
- 벽과 땅을 구분하고 벽에는 Bounce + 이동방향 변경, 땅에는 각저항 증가
2) Bounce 구성하기
- 벽에 팽이 Collider가 충돌하면 OnCollisionEnter()를 통해 진행방향 벡터 변경
1. 테스트 환경 구성
1) 기존 필드에 팽이 대신 테스트용 오브젝트 추가
기존 팽이는 비활성화하고 3D 오브젝트 구에 RigidBody와 Wall, Ground에 Tag 추가 카메라 Follow 설정 변경
벽은 Kinematic를 활성화하고 충돌과 관련한 모든 오브젝트에 Collision Detection을 Continuous로 변경하여 오브젝트가 프레임 차이시간에 뚫고 나가는 것을 방지.
2) ColliderTest 스크립트 임시 추가
- 상하좌우 입력받고 벽에 붙을때 Log 출력 추후 다른 오브젝트 충돌과도 고려하여 switch 문으로 작성하고 오브젝트의 Tag를 비교하여 각 오브젝트에 대한 함수 실행
private void OnCollisionEnter(Collision other) { switch(other.gameObject.tag){ case "Floor": Debug.Log("땅"); break; case "Wall": Debug.Log("벽"); break; } }
- 벽과 충돌시 입력된 벡터의 반사 벡터 방향으로 충돌 오브젝트에 AddForce() 하는 함수 구현.
private void OnCollisionEnter(Collision other)
{
switch(other.gameObject.tag){
case "Floor":
Debug.Log("땅");
break;
case "Wall":
Vector3 normal =other.contacts[0].normal;
Debug.Log("벽");
DoBounce(normal);
break;
}
}
void DoBounce(Vector3 normal)
{
Debug.Log("Dobounce = " + Vector3.Reflect(inputVec,normal) );
rigid.AddForce(Vector3.Reflect(inputVec,normal)*speed, ForceMode.VelocityChange);
}
Vector에서 Reflect 매게변수는 입사 벡터, 법선벡터로 벽과 충돌시점의 포인트의 법선벡터 인 normal을 이용하여 DoBounce를 수행한다. 보기 쉽게 임시적으로 반사벡터에 100f 의 힘을 추가했다.
using System.Collections;
using System.Collections.Generic;
using UnityEditor.Callbacks;
using UnityEngine;
public class ColliderTester : MonoBehaviour
{
public float speed = 10f;
public float transX;
public float transY;
Vector3 inputVec;
Rigidbody rigid;
private void Awake()
{
rigid = GetComponent<Rigidbody>();
}
private void Update()
{
transX = Input.GetAxisRaw("Horizontal");
transY = Input.GetAxisRaw("Vertical");
inputVec = new Vector3(transX, 0, transY).normalized * Time.deltaTime * speed ;
}
private void FixedUpdate()
{
transform.Translate(inputVec);
}
private void OnCollisionEnter(Collision other) {
switch(other.gameObject.tag){
case "Floor":
Debug.Log("땅");
break;
case "Wall":
Debug.Log("벽");
Vector3 vector3 =other.contacts[0].normal;
DoBounce(vector3);
break;
}
}
void DoBounce(Vector3 inNor){
Debug.Log("Dobounce = " + Vector3.Reflect(inputVec,inNor) );
rigid.AddForce(Vector3.Reflect(inputVec,inNor)*100,ForceMode.VelocityChange);
}
}
테스트를 하고나니 오래 돌게할려고 꺼둔 중력이 문제다.
벽에 충돌하는 순간 팽이에 Y 값이 충돌한 벡터 만큼 변경되어 중구난방으로 튀어버리는 것.
모양이 큐브이거나 구체인 경우 덜컹거리는(?) 느낌의 조정으로 다시 회전시키면 괜찮은데 팽이가 진행방향과 다른 방향의 기울기로 변경되고 중력이 꺼지면서 매우 이상하게 회전했다. 다음에는 해당 내용을 좀 연구해서 충돌을 추가하려 한다.
'게임만들기 > UNITY' 카테고리의 다른 글
[UNITY] 첫 3D 팽이 게임 만들기 - 각저항 분석 후 팽이 '잘'돌리기 (2) | 2024.10.16 |
---|---|
[UNITY] 첫 3D 팽이 게임 만들기 - 원뿔로 팽이 프로토타입 만들기 (1) | 2024.10.15 |