241223

lililllilillll·2024년 12월 23일

개발 일지

목록 보기
29/350

✅ 오늘 한 일


  • Project Etude


🎮 Project Etude


게임 시작 씬 제작

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class StartDirector : MonoBehaviour
{
    [SerializeField] private Cinemachine.CinemachineVirtualCamera virtualCamera;
    [SerializeField] private GameObject player;
    [SerializeField] private float titleFadeDuration;
    [SerializeField] private float PressAnyKeyFadeDuration;
    [SerializeField] private GameObject canvas;
    [SerializeField] private CanvasRenderer Title;
    [SerializeField] private CanvasRenderer PressAnyKey;
    [SerializeField] private GameObject middle;
    [SerializeField] private float orthTargetSize;
    [SerializeField] private float orthSmoothTime;
    private bool game_start = false;
    private float velocity = 0.0f;
    SpriteRenderer playerSprite;


    // Start is called before the first frame update
    void Start()
    {
        playerSprite = player.GetComponent<SpriteRenderer>();
    }

    // Update is called once per frame
    void Update()
    {
        // PressAnyKey.SetAlpha(Mathf.PingPong(Time.time * blinkSpeed, 1)); // Alpha 값을 0과 1 사이로 반복
        if (Input.anyKeyDown && !game_start)
        {
            StartCoroutine(TitleFadeOut());
            StartCoroutine(PressAnykeyFadeOut());
        }
        if (!game_start)
        {
            PressAnyKey.SetAlpha(Mathf.PingPong(Time.time * 1f, 0.75f) + 0.25f); // Alpha 값을 0.5와 1 사이로 반복
        }
    }

    private IEnumerator TitleFadeOut()
    {
        game_start = true;
        yield return new WaitForSeconds(1.5f); // 1초 대기
        float elapsedTime = 0f;
        player.SetActive(true);

        while (elapsedTime < titleFadeDuration)
        {
            elapsedTime += Time.deltaTime;
            Title.SetAlpha(Mathf.SmoothStep(1f, 0f, elapsedTime / titleFadeDuration)); // 초반에 급하게 사라지다가 후반에 느리게 사라지게                                                                           
            yield return null;
        }

        yield return new WaitForSeconds(0.5f); // 0.5초 대기

        // 완전히 투명해진 뒤 오브젝트 비활성화
        canvas.SetActive(false);
        elapsedTime = 0f;

        while (elapsedTime < titleFadeDuration)
        {
            elapsedTime += Time.deltaTime;
            // 플레이어 sprite renderer alpha 서서히 증가시키기
            if (playerSprite != null)
            {
                playerSprite.color = new Color(playerSprite.color.r, playerSprite.color.g, playerSprite.color.b, Mathf.SmoothStep(0f, 1f, elapsedTime / titleFadeDuration));
            }
            yield return null;
        }

        virtualCamera.Follow = middle.transform;
        StartCoroutine(SmoothOrthographicSizeChange());
    }

    private IEnumerator PressAnykeyFadeOut()
    {
        float elapsedTime = 0f;

        while (elapsedTime < PressAnyKeyFadeDuration)
        {
            elapsedTime += Time.deltaTime;
            PressAnyKey.SetAlpha(Mathf.Lerp(1f, 0f, elapsedTime / PressAnyKeyFadeDuration)); // 서서히 Alpha 값을 0으로
            yield return null;
        }
    }

    private IEnumerator SmoothOrthographicSizeChange()
    {
        while (Mathf.Abs(virtualCamera.m_Lens.OrthographicSize - orthTargetSize) > 0.01f)
        {
            virtualCamera.m_Lens.OrthographicSize = Mathf.SmoothDamp(
                virtualCamera.m_Lens.OrthographicSize,
                orthTargetSize,
                ref velocity,
                orthSmoothTime
            );
            yield return null;
        }

        // 플레이어 스크립트 활성화
        player.GetComponent<Bar_Judge_Movement>().enabled = true;
    }

}

씬 연출 코드.

게임 오버 후 콜라이더 제대로 안 켜짐

    void Update()
    {
        if (Input.GetMouseButtonDown(1))
        {
            player.GameOver(); // 디버그용 게임 오버
        }
    }

