So I've been working on a music player in Unity. It gets the audioclips from an array within Unity, and a random number generator picks a clip between 0 and the size set in Unity. However, nothing stops it from picking the same number (and thus same song) twice in a row which is something I do not want. I've been trying a few things but ended up with a NullReferenceException. If you'd like to take a look I'd greatly appreciate it!
Code:
using System.Collections;
using UnityEngine;
public class MusicPlayer : MonoBehaviour
{
#region Variables
//Variables needed for this code
public AudioClip[] clips;
private AudioSource audioSource;
string currentTitle = "";
#endregion
#region Start Void
// Start is called before the first frame update
void Start()
{
//Finds AudioSource in the unity editor and turns off the "loop" function.
audioSource = FindObjectOfType<AudioSource>();
audioSource.loop = false;
}
#endregion
#region Private AudioClip
//The code below will grab a random audio clip between 0 and the amount set in the Unity Editor.
private AudioClip GetRandomClip()
{
return clips[Random.Range(0, clips.Length)];
}
#endregion
#region Update Void
// Update is called once per frame
void Update()
{
if (audioSource.clip.name.Length >= 0)
{
currentTitle = audioSource.clip.name;
}
if (!audioSource.isPlaying)
{
var nextTitle = currentTitle;
ulong index = 0;
while (nextTitle == currentTitle)
{
index = (ulong) Random.Range(0, clips.Length);
nextTitle = clips[index].name;
}
audioSource.Play(index);
}
}
#endregion
}
Went back into my code to prepare it for future stuff as well like calling audio clips from multiple arrays and with the help of both Silleknarf and derHugo I got it worked out. Thank you all so much. Here is the code I ended up with:
/*
AudioPlayer.cs
RTS Game
Created by Robin den Ambtman on 17-06-2019
Copyright © Robinblitz. All rights reserved.
*/
using System.Collections;
using UnityEngine;
using System.Linq;
public class AudioPlayer : MonoBehaviour
{
#region Variables
//Variables needed for this code
[Header("Sound arrays")]
public AudioClip[] musicClips;
[Space(10)]
public AudioClip[] announcerClips;
[Space(10)]
public AudioClip[] TBDClips;
[Header("Effect/Music sources")]
public AudioSource effectAudioSource;
public AudioSource musicAudioSource;
#endregion
#region Start Void
// Start is called before the first frame update
void Start()
{
//Finds AudioSource in the unity editor and turns off the "loop" function.
musicAudioSource.loop = false;
Random.InitState((int)System.DateTime.Now.Ticks);
}
#endregion
#region Music RNG
//The code below will grab a random audio clip between 0 and the amount of clips set in the Unity Editor.
private AudioClip GetRandomMusicClip()
{
// This returns only those clips that are not the currenty played one
var filteredClips = musicClips.Where(c => c != musicAudioSource.clip).ToArray();
return filteredClips[Random.Range(0, filteredClips.Length)];
}
#endregion
#region Update Void
// Update is called once per frame
void Update()
{
//If the audio source is playing it will grab the song that's picked out by GetRandomClip() and plays it.
if (!musicAudioSource.isPlaying)
{
var newTitle = GetRandomMusicClip();
musicAudioSource.clip = newTitle;
musicAudioSource.Play();
}
//Piece of code as a test to play a specific audio clip on key press.
if (Input.GetKeyDown(KeyCode.Space))
{
effectAudioSource.PlayOneShot(effectAudioSource.clip, 0.7f);
}
}
#endregion
}