키입력을 받아 코인을 생성하여 랜덤 한 방향으로 뿌리는 간단한 예제입니다.
※ 유니티 버전은 2021.3.19f1 에서 진행하였습니다.
결과화면
Coin 프리팹 구조
코인 오브젝트 구조는 부모 오브젝트인 [Coin]
자식 오브젝트인 [Sprite], [Shadow]로 이루어져있습니다.
[Coin] 오브젝트에는 Coin 아래의 coin스크립트를 할당하고
[Sprite] , [Shadow] 오브젝트에는 Sprite Render와 Animaotr 컴포넌트를 할당합니다.
※ Shadow 오브젝트는 Color를 검게 변경해주시고 Layer를 -1변경합니다.
※ Animator는 굳이 포함하지 않으셔도 관계없습니다.
할당을 마친 후에는 코인 오브젝트를 프로젝트에 드래그하여 프리팹화 시켜주고
이후에 Spawn 스크립트에 프리팹을 등록해 줍니다.
Spawn 스크립트 예제
public class Spawn : MonoBehaviour
{
public int spawnCont;
public GameObject coin;
void Update() {
if(Input.GetKeyDown(KeyCode.Space)) {
for (int i = 0; i < spawnCont; i++) {
Instantiate(coin);
}
}
}
}
Spawn 예제는 Space입력을 받을 시 등록 되어있는 프리팹을 Count 만큼 생성합니다.
Coin 스크립트 예제
public class Coin : MonoBehaviour {
public int maxBounce; // 팅기는 횟수
public float xForce; // x축 힘 (더 멀리)
public float yForce; // Y축 힘 (더 높이)
public float gravity; // 중력 (떨어지는 속도 제어)
private Vector2 direction;
private int currentBounce = 0;
private bool isGrounded = true;
private float maxHeight;
private float currentheight;
public Transform sprite;
public Transform shadow;
void Start() {
currentheight = Random.Range(yForce - 1, yForce);
maxHeight = currentheight;
Initialize(new Vector2(Random.Range(-xForce, xForce), Random.Range(-xForce, xForce)));
}
void Update() {
if (!isGrounded) {
currentheight += -gravity * Time.deltaTime;
sprite.position += new Vector3(0, currentheight, 0) * Time.deltaTime;
transform.position += (Vector3)direction * Time.deltaTime;
float totalVelocity = Mathf.Abs(currentheight) + Mathf.Abs(maxHeight);
float scaleXY = Mathf.Abs(currentheight) / totalVelocity;
shadow.localScale = Vector2.one * Mathf.Clamp(scaleXY, 0.5f, 1.0f);
CheckGroundHit();
}
}
void Initialize(Vector2 _direction) {
isGrounded = false;
maxHeight /= 1.5f;
direction = _direction;
currentheight = maxHeight;
currentBounce++;
}
void CheckGroundHit() {
if (sprite.position.y < shadow.position.y) {
sprite.position = shadow.position;
shadow.localScale = Vector2.one;
if (currentBounce < maxBounce) {
Initialize(direction / 1.5f);
} else {
isGrounded = true;
}
}
}
}
(1) 오브젝트가 특정한 방향으로 포물선을 그린다.
[Coin] 부모 오브젝트를 Random.Range 만큼 X축으로 이동
transform.position += (Vector3) direction * Time.deltaTime;
[Sprite] 자식 오브젝트에서 Y축을 상승시키고 Grvity 만큼 감소시키면
sprite.position += new Vector3(0, currentheight, 0) * Time.deltaTime;
currentheight += -gravity * Time.deltaTime;
코인이 랜덤한 방향으로 포물선을 그리는 모습을 확인할 수 있습니다.
※ 한 오브젝트에서 XY축을 움직이는것이 아니라 부모 오브젝트 X축을 제어, 자식 오브젝트의 Y축을 제어하는게 포인트
(2) 추락을 멈추고 다시 포물선을 (이전 보다 낮게 상승한다) 그린다.
[Sprite] 자식 오브젝트가 점차 추락하여 기존에 멈추어있던
[Shadow] 자식 오브젝트의 위치보다 낮아질 경우
if (sprite.position.y < shadow.position.y)
current Bounce를 증가시키고 xForce, yForce축의 수치를 1.5 나눈만큼 감소시킨채
(1) 작업을 (포물선 그리기) 반복합니다.
Initialize(direction / 1.5f);
maxHeight /= 1.5f;
※ Shadow 오브젝트를 땅이라 생각하고 Sprite 오브젝트와 위치 비교를 트리거로 건 부분이 포인트
(3) Bounce 초과 시 정지
currentBounce의 수치가 maxBounce 를 넘어서게 되면 오브젝트는 바운스를 멈추고 정지합니다.
if (currentBounce < maxBounce) {
Initialize(direction / 1.5f);
} else {
isGrounded = true;
}
}
부족한 예제와 설명이였지만 많은 도움이 되셨으면 좋겠습니다.
감사합니다.
'유니티실습' 카테고리의 다른 글
유니티 시간 경과에 따른 이미지 변경해보기 (0) | 2023.03.25 |
---|---|
유니티 2D 아이템 루팅 만들어 보기 Item Looting (0) | 2023.03.24 |
유니티 Mathf.PingPong 사용해보기 (0) | 2023.03.22 |
유니티 No Sprite Editor Window registered 해결 방법 (0) | 2021.04.16 |
유니티 Platform Effector2D 관통되는 바닥만들기 (0) | 2021.04.16 |