AudioSource won't play

I’m trying to program footsteps for my player character. I’m doing this by attaching a simple boolean to the Headbob script: when the head is bobbing (ie the character is moving), play the clip, otherwise don’t. The script is attached to the main camera, while the source is attached to the player, so I’ve been using ((AudioSource)GameObject.Find(“~player~”).GetComponent(“AudioSource”)) to first access the AudioSource and then use it with either audio.Play() or audio.Pause(). However, I just can’t get it to work. The most I get is a random muffled tap every so often, or a very very faint and constant sound, but obviously neither of these are footsteps. I’ve even used Debug.Log(((AudioSource)GameObject.Find(“~player~”).GetComponent(“AudioSource”)).audio.isPlaying) to try and figure out my problem, but it returns true at all the appropriate times. Any suggestions?

UPDATE Upon further testing, it seems that the footsteps are playing, they just sound incredibly, incredibly distorted, like the player is running on uneven bubblewrap as opposed to, you know, walking.

using UnityEngine;
using System.Collections;

[RequireComponent(typeof(AudioSource))]
public class Headbobber: MonoBehaviour 
{
 
  public float moveSpeed = 1.5F;
  private Vector3 moveDir = new Vector3(0, 0.1F, 0);
  private Vector3 initPos, movement;
  private float moveTime = 0;
  private float twoPI = Mathf.PI * 2;
  public bool isBobbing = false;

  void Start()
  {
    initPos = transform.localPosition;
  }
 
   void Update () 
   {
    Debug.Log(((AudioSource)GameObject.Find("~player~").GetComponent("AudioSource")).audio.isPlaying);
      if(((navigation)GameObject.Find("~player~").GetComponent("navigation")).isMoving == true)
      {
        isBobbing = true;
        moveTime += Time.deltaTime * moveSpeed;
        movement = transform.TransformDirection(moveDir) * Mathf.Sin(twoPI * moveTime);
        transform.localPosition = initPos + movement;
        ((AudioSource)GameObject.Find("~player~").GetComponent("AudioSource")).audio.Play();
      }
      else
      {
        isBobbing = false;
        ((AudioSource)GameObject.Find("~player~").GetComponent("AudioSource")).audio.Pause();
        
      }
   }
 
 
}

I believe your problem is that you are calling ‘audio.Play()’ every frame, even if the audio clip is already playing. You might be able to fix this just by only calling it if AudioSource.isPlaying is false. There are a few other issues here as well. You don’t want to call GameObject.Find() or even GetComponent() every frame if you can avoid it. Also, since the Audio source is on the player, not the camera, you don’t need to require an AudioSource component on this game object. Here is a bit of cleanup and rewrite. I’m using InvokeRepeating() to time the footsteps, but you could use a timer or even the isPlaying check outlined above (untested):

using UnityEngine;
using System.Collections;
 
public class Headbobber: MonoBehaviour 
{
	public float moveSpeed = 1.5F;
	private Vector3 moveDir = new Vector3(0, 0.1F, 0);
	private Vector3 initPos, movement;
	private float moveTime = 0;
	private float twoPI = Mathf.PI * 2;
	private GameObject goPlayer;
	private navigation nav;
	private AudioSource aud;
	
	void Start()
	{
		initPos = transform.localPosition;
		goPlayer = GameObject.Find("~player~");
		nav = goPlayer.Getcomponent(navigation);
		aud = goPlayer.audio;
		InvokeRepeating ("PlayFootstep", 0.0f, 0.75f);
	}
	
	void PlayFootstep()
	{
		if (nav.isMoving)
			aud.Play();
	}
	
	void Update () 
	{
		Debug.Log(aud.isPlaying);
		if(nav.isMoving)
		{
			moveTime += Time.deltaTime * moveSpeed;
			movement = transform.TransformDirection(moveDir) * Mathf.Sin(twoPI * moveTime);
			transform.localPosition = initPos + movement;
		}

	}
}

Try setting an AudioSource variable as

public AudioClip theClip = ((AudioSource)GameObject.Find("~player~").GetComponent("AudioSource"));
theClip.Play(0);