Listener

From Unify Community Wiki
(Difference between revisions)
Jump to: navigation, search
(C# - Listener.cs)
(C# - Listener.cs)
Line 56: Line 56:
 
<csharp>using UnityEngine;
 
<csharp>using UnityEngine;
 
using System.Collections;
 
using System.Collections;
 +
[RequireComponent (typeof(AudioListener))]
  
// helps to automatically link the first attached instance of this script
+
public class Listener : MonoBehaviour  
// to an Audio Source, if no Audio Sources were present
+
[RequireComponent (typeof(AudioSource))]
+
 
+
// also helps to automatically link the Audio Listener
+
[ExecuteInEditMode()]
+
 
+
public class Audio : MonoBehaviour  
+
 
{
 
{
public AudioSource audioSource;
 
public Transform audioListener;
 
 
public float volume = 1;
 
public float volume = 1;
public float minVolume = 0;
 
public float maxVolume = 1;
 
public float rolloffFactor = 1;
 
public float rolloffThreshold = 1;
 
public bool ignoreDistance = false;
 
 
 
float loudness;
 
float minLoudness;
 
float maxLoudness;
 
 
float loudnessExponent = Mathf.Log(Mathf.Sqrt(10), 2);
 
float loudnessExponent = Mathf.Log(Mathf.Sqrt(10), 2);
 
public float Volume
 
{
 
get
 
{return loudness;}
 
set
 
{
 
volume = value;
 
loudness = Mathf.Pow(volume, loudnessExponent);
 
if (audioSource && ignoreDistance)
 
audioSource.volume = Mathf.Clamp(loudness, minLoudness, maxLoudness);
 
}
 
}
 
 
 
public float MinVolume
+
public float Volume
 
{
 
{
get
+
// no need for a getter; use AudioListener.volume instead
{return minLoudness;}
+
set
+
{
+
// volume values less than 0 mean nothing in Unity
+
// ensure minVolume is not greater than maxVolume;
+
minVolume = Mathf.Clamp(value, 0, maxVolume);
+
 
+
minLoudness = Mathf.Pow(minVolume, loudnessExponent);
+
}
+
}
+
 
 
public float MaxVolume
 
{
 
get
 
{return maxLoudness;}
 
 
set  
 
set  
 
{
 
{
// ensure maxVolume is not less than minVolume;
+
// volume values outside 0-1 mean nothing in Unity  
// volume values greater than 1 mean nothing in Unity
+
volume = Mathf.Clamp01(value);
maxVolume = Mathf.Clamp(value, minVolume, 1);
+
AudioListener.volume = Mathf.Pow(volume, loudnessExponent);
+
maxLoudness = Mathf.Pow(maxVolume, loudnessExponent);
+
 
}
 
}
 
}
 
}
 
 
float rolloffExponent;
+
void Start()
 
+
{Volume = volume;}
public float RolloffFactor
+
{
+
get
+
{return rolloffExponent;}
+
set
+
{
+
// Negative values don't make sense for this
+
rolloffFactor = Mathf.Max(value, 0);
+
+
rolloffExponent = Mathf.Log(.5f, (1 / rolloffFactor + 1));
+
}
+
}
+
 
 
public float RolloffThreshold
+
// Change values in the Editor; get results.
{
+
void OnDrawGizmos ()  
// no need for a getter; use rolloffThreshold directly
+
{Volume = volume;}
+
set
+
{
+
// Negative values don't make sense for this
+
rolloffThreshold = Mathf.Max(value, 0);
+
}
+
}
+
 
+
Transform thisTransform;
+
+
void Start()
+
{
+
// If there is only one Audio Source attached to this game object,
+
// and there are no other instances of this script attached,
+
// automatically link this script to the Audio Source.
+
if (GetComponents(typeof(AudioSource)).Length < 2 &&
+
GetComponents(this.GetType()).Length < 2)
+
audioSource = audio;
+
+
if (!audioListener)
+
{
+
Component listenerComponent = FindObjectOfType(typeof(AudioListener)) as Component;
+
if (listenerComponent)
+
audioListener = listenerComponent.gameObject.transform;
+
}
+
 
+
// These properties are not useful;
+
// initializing them this way keeps this script as tidy as possible.
+
if (audioSource)
+
{
+
audioSource.minVolume = 0;
+
audioSource.maxVolume = 1;
+
audioSource.rolloffFactor = 0;
+
}
+
+
thisTransform = transform;
+
+
Volume = volume;
+
MinVolume = minVolume;
+
MaxVolume = maxVolume;
+
RolloffFactor = rolloffFactor;
+
+
// Change values in the Editor (during Play Mode); get results.
+
if (Application.isEditor & Application.isPlaying)
+
StartCoroutine("RefreshProperties");
+
}
+
+
// Using OnDrawGizmos() would be a performance hit
+
// in the Editor, given several properties to update.
+
IEnumerator RefreshProperties ()
+
{
+
while (true)
+
{
+
Volume = volume;
+
yield return 0;
+
MinVolume = minVolume;
+
yield return 0;
+
MaxVolume = maxVolume;
+
yield return 0;
+
RolloffFactor = rolloffFactor;
+
        yield return 0;
+
}
+
    }
+
+
void Update ()
+
{
+
if (Application.isPlaying && audioSource && audioListener && (ignoreDistance == false))
+
{
+
float distanceToListener = Vector3.Distance(thisTransform.position, audioListener.position);
+
float rolloffBase = distanceToListener / rolloffThreshold;
+
float positionalVolume = Mathf.Pow(rolloffBase, rolloffExponent) * loudness;
+
audioSource.volume = Mathf.Clamp(positionalVolume, minLoudness, maxLoudness);
+
}
+
}
+
 
}</csharp >
 
}</csharp >

Revision as of 07:05, 19 May 2009

Author: Jessy

Contents

Description

This is a script that replaces the Volume property of the Audio Listener. It behaves more intuitively than that of the Audio Listener itself. See the page for my Audio script for extensive details.  :-D

Instructions

The Volume property performs the task that the similarly-named parameter of an Audio Listener was intended to perform. Change its value in the Editor for immediate results, or use the methods described in the JavaScript or C# sections.


JavaScript Instructions

Use the following variable declaration in an external script, and drag the Game Object containing the Audio Listener component onto the Listener variable slot in the inspector:

<javascript>var listener : Listener;</javascript>


Use listener.Volume(newVolume); to assign the volume parameter a value of newVolume, instead of assigning a value to volume directly. (You may find the way this is handled via C# to be more intuitive.)

JavaScript - Listener.js

<javascript>@script RequireComponent(AudioListener)

var volume : float = 1;

private var loudnessExponent = Mathf.Log(Mathf.Sqrt(10), 2);

function Volume (newVolume) { volume = newVolume; var listenerLoudness = Mathf.Pow(volume, loudnessExponent);

// volume values outside 0-1 mean nothing in Unity listenerLoudness = Mathf.Clamp(listenerLoudness, 0, 1);

AudioListener.volume = listenerLoudness; }

function Start() {Volume(volume);}

// Change values in the Editor; get results. function OnDrawGizmos () {Volume(volume);}</javascript>


C# Instructions

Use the following variable declaration in an external script, and drag the Game Object containing the Audio Listener component onto the Listener variable slot in the inspector:

<csharp>public Listener listener;</csharp>


Use listener.Volume = newVolume; to assign the volume parameter a value of newVolume, instead of assigning a value to volume directly.

C# - Listener.cs

<csharp>using UnityEngine; using System.Collections; [RequireComponent (typeof(AudioListener))]

public class Listener : MonoBehaviour { public float volume = 1;

float loudnessExponent = Mathf.Log(Mathf.Sqrt(10), 2);

public float Volume { // no need for a getter; use AudioListener.volume instead

set { // volume values outside 0-1 mean nothing in Unity volume = Mathf.Clamp01(value); AudioListener.volume = Mathf.Pow(volume, loudnessExponent); } }

void Start() {Volume = volume;}

// Change values in the Editor; get results. void OnDrawGizmos () {Volume = volume;} }</csharp >

Personal tools
Namespaces

Variants
Actions
Navigation
Extras
Toolbox