Unity 입문 TopDown Shooting - 파티클 생성

Amberjack·2024년 1월 22일
0

Unity

목록 보기
18/44
post-custom-banner

🪄 파티클 시스템(Particle System)

  • 파티클 시스템은 수 천개의 작은 2D 또는 3D 오브젝트들을 관리하고, 그들의 동작과 생애를 제어한다. 각각의 작은 오브젝트를 '파티클'이라고 한다.
  • 파티클 시스템의 주요 컴포넌트는 'emitter'(발사체), 'particles'(파티클), 'animator'(애니메이터), 'renderer'(렌더러) 등으로 이루어져 있다.
  • Unity의 파티클 시스템은 시간에 따른 파티클의 행동을 시뮬레이션하며, 이를 위해 각 파티클에 대해 위치, 속도, 수명, 색상, 크기 등의 정보를 저장한다.
  • 파티클 시스템은 성능 최적화를 위해 다양한 기능을 제공한다. 예를 들어, 시스템의 최대 파티클 수를 제한하거나, 파티클의 적용 범위를 제한하는 등의 기능이 있다.

❗ 애니메이션 이벤트(Animation Events)

  • 애니메이션 이벤트를 사용하면 애니메이션이 진행되는 동안 코드를 실행시킬 수 있다. 예를 들어, 캐릭터가 특정 동작을 할 때 사운드를 재생하거나, 특정 애니메이션 프레임에서 파티클 시스템을 발사하는 등의 작업을 할 수 있다.
  • 애니메이션 이벤트는 Unity 애니메이션 편집기에서 설정할 수 있다. 편집기를 통해 애니메이션 타임라인에 이벤트를 추가하고, 해당 이벤트가 호출할 함수를 지정할 수 있다.
  • 애니메이션 이벤트는 해당 애니메이션 클립이 재생되는 게임 오브젝트에 연결된 모든 스크립트에서 호출할 수 있는 함수를 실행할 수 있다.
  • 이벤트는 특정 프레임에서만 실행되며, 애니메이션 상태가 변경될 때에도 자동으로 실행되지 않는다.
  • 애니메이션 이벤트를 사용하면 애니메이션과 코드의 상호작용을 더욱 유연하게 관리할 수 있다. 이를 통해 애니메이션의 시각적 효과와 사운드, 효과 등의 프로그래밍적 요소를 조화롭게 통합할 수 있다.
  • 애니메이션 이벤트를 통해 호출되는 함수는 일반적으로 공용 함수(public function)이어야 하며, 매개변수가 없거나 최대 하나의 매개변수를 가질 수 있다.

🪄 파티클 생성!

  • 걸어다닐 때 바닥에 일어나는 먼지를 구현해보자!
  • 화살이 벽에 부딪힐 때의 파티클을 구현해보자!

🪄 먼지!

Player 밑에 Effects → Particle System을 생성한다. 이름을 DustParticles로 변경한다.

이후, DustParticles의 Inspector에서 Renderer → Order in layer를 4로 변경한다.

세부 설정!

duration : 0.2
Looping : false
Start Life Time : 0.5
Start Speed : 0.2
Start Size : Random Between Two Constants 로 변경, 0.1 ~ 0.3

Start Color : Random Between Two Colors 로 변경, 첫 번째 색은 회색, 두 번째 색은 연한 검은색 정도로 조정한다(먼지 색깔)

Simulation Space를 World로 변경한다. → 파티클이 플레이어의 하단에 끌려다니는 것이 아니라, 월드에 흩뿌린다는 의미.

Emission 탭을 수정한다.

Rate over Time은 0으로 변경.
Bursts는 새로 추가하여 Count를 5로 변경한다.(먼지의 개수)

Shape 탭을 수정한다.

Shape을 Circle로 변경해준다. → 2D이기 때문에 Corn(꼬깔)모양이 필요 없다.

Radius를 0.1로 변경한다.

