-
Notifications
You must be signed in to change notification settings - Fork 2
develop‐Sound
Seong Hyeok OH edited this page Jul 22, 2023
·
3 revisions
- SoundManager를 Loading씬에 배치
- Audio Source는 스크립트로 추가하기에 컨포넌트에 추가하지 않는다.
- 필요한 BGM과 Click 소리를 넣는다.
- SoundManager: 사운드 값 저장, 상황 별 BGM과 사운드 이팩트 재생
using UnityEngine;
using UnityEngine.SceneManagement;
using System.Collections;
public class SoundManager : MonoBehaviour
{
public static SoundManager instance;
public float BgmVolume { get; set; } = 1.0f; // BGM 볼륨
public float SoundEffectVolume { get; set; } = 1.0f; // 사운드 이펙트 볼륨
public bool IsFullScreen { get; set; } = true; // 전체 화면 토글 상태
public AudioClip ButtonSoundClip; // 버튼 소리 파일
public AudioClip[] Bgm;
public AudioSource BgmAudioSource; // BGM을 재생할 오디오 소스
public AudioSource SoundEffectAudioSource; // 사운드 이펙트를 재생할 오디오 소스
private string mCurrentScene; // 현재 씬의 이름을 저장할 변수
private AudioClip currentSoundEffect;
private void Awake()
{
if (instance == null)
{
instance = this;
DontDestroyOnLoad(gameObject);
BgmAudioSource = gameObject.AddComponent();
SoundEffectAudioSource = gameObject.AddComponent();
}
else if (instance != this)
{
Destroy(gameObject);
return;
}
}
private void Start()
{
mCurrentScene = SceneManager.GetActiveScene().name;
SceneManager.sceneLoaded += OnSceneLoaded;
LoadSettings();
PlayBgm(mCurrentScene);
}
#region 저장
private void LoadSettings()
{
// BGM 볼륨 로드
BgmVolume = PlayerPrefs.GetFloat("SoundManager_BgmVolume", 1.0f);
// 사운드 이펙트 볼륨 로드
SoundEffectVolume = PlayerPrefs.GetFloat("SoundManager_SoundEffectVolume", 1.0f);
// 전체 화면 토글 로드
IsFullScreen = PlayerPrefs.GetInt("SoundManager_IsFullScreen", 0) == 1;
}
public void SaveSettings()
{
// BGM 볼륨 저장
PlayerPrefs.SetFloat("SoundManager_BgmVolume", BgmVolume);
// 사운드 이펙트 볼륨 저장
PlayerPrefs.SetFloat("SoundManager_SoundEffectVolume", SoundEffectVolume);
// 전체 화면 토글 저장
PlayerPrefs.SetInt("SoundManager_IsFullScreen", IsFullScreen ? 1 : 0);
// PlayerPrefs 데이터를 디스크에 저장
PlayerPrefs.Save();
}
#endregion
#region 사운드 재생
public void ChangeBGM(AudioClip clip)
{
BgmAudioSource.clip = clip;
BgmAudioSource.volume = BgmVolume;
BgmAudioSource.Play();
}
public void PlayButtonSound()
{
SoundEffectAudioSource.PlayOneShot(ButtonSoundClip, SoundEffectVolume);
}
public void PlaySoundEffect(AudioClip soundEffectClip)
{
SoundEffectAudioSource.PlayOneShot(soundEffectClip, SoundEffectVolume);
}
public void PlayRateSound(AudioClip soundEffectClip)
{
SoundEffectAudioSource.PlayOneShot(soundEffectClip, SoundEffectVolume * Constants.SOUND_EFFECT_RATE);
}
public void PlayOverlapSound(AudioClip soundEffectClip)
{
if (currentSoundEffect != null && currentSoundEffect == soundEffectClip)
{
// 현재 사운드 이펙트가 이미 재생 중인 경우, 중첩 재생을 피하기 위해 종료합니다.
return;
}
currentSoundEffect = soundEffectClip;
SoundEffectAudioSource.PlayOneShot(soundEffectClip, SoundEffectVolume);
StartCoroutine(ResetCurrentSoundEffect(soundEffectClip.length));
}
private IEnumerator ResetCurrentSoundEffect(float delay)
{
yield return new WaitForSeconds(delay);
currentSoundEffect = null;
}
private void OnSceneLoaded(Scene scene, LoadSceneMode mode)
{
if (scene.name != mCurrentScene)
{
if (scene.name == "InGame")
{
// 이전 씬과 다른 BGM인 경우 새로운 BGM 재생
StopBgm();
PlayBgm(scene.name);
}
else if (scene.name == "GameResult")
{
StopBgm();
PlayBgm(scene.name);
}
else
{
// 이전 씬과 동일한 BGM인 경우 이어서 재생
}
}
}
private void PlayBgm(string sceneName)
{
if (BgmAudioSource == null)
{
Debug.LogError("AudioSource 컴포넌트가 없습니다!");
return;
}
AudioClip bgmClip;
if (sceneName == "InGame")
{
// InGame 씬에 진입한 경우
bgmClip = Bgm[(int)Enums.EBgm.Stage1]; // InGame 씬에 해당하는 BGM
}
else
{
// 나머지 씬에 진입한 경우
bgmClip = Bgm[(int)Enums.EBgm.BGM]; // 나머지 씬에 해당하는 BGM
}
BgmAudioSource.clip = bgmClip;
BgmAudioSource.volume = BgmVolume;
BgmAudioSource.Play();
}
private void StopBgm()
{
BgmAudioSource.Stop();
}
#endregion
}
- OptionalController: 변경된 값 보내기, 저장하기
using UnityEngine;
using UnityEngine.UI;
public class OptionalController : MonoBehaviour
{
[SerializeField] Slider mBgmSlider;
[SerializeField] Slider mSoundEffectSlider;
[SerializeField] Toggle mFullScreenToggle;
private SoundManager mSoundManager;
private void Start()
{
mSoundManager = SoundManager.instance;
// 저장된 설정 값을 슬라이더에 반영
LoadSettings();
mBgmSlider.onValueChanged.AddListener(OnBgmVolumeChanged);
mSoundEffectSlider.onValueChanged.AddListener(OnSoundEffectVolumeChanged);
mFullScreenToggle.onValueChanged.AddListener(OnFullScreenToggleChanged);
}
private void LoadSettings()
{
// BGM 볼륨 로드
float bgmVolume = mSoundManager.BgmVolume;
mBgmSlider.value = bgmVolume;
// 사운드 이펙트 볼륨 로드
float soundEffectVolume = mSoundManager.SoundEffectVolume;
mSoundEffectSlider.value = soundEffectVolume;
// 전체 화면 토글 로드
bool isFullScreen = mSoundManager.IsFullScreen;
mFullScreenToggle.isOn = isFullScreen;
OnFullScreenToggleChanged(isFullScreen);
}
public void OnBgmVolumeChanged(float value)
{
// BGM 볼륨 값을 변경
mSoundManager.BgmVolume = value;
mSoundManager.BgmAudioSource.volume = value;
mSoundManager.SaveSettings();
}
public void OnSoundEffectVolumeChanged(float value)
{
// 사운드 이펙트 볼륨 값을 변경
mSoundManager.SoundEffectVolume = value;
mSoundManager.SoundEffectAudioSource.volume = value;
mSoundManager.SaveSettings();
}
public void OnFullScreenToggleChanged(bool value)
{
mSoundManager.IsFullScreen = value;
if (value)
{
Screen.SetResolution(Screen.currentResolution.width, Screen.currentResolution.height, true);
}
else
{
Screen.SetResolution(1920, 1080, false);
}
mSoundManager.SaveSettings();
}
}