ETC/Project

BMS 기반 리듬게임 개발

VallistA2014. 6. 21. 01:17


 

(그림 1) 현재 진행된 게임 스크린샷


bms 파싱게임 RhythmStar 프로토 타입


조작키 : A S D F J K L ;


P : 증속

O : 감속


--------------------------------------------------------------------------------


사용 엔진 : Cocos2d-x  , FMOD

사용 언어 : c++ , Java 


참조 문서 : 

http://cosmic.mearie.org/2005/03/bmsguide/ (BMS 관련 파일 형식 사이트)

http://smilejsu.tistory.com/380 (BPM 계산방식)

http://cafe.naver.com/cocos2dxusers (Cocos2d-x 사용자 모임)

http://lab.gamecodi.com/board/zboard.php?id=GAMECODILAB_Lecture_series&page=1&sn1=&divpage=1&sn=off&ss=on&sc=on&select_arrange=hit&desc=asc&no=38 (게임코디 C# BMS 리더기)

 

개발 기간 :


처음으로 개발해보는 BMS 연동 리듬게임이라 만드는데 시간이 꽤나 걸림. (c++ 관련해서는 자료 하나도 없었다.)

C#은 자료가 있어서 그쪽 좀 보고 했음. (위에 보면 게임코디 뭐시기 있을겁니다. 그 사이트로 이동하시면 보이실겁니다.)


개발 소요 약 2달 (Cocos2d-x 로 안했으면 더 빠르게 완성 되었을듯 싶네요)


소스 코드 구조 및 현재 진행된 구조 상황


(그림 2) 구조


STEP 0.

  - 게임 구조 및 기틀 마련


STEP 1.

  - BMS 스크립트 해석

  - BMS 스크립트 적용


STEP 2.

  - BMS 스크립트 기반 노트 생성

  - 노트 떨어지는 시간 맞추기

  - 노트 떨어지고 마지막 라인 닿으면 소리 나도록


-> 여기까지 하시면 BMS 음악 플레이어의 완성


STEP 3.

  - UI 만들기

  - 키보드 누를시 이벤트 생성

  - 각각 키 누를시 다음 노트 분석해서 키음 출력


STEP 4.

  - 노트 판정 추가

  - 노트 판정이 일어난 후 노트 삭제

  - 배속 추가

 

STEP 5.

  - 잡다한 이펙트 , UI 디자인

  - 콤보 및 판정 띄우기

  - 점수 및 최대 콤보, BPM 띄우기

  - 현재 재생 시간 바로 나타내기


 - > 여기까지 완료


STEP 6.

  - 뒷배경 동영상 띄우기 <진행중>

  - 안드로이드 연동

  - FMOD 안드로이드 연동

  - FFMPEG 안드로이드 , PC 연동

  - 롱노트


--------------------------------------------------------------------------------


Ver 0.1 동영상


 - 쪽팔려서 삭제


Ver 0.2 동영상

 

 

테스트 음악

削除 : Kronos


 - 배속 추가

 - UI 추가

 - 키음 추가

 - 키보드 이펙트 추가

 - HP 추가

 - HP 바 추가


Ver 0.3 동영상



테스트 음악

Daisan : -+


 - 점수 추가

 - 판정 추가

 - 체력 감소 증가 이벤트 추가

 - 콤보 , 판정 뷰

 - 최대 콤보

 - 이펙트 추가

 - 재생시간 추가


---------------------------------------------------------------


코딩방식