게임 매니저에 대충 게임 오버 기능 달아놨는데

    public void GameOver()
    {
        NoteBlock turnOnBlock = missionBlockCollider.GetComponentInParent<NoteBlock>();
        while (turnOnBlock.noteBlockIndex != 0)
        {
            turnOnBlock.EnableCollider();
            turnOnBlock = turnOnBlock.prevNoteBlock.GetComponent<NoteBlock>();
        }

인덱스 0인 건 콜라이더를 다시 켜주질 않는다. 이거 누가 짬;

        NoteBlock turnOnBlock = missionBlockCollider.GetComponentInParent<NoteBlock>();
        while (turnOnBlock != null)
        {
            turnOnBlock.EnableCollider();
            turnOnBlock = (turnOnBlock.prevNoteBlock != null)
            ? turnOnBlock.prevNoteBlock.GetComponent<NoteBlock>() : null;
        }

고쳤다.

오프셋 테스트

        if (OffsetTestMode) // 오프셋 계산할때만 작동
        {
            if (missionBlockIndex == 2)
            {
                WakeUpAllBlocks();
                missionBlockIndex = 0;
            }

            offsetTest.GetOffset();
        }

방금 만들었던 블럭 깨우는 함수 따로 메서드로 빼주고 WakeUpAllBlocks()로 호출
이제 두 블럭 사이 와리가리 무한 반복은 됨.

문제는 85bpm 메트로놈 음원 가져와서 정확히 bpm에 맞게 자르고 재생했는데
시간이 지날때마다 박자가 점점 어긋난다는거. 이래서야 박자 오프셋 테스트가 될 수가 없다.

편집 안 한 30분짜리 그대로 갖다 써봤더니 박자는 맞다. 자르는 과정에서 오차 때문에 박자가 어긋났는듯.

그리고 현재 translate의 문제점이 있다. 1프레임 당 이동하는 시간이 있다 보니까 필연적으로 오차가 발생함.
애써 외면해왔던 문제인데, 이제 정확하게 어떻게 계산되는지 생각을 해야할 것 같음.

정확한 파일 길이는 생성 > 리듬 트랙 (audacity 내장 기능)으로 해결
된줄 알았는데 이것도 Loop를 돌려도 재생 딜레이가 있어서 살짝씩 늦춰진다.
무조건 긴 파일로 해야 딜레이 없이 띵동거리는듯.

내장 기능 소리는 길이 재는 용도로 쓰면 될듯. 소리는 메트로놈이 더 나음.

그냥 5분짜리 박아버리려고 했는데, 분명 로딩 될때까지 기다리는데도 인풋 렉이 발생함.

처음 띵동 시작할 때 렉 걸리면서 점프해버리는게 녹화 렉이나 영상 렉이 아니다.
순수 유니티 에디터 렉임.

아니 처음 시작할 때 렉 걸리는거면 시작하자마자 바로 재생하고 바로 다시 멈춰놓은 다음에
필요할 때 다시 틀면 되겠네? 천잰가;

    void Start()
    {
        playerSprite = player.GetComponent<SpriteRenderer>();
        Metronome.Play();
        Metronome.Pause();
    }

놀랍지만 해결됐다.
엉터리같지만 메모리에 올라오는 딜레이를 없앤다는 점에서 완벽한 해결책.
빌드했을 때 게임 시작시 이것 때문에 렉 걸리는지만 확인해보면 될듯.

이름 바꾸기

스팀에 데모 올리려고 스팀웍스 등록하고 있었는데,
상표권 이슈가 갑자기 생각남.

https://brunch.co.kr/@abcip/11

여기에 적힌 바에 의하면 스타필드는 "내려받기 가능한 컴퓨터 프로그램"이라는 것 때문에 문제 생겼다고 하는데
Etude는 첫 번째 용어인 컴퓨터 작동 소프트웨어가 마음에 걸림.
출시명은 살짝 바꿔야할듯

https://musescore.com/user/38235231/scores/5940010
슈만이 작곡한 Little Etude라는 곡도 있다. 이걸 인트로 bgm으로 쓰면 될듯?

오늘 최종 결과물



profile
너 정말 **핵심**을 찔렀어

0개의 댓글