using UnityEngine; #if UNITY_EDITOR using UnityEditor; #endif using UnityEngine.Audio; public class MusicManager : MonoBehaviour { public static MusicManager Instance { get; private set; } [Header("Clip & Output")] [Tooltip("The music track to loop.")] public AudioClip musicClip; [Tooltip("Optional mixer group output (Master/Music).")] public AudioMixerGroup outputMixer; [Header("Playback")] [Tooltip("Start playback automatically when the game starts.")] public bool playOnStart = true; [Tooltip("Loop the music indefinitely.")] public bool loop = true; [Header("Controls")] [Range(0f, 1f)] [Tooltip("Music volume (0..1).")] public float volume = 0.6f; [Tooltip("Mute/unmute music.")] public bool mute = false; AudioSource _source; void Awake() { // Singleton guard if (Instance != null && Instance != this) { Destroy(gameObject); return; } Instance = this; DontDestroyOnLoad(gameObject); // AudioSource setup _source = GetComponent(); if (_source == null) _source = gameObject.AddComponent(); _source.playOnAwake = false; _source.loop = loop; _source.clip = musicClip; _source.spatialBlend = 0f; // 2D music if (outputMixer) _source.outputAudioMixerGroup = outputMixer; ApplyInspectorSettings(); if (playOnStart && musicClip != null) _source.Play(); } void OnValidate() { // Keep runtime in sync with inspector tweaks if (_source != null) { ApplyInspectorSettings(); // If you assign a new clip at runtime and playOnStart is true, auto-play it if (!_source.isPlaying && playOnStart && musicClip != null && Application.isPlaying) _source.Play(); } } void ApplyInspectorSettings() { if (_source == null) return; _source.mute = mute; _source.volume = Mathf.Clamp01(volume); _source.loop = loop; if (_source.clip != musicClip) { _source.clip = musicClip; } } // Public helpers if you ever want to drive it from code/UI public void SetMuted(bool value) { mute = value; ApplyInspectorSettings(); } public void SetVolume(float value) { volume = Mathf.Clamp01(value); ApplyInspectorSettings(); } public void Play() { if (musicClip != null) _source.Play(); } public void Stop() { _source.Stop(); } }