Color of Life Time을 수정한다.


맨 끝의 알파 값을 75로 변경하여 점점 투명해지도록 만든다.

Size of Life Time을 수정한다.

Size가 점점 작아지는 Curve로 변경한다.

Renderer 를 수정한다.

스프라이트 를 변경해준다.

⌨️ DustParticleController.cs

Controllers 폴더 밑에 DustParticleController.cs를 만들어 준다.

public class DustParticleController : MonoBehaviour
{
    [SerializeField] private bool createDustOnWalk = true;      // 걸을 건지에 대한 bool 값
    [SerializeField] private ParticleSystem dustParticleSystem;     // 파티클 시스템 가져오기

    public void CreateDustParticles()
    {
        // 걷기 시작할 경우
        if (createDustOnWalk)
        {
            dustParticleSystem.Stop();      // 이미 진행하던 먼지 파티클을 종료하고,
            dustParticleSystem.Play();      // 다시 실행
        }
    }
}

이후, DustParticleController를 Player의 MainSprite에 추가한다. → Animator가 달려있는 곳에 달아준다!!!

❗ DustParticleController 실행하기!

플레이어의 애니메이션 레코더, player_run 애니메이션에 들어간다.

1 프레임, 3 프레임에 Add Event를 해준다.

Add Event를 해주면 Inspector 창에 Animation Event를 설정하는 창이 나온다.

Animation Event의 Function을 DustParticleController → Methods → CreateDustParticles로 변경한다.

확인해보기!

🏹 화살!

화살이 벽에 부딪힐 때의 파티클을 만들어 보자.
ProjectileManager 밑에 Particle System을 추가하자.

이후 아래와 같이 수정하기!

Limit Velocity over LifeTime을 수정한다.

Speed → 0
Dampen → 0.2
Multiply by Size는 false

Dampen은 속도의 감소.

Color of LifeTime을 수정한다.


알파값은 75, 시작 색은 약간 주황색으로 변경!

Size of Life Time을 수정한다.

앞서와 마찬가지로 점점 작아지도록 설정한다.

Collision을 수정한다!

Type을 World로 변경한다. → 월드에서 충돌하도록 설정한다.

Mode는 2D로 수정,
Dampen : 0.8,
Bounce : 0.1,
Radius : 0.2
Collider Force : 35 → 이 값을 설정해야 튕겨져 나온다.

ProjectileManager에 추가해준다.

ProjectileManager.cs에 이미 Impact Particle System을 추가했었다.

⌨️ ProjectileManager 수정하기

// ProjectileManager.cs

public void CreateImpactParticlesAtPosition(Vector3 position, RangedAttackData attackData)
{
    _impactParticleSystem.transform.position = position;        // 파티클 시스템을 충돌 위치로 옮긴다.(화살이 부딪히는 지점)
    ParticleSystem.EmissionModule em = _impactParticleSystem.emission;      // 파티클 생성

    em.SetBurst(0, new ParticleSystem.Burst(0, Mathf.Ceil(attackData.size * 5)));       // 실제 사이즈에 맞춰 충격파가 더 커지게 생성해준다.

    ParticleSystem.MainModule mainModule = _impactParticleSystem.main;
    mainModule.startSpeedMultiplier = attackData.size * 10f;        // 실제 사이즈에 맞춰 속도를 빠르게 변경해준다.

    _impactParticleSystem.Play();       // 파티클 재생
}

⌨️ RangedAttackController 수정하기

RangedAttackController.cs

// 발사체 삭제
private void DestroyProjectile(Vector3 position, bool createFx)
{
    if (createFx)
    {
        _projectileManager.CreateImpactParticlesAtPosition(position, _attackData);  // 발사체가 없어질 때 파티클 재생시키기
    }
    gameObject.SetActive(false);        // 재사용을 하기 위해 삭제가 아니라 false로 설정하기
}

확인해보기!

post-custom-banner

0개의 댓글