[C++] 1.5 FMOD를 이용한 소리 재생

Date:     Updated:

카테고리:

태그:

인프런에 있는 홍정모 교수님의 홍정모의 게임 만들기 연습 문제 패키지 강의를 듣고 정리한 필기입니다.😀
🌜 공부에 사용된 홍정모 교수님의 코드들 보러가기
🌜 [홍정모의 게임 만들기 연습 문제 패키지] 강의 들으러 가기!


Chapter 1. 기본 기능 구현

1.5 FMOD를 이용한 소리 재생

FMOD 설치 및 위치와 설정

설치는 FMOP 공식 사이트에서! https://www.fmod.com

FMOD API 문서 https://www.fmod.com/resources/documentation-api

로컬 위치

image

  • 설치 경로로 찾아가자. /📁FMOD Studio API Windows
  • 아래와 같은 파일 & 폴더들을 내 C++ 프로젝트 폴더에 복사해주자.
    1. 📁core 혹은 📁fmod_lowlevel
      • 이 폴더안에는 📁inc 폴더와 📁lib이 들어 있는데 📁inc 폴더는 include해야 하는 헤더 파일들이 들어있고 📁lib 폴더엔 dll 파일들이 들어있다.
    2. 사용할 🎵wav 파일 혹은 🎵mp3 파일
    3. dll 파일들
      • 📃fmod.dll
      • 📃fmod64.dll

비주얼 스튜디오에서의 라이브러리 설정

image

프로젝트 속성이 x64로 맞춰있어야 한다.

  1. 프로젝트 속성 - V/C++디렉터리 - 라이브러리 디렉터리 - 편집
    • 하얀창에다가 같은 프로젝트 폴더로 복사해서 옮겨온 fmod의 (fmod_lowlevel) 📁lib파일의 경로를 복사하여 쓰고 확인.
  2. 프로젝트 속성 - V/C++디렉터리 - 포함 디렉터리 - 편집
    • 하얀창에다가 같은 프로젝트 폴더로 복사해서 옮겨온 fmod의 (fmod_lowlevel) 📁inc파일의 경로를 복사하여 쓰고 확인.
  3. 프로젝트 속성 - 링커 - 입력 - 추가 종속성 - 편집
    • 하얀창에다가 “fmod64_vc.lib” 입력 후 확인


FMOD 를 사용한 코드 설명

//#include "fmod.h"  // c-context
#include "fmod.hpp"
#include <iostream>
#include <conio.h>

using namespace std;

int main()
{
	cout << "FMOD cpp conext example" << endl;

	FMOD::System     *system(nullptr);   
	FMOD::Sound      *sound(nullptr);
	FMOD::Channel    *channel(nullptr);
	FMOD_RESULT       result;
	unsigned int      version;
	void             *extradriverdata(nullptr);  // 본 예제에서는 사용 x

	/* ==============================================================================
	
    각 함수마다 함수가 잘 실행됐는지 체크하는 파트 ! 
    문제가 있다면 return -1 하고 종료 
	각 함수가 정상적으로 실행 됐다면 FMOD_OK가 true일 것
	*/

	result = FMOD::System_Create(&system);
	if (result != FMOD_OK) return -1;                  // 첫번째로 꼭 꼭 !! 시스템 객체를 먼저 생성시켜야 한다.
	
	result = system->getVersion(&version);
	if (result != FMOD_OK) return -1;
	else printf("FMOD version %08x\n", version);

	result = system->init(32, FMOD_INIT_NORMAL, extradriverdata);  // 시스템 초기화 : chaneel 32개까지 사용하겠다.
	if (result != FMOD_OK) return -1;

	//result = system->createSound("singing.wav", FMOD_LOOP_NORMAL, 0, &sound);
	result = system->createSound("singing.wav", FMOD_LOOP_OFF, 0, &sound); // wav 파일로부터 sound 생성
	if (result != FMOD_OK) return -1;

	result = system->playSound(sound, 0, false, &channel); // 재생. 단 이때 딱 한번만 실행되므로 제대로 사운드가 끝까지 재생되지 않는다.  무한루프 안에서 시스템 객체를 계~~속 업데이트 시켜줘야 함.
	if (result != FMOD_OK) return -1;

	/* ===============================================================================*/

	while (true)
	{
	
		//시스템을 계속해서 업데이트 해주고 문제가 있나 체크  (사실 이 부분이 없어도 잘 돌아간다. 그치만 해주자)

		result = system->update();                  
		if (result != FMOD_OK) return -1;
		

        // 1. 이부분 실행해보거나 
		if (channel)
		{
			bool playing = false;
			result = channel->isPlaying(&playing);  // 곡이 재생 중이라면 playing이 true가 되고 재생이 끝났다면 false가 되어 무한 루프 빠져나오고 프로그램 종료 
			if (!playing) break;
		}


        // 2. 이 부분 실행해보기  ( 1, 2 중 하나만. 하나는 주석 처리하고 실행시켜 보기. 2에서 퍼즈할거니까 1 주석처리 )

		cout << "Press 0 to pause, 1 to resume, and x to exit" << endl;
		
		int i = getch(); // 키보드 입력 받아들이기. 이때 i는 아스키 코드로 정수.

		if (i == '0')                 // 0 키를 눌렀다면 채널을 잠깐 멈추기 퍼즈
			channel->setPaused(true);    // 단 channel->setPaused 는 FMOD_LOOP_NORMAL 일때만 사용 가능하다. FMOD_LOOP_NORMAL 로 바꿔주기
		else if (i == '1')             // 0 키를 눌렀다면 음악을 다시 재생
			channel->setPaused(false);
		else if (i == 'x')               // x 키를 눌렀다면 프로그램 종료 (그냥 무한루프 나가면 됨)
			break;
	}

	system->release();	// 프로그램이 끝난 후에는 리소스 릴리즈. 시스템 객체 해제.
}
  • C를 사용할거면 #include “fmod.h”
  • C++을 사용할거면 #include “fmod.hpp”
    • hpp는 C++ 전용 헤더파일이다.
  • FMOD 네임스페이스에 System, Sound, Channel이 정의 되어 있다.
    • FMOD::System * system
      • 보통 1개를 설정
    • FMOD::Sound * sound
      • 게임 내에서 사운드는 여러개가 쓰이기 때문에 보통 여러개 설정 (배열로 정리)
    • FMOD::Channel * channel
      • 얘도 보통 여러개 둠. 채널을 컨트롤하여 사운드를 볼륨 설정하거나 퍼즈함
      • 채널은 그 해당 채널에 담긴 사운드를 통째로 컨트롤 하는 용도. 볼륨 설정하거나 끄거나 퍼즈하거나.
  • FMOD_RESULT result
    • 작업 결과가 잘 나왔나 확인하는 flag
  • unsigned int version
  • FMOD 버전 확인