- 배속

 배속같은 경우에는 보이는 위치만 변경시켜 주었습니다.

 보이는 위치를 변경시켜주면 빨리 내려오는 것 처럼 보이기 때문이죠.


 m_pNote->getAnimation()->setPosition(ccp(m_pNote->getPos().x, (dTemp - D_JUDGE_POSITIONY) * D_ASSET_MNG->getAttachment() + D_JUDGE_POSITIONY )); 

 이런식 입니다.


 - 매니저

 각각의 Game 과 UI 쪽은 모두 분할되어 있습니다. UI Manager 와 GameManager로 분할되어있고, UI Manager를 GameManager 안에서 사용하는 방식이죠.

 그리고 UIManager와 게임은 이벤트로 서로 통신을 합니다.

 이름하여 이벤트식 코딩이랄까요?

 

 콤보같은 경우도 게임에서 이벤트를 보냅니다. 그러면 UI 쪽에서 받고 이펙트를 보여주는 방식인 겁니다.


 - BMS 

 BMS 의 경우에는 상당히 복잡한 구조로 되어있습니다.

 파일을 받은 포인터를 가져와서 포인터를 한줄씩 읽는 방식입니다.

 한줄에서 #이 들어가 있나를 체크를 하고 없으면 Next Line , 있으면 매소드중 분석하여 넣는 방식입니다.


 - 연주 방식

 노트 하나당 모두 키음을 가지고 있고, 보이지 않는 공간에서 치는 노트가 아닌 다른 노트들이 돌아갑니다.

 판정라인에 붙이쳐서 소리가 나는 방식이고, 그저 보이지 않는 곳에서 노트가 계속 떨어져서 음을 재생시킨다고 보시면 되겠습니다.


 

 

이 프로젝트에는 쓰레드가 들어가 있지 않아서 로딩속도가 굉장히 느립니다 ^^

로딩 속도를 늘리시려면 쓰레드를 추가해주신후 거기서 추가적으로 노트 데이터를 로드 하시면 됩니다


====================================================================================================


깃허브에 공유했습니다. 링크는 아래와 같습니다.


https://github.com/Vallista/ProjectBMSReader

리소스 파일이 저작권 침해의 문제가 있어서 뺏습니다.

소스만 보시면 될 것 같습니다.

'ETC > Project' 카테고리의 다른 글

BMS 기반 리듬게임 개발  (291) 2014.06.21

댓글

  • 이전 댓글 더보기
  • 2016.01.08 14:31 비밀댓글입니다
  • BlogIcon VallistA2016.01.11 14:29 신고 안녕하세요

    소스코드 보내드렸습니다 ^^

    도움이 되셨으면 좋겠습니다.
  • 2016.01.13 11:05 비밀댓글입니다
  • BlogIcon VallistA2016.01.13 12:00 신고 안녕하세요
    소스코드를 깃헙에 공유했습니다 링크는 아래와 같습니다.

    https://github.com/Vallista/ProjectBMSReader

    참고하시면 되겠습니다 ^^
  • 2016.01.16 22:49 비밀댓글입니다
  • BlogIcon VallistA2016.01.19 08:42 신고 안녕하세요 Johell 님

    https://github.com/Vallista/ProjectBMSReader/blob/master/ProjectRhythmstar/Classes/CShortNote.cpp

    에 소스코드를 보시면 MoveTime이라는 함수가 있습니다.
    내부를 살펴보면 4줄정도의 소스코드가 있습니다.

    첫번째 줄인
    m_dBarperSecond = ((4 * 60) / D_ASSET_MNG->getBPM());
    부터 설명을 드리자면, 이 부분은 분당 마디의 갯수를 나타냅니다.
    BPM이 144라고 하면, 1마디는 4박자이므로, 기준은 60BPM으로 두고 4 * 60을 하면 대강 분당 비트수를 알 수 있으며, 거기서 BPM을 나누게 되면 나오게 됩니다.

    BPM에 관한 정보는 아래와 같습니다.
    http://vallista.tistory.com/entry/리듬게임-강좌-01-BPM이-무엇인가

    그리고 코딩 방법인데요, 저기서 보시면 저는 노트 하나하나마다 업데이트를 돌려서 내렸습니다.
    물론 여기서 최적화를 한다면 최적화를 하겠지만, 최적화를 안해도 그럭저럭 굴러가더라군요,...
  • 2016.01.20 02:49 비밀댓글입니다
  • BlogIcon VallistA2016.02.01 09:34 신고
    마디 분 속 (m) : ((4 * 60) / 노래의 BPM)
    마디 내려오는 시간 (ms) : (높이 10으로 가정) 10 * (deltaTime / m)

    프레임당 노트의 이동속도는
    마디 분 속에서 프레임 값 나누면 나올듯 싶습니다.
  • 2016.01.29 11:51 비밀댓글입니다
  • BlogIcon VallistA2016.02.01 09:35 신고 재가공 없이 만드시는 게임에 삽입할 때는
    런칭 하실때 문제가 됩니다.

    이미 다른 게임이 상용에 있고, 그것에 대해서는 재산권을 보유중인 거라..
  • 2016.02.01 18:20 비밀댓글입니다
  • BlogIcon VallistA2016.02.02 09:41 신고 답변 달아주셔서 감사합니다.
    제가 야근을 많이 하고 있어서.. ㅠ 최근에 못봅니다...
  • Untiy2016.01.30 00:05 혹시 유니티코드는 공유안되나요?!?!ㅠㅠ개발중인데 잘안되네요 참고만하고싶습니다
  • BlogIcon VallistA2016.02.01 09:35 신고 유니티 코드 날라가서 드리고 싶은데 못드리네요 ㅠ
  • 2016.02.05 14:37 비밀댓글입니다
  • BlogIcon VallistA2016.02.12 08:59 신고 안녕하세요 보내드렸습니다 ^
  • 2016.02.11 23:48 비밀댓글입니다
  • BlogIcon VallistA2016.02.12 09:37 신고 안녕하세요 초보 개발자님 ^^

    FMOD와 Media Player 는 둘 중 어떤 것을 쓰셔도 별 상관은 없지만, FMOD는 아무래도 전문 라이브러리다 보니 녹음, 속도등 기본 제공 보다 빠릅니다. 그리고 수많은 코덱을 더 지원하다 보니 ogg, mp3, flac 등 여러가지를 폭넓게 지원할거에요.

    개인적인 생각이지만, FMOD를 사용하는 편이 범용적인 부분에서는 좋은 것 같고 개발론 적인 부분에서는 Media Player 가 더 간편하므로 그거 쓰는게 쉽고 간편하지 않을까 싶습니다.
  • 2016.02.25 16:14 비밀댓글입니다
  • BlogIcon VallistA2016.03.02 16:42 신고 안녕하세요 초보학생님.
    게시글에 하단부분 보시면 깃허브에서 확인 하실 수 있습니다.
    감사합니다
  • pke2016.03.02 12:26 안녕하세요 지금 OpenAL을 사용해서 ogg를 미리 압축을 푼 뒤에 메모리에 올려놓은 뒤에 재생시켜주는 오인페 매니저를 제작하고 있습니다.

    그런데 FMOD 소스랑 사이트 예제보니까 OpenAL로 만든거에 비해서 너무 간편하더군요.

    혹시 FMOD에서 ogg나 mp3의 압축을 풀어서 메모리에 올리는 함수가 있는지 궁금해서요. 리듬게임이라 아무래도 그냥 처음부터 ogg나 mp3를 재생시켜버리기엔 핸드폰 기종이 너무 천차만별이고 저사양 고사양까지 시작 딜레이를 맞춰주려니 압축을 풀고 미리 올리는건 거의 필수더군요.

    현재는 싱크 조절기능을 넣어두고 OpenAL이랑 OggVorbis를 이용해 직접 압축 풀고 메모리에 올리는걸 만들어서 현재는 어느정도 해결이 된 상태인데, 혹시나 FMOD에서 지원해주는 것이 있다면 그냥 그걸로 갈아타고 싶습니다. 아무래도 검증된 것을 사용하는게 좋을 것이니까요 ㅠㅠ

    알고 계신 정보가 있으시면 공유해주시면 감사하겠습니다 꾸벅

    아 참고로 코코스투디x의 기본 탑재된 오디오 라이브러리가 win32랑 iOS는 OpenAL을 사용하는데, 안드로이드는 OpenSL을 사용합니다
  • BlogIcon VallistA2016.03.02 16:48 신고 안녕하세요.

    FMOD는 OpenAL또는 OpenSL 와 틀리게 처음부터 상용으로 나온거라 상당히 많은양의 라이브러리를 제공하지만. 무료버전에는 FMOD_MODE 등의 압축 메서드를 안가지고 있는것으로 알고 있습니다.

    FMOD 에서 Sound Initialize Function은 compression 하여 기본적으로 PCM 메모리에 올라가게 됩니다.
  • BlogIcon VallistA2016.03.02 16:50 신고 Cocos2d-x가 Android OS에서 상당히 구진이유중에 하나인데..
    Cocos2d-x SoundLibrary는 Linux Kernel 단에서 Sound Resource를 최대 1024 메모리를 할당하게 되어있는데, 이러한 문제는 BMS같은 수많은 Sound Sample을 사용하는 곳에서 로딩이라던가의 문제가 야기됩니다.

    이 것을 해제하기 위해서 삽질을 해봤는데 OpenSL을 깊게 다뤄본게 아닌지라..
  • 2016.04.27 01:55 비밀댓글입니다
  • BlogIcon VallistA2016.04.27 15:55 신고 안녕하세요. 음원의 파형을 분석하여 자동으로 노트를 생성 할 수 있는 기능 구현 가능합니다. Unity, 등등 대중화된 툴에 에셋에는 사운드 높낮이, 파형 분석 이퀄라이저, 등이 있으며 오픈 소스로도 존재합니다.
    구현 장벽은 현저하게 낮아졌습니다.

    다만 정교한 구현에 대해서는 구현 방법에 대해서 삽질을 해봐야 할 것 같습니다.
  • 2016.04.28 10:34 비밀댓글입니다
  • 2016.05.15 22:55 비밀댓글입니다
  • BlogIcon VallistA2016.05.20 13:52 신고 안녕하세요.

    FMOD DSP, wavelength 에 대해서 찾아보시면 빠르실꺼에요
  • 2016.06.02 15:04 비밀댓글입니다
  • BlogIcon VallistA2016.06.08 09:39 신고 안녕하세요.

    소스코드 : https://github.com/Vallista/ProjectBMSReader

    깃 허브에 소스코드를 올려놨습니다.
    Cocos2d-x로 mp3 플레이어를 구현하실 수 있을 겁니다.
    가능하십니다.

    FMOD를 쓰셔야 할 것이에요. 왜냐하면 Cocos2d-x에서는 기본적으로 자체 제작 사운드라이브러리를 사용하는데 이게 기능이 별로 좋지 않아서..
  • 김시현2016.08.16 10:06 와 정말로 감사합니다. 많은 도움이 될 것같습니다. 정말 감사합니다
  • 2016.11.10 12:01 비밀댓글입니다
  • 2016.11.25 15:13 비밀댓글입니다
  • 2017.03.07 15:55 비밀댓글입니다
  • 2017.03.16 17:36 비밀댓글입니다
  • 송준섭2017.07.07 09:13 저도 리듬게임을 만들어 봤는데 키 입력을 한채로 가만히 있어도 콤보가 올라가는데 해결방법이 있을까요...?
  • BlogIcon VallistA2017.07.11 10:24 신고 KeyDown 될때만 올라가도록 설정하세요
  • 2017.12.01 22:04 비밀댓글입니다
  • 2017.12.01 22:05 비밀댓글입니다
댓글쓰기 폼

VallistA

병특이 끝나서 게임에서 웹으로 스위칭한 프로그래머.
프로그래밍 정보등을 공유합니다.

자고 싶습니다. ㅠㅠ

페이스북    :: 링크
카카오톡    :: kingbye1
Github      :: 링크

궁금한점 문의 주시면 답변드리도록 하겠습니다

VISITED

Today : 17

Total : 341,806

SNS

  • 페이스북아이콘
  • 카카오톡아이콘
  • 트위터아이콘