CreateSound

system->createSound("singing.wav", FMOD_LOOP_OFF, 0, &sound);
  • 사운드 객체를 만드는건 System이다.
  • wav, mp3 파일로부터 sound 생성한다.
  • FMOD_LOOP_OFF : 무한재생 끔
  • FMOD_LOOP_NORMAL : 무한재생 켬

PlaySound

system->playSound(sound, 0, false, &channel); // 재생
  • &channel : 어떤 채널을 통해서 재생 되는지 마지막 파라미터로 해당 채널의 포인터 넘기기
  • 사운드 객체를 재생시키는건 시스템이다.
  • 한 채널에서 여러개의 사운드를 재생할 수 있다.
  • ⭐ 단 이 함수는 딱 한번만 실행 되기 때문에 이 함수가 한 파일을 끝까지 재생시키려면 무한 루프를 넣어서 시스템을 계속해서 업데이트 시켜야함
    • 그래서 while(true)문 안에서 result = system->update();를 해주어 프로그램을 계속 실행 상태로 유지하는 것.
    • 무한루프 없다면 바로 playSound 한번 실행하고 음악 1초도 재생 안되서 프로그램 자체가 종료 될테니까!

while(true) 무한 루프

  • 무한 루프문을 돌리는 이유
    • 사운드 재생시키는 함수를 실행하고 프로그램이 바로 끝나버리지 않기 위하여.
    • 사운드 끝까지 재생이 다 끝날 때까지 프로그램이 종료되지 않게 함.
  • result = system->update();
    • PlaySound 함수가 한 파일을 끝까지 재생시키게 하기 위해 무한 루프 안에서 계속 system을 업데이트
  • channel->isPlaying(&playing)
    • 채널의 isPlaying 함수
      • 현재 재생 중이면 playing이 true가됨.
      • 재생 중이 아니라서 false면 while문 break
  • channel->setPaused(true)
    • true면 퍼즈 false면 퍼즈를 푼다.
    • 단 이 함수를 실행하려면 system->createSound(“singing.wav”, FMOD_LOOP_NORMAL, 0, &sound) Normal 상태여야 한다.
      • FMOD_LOOP_NORMAL 상태 일때만 사용 가능

기타

  • 프로그램이 끝난 후에는 system->release(); 해주어 리소스를 릴리즈 시킨다.
  • 🎵파일 이름 꼭 검토하기! .mp3파일인데 .wmv라고 쓰면 실행되지 않는다. 파일 이름 쓸 때 확장자까지 명확히 써주어야 함.


사운드 구하기

저작권 없는 무료 효과음들을 이 사이트에서 구하자. https://freesound.org



🌜 개인 공부 기록용 블로그입니다. 오류나 틀린 부분이 있을 경우 
언제든지 댓글 혹은 메일로 지적해주시면 감사하겠습니다! 😄

맨 위로 이동하기

C++ games 카테고리 내 다른 글 보러가기

댓글 남기기