Feat : Wwise Integration

This commit is contained in:
Alex
2026-03-23 14:28:21 +01:00
parent 627d787695
commit 004bc328ed
1149 changed files with 226567 additions and 19 deletions
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: cee327f9ecce0444a8a99dcd4dd4de19
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,164 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if !(UNITY_QNX) // Disable under unsupported platforms.
/// <summary>
/// This class represents an example audio input manager and is responsible for managing the audio sample and format
/// callbacks provided to the Wwise Audio Input plug-in.
/// </summary>
public static class AkAudioInputManager
{
/// <summary>
/// Sanitized audio format delegate to be used by classes that implement audio input plug-ins. The samples are ALWAYS
/// set to be non-interleaved 32-bit float.
/// </summary>
/// <param name="playingID">The playingID of a sound that uses the audio input plug-in.</param>
/// <param name="format">The C# analog of the C++ AkAudioFormat class.</param>
public delegate void AudioFormatDelegate(uint playingID, AkAudioFormat format);
/// <summary>
/// Audio format delegate that is sent to C++.
/// </summary>
[System.Runtime.InteropServices.UnmanagedFunctionPointer(System.Runtime.InteropServices.CallingConvention.StdCall)]
public delegate void AudioFormatInteropDelegate(uint playingID, System.IntPtr format);
/// <summary>
/// Sanitized audio sample delegate to be used by classes that implement audio input plug-ins. For every event posted,
/// this delegate is called once per audio frame for each channel until the delegates for all the channels associated
/// with this event return false.
/// </summary>
/// <param name="playingID">The playingID of a sound that uses the audio input plug-in.</param>
/// <param name="channelIndex">The number of the channel associated with this specific invocation of the delegate.</param>
/// <param name="samples">The sample array that MUST be filled even when returning false.</param>
/// <returns>Return true when more sample frames are require and false when complete.</returns>
public delegate bool AudioSamplesDelegate(uint playingID, uint channelIndex, float[] samples);
/// <summary>
/// Audio sample delegate that is sent to C++.
/// </summary>
[System.Runtime.InteropServices.UnmanagedFunctionPointer(System.Runtime.InteropServices.CallingConvention.StdCall)]
public delegate bool AudioSamplesInteropDelegate(uint playingID,
[System.Runtime.InteropServices.In]
[System.Runtime.InteropServices.Out]
[System.Runtime.InteropServices.MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPArray, SizeParamIndex = 3)]
float[] samples, uint channelIndex, uint frames);
private static bool initialized;
private static readonly System.Collections.Generic.Dictionary<uint, AudioSamplesDelegate> audioSamplesDelegates =
new System.Collections.Generic.Dictionary<uint, AudioSamplesDelegate>();
private static readonly System.Collections.Generic.Dictionary<uint, AudioFormatDelegate> audioFormatDelegates =
new System.Collections.Generic.Dictionary<uint, AudioFormatDelegate>();
private static readonly AkAudioFormat audioFormat = new AkAudioFormat();
private static readonly AudioSamplesInteropDelegate audioSamplesDelegate = InternalAudioSamplesDelegate;
private static readonly AudioFormatInteropDelegate audioFormatDelegate = InternalAudioFormatDelegate;
/// <summary>
/// This method is used to post events that use the Wwise Audio Input plug-in.
/// </summary>
/// <param name="akEventID">The ID of the event to post.</param>
/// <param name="gameObject">The GameObject that the event will be posted on.</param>
/// <param name="sampleDelegate">The C# audio sample delegate.</param>
/// <param name="formatDelegate">
/// The C# audio format delegate. If not specified, defaults to a mono source running at the
/// sample rate of the sound engine.
/// </param>
/// <returns>The playingID of the newly instantiated sound associated with the posted event.</returns>
public static uint PostAudioInputEvent(uint akEventID, UnityEngine.GameObject gameObject,
AudioSamplesDelegate sampleDelegate, AudioFormatDelegate formatDelegate = null)
{
TryInitialize();
var playingID =
AkUnitySoundEngine.PostEvent(akEventID, gameObject, (uint) AkCallbackType.AK_EndOfEvent, EventCallback, null);
AddPlayingID(playingID, sampleDelegate, formatDelegate);
return playingID;
}
/// <summary>
/// This method is used to post events that use the Wwise Audio Input plug-in.
/// </summary>
/// <param name="akEventName">The name of the event to post.</param>
/// <param name="gameObject">The GameObject that the event will be posted on.</param>
/// <param name="sampleDelegate">The C# audio sample delegate.</param>
/// <param name="formatDelegate">
/// The C# audio format delegate. If not specified, defaults to a mono source running at the
/// sample rate of the sound engine.
/// </param>
/// <returns>The playingID of the newly instantiated sound associated with the posted event.</returns>
public static uint PostAudioInputEvent(string akEventName, UnityEngine.GameObject gameObject,
AudioSamplesDelegate sampleDelegate, AudioFormatDelegate formatDelegate = null)
{
TryInitialize();
var playingID =
AkUnitySoundEngine.PostEvent(akEventName, gameObject, (uint) AkCallbackType.AK_EndOfEvent, EventCallback, null);
AddPlayingID(playingID, sampleDelegate, formatDelegate);
return playingID;
}
[AOT.MonoPInvokeCallback(typeof(AudioSamplesInteropDelegate))]
private static bool InternalAudioSamplesDelegate(uint playingID, float[] samples, uint channelIndex, uint frames)
{
return audioSamplesDelegates.ContainsKey(playingID) &&
audioSamplesDelegates[playingID](playingID, channelIndex, samples);
}
[AOT.MonoPInvokeCallback(typeof(AudioFormatInteropDelegate))]
private static void InternalAudioFormatDelegate(uint playingID, System.IntPtr format)
{
if (audioFormatDelegates.ContainsKey(playingID))
{
audioFormat.setCPtr(format);
audioFormatDelegates[playingID](playingID, audioFormat);
}
}
private static void TryInitialize()
{
if (!initialized)
{
initialized = true;
AkUnitySoundEngine.SetAudioInputCallbacks(audioSamplesDelegate, audioFormatDelegate);
}
}
private static void AddPlayingID(uint playingID, AudioSamplesDelegate sampleDelegate,
AudioFormatDelegate formatDelegate)
{
if (playingID == AkUnitySoundEngine.AK_INVALID_PLAYING_ID || sampleDelegate == null)
return;
audioSamplesDelegates.Add(playingID, sampleDelegate);
if (formatDelegate != null)
audioFormatDelegates.Add(playingID, formatDelegate);
}
private static void EventCallback(object cookie, AkCallbackType type, AkCallbackInfo callbackInfo)
{
if (type == AkCallbackType.AK_EndOfEvent)
{
var info = callbackInfo as AkEventCallbackInfo;
if (info != null)
{
audioSamplesDelegates.Remove(info.playingID);
audioFormatDelegates.Remove(info.playingID);
}
}
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: d757a00bf39f6ac4393a2295299c2f2a
@@ -0,0 +1,343 @@
using AK.Wwise.Unity.Logging;
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
/// @brief Maintains the list of loaded SoundBanks loaded. This is currently used only with AkAmbient objects.
public static class AkBankManager
{
private static readonly System.Collections.Generic.Dictionary<string, BankHandle> m_BankHandles =
new System.Collections.Generic.Dictionary<string, BankHandle>();
private static readonly System.Collections.Generic.List<BankHandle> BanksToUnload =
new System.Collections.Generic.List<BankHandle>();
public static void DoUnloadBanks()
{
var count = BanksToUnload.Count;
for (var i = 0; i < count; ++i)
BanksToUnload[i].UnloadBank();
BanksToUnload.Clear();
}
internal static void Reset()
{
lock (m_BankHandles)
{
m_BankHandles.Clear();
}
BanksToUnload.Clear();
}
public static void ReloadAllBanks()
{
if (!AkUnitySoundEngine.IsInitialized())
{
return;
}
lock (m_BankHandles)
{
foreach (var bankHandle in m_BankHandles.Values)
{
if (bankHandle != null)
{
bankHandle.UnloadBank(false);
}
}
UnloadInitBank();
LoadInitBank(false);
foreach (var bankHandle in m_BankHandles.Values)
{
if (bankHandle != null)
{
bankHandle.DoLoadBank();
}
}
}
}
public static void LoadInitBank(bool doReset = true)
{
if (doReset)
{
Reset();
}
uint BankID;
var result = AkUnitySoundEngine.LoadBank("Init.bnk", out BankID);
if (result != AKRESULT.AK_Success)
{
WwiseLogger.Error("Failed load Init.bnk with result: " + result);
}
}
public static void UnloadInitBank()
{
AkUnitySoundEngine.UnloadBank("Init.bnk", System.IntPtr.Zero);
}
/// Loads a SoundBank. This version blocks until the bank is loaded. See AK::SoundEngine::LoadBank for more information.
public static uint LoadBank(string name, bool decodeBank, bool saveDecodedBank, AkBankTypeEnum bankType = AkBankTypeEnum.AkBankType_User)
{
BankHandle handle = null;
lock (m_BankHandles)
{
if (m_BankHandles.TryGetValue(name, out handle))
{
// Bank already loaded, increment its ref count.
handle.IncRef();
return AkUnitySoundEngine.AK_INVALID_UNIQUE_ID;
}
if (decodeBank && bankType != AkBankTypeEnum.AkBankType_User)
{
WwiseLogger.Error("Decoding Auto-generated SoundBanks is not supported.");
decodeBank = false;
}
handle = decodeBank && AkUnitySoundEngine.PlatformSupportsDecodeBank() ?
new DecodableBankHandle(name, saveDecodedBank) : new BankHandle(name, bankType);
m_BankHandles.Add(name, handle);
}
return handle.LoadBank();
}
/// Loads a SoundBank. This version returns right away and loads in background. See AK::SoundEngine::LoadBank for more information.
public static uint LoadBankAsync(string name, AkCallbackManager.BankCallback callback = null, AkBankTypeEnum bankType = AkBankTypeEnum.AkBankType_User)
{
BankHandle handle = null;
lock (m_BankHandles)
{
if (m_BankHandles.TryGetValue(name, out handle))
{
// Bank already loaded, increment its ref count.
handle.IncRef();
return AkUnitySoundEngine.AK_INVALID_UNIQUE_ID;
}
handle = new AsyncBankHandle(name, callback, bankType);
m_BankHandles.Add(name, handle);
}
return handle.LoadBank();
}
/// Unloads a SoundBank. See AK::SoundEngine::UnloadBank for more information.
public static void UnloadBank(string name)
{
lock (m_BankHandles)
{
BankHandle handle = null;
if (m_BankHandles.TryGetValue(name, out handle))
handle.DecRef();
}
}
public static void UnloadAllBanks()
{
lock (m_BankHandles)
{
foreach(var bank in m_BankHandles)
{
bank.Value.UnloadBank(false);
}
Reset();
}
}
private class BankHandle
{
protected readonly string bankName;
protected uint m_BankID;
protected AkBankTypeEnum m_BankType;
public BankHandle(string name, AkBankTypeEnum bankType)
{
bankName = name;
m_BankType = bankType;
}
public int RefCount { get; private set; }
/// Loads a bank. This version blocks until the bank is loaded. See AK::SoundEngine::LoadBank for more information.
public virtual AKRESULT DoLoadBank()
{
return AkUnitySoundEngine.LoadBank(bankName, out m_BankID, (uint)m_BankType);
}
public uint LoadBank()
{
if (RefCount == 0 && !BanksToUnload.Remove(this))
{
var res = DoLoadBank();
LogLoadResult(res);
}
IncRef();
return m_BankID;
}
/// Unloads a bank.
public virtual void UnloadBank(bool remove = true)
{
AkUnitySoundEngine.UnloadBank(m_BankID, System.IntPtr.Zero, null, null, (uint) m_BankType);
if (remove)
{
lock (m_BankHandles)
m_BankHandles.Remove(bankName);
}
}
public void IncRef()
{
if (RefCount == 0)
BanksToUnload.Remove(this);
RefCount++;
}
public void DecRef()
{
RefCount--;
if (RefCount == 0)
BanksToUnload.Add(this);
}
protected void LogLoadResult(AKRESULT result)
{
if (result != AKRESULT.AK_Success && AkUnitySoundEngine.IsInitialized())
WwiseLogger.Warning("Bank " + bankName + " failed to load (" + result + ")");
}
}
private class AsyncBankHandle : BankHandle
{
private readonly AkCallbackManager.BankCallback bankCallback;
public AsyncBankHandle(string name, AkCallbackManager.BankCallback callback, AkBankTypeEnum bankType) : base(name, bankType)
{
bankCallback = callback;
}
private static void GlobalBankCallback(uint in_bankID, System.IntPtr in_pInMemoryBankPtr, AKRESULT in_eLoadResult, object in_Cookie)
{
var handle = (AsyncBankHandle)in_Cookie;
var callback = handle.bankCallback;
if (in_eLoadResult != AKRESULT.AK_Success)
{
handle.LogLoadResult(in_eLoadResult);
if (in_eLoadResult != AKRESULT.AK_BankAlreadyLoaded)
lock (m_BankHandles)
m_BankHandles.Remove(handle.bankName);
}
if (callback != null)
callback(in_bankID, in_pInMemoryBankPtr, in_eLoadResult, null);
}
/// Loads a bank. This version returns right away and loads in background. See AK::SoundEngine::LoadBank for more information
public override AKRESULT DoLoadBank()
{
return AkUnitySoundEngine.LoadBank(bankName, GlobalBankCallback, this, out m_BankID, (uint)m_BankType);
}
}
private class DecodableBankHandle : BankHandle
{
private readonly bool decodeBank = true;
private readonly string decodedBankPath;
private readonly bool saveDecodedBank;
public DecodableBankHandle(string name, bool save) : base(name, AkBankTypeEnum.AkBankType_User)
{
saveDecodedBank = save;
var bankFileName = bankName + ".bnk";
// test language-specific decoded file path
var language = AkUnitySoundEngine.GetCurrentLanguage();
var akBasePathGetterInstance = AkBasePathGetter.Get();
var decodedBankFullPath = akBasePathGetterInstance.DecodedBankFullPath;
decodedBankPath = System.IO.Path.Combine(decodedBankFullPath, language);
var decodedBankFilePath = System.IO.Path.Combine(decodedBankPath, bankFileName);
var decodedFileExists = System.IO.File.Exists(decodedBankFilePath);
if (!decodedFileExists)
{
// test non-language-specific decoded file path
decodedBankPath = decodedBankFullPath;
decodedBankFilePath = System.IO.Path.Combine(decodedBankPath, bankFileName);
decodedFileExists = System.IO.File.Exists(decodedBankFilePath);
}
if (decodedFileExists)
{
try
{
var decodedFileTime = System.IO.File.GetLastWriteTime(decodedBankFilePath);
var encodedBankFilePath = System.IO.Path.Combine(akBasePathGetterInstance.SoundBankBasePath, bankFileName);
var encodedFileTime = System.IO.File.GetLastWriteTime(encodedBankFilePath);
decodeBank = decodedFileTime <= encodedFileTime;
}
catch
{
// Assume the decoded bank exists, but is not accessible. Re-decode it anyway, so we do nothing.
}
}
}
/// Loads a bank. This version blocks until the bank is loaded. See AK::SoundEngine::LoadBank for more information.
public override AKRESULT DoLoadBank()
{
if (decodeBank)
{
return AkUnitySoundEngine.LoadAndDecodeBank(bankName, saveDecodedBank, out m_BankID);
}
if (string.IsNullOrEmpty(decodedBankPath))
{
return AkUnitySoundEngine.LoadBank(bankName, out m_BankID, (uint) m_BankType);
}
var res = AkUnitySoundEngine.SetBasePath(decodedBankPath);
if (res == AKRESULT.AK_Success)
{
res = AkUnitySoundEngine.LoadBank(bankName, out m_BankID, (uint)m_BankType);
AkUnitySoundEngine.SetBasePath(AkBasePathGetter.Get().SoundBankBasePath);
}
return res;
}
/// Unloads a bank.
public override void UnloadBank(bool remove = true)
{
if (decodeBank && !saveDecodedBank)
AkUnitySoundEngine.PrepareBank(AkPreparationType.Preparation_Unload, m_BankID);
else
base.UnloadBank(remove);
}
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: f01d098db23d1ff498bf56cb525747f2
@@ -0,0 +1,311 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using System.Collections.Generic;
using System.IO;
using System.Text.RegularExpressions;
using UnityEditor;
using AK.Wwise.Unity.Logging;
/// <summary>
/// This class is responsible for determining the path where sound banks are located. When using custom platforms, this
/// class needs to be extended.
/// </summary>
public partial class AkBasePathGetter
{
/// <summary>
/// User hook called to retrieve the custom platform name used to determine the base path. Do not modify platformName
/// to use default platform names.
/// </summary>
/// <param name="platformName">The custom platform name. Leave unaffected if the default location is acceptable.</param>
public delegate void CustomPlatformNameGetter(ref string platformName);
public static CustomPlatformNameGetter GetCustomPlatformName;
/// <summary>
/// Determines the platform name which is also the sub-folder within the base path where sound banks are located for
/// this platform.
/// </summary>
/// <returns>The platform name.</returns>
public static string GetPlatformName()
{
var platformSubDir = string.Empty;
GetCustomPlatformName?.Invoke(ref platformSubDir);
if (!string.IsNullOrEmpty(platformSubDir))
return platformSubDir;
return DefaultPlatformName;
}
#if UNITY_EDITOR
/// <summary>
/// User hook called to retrieve the custom target platform name used to determine the base path. Do not modify platformName
/// to use default platform names.
/// </summary>
/// <param name="platformName">The custom platform name. Leave unaffected if the default location is acceptable.</param>
public delegate void CustomTargetPlatformNameGetter(ref string platformName, UnityEditor.BuildTarget target);
public static CustomTargetPlatformNameGetter GetCustomTargetPlatformName;
private static Dictionary<UnityEditor.BuildTarget, string> TargetPlatforms = new Dictionary<UnityEditor.BuildTarget, string>();
public static void AddTargetPlatform(UnityEditor.BuildTarget target, string platformName)
{
TargetPlatforms[target] = platformName;
}
public static string GetTargetPlatformName(UnityEditor.BuildTarget target)
{
var platformSubDir = string.Empty;
GetCustomTargetPlatformName?.Invoke(ref platformSubDir, target);
if (!string.IsNullOrEmpty(platformSubDir))
return platformSubDir;
if (TargetPlatforms.ContainsKey(target))
{
return TargetPlatforms[target];
}
WwiseLogger.Warning($"Target {target.ToString()} is not supported by default by Wwise. Make sure to create a custom script and subscribe to GetCustomTargetPlatformName delegate to add it. ");
return string.Empty;
}
#endif
}
public partial class AkBasePathGetter
{
public static readonly string DefaultBasePath = System.IO.Path.Combine("Audio", "GeneratedSoundBanks");
private const string DecodedBankFolder = "DecodedBanks";
private static bool LogWarnings_Internal = true;
public static bool LogWarnings
{
get { return LogWarnings_Internal; }
set { LogWarnings_Internal = value; }
}
/// <summary>
/// Returns the absolute path to the platform specific sound banks.
/// </summary>
/// <returns>The absolute path to the platform specific sound banks.</returns>
public static string GetPlatformBasePath()
{
var platformName = GetPlatformName();
#if UNITY_EDITOR
var platformBasePathEditor = GetPlatformBasePathEditor(platformName);
if (!string.IsNullOrEmpty(platformBasePathEditor))
return platformBasePathEditor;
var fullBasePath = AkWwiseEditorSettings.Instance.WwiseStreamingAssetsPath;
#else
var fullBasePath = string.Empty;
#endif
if (string.IsNullOrEmpty(fullBasePath))
fullBasePath = AkWwiseInitializationSettings.ActivePlatformSettings.SoundbankPath;
AdjustFullBasePathForPlatform(ref fullBasePath);
// Combine base path with platform sub-folder
var platformBasePath = System.IO.Path.Combine(fullBasePath, platformName);
AkUtilities.FixSlashes(ref platformBasePath);
return platformBasePath;
}
#if UNITY_EDITOR
public static bool GetSoundBankPaths(string platformName, out string sourcePlatformBasePath, out string destinationPlatformBasePath)
{
sourcePlatformBasePath = GetPlatformBasePathEditor(platformName);
if (string.IsNullOrEmpty(sourcePlatformBasePath))
{
if (LogWarnings)
WwiseLogger.ErrorFormat("Could not find source folder for <{0}> platform. Did you remember to generate your banks?", platformName);
destinationPlatformBasePath = string.Empty;
return false;
}
destinationPlatformBasePath = System.IO.Path.Combine(GetFullSoundBankPathEditor(), platformName);
if (string.IsNullOrEmpty(destinationPlatformBasePath))
{
if (LogWarnings)
WwiseLogger.ErrorFormat("Could not find destination folder for <{0}> platform", platformName);
return false;
}
return true;
}
/// <summary>
/// Returns the absolute path to the folder above the platform specific sound banks sub-folders.
/// </summary>
/// <returns>The absolute sound bank base path.</returns>
public static string GetFullSoundBankPathEditor()
{
string fullBasePath = System.IO.Path.Combine(UnityEngine.Application.streamingAssetsPath, AkWwiseEditorSettings.Instance.WwiseStreamingAssetsPath);
AkUtilities.FixSlashes(ref fullBasePath);
return fullBasePath;
}
public static string GetWwiseProjectPath()
{
var Settings = AkWwiseEditorSettings.Instance;
return AkUtilities.GetFullPath(UnityEngine.Application.dataPath, Settings.WwiseProjectPath);
}
public static string GetWwiseProjectDirectory(string wwiseAbsolutePath = "")
{
var projectPath= AkUtilities.GetFullPath(UnityEngine.Application.dataPath, wwiseAbsolutePath == "" ? AkWwiseEditorSettings.Instance.WwiseProjectPath : wwiseAbsolutePath);
return System.IO.Path.GetDirectoryName(projectPath);
}
public static string GetDefaultRootOutputPath()
{
string path = Path.GetDirectoryName(GetWwiseProjectPath());
if (path == null)
{
return null;
}
path = System.IO.Path.Combine(path, "GeneratedSoundBanks");
return AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
}
/// <summary>
/// Determines the platform base path for use within the Editor.
/// </summary>
/// <param name="platformName">The platform name.</param>
/// <returns>The full path to the sound banks for use within the Editor.</returns>
private static string GetPlatformBasePathEditor(string platformName)
{
var WwiseProjectFullPath = GetWwiseProjectPath();
var SoundBankDest = AkUtilities.GetWwiseSoundBankDestinationFolder(platformName, AkWwiseEditorSettings.WwiseProjectAbsolutePath);
try
{
if (System.IO.Path.GetPathRoot(SoundBankDest) == "")
{
// Path is relative, make it full
SoundBankDest = AkUtilities.GetFullPath(System.IO.Path.GetDirectoryName(WwiseProjectFullPath), SoundBankDest);
}
}
catch
{
SoundBankDest = string.Empty;
}
if (LogWarnings)
{
if (string.IsNullOrEmpty(SoundBankDest))
{
WwiseLogger.Warning("The platform SoundBank subfolder within the Wwise project could not be found.");
return null;
}
try
{
// Verify if there are banks in there
var di = new System.IO.DirectoryInfo(SoundBankDest);
var foundBanks = di.GetFiles("*.bnk", System.IO.SearchOption.AllDirectories);
if (foundBanks.Length == 0)
{
return null;
}
if (!SoundBankDest.Contains(platformName))
{
if (LogWarnings)
WwiseLogger.Warning("The platform SoundBank subfolder does not match your platform name. You will need to create a custom platform name getter for your game. See section \"Using Wwise Custom Platforms in Unity\" of the Wwise Unity integration documentation for more information");
}
return SoundBankDest;
}
catch
{
return null;
}
}
else
{
return SoundBankDest;
}
}
#endif
private static AkBasePathGetter Instance;
public static AkBasePathGetter Get()
{
if (Instance == null)
{
Instance = new AkBasePathGetter();
Instance.EvaluateGamePaths();
}
return Instance;
}
public void EvaluateGamePaths()
{
string tempPersistentDataPath = GetPersistentDataPath();
PersistentDataPath = tempPersistentDataPath;
var persistentDataSubfolder = AkWwiseInitializationSettings.ActivePlatformSettings.SoundBankPersistentDataPath;
string tempSoundBankBasePath = null;
if (!string.IsNullOrEmpty(tempPersistentDataPath) && !string.IsNullOrEmpty(persistentDataSubfolder))
{
tempSoundBankBasePath = System.IO.Path.GetFullPath(System.IO.Path.Combine(tempPersistentDataPath, persistentDataSubfolder));
if (LogWarnings)
WwiseLogger.LogFormat("Using persistentDataPath. SoundBanks base path set to <{0}>.", tempSoundBankBasePath);
}
else
{
tempSoundBankBasePath = GetPlatformBasePath();
#if !AK_WWISE_ADDRESSABLES //Don't log this if we're using addressables
if (string.IsNullOrEmpty(tempSoundBankBasePath) || !InitBankExists(tempSoundBankBasePath))
{
if (LogWarnings)
{
#if UNITY_EDITOR
var format = "Could not locate the SoundBanks in {0}. Did you make sure to generate them?";
#else
var format = "Could not locate the SoundBanks in {0}. Did you make sure to copy them to the StreamingAssets folder?";
#endif
WwiseLogger.ErrorFormat(format, tempSoundBankBasePath);
}
}
#endif
}
SoundBankBasePath = tempSoundBankBasePath;
DecodedBankFullPath = GetDecodedBankPath();
}
public string SoundBankBasePath { get; private set; }
public string PersistentDataPath { get; private set; }
public string DecodedBankFullPath { get; private set; }
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 6f10243057648c44a8ea5dc719b40db1
@@ -0,0 +1,567 @@
using UnityEngine;
using System.Collections.Generic;
using System.Linq;
using AK.Wwise.Unity.Logging;
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
/// <summary>
/// This class manages the callback queue. All callbacks from the native Wwise SDK go through this queue.
/// The queue needs to be driven by regular calls to PostCallbacks(). This is currently done in AkInitializer.cs, in
/// LateUpdate().
/// </summary>
public static class AkCallbackManager
{
/// <summary>
/// Event callback used when posting events.
/// </summary>
public delegate void EventCallback(object in_cookie, AkCallbackType in_type, AkCallbackInfo in_info);
/// <summary>
/// Monitoring callback called when Wwise reports errors.
/// </summary>
public delegate void MonitoringCallback(AkMonitorErrorCode in_errorCode, AkMonitorErrorLevel in_errorLevel,
uint in_playingID, ulong in_gameObjID, string in_msg);
/// <summary>
/// Bank callback called upon bank load and unload and when errors occur.
/// </summary>
public delegate void BankCallback(uint in_bankID, System.IntPtr in_InMemoryBankPtr, AKRESULT in_eLoadResult, object in_Cookie);
private static bool IsLoggingEnabled { get; set; }
private static readonly AkEventCallbackInfo AkEventCallbackInfo = new AkEventCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkDynamicSequenceItemCallbackInfo AkDynamicSequenceItemCallbackInfo =
new AkDynamicSequenceItemCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkMIDIEventCallbackInfo AkMIDIEventCallbackInfo =
new AkMIDIEventCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkMarkerCallbackInfo
AkMarkerCallbackInfo = new AkMarkerCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkDurationCallbackInfo AkDurationCallbackInfo =
new AkDurationCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkMusicSyncCallbackInfo AkMusicSyncCallbackInfo =
new AkMusicSyncCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkMusicPlaylistCallbackInfo AkMusicPlaylistCallbackInfo =
new AkMusicPlaylistCallbackInfo(System.IntPtr.Zero, false);
#if UNITY_IOS && !UNITY_EDITOR
private static AkAudioInterruptionCallbackInfo AkAudioInterruptionCallbackInfo =
new AkAudioInterruptionCallbackInfo(System.IntPtr.Zero, false);
#endif // #if UNITY_IOS && ! UNITY_EDITOR
private static readonly AkAudioSourceChangeCallbackInfo AkAudioSourceChangeCallbackInfo =
new AkAudioSourceChangeCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkMonitoringCallbackInfo AkMonitoringCallbackInfo =
new AkMonitoringCallbackInfo(System.IntPtr.Zero, false);
private static readonly AkBankCallbackInfo AkBankCallbackInfo = new AkBankCallbackInfo(System.IntPtr.Zero, false);
/// <summary>
/// This class holds the data associated with an event callback.
/// </summary>
public class EventCallbackPackage
{
public bool m_bNotifyEndOfEvent;
public EventCallback m_Callback;
public object m_Cookie;
public uint m_playingID;
public static EventCallbackPackage Create(EventCallback in_cb, object in_cookie, ref uint io_Flags)
{
if (io_Flags == 0 || in_cb == null)
{
return null;
}
var evt = new EventCallbackPackage();
evt.m_Callback = in_cb;
evt.m_Cookie = in_cookie;
evt.m_bNotifyEndOfEvent = (io_Flags & (uint) AkCallbackType.AK_EndOfEvent) != 0;
io_Flags = io_Flags | (uint) AkCallbackType.AK_EndOfEvent;
m_mapEventCallbacks[evt.GetHashCode()] = evt;
m_LastAddedEventPackage = evt;
return evt;
}
}
/// <summary>
/// This class holds the data associated with a bank load or unload callback.
/// </summary>
public class BankCallbackPackage
{
public BankCallback m_Callback;
public object m_Cookie;
public BankCallbackPackage(BankCallback in_cb, object in_cookie)
{
m_Callback = in_cb;
m_Cookie = in_cookie;
m_mapBankCallbacks[GetHashCode()] = this;
}
}
private static readonly System.Collections.Generic.Dictionary<int, EventCallbackPackage> m_mapEventCallbacks =
new System.Collections.Generic.Dictionary<int, EventCallbackPackage>();
private static readonly System.Collections.Generic.Dictionary<int, BankCallbackPackage> m_mapBankCallbacks =
new System.Collections.Generic.Dictionary<int, BankCallbackPackage>();
private static EventCallbackPackage m_LastAddedEventPackage;
public static void RemoveEventCallback(EventCallbackPackage in_package)
{
if (in_package != null)
{
m_mapEventCallbacks.Remove(in_package.GetHashCode());
if (in_package.m_playingID != AkUnitySoundEngine.AK_INVALID_PLAYING_ID)
{
AkUnitySoundEnginePINVOKE.CSharp_CancelEventCallbackCookie((global::System.IntPtr) in_package.GetHashCode());
}
}
}
public static IEnumerable<EventCallbackPackage> GetEventCallbacks()
{
return m_mapEventCallbacks.Select(pacakge => pacakge.Value);
}
public static void RemoveEventCallback(uint in_playingID)
{
var cookiesToRemove = new System.Collections.Generic.List<int>();
foreach (var pair in m_mapEventCallbacks)
{
if (pair.Value.m_playingID == in_playingID)
{
cookiesToRemove.Add(pair.Key);
break;
}
}
var Count = cookiesToRemove.Count;
for (var ii = 0; ii < Count; ++ii)
m_mapEventCallbacks.Remove(cookiesToRemove[ii]);
if (in_playingID != AkUnitySoundEngine.AK_INVALID_PLAYING_ID)
{
AkUnitySoundEnginePINVOKE.CSharp_CancelEventCallback(in_playingID);
}
}
public static void RemoveEventCallbackCookie(object in_cookie)
{
var cookiesToRemove = new System.Collections.Generic.List<int>();
foreach (var pair in m_mapEventCallbacks)
{
if (pair.Value.m_Cookie == in_cookie)
cookiesToRemove.Add(pair.Key);
}
var Count = cookiesToRemove.Count;
for (var ii = 0; ii < Count; ++ii)
{
var toRemove = cookiesToRemove[ii];
m_mapEventCallbacks.Remove(toRemove);
AkUnitySoundEnginePINVOKE.CSharp_CancelEventCallbackCookie((System.IntPtr) toRemove);
}
}
public static IEnumerable<BankCallbackPackage> GetBankCallbacks()
{
return m_mapBankCallbacks.Select(pacakge => pacakge.Value);
}
public static void RemoveBankCallback(object in_cookie)
{
var cookiesToRemove = new System.Collections.Generic.List<int>();
foreach (var pair in m_mapBankCallbacks)
{
if (pair.Value.m_Cookie == in_cookie)
cookiesToRemove.Add(pair.Key);
}
var Count = cookiesToRemove.Count;
for (var ii = 0; ii < Count; ++ii)
{
var toRemove = cookiesToRemove[ii];
m_mapBankCallbacks.Remove(toRemove);
AkUnitySoundEnginePINVOKE.CSharp_CancelBankCallbackCookie((System.IntPtr) toRemove);
}
}
public static void SetLastAddedPlayingID(uint in_playingID)
{
if (m_LastAddedEventPackage != null && m_LastAddedEventPackage.m_playingID == 0)
{
m_LastAddedEventPackage.m_playingID = in_playingID;
}
}
private static MonitoringCallback m_MonitoringCB;
#if UNITY_IOS && !UNITY_EDITOR
public delegate AKRESULT AudioInterruptionCallback(bool in_bEnterInterruption, object in_Cookie);
// App implements its own callback.
private static AudioInterruptionCallbackPackage ms_interruptCallbackPkg = null;
public class AudioInterruptionCallbackPackage
{
public object m_Cookie;
public AudioInterruptionCallback m_Callback;
}
#endif // #if UNITY_IOS && ! UNITY_EDITOR
public delegate AKRESULT BGMCallback(bool in_bOtherAudioPlaying, object in_Cookie);
// App implements its own callback.
private static BGMCallbackPackage ms_sourceChangeCallbackPkg;
public class BGMCallbackPackage
{
public BGMCallback m_Callback;
public object m_Cookie;
}
public class InitializationSettings
{
public const bool DefaultIsLoggingEnabled = true;
public bool IsLoggingEnabled = DefaultIsLoggingEnabled;
}
public static void Init(InitializationSettings settings)
{
IsLoggingEnabled = settings.IsLoggingEnabled;
AkCallbackSerializer.Init();
SetLocalOutput(AkMonitorErrorLevel.ErrorLevel_All);
}
public static void Term()
{
AkCallbackSerializer.Term();
}
/// Call this to set a function to call whenever Wwise prints a message (warnings or errors).
public static void SetMonitoringCallback(AkMonitorErrorLevel in_Level, MonitoringCallback in_CB)
{
SetLocalOutput(in_CB != null ? in_Level : 0);
m_MonitoringCB = in_CB;
}
private static void SetLocalOutput(AkMonitorErrorLevel in_Level)
{
#if UNITY_EDITOR
try
{
uint XmlTimeout = uint.Parse(AkWwiseEditorSettings.Instance.XMLTranslatorTimeout);
//Check if SoundbanksInfo.xml exist. If not, let the user know that it was disabled.
if (XmlTimeout > 0)
{
string soundBankPath = System.IO.Path.Combine(AkBasePathGetter.GetPlatformBasePath(), "SoundbanksInfo.xml");
if (!System.IO.File.Exists(soundBankPath))
{
WwiseLogger.Warning("The XMLTranslator has been disabled since the SoundbanksInfo.xml couldn't be located at " + soundBankPath + ". To remove the warning," +
" either disable the XMLTranslator by going to Project Settings -> Wwise Integration and setting XML Translator Timeout to 0 or generate the xml file by editing the wwise project settings.");
XmlTimeout = 0;
}
}
uint WaapiTimeout = uint.Parse(AkWwiseEditorSettings.Instance.WaapiTranslatorTimeout);
uint portAsInt = uint.Parse(AkWwiseEditorSettings.Instance.WaapiPort);
string baseSoundBankPath = AkBasePathGetter.GetPlatformBasePath();
baseSoundBankPath += "SoundbanksInfo.xml";
AkCallbackSerializer.SetLocalOutput((uint)in_Level,
AkWwiseEditorSettings.Instance.WaapiIP, portAsInt,
baseSoundBankPath,
XmlTimeout, WaapiTimeout);
}
catch (System.Exception)
{
WwiseLogger.Warning("Error parsing WaapiPort, XMLTranslatorTimeout or WaapiTranslatorTimeout. Must be an integer.");
}
#endif
}
#if UNITY_EDITOR
private static void FreeXMLFileHandle(uint xmlTimeout)
{
string baseSoundBankPath = AkBasePathGetter.GetPlatformBasePath();
baseSoundBankPath += "SoundbanksInfo.xml";
AkCallbackSerializer.FreeXmlTranslatorHandle(baseSoundBankPath, xmlTimeout);
}
#endif
#if UNITY_IOS && !UNITY_EDITOR
/// Call this function to set a iOS callback interruption function. By default this callback is not defined.
public static void SetInterruptionCallback(AudioInterruptionCallback in_CB, object in_cookie)
{
ms_interruptCallbackPkg = new AudioInterruptionCallbackPackage { m_Callback = in_CB, m_Cookie = in_cookie };
}
#endif // #if UNITY_IOS && ! UNITY_EDITOR
/// Call this to set a background music callback function. By default this callback is not defined.
public static void SetBGMCallback(BGMCallback in_CB, object in_cookie)
{
ms_sourceChangeCallbackPkg = new BGMCallbackPackage { m_Callback = in_CB, m_Cookie = in_cookie };
}
public static void ParseCallbackInfoMessage(ref string in_message)
{
if(in_message.Contains("$g"))
{
int currentPos = in_message.IndexOf("$g", 0);
while (currentPos > 0)
{
if (currentPos == -1)
break;
int spacePos = in_message.IndexOf(' ', currentPos);
int idStringSize = (spacePos == -1 ? in_message.Length : spacePos )- currentPos - 2;
string s_gID = in_message.Substring(currentPos + 2, idStringSize);
ulong gId = AkUnitySoundEngine.AK_INVALID_GAME_OBJECT;
try
{
gId = ulong.Parse(s_gID);
}
catch (System.ArgumentNullException)
{
WwiseLogger.Warning(s_gID + " was null.");
}
catch (System.ArgumentException)
{
WwiseLogger.Warning(s_gID + " is not a number.");
}
catch (System.FormatException)
{
WwiseLogger.Warning("Unable to parse " + s_gID + ".");
}
catch (System.OverflowException)
{
WwiseLogger.Warning(s_gID + " is out of range of the UInt64 type.");
}
bool gameIdResolved = false;
#if UNITY_EDITOR
if (gId != AkUnitySoundEngine.AK_INVALID_GAME_OBJECT)
{
#if UNITY_6000_3_OR_NEWER
var obj =
UnityEditor.EditorUtility.EntityIdToObject((int)AkMonitoringCallbackInfo.gameObjID) as
UnityEngine.GameObject;
#else
var obj =
UnityEditor.EditorUtility.InstanceIDToObject((int)AkMonitoringCallbackInfo.gameObjID) as
UnityEngine.GameObject;
#endif
if (obj != null)
{
in_message = in_message.Replace(in_message.Substring(currentPos, idStringSize + 2), obj.name);
in_message += " (Instance ID: " + AkMonitoringCallbackInfo.gameObjID + ")";
gameIdResolved = true;
}
}
#endif
if(!gameIdResolved)
in_message = in_message.Replace(in_message.Substring(currentPos, idStringSize + 2), in_message.Substring(currentPos + 2, idStringSize));
currentPos += 1;
currentPos = in_message.IndexOf("$g", currentPos);
}
}
}
/// This function dispatches all the accumulated callbacks from the native sound engine.
/// It must be called regularly. By default this is called in AkInitializer.cs.
public static int PostCallbacks()
{
try
{
var numCallbacks = 0;
#if UNITY_EDITOR
bool atLeastOneMonitoringCallback = false;
#endif
for (var pNext = AkCallbackSerializer.Lock();
pNext != System.IntPtr.Zero;
pNext = AkUnitySoundEnginePINVOKE.CSharp_AkSerializedCallbackHeader_pNext_get(pNext), ++numCallbacks)
{
var pPackage = AkUnitySoundEnginePINVOKE.CSharp_AkSerializedCallbackHeader_pPackage_get(pNext);
var eType = (AkCallbackType) AkUnitySoundEnginePINVOKE.CSharp_AkSerializedCallbackHeader_eType_get(pNext);
var eCallbackCategory = (AkCallbackCategory) AkUnitySoundEnginePINVOKE.CSharp_AkSerializedCallbackHeader_eCategory_get(pNext);
var pData = AkUnitySoundEnginePINVOKE.CSharp_AkSerializedCallbackHeader_GetData(pNext);
switch (eCallbackCategory)
{
case AkCallbackCategory.AudioInterruption:
#if UNITY_IOS && !UNITY_EDITOR
if (ms_interruptCallbackPkg != null && ms_interruptCallbackPkg.m_Callback != null)
{
AkAudioInterruptionCallbackInfo.setCPtr(pData);
ms_interruptCallbackPkg.m_Callback(AkAudioInterruptionCallbackInfo.bEnterInterruption, ms_interruptCallbackPkg.m_Cookie);
}
#endif // #if UNITY_IOS && ! UNITY_EDITOR
break;
case AkCallbackCategory.AudioSourceChange:
if (ms_sourceChangeCallbackPkg != null && ms_sourceChangeCallbackPkg.m_Callback != null)
{
AkAudioSourceChangeCallbackInfo.setCPtr(pData);
ms_sourceChangeCallbackPkg.m_Callback(AkAudioSourceChangeCallbackInfo.bOtherAudioPlaying,
ms_sourceChangeCallbackPkg.m_Cookie);
}
break;
case AkCallbackCategory.Monitoring:
if (m_MonitoringCB != null)
{
AkMonitoringCallbackInfo.setCPtr(pData);
m_MonitoringCB(AkMonitoringCallbackInfo.errorCode, AkMonitoringCallbackInfo.errorLevel,
AkMonitoringCallbackInfo.playingID, AkMonitoringCallbackInfo.gameObjID, AkMonitoringCallbackInfo.message);
}
#if UNITY_EDITOR
else if (IsLoggingEnabled)
{
AkMonitoringCallbackInfo.setCPtr(pData);
var msg = "WwiseMonitor: " + AkMonitoringCallbackInfo.message;
ParseCallbackInfoMessage(ref msg);
if (AkMonitoringCallbackInfo.errorLevel == AkMonitorErrorLevel.ErrorLevel_Error)
WwiseLogger.Error(msg);
else
WwiseLogger.Log(msg);
}
atLeastOneMonitoringCallback = true;
#endif
break;
case AkCallbackCategory.Bank:
BankCallbackPackage bankPkg = null;
if (!m_mapBankCallbacks.TryGetValue((int) pPackage, out bankPkg))
{
WwiseLogger.Error("BankCallbackPackage not found for <" + pPackage + ">.");
break;
}
m_mapBankCallbacks.Remove((int) pPackage);
if (bankPkg != null && bankPkg.m_Callback != null)
{
AkBankCallbackInfo.setCPtr(pData);
bankPkg.m_Callback(AkBankCallbackInfo.bankID, AkBankCallbackInfo.inMemoryBankPtr, AkBankCallbackInfo.loadResult, bankPkg.m_Cookie);
}
break;
case AkCallbackCategory.Event:
EventCallbackPackage eventPkg = null;
if (!m_mapEventCallbacks.TryGetValue((int) pPackage, out eventPkg))
{
WwiseLogger.Error("EventCallbackPackage not found for <" + pPackage + ">.");
break;
}
AkCallbackInfo info = null;
switch (eType)
{
case AkCallbackType.AK_EndOfEvent:
m_mapEventCallbacks.Remove(eventPkg.GetHashCode());
if (eventPkg.m_bNotifyEndOfEvent)
{
AkEventCallbackInfo.setCPtr(pData);
info = AkEventCallbackInfo;
}
break;
case AkCallbackType.AK_MusicPlayStarted:
AkEventCallbackInfo.setCPtr(pData);
info = AkEventCallbackInfo;
break;
case AkCallbackType.AK_EndOfDynamicSequenceItem:
AkDynamicSequenceItemCallbackInfo.setCPtr(pData);
info = AkDynamicSequenceItemCallbackInfo;
break;
case AkCallbackType.AK_MIDIEvent:
AkMIDIEventCallbackInfo.setCPtr(pData);
info = AkMIDIEventCallbackInfo;
break;
case AkCallbackType.AK_Marker:
AkMarkerCallbackInfo.setCPtr(pData);
info = AkMarkerCallbackInfo;
break;
case AkCallbackType.AK_Duration:
AkDurationCallbackInfo.setCPtr(pData);
info = AkDurationCallbackInfo;
break;
case AkCallbackType.AK_MusicSyncUserCue:
case AkCallbackType.AK_MusicSyncBar:
case AkCallbackType.AK_MusicSyncBeat:
case AkCallbackType.AK_MusicSyncEntry:
case AkCallbackType.AK_MusicSyncExit:
case AkCallbackType.AK_MusicSyncGrid:
case AkCallbackType.AK_MusicSyncPoint:
AkMusicSyncCallbackInfo.setCPtr(pData);
info = AkMusicSyncCallbackInfo;
break;
case AkCallbackType.AK_MusicPlaylistSelect:
AkMusicPlaylistCallbackInfo.setCPtr(pData);
info = AkMusicPlaylistCallbackInfo;
break;
default:
WwiseLogger.Error("Undefined callback type <" + eType + "> received. Callback object possibly corrupted.");
break;
}
if (info != null)
eventPkg.m_Callback(eventPkg.m_Cookie, eType, info);
break;
}
}
#if UNITY_EDITOR
uint xmlTimeout = uint.Parse(AkWwiseEditorSettings.Instance.XMLTranslatorTimeout);
if (atLeastOneMonitoringCallback && xmlTimeout > 0)
{
FreeXMLFileHandle(xmlTimeout);
}
#endif
return numCallbacks;
}
finally
{
AkCallbackSerializer.Unlock();
}
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: a9ec57d1cc1240d4e9c92ded10767abf
@@ -0,0 +1,790 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using AK.Wwise.Unity.Logging;
public class AkBasePlatformSettings : UnityEngine.ScriptableObject
{
public virtual AkInitializationSettings AkInitializationSettings
{
get { return new AkInitializationSettings(); }
}
public virtual AkSpatialAudioInitSettings AkSpatialAudioInitSettings
{
get { return new AkSpatialAudioInitSettings(); }
}
public virtual AkCallbackManager.InitializationSettings CallbackManagerInitializationSettings
{
get { return new AkCallbackManager.InitializationSettings(); }
}
public virtual string SoundBankPersistentDataPath
{
get { return null; }
}
public virtual string InitialLanguage
{
get { return "English(US)"; }
}
public virtual bool LoadBanksAsynchronously
{
get
{
#if AK_WWISE_ADDRESSABLES && UNITY_ADDRESSABLES
return true;
#else
return false;
#endif
}
set { }
}
public virtual bool SuspendAudioDuringFocusLoss
{
get { return true; }
}
public virtual bool RenderDuringFocusLoss
{
get { return false; }
}
public virtual string SoundbankPath
{
get { return AkBasePathGetter.DefaultBasePath; }
}
public virtual AkCommunicationSettings AkCommunicationSettings
{
get { return new AkCommunicationSettings(); }
}
public virtual bool UseSubFoldersForGeneratedFiles
{
get { return false; }
}
public virtual uint MemoryDebugLevel
{
get { return 0; }
}
public virtual bool IsDecodedBankEnabled
{
get { return false; }
}
public virtual bool IsAutoBankEnabled
{
get { return true; }
set { }
}
public virtual float defaultListenerScalingFactor
{
get { return 1f; }
}
}
[System.Serializable]
public class AkCommonOutputSettings
{
[UnityEngine.Tooltip("The name of a custom audio device to use. Custom audio devices are defined in the Audio Device Shareset section of the Wwise project. Leave this empty to output normally through the default audio device.")]
public string m_AudioDeviceShareset = string.Empty;
[UnityEngine.Tooltip("Device specific identifier, when multiple devices of the same type are possible. If only one device is possible, leave to 0.")]
public uint m_DeviceID = AkUnitySoundEngine.AK_INVALID_UNIQUE_ID;
public enum PanningRule
{
Speakers = 0,
Headphones = 1
}
[UnityEngine.Tooltip("Rule for 3D panning of signals routed to a stereo bus. In \"Speakers\" mode, the angle of the front loudspeakers is used. In \"Headphones\" mode, the speaker angles are superseded by constant power panning between two virtual microphones spaced 180 degrees apart.")]
public PanningRule m_PanningRule = PanningRule.Speakers;
[System.Serializable]
public class ChannelConfiguration
{
public enum ChannelConfigType
{
Anonymous = 0x0,
Standard = 0x1,
Ambisonic = 0x2
}
[UnityEngine.Tooltip("A code that completes the identification of channels by uChannelMask. Anonymous: Channel mask == 0 and channels. Standard: Channels must be identified with standard defines in AkSpeakerConfigs. Ambisonic: Channel mask == 0 and channels follow standard ambisonic order.")]
public ChannelConfigType m_ChannelConfigType = ChannelConfigType.Anonymous;
public enum ChannelMask
{
NONE = 0x0,
/// Standard speakers (channel mask):
FRONT_LEFT = 0x1, ///< Front left speaker bit mask
FRONT_RIGHT = 0x2, ///< Front right speaker bit mask
FRONT_CENTER = 0x4, ///< Front center speaker bit mask
LOW_FREQUENCY = 0x8, ///< Low-frequency speaker bit mask
BACK_LEFT = 0x10, ///< Rear left speaker bit mask
BACK_RIGHT = 0x20, ///< Rear right speaker bit mask
BACK_CENTER = 0x100, ///< Rear center speaker ("surround speaker") bit mask
SIDE_LEFT = 0x200, ///< Side left speaker bit mask
SIDE_RIGHT = 0x400, ///< Side right speaker bit mask
/// "Height" speakers.
TOP = 0x800, ///< Top speaker bit mask
HEIGHT_FRONT_LEFT = 0x1000, ///< Front left speaker bit mask
HEIGHT_FRONT_CENTER = 0x2000, ///< Front center speaker bit mask
HEIGHT_FRONT_RIGHT = 0x4000, ///< Front right speaker bit mask
HEIGHT_BACK_LEFT = 0x8000, ///< Rear left speaker bit mask
HEIGHT_BACK_CENTER = 0x10000, ///< Rear center speaker bit mask
HEIGHT_BACK_RIGHT = 0x20000, ///< Rear right speaker bit mask
//
// Supported speaker setups. Those are the ones that can be used in the Wwise Sound Engine audio pipeline.
//
SETUP_MONO = FRONT_CENTER, ///< 1.0 setup channel mask
SETUP_0POINT1 = LOW_FREQUENCY, ///< 0.1 setup channel mask
SETUP_1POINT1 = (FRONT_CENTER | LOW_FREQUENCY), ///< 1.1 setup channel mask
SETUP_STEREO = (FRONT_LEFT | FRONT_RIGHT), ///< 2.0 setup channel mask
SETUP_2POINT1 = (SETUP_STEREO | LOW_FREQUENCY), ///< 2.1 setup channel mask
SETUP_3STEREO = (SETUP_STEREO | FRONT_CENTER), ///< 3.0 setup channel mask
SETUP_3POINT1 = (SETUP_3STEREO | LOW_FREQUENCY), ///< 3.1 setup channel mask
SETUP_4 = (SETUP_STEREO | SIDE_LEFT | SIDE_RIGHT), ///< 4.0 setup channel mask
SETUP_4POINT1 = (SETUP_4 | LOW_FREQUENCY), ///< 4.1 setup channel mask
SETUP_5 = (SETUP_4 | FRONT_CENTER), ///< 5.0 setup channel mask
SETUP_5POINT1 = (SETUP_5 | LOW_FREQUENCY), ///< 5.1 setup channel mask
SETUP_6 = (SETUP_4 | BACK_LEFT | BACK_RIGHT), ///< 6.0 setup channel mask
SETUP_6POINT1 = (SETUP_6 | LOW_FREQUENCY), ///< 6.1 setup channel mask
SETUP_7 = (SETUP_6 | FRONT_CENTER), ///< 7.0 setup channel mask
SETUP_7POINT1 = (SETUP_7 | LOW_FREQUENCY), ///< 7.1 setup channel mask
SETUP_SURROUND = (SETUP_STEREO | BACK_CENTER), ///< Legacy surround setup channel mask
// Note. DPL2 does not really have 4 channels, but it is used by plugins to differentiate from stereo setup.
SETUP_DPL2 = (SETUP_4), ///< Legacy DPL2 setup channel mask
SETUP_HEIGHT_4 = (HEIGHT_FRONT_LEFT | HEIGHT_FRONT_RIGHT | HEIGHT_BACK_LEFT | HEIGHT_BACK_RIGHT), ///< 4 speaker height layer.
SETUP_HEIGHT_5 = (SETUP_HEIGHT_4 | HEIGHT_FRONT_CENTER), ///< 5 speaker height layer.
SETUP_HEIGHT_ALL = (SETUP_HEIGHT_5 | HEIGHT_BACK_CENTER), ///< All height speaker layer.
// Auro speaker setups
SETUP_AURO_222 = (SETUP_4 | HEIGHT_FRONT_LEFT | HEIGHT_FRONT_RIGHT), ///< Auro-222 setup channel mask
SETUP_AURO_8 = (SETUP_AURO_222 | HEIGHT_BACK_LEFT | HEIGHT_BACK_RIGHT), ///< Auro-8 setup channel mask
SETUP_AURO_9 = (SETUP_AURO_8 | FRONT_CENTER), ///< Auro-9.0 setup channel mask
SETUP_AURO_9POINT1 = (SETUP_AURO_9 | LOW_FREQUENCY), ///< Auro-9.1 setup channel mask
SETUP_AURO_10 = (SETUP_AURO_9 | TOP), ///< Auro-10.0 setup channel mask
SETUP_AURO_10POINT1 = (SETUP_AURO_10 | LOW_FREQUENCY), ///< Auro-10.1 setup channel mask
SETUP_AURO_11 = (SETUP_AURO_10 | HEIGHT_FRONT_CENTER), ///< Auro-11.0 setup channel mask
SETUP_AURO_11POINT1 = (SETUP_AURO_11 | LOW_FREQUENCY), ///< Auro-11.1 setup channel mask
SETUP_AURO_11_740 = (SETUP_7 | SETUP_HEIGHT_4), ///< Auro-11.0 (7+4) setup channel mask
SETUP_AURO_11POINT1_740 = (SETUP_AURO_11_740 | LOW_FREQUENCY), ///< Auro-11.1 (7+4) setup channel mask
SETUP_AURO_13_751 = (SETUP_7 | SETUP_HEIGHT_5 | TOP), ///< Auro-13.0 setup channel mask
SETUP_AURO_13POINT1_751 = (SETUP_AURO_13_751 | LOW_FREQUENCY), ///< Auro-13.1 setup channel mask
// Dolby speaker setups: in Dolby nomenclature, [#plane].[lfe].[#height]
SETUP_DOLBY_5_0_2 = (SETUP_5 | HEIGHT_FRONT_LEFT | HEIGHT_FRONT_RIGHT), ///< Dolby 5.0.2 setup channel mask
SETUP_DOLBY_5_1_2 = (SETUP_DOLBY_5_0_2 | LOW_FREQUENCY), ///< Dolby 5.1.2 setup channel mask
SETUP_DOLBY_6_0_2 = (SETUP_6 | HEIGHT_FRONT_LEFT | HEIGHT_FRONT_RIGHT), ///< Dolby 6.0.2 setup channel mask
SETUP_DOLBY_6_1_2 = (SETUP_DOLBY_6_0_2 | LOW_FREQUENCY), ///< Dolby 6.1.2 setup channel mask
SETUP_DOLBY_6_0_4 = (SETUP_DOLBY_6_0_2 | HEIGHT_BACK_LEFT | HEIGHT_BACK_RIGHT), ///< Dolby 6.0.4 setup channel mask
SETUP_DOLBY_6_1_4 = (SETUP_DOLBY_6_0_4 | LOW_FREQUENCY), ///< Dolby 6.1.4 setup channel mask
SETUP_DOLBY_7_0_2 = (SETUP_7 | HEIGHT_FRONT_LEFT | HEIGHT_FRONT_RIGHT), ///< Dolby 7.0.2 setup channel mask
SETUP_DOLBY_7_1_2 = (SETUP_DOLBY_7_0_2 | LOW_FREQUENCY), ///< Dolby 7.1.2 setup channel mask
SETUP_DOLBY_7_0_4 = (SETUP_DOLBY_7_0_2 | HEIGHT_BACK_LEFT | HEIGHT_BACK_RIGHT), ///< Dolby 7.0.4 setup channel mask
SETUP_DOLBY_7_1_4 = (SETUP_DOLBY_7_0_4 | LOW_FREQUENCY), ///< Dolby 7.1.4 setup channel mask
SETUP_ALL_SPEAKERS = (SETUP_7POINT1 | BACK_CENTER | SETUP_HEIGHT_ALL | TOP), ///< All speakers.
};
[UnityEngine.Tooltip("A bit field, whose channel identifiers depend on AkChannelConfigType (up to 20).")]
[AkEnumFlag(typeof(ChannelMask))]
public ChannelMask m_ChannelMask = ChannelMask.NONE;
[UnityEngine.Tooltip("The number of channels, identified (deduced from channel mask) or anonymous (set directly).")]
public uint m_NumberOfChannels = 0;
public void CopyTo(AkChannelConfig config)
{
switch (m_ChannelConfigType)
{
case ChannelConfigType.Anonymous:
config.SetAnonymous(m_NumberOfChannels);
break;
case ChannelConfigType.Standard:
config.SetStandard((uint)m_ChannelMask);
break;
case ChannelConfigType.Ambisonic:
config.SetAmbisonic(m_NumberOfChannels);
break;
}
}
}
[UnityEngine.Tooltip("Channel configuration for this output. Hardware might not support the selected configuration.")]
public ChannelConfiguration m_ChannelConfig = new ChannelConfiguration();
public void CopyTo(AkOutputSettings settings)
{
settings.audioDeviceShareset = string.IsNullOrEmpty(m_AudioDeviceShareset) ? AkUnitySoundEngine.AK_INVALID_UNIQUE_ID : AkUtilities.ShortIDGenerator.Compute(m_AudioDeviceShareset);
settings.idDevice = m_DeviceID;
settings.ePanningRule = (AkPanningRule)m_PanningRule;
m_ChannelConfig.CopyTo(settings.channelConfig);
}
}
[System.Serializable]
public partial class AkCommonUserSettings
{
[UnityEngine.Tooltip("Path for the SoundBanks. This must contain one sub folder per platform, with the same as in the Wwise project.")]
public string m_BasePath = AkBasePathGetter.DefaultBasePath;
[UnityEngine.Tooltip("Language sub-folder used at startup.")]
public string m_StartupLanguage = "English(US)";
[UnityEngine.Tooltip("Enable Wwise engine logging. This is used to turn on/off the logging of the Wwise engine.")]
public bool m_EngineLogging = AkCallbackManager.InitializationSettings.DefaultIsLoggingEnabled;
[UnityEngine.Tooltip("Whether Decoded Banks are enabled.")]
public bool m_IsDecodedBankEnabled = false;
[UnityEngine.Tooltip("Whether Auto Bank is enabled in Wwise.")]
public bool m_IsAutoBankEnabled = true;
[UnityEngine.Tooltip("The default value of the \"Attenuation Scaling Factor\" when an AkAudioListener is created.")]
public float m_DefaultListenerScalingFactor = 1.0f;
[UnityEngine.Tooltip("Maximum number of automation paths for positioning sounds.")]
public uint m_MaximumNumberOfPositioningPaths = 255;
[UnityEngine.Tooltip("Size of the command queue.")]
public uint m_CommandQueueSize = 256 * 1024;
[UnityEngine.Tooltip("Number of samples per audio frame (256, 512, 1024, or 2048).")]
public uint m_SamplesPerFrame = 512;
[UnityEngine.Tooltip("Main output device settings.")]
public AkCommonOutputSettings m_MainOutputSettings;
protected partial string GetPluginPath();
public virtual void CopyTo(AkInitSettings settings)
{
settings.uMaxNumPaths = m_MaximumNumberOfPositioningPaths;
settings.uCommandQueueSize = m_CommandQueueSize;
settings.uNumSamplesPerFrame = m_SamplesPerFrame;
settings.fStreamingLookAheadRatio = m_StreamingLookAheadRatio;
m_MainOutputSettings.CopyTo(settings.settingsMainOutput);
settings.szPluginDLLPath = GetPluginPath();
WwiseLogger.Log("Setting Plugin DLL path to: " + (settings.szPluginDLLPath == null ? "NULL" : settings.szPluginDLLPath));
}
[UnityEngine.Tooltip("Multiplication factor for all streaming look-ahead heuristic values.")]
[UnityEngine.Range(0, 1)]
public float m_StreamingLookAheadRatio = 1.0f;
public void CopyTo(AkStreamMgrSettings settings)
{
}
public virtual void CopyTo(AkDeviceSettings settings) { }
[UnityEngine.Tooltip("Sampling rate in Hz. The default value is 48000. Use 24000 for low quality audio. Any positive, reasonable sample rate is supported. However, very low sample rates might cause the sound engine to malfunction.")]
public uint m_SampleRate = 48000;
[UnityEngine.Tooltip("Number of refill buffers in voice buffer. Set to 2 for double-buffered. The default value is to 4.")]
public ushort m_NumberOfRefillsInVoice = 4;
partial void SetSampleRate(AkPlatformInitSettings settings);
public virtual void CopyTo(AkPlatformInitSettings settings)
{
SetSampleRate(settings);
settings.uNumRefillsInVoice = m_NumberOfRefillsInVoice;
}
[System.Serializable]
public class SpatialAudioSettings
{
public enum TransmissionOperation
{
Add,
Multiply,
Max
};
[UnityEngine.Tooltip("Maximum number of portals that sound can propagate through. The default value is 8.")]
[UnityEngine.Range(0, AkUnitySoundEngine.AK_MAX_SOUND_PROPAGATION_DEPTH)]
public uint m_MaxSoundPropagationDepth = AkUnitySoundEngine.AK_MAX_SOUND_PROPAGATION_DEPTH;
[UnityEngine.Tooltip("Distance (in game units) that an emitter or listener has to move to trigger a recalculation of reflections and diffraction. A high distance value has a lower CPU load than a low distance value, but the accuracy is also lower. Note that this value does not affect the ray tracing itself. Rays are cast each time a Spatial Audio update is executed. The default value is 0.25.")]
/// Distance (in game units) that an emitter or listener has to move to trigger a recalculation of reflections and diffraction.
/// A high distance value has a lower CPU load than a low distance value, but the accuracy is also lower. Note that this value does not affect the ray tracing itself. Rays are cast each time a Spatial Audio update is executed.
/// The default value is 0.25.
public float m_MovementThreshold = 0.25f;
[UnityEngine.Tooltip("The number of primary rays used in the ray tracing engine. A larger value increases the chances of finding reflection and diffraction paths but results in higher CPU usage. The default value is 35.")]
/// The number of primary rays used in the ray tracing engine. A larger value increases the chances of finding reflection and diffraction paths but results in higher CPU usage.
/// The default value is 35.
public uint m_NumberOfPrimaryRays = 35;
[UnityEngine.Range(0, 4)]
[UnityEngine.Tooltip("The maximum reflection order: the number of \"bounces\" in a reflection path. A higher reflection order renders more detail at the expense of higher CPU usage. The default value is 2.")]
[UnityEngine.Serialization.FormerlySerializedAs("m_ReflectionsOrder")]
/// The maximum reflection order: the number of "bounces" in a reflection path. A higher reflection order renders more detail at the expense of higher CPU usage.
/// Valid range: 1-4. The default value is 2.
public uint m_MaxReflectionOrder = 2;
[UnityEngine.Range(0, 8)]
[UnityEngine.Tooltip("Maximum diffraction order: the number of \"bends\" in a diffraction path. A high diffraction order accommodates more complex geometry at the expense of higher CPU usage. Diffraction must be enabled on the geometry to find diffraction paths. Set to 0 to disable diffraction on all geometry. This parameter limits the recursion depth of diffraction rays cast from the listener to scan the environment and also the depth of the diffraction search to find paths between emitter and listener. To optimize CPU usage, set it to the maximum number of edges you expect the obstructing geometry to traverse. The default value is 4.")]
/// Maximum diffraction order: the number of "bends" in a diffraction path. A high diffraction order accommodates more complex geometry at the expense of higher CPU usage.
/// Diffraction must be enabled on the geometry to find diffraction paths. Set to 0 to disable diffraction on all geometry.
/// This parameter limits the recursion depth of diffraction rays cast from the listener to scan the environment and also the depth of the diffraction search to find paths between emitter and listener.
/// To optimize CPU usage, set it to the maximum number of edges you expect the obstructing geometry to traverse.
/// Valid range: 1-4. The default value is 4.
public uint m_MaxDiffractionOrder = 4;
[UnityEngine.Range(0, 4)]
[UnityEngine.Tooltip("The maximum possible number of diffraction points at each end of a reflection path. Diffraction on reflection allows reflections to fade in and out smoothly as the listener or emitter moves in and out of the reflection's shadow zone. When greater than zero, diffraction rays are sent from the listener to search for reflections around one or more corners from the listener. Diffraction must be enabled on the geometry to find diffracted reflections. Set to 0 to disable diffraction on reflections. Set to 2 or greater to allow Reflection paths to travel through Portals. The default value is 2.")]
/// The maximum possible number of diffraction points at each end of a reflection path.
/// Diffraction on reflection allows reflections to fade in and out smoothly as the listener or emitter moves in and out of the reflection's shadow zone.
/// When greater than zero, diffraction rays are sent from the listener to search for reflections around one or more corners from the listener.
/// Diffraction must be enabled on the geometry to find diffracted reflections.
/// Set to 0 to disable diffraction on reflections. Set to 2 or greater to allow Reflection paths to travel through Portals. The default value is 2.
public uint m_DiffractionOnReflectionsOrder = 2;
[UnityEngine.Tooltip("The maximum number of game-defined auxiliary sends that can originate from a single emitter. An emitter can send to its own Room and to all adjacent Rooms if the emitter and listener are in the same Room. If a limit is set, the most prominent sends are kept, based on spread to the adjacent portal from the emitter's perspective. Set to 1 to only allow emitters to send directly to their current Room, and to the Room a listener is transitioning to if inside a portal. Set to 0 to disable the limit. The default value is 3.")]
/// The maximum number of game-defined auxiliary sends that can originate from a single emitter.
/// An emitter can send to its own Room and to all adjacent Rooms if the emitter and listener are in the same Room.
/// If a limit is set, the most prominent sends are kept, based on spread to the adjacent portal from the emitter's perspective.
/// Set to 1 to only allow emitters to send directly to their current Room, and to the Room a listener is transitioning to if inside a portal.
/// Set to 0 to disable the limit. The default value is 3.
public uint m_MaxEmitterRoomAuxSends = 3;
[UnityEngine.Tooltip("Length of the rays that are cast inside Spatial Audio. Effectively caps the maximum length of an individual segment in a reflection or diffraction path. The default value is 1000.")]
/// Length of the rays that are cast inside Spatial Audio. Effectively caps the maximum length of an individual segment in a reflection or diffraction path. The default value is 1000.
public float m_MaxPathLength = 1000.0f;
[UnityEngine.Tooltip("Defines the targeted maximum computation time allocated for Spatial Audio as a percentage [0, 100] of the current audio frame. When the value is greater than 0, Spatial Audio dynamically adapts the load-balancing based on the current CPU usage and the specified CPU limit. Set to 0 to disable the dynamic load balancing spread computation. The default value is 0.")]
/// Defines the targeted maximum computation time allocated for Spatial Audio as a percentage [0, 100] of the current audio frame.
/// When the value is greater than 0, Spatial Audio dynamically adapts the load-balancing spread based on the current CPU usage and the specified CPU limit.
/// Set to 0 to disable the dynamic load-balancing spread computation.
/// The default value is 0.
public float m_CPULimitPercentage = 0.0f;
[UnityEngine.Tooltip("Enable computation of geometric diffraction and transmission paths for all sources that have the \"Diffraction and Transmission\" option selected in the Positioning tab of the Wwise Property Editor. This flag enables sound paths around (diffraction) and through (transmission) geometry. Setting EnableGeometricDiffractionAndTransmission to false implies that geometry is only to be used for reflection calculation. Diffraction edges must be enabled on geometry for diffraction calculation. If EnableGeometricDiffractionAndTransmission is false but a sound has \"Diffraction and Transmission\" selected in the Positioning tab of Wwise Authoring, the sound will diffract through portals but pass through geometry as if it isn't there. Typically, we recommend you disable this setting if the game will perform obstruction calculations, but geometry is still passed to Spatial Audio for reflection calculations. The default value is true.")]
[UnityEngine.Serialization.FormerlySerializedAs("m_EnableDirectPathDiffraction")]
/// Enable computation of geometric diffraction and transmission paths for all sources that have the \"Diffraction and Transmission\" option selected in the Positioning tab of the Wwise Property Editor.
/// This flag enables sound paths around (diffraction) and through (transmission) geometry. Setting EnableGeometricDiffractionAndTransmission to false implies that geometry is only to be used for reflection calculation.
/// Diffraction edges must be enabled on geometry for diffraction calculation.
/// If EnableGeometricDiffractionAndTransmission is false but a sound has \"Diffraction and Transmission\" selected in the Positioning tab of Wwise Authoring, the sound will diffract through portals but pass through geometry as if it isn't there.
/// Typically, we recommend you disable this setting if the game will perform obstruction calculations, but geometry is still passed to Spatial Audio for reflection calculations.
/// The default value is true.
public bool m_EnableGeometricDiffractionAndTransmission = true;
[UnityEngine.Tooltip("An emitter that is diffracted through a portal or around geometry will have its apparent or virtual position calculated by Wwise Spatial Audio and passed on to the sound engine. The default value is true.")]
/// An emitter that is diffracted through a portal or around geometry will have its apparent or virtual position calculated by Wwise Spatial Audio and passed on to the sound engine. The default value is true.
public bool m_CalcEmitterVirtualPosition = true;
[UnityEngine.MinAttribute(1)]
[UnityEngine.Tooltip("The computation of spatial audio paths is spread on LoadBalancingSpread frames. Spreading the computation of paths over several frames can prevent CPU peaks. The spread introduces a delay in path computation. The default value is 1.")]
/// The computation of spatial audio paths is spread on LoadBalancingSpread frames.
/// Spreading the computation of paths over several frames can prevent CPU peaks. The spread introduces a delay in path computation. The default value is 1.
public uint m_LoadBalancingSpread = 1;
[UnityEngine.MinAttribute(0)]
[UnityEngine.Tooltip("Limit the maximum number of diffraction paths computed per emitter, excluding the direct/transmission path. The acoustics engine searches for up to uMaxDiffractionPaths paths and stops searching when this limit is reached. Setting a low number for uMaxDiffractionPaths (1-4) uses fewer CPU resources, but is more likely to cause discontinuities in the resulting audio. This can occur, for example, when a more prominent path is discovered, displacing a less prominent one. Conversely, a larger number (8 or more) produces higher quality output but requires more CPU resources. The recommended range is 2-8.")]
/// Limit the maximum number of diffraction paths computed per emitter, excluding the direct/transmission path. The acoustics engine searches for up to uMaxDiffractionPaths paths and stops searching when this limit is reached.
/// Setting a low number for uMaxDiffractionPaths (1-4) uses fewer CPU resources, but is more likely to cause discontinuities in the resulting audio. This can occur, for example, when a more prominent path is discovered, displacing a less prominent one.
/// Conversely, a larger number (8 or more) produces higher quality output but requires more CPU resources. The recommended range is 2-8.
public uint m_MaxDiffractionPaths = 8;
[UnityEngine.MinAttribute(0)]
[UnityEngine.Tooltip("[\"Experimental\"] Set a global reflection path limit among all sound emitters with early reflections enabled. Potential reflection paths, discovered by raycasting, are first sorted according to a heuristic to determine which paths are the most prominent. Afterwards, the full reflection path calculation is performed on only the uMaxReflectionPaths, most prominent paths. Limiting the total number of reflection path calculations can significantly reduce CPU usage. Recommended range: 10-50. Set to 0 to disable the limit. In this case, the number of paths computed is unbounded and depends on how many are discovered by raycasting.")]
/// [\ref spatial_audio_experimental "Experimental"] Set a global reflection path limit among all sound emitters with early reflections enabled. Potential reflection paths, discovered by raycasting, are first sorted according to a heuristic to determine which paths are the most prominent.
/// Afterwards, the full reflection path calculation is performed on only the uMaxGlobalReflectionPaths, most prominent paths. Limiting the total number of reflection path calculations can significantly reduce CPU usage. Recommended range: 10-50.
/// Set to 0 to disable the limit. In this case, the number of paths computed is unbounded and depends on how many are discovered by raycasting.
public uint m_MaxGlobalReflectionPaths = 0;
[UnityEngine.MinAttribute(0.0f)]
[UnityEngine.Tooltip("The largest possible diffraction value, in degrees, beyond which paths are not computed and are inaudible. Must be greater than zero. Default value: 180 degrees. A large value (for example, 360 degrees) allows paths to propagate further around corners and obstacles, but takes more CPU time to compute. A gain is applied to each diffraction path to taper the volume of the path to zero as the diffraction angle approaches fMaxDiffractionAngleDegrees, and appears in the Voice Inspector as 'Propagation Path Gain'. This tapering gain is applied in addition to the diffraction curves, and prevents paths from popping in or out suddenly when the maximum diffraction angle is exceeded. In Wwise Authoring, the horizontal axis of a diffraction curve in the attenuation editor is defined over the range 0-100%, corresponding to angles 0-180 degrees. If fMaxDiffractionAngleDegrees is greater than 180 degrees, diffraction coefficients over 100% are clamped and the curve is evaluated at the rightmost point.")]
/// The largest possible diffraction value, in degrees, beyond which paths are not computed and are inaudible. Must be greater than zero. Default value: 180 degrees.
/// A large value (for example, 360 degrees) allows paths to propagate further around corners and obstacles, but takes more CPU time to compute.
/// A gain is applied to each diffraction path to taper the volume of the path to zero as the diffraction angle approaches fMaxDiffractionAngleDegrees,
/// and appears in the Voice Inspector as "Propagation Path Gain". This tapering gain is applied in addition to the diffraction curves, and prevents paths from popping in or out suddenly when the maximum diffraction angle is exceeded.
/// In Wwise Authoring, the horizontal axis of a diffraction curve in the attenuation editor is defined over the range 0-100%, corresponding to angles 0-180 degrees.
/// If fMaxDiffractionAngleDegrees is greater than 180 degrees, diffraction coefficients over 100% are clamped and the curve is evaluated at the rightmost point.
public float m_MaxDiffractionAngleDegrees = 180.0f;
[UnityEngine.Tooltip("[\"Experimental\"] Enable parameter smoothing on the diffraction paths output from the Acoustics Engine. Set fSmoothingConstantMs to a value greater than 0 to define the time constant (in milliseconds) for parameter smoothing. The time constant of an exponential moving average is the amount of time for the smoothed response of a unit step function to reach 1 - 1/e ~= 63.2% of the original signal. A large value (eg. 500-1000 ms) results in less variance but introduces lag, which is a good choice when using conservative values for uNumberOfPrimaryRays (eg. 5-10), uMaxDiffractionPaths (eg. 1-3) or fMovementThreshold ( > 1m ), in order to reduce overall CPU cost. A small value (eg. 10-100 ms) results in greater accuracy and faster convergence of rendering parameters. Set to 0 to disable path smoothing.")]
/// [\ref spatial_audio_experimental "Experimental"] Enable parameter smoothing on the diffraction paths output from the Acoustics Engine. Set fSmoothingConstantMs to a value greater than 0 to define the time constant (in milliseconds) for parameter smoothing.
/// The time constant of an exponential moving average is the amount of time for the smoothed response of a unit step function to reach 1 - 1/e ~= 63.2% of the original signal.
/// A large value (eg. 500-1000 ms) results in less variance but introduces lag, which is a good choice when using conservative values for uNumberOfPrimaryRays (eg. 5-10), uMaxDiffractionPaths (eg. 1-3) or fMovementThreshold ( > 1m ), in order to reduce overall CPU cost.
/// A small value (eg. 10-100 ms) results in greater accuracy and faster convergence of rendering parameters. Set to 0 to disable path smoothing.
public float m_SmoothingConstantMs = 0.0f;
[UnityEngine.Tooltip("The operation used to determine transmission loss on direct paths.")]
public TransmissionOperation m_TransmissionOperation = TransmissionOperation.Max;
[UnityEngine.Tooltip("[\"Experimental\"] Enable/Disable emitter clustering by defining the minimum number of emitters in a cluster. Default value is 0. Values less than 2 disable the clustering.")]
///< Note: Emitters with multi-positions are not clustered and are treated as independant emitters.
///< Note: Changing an emitter from single to multi-positions with load balancing enabled (see \ref AkSpatialAudioInitSettings::uLoadBalancingSpread) might lead to unknown behaviors for a few frames.)
public uint m_ClusteringMinPoints = 0;
[UnityEngine.MinAttribute(0)]
[UnityEngine.Tooltip("Max distance between emitters to be considered as neighbors. This distance is specified for the reference distance defined by m_ClusteringDeadZoneDistance. Default value is 5.0.")]
public float m_ClusteringMaxDistance = 5.0f;
[UnityEngine.MinAttribute(0)]
[UnityEngine.Tooltip("Defines a dead zone around the listener where no emitters are clusters. Default value is 10.0.")]
public float m_ClusteringDeadZoneDistance = 10.0f;
}
[UnityEngine.Tooltip("Spatial audio common settings.")]
public SpatialAudioSettings m_SpatialAudioSettings;
public virtual void CopyTo(AkSpatialAudioInitSettings settings)
{
settings.uMaxSoundPropagationDepth = m_SpatialAudioSettings.m_MaxSoundPropagationDepth;
settings.fMovementThreshold = m_SpatialAudioSettings.m_MovementThreshold;
settings.uNumberOfPrimaryRays = m_SpatialAudioSettings.m_NumberOfPrimaryRays;
settings.uMaxReflectionOrder = m_SpatialAudioSettings.m_MaxReflectionOrder;
settings.uMaxDiffractionOrder = m_SpatialAudioSettings.m_MaxDiffractionOrder;
settings.uMaxDiffractionPaths = m_SpatialAudioSettings.m_MaxDiffractionPaths;
settings.uMaxGlobalReflectionPaths = m_SpatialAudioSettings.m_MaxGlobalReflectionPaths;
settings.uMaxEmitterRoomAuxSends = m_SpatialAudioSettings.m_MaxEmitterRoomAuxSends;
settings.uDiffractionOnReflectionsOrder = m_SpatialAudioSettings.m_DiffractionOnReflectionsOrder;
settings.fMaxDiffractionAngleDegrees = m_SpatialAudioSettings.m_MaxDiffractionAngleDegrees;
settings.fMaxPathLength = m_SpatialAudioSettings.m_MaxPathLength;
settings.fCPULimitPercentage = m_SpatialAudioSettings.m_CPULimitPercentage;
settings.fSmoothingConstantMs = m_SpatialAudioSettings.m_SmoothingConstantMs;
settings.uLoadBalancingSpread = m_SpatialAudioSettings.m_LoadBalancingSpread;
settings.bEnableGeometricDiffractionAndTransmission = m_SpatialAudioSettings.m_EnableGeometricDiffractionAndTransmission;
settings.bCalcEmitterVirtualPosition = m_SpatialAudioSettings.m_CalcEmitterVirtualPosition;
settings.eTransmissionOperation = (AkTransmissionOperation)m_SpatialAudioSettings.m_TransmissionOperation;
settings.uClusteringMinPoints = m_SpatialAudioSettings.m_ClusteringMinPoints;
settings.fClusteringMaxDistance = m_SpatialAudioSettings.m_ClusteringMaxDistance;
settings.fClusteringDeadZoneDistance = m_SpatialAudioSettings.m_ClusteringDeadZoneDistance;
}
public virtual void Validate()
{
if (m_SpatialAudioSettings.m_MovementThreshold < 0.0f)
{
m_SpatialAudioSettings.m_MovementThreshold = 0.0f;
}
if (m_SpatialAudioSettings.m_MaxPathLength < 0.0f)
{
m_SpatialAudioSettings.m_MaxPathLength = 0.0f;
}
if (m_SpatialAudioSettings.m_CPULimitPercentage < 0.0f)
{
m_SpatialAudioSettings.m_CPULimitPercentage = 0.0f;
}
else if (m_SpatialAudioSettings.m_CPULimitPercentage > 100.0f)
{
m_SpatialAudioSettings.m_CPULimitPercentage = 100.0f;
}
}
}
[System.Serializable]
public class AkCommonAdvancedSettings
{
[UnityEngine.Tooltip("Size of memory pool for I/O (for automatic streams). It is rounded down to a multiple of uGranularity and then passed directly to AK::MemoryMgr::CreatePool().")]
public uint m_IOMemorySize = 2 * 1024 * 1024;
[UnityEngine.Tooltip("Targeted automatic stream buffer length (ms). When a stream reaches that buffering, it stops being scheduled for I/O except if the scheduler is idle.")]
public float m_TargetAutoStreamBufferLengthMs = 380.0f;
[UnityEngine.Tooltip("If true the device attempts to reuse IO buffers that have already been streamed from disk. This is particularly useful when streaming small looping sounds. The drawback is a small CPU hit when allocating memory, and a slightly larger memory footprint in the StreamManager pool.")]
public bool m_UseStreamCache = false;
[UnityEngine.Tooltip("Default settings for loading banks.This setting can be overriden by each bank.")]
public bool m_LoadBankAsynchronously = false;
[UnityEngine.Tooltip("Maximum number of bytes that can be \"pinned\" using AK::SoundEngine::PinEventInStreamCache() or AK::IAkStreamMgr::PinFileInCache()")]
public uint m_MaximumPinnedBytesInCache = unchecked((uint)(-1));
public virtual void CopyTo(AkDeviceSettings settings)
{
settings.uIOMemorySize = m_IOMemorySize;
settings.fTargetAutoStmBufferLength = m_TargetAutoStreamBufferLengthMs;
settings.bUseStreamCache = m_UseStreamCache;
settings.uMaxCachePinnedBytes = m_MaximumPinnedBytesInCache;
}
[UnityEngine.Tooltip("Set to true to enable AK::SoundEngine::PrepareGameSync usage.")]
public bool m_EnableGameSyncPreparation = false;
[UnityEngine.Tooltip("Number of quanta ahead when continuous containers instantiate a new voice before the following sounds start playing. This look-ahead time allows I/O to occur, and is especially useful to reduce the latency of continuous containers with trigger rate or sample-accurate transitions.")]
public uint m_ContinuousPlaybackLookAhead = 1;
[UnityEngine.Tooltip("Size of the monitoring queue pool. This parameter is ignored in Release build.")]
public uint m_MonitorQueuePoolSize = 1024 * 1024;
[UnityEngine.Tooltip("Time (in milliseconds) to wait to wait for hardware devices to trigger an audio interrupt. If there is no interrupt after that time, the sound engine reverts to silent mode and continues operating until the hardware responds.")]
public uint m_MaximumHardwareTimeoutMs = 1000;
[UnityEngine.Tooltip("Debug setting: Enable checks for out-of-range (and NAN) floats in the processing code. Do not enable in any normal usage because this setting uses a lot of CPU. It prints error messages in the log if invalid values are found at various points in the pipeline. Contact AK Support with the new error messages for more information.")]
public bool m_DebugOutOfRangeCheckEnabled = false;
[UnityEngine.Tooltip("Debug setting: Only used when bDebugOutOfRangeCheckEnabled is true. This defines the maximum values samples can have. Normal audio must be contained within +1/-1. Set this limit to a value greater than 1 to allow temporary or short excursions out of range. The default value is 16.")]
public float m_DebugOutOfRangeLimit = 16.0f;
public virtual void CopyTo(AkInitSettings settings)
{
settings.bEnableGameSyncPreparation = m_EnableGameSyncPreparation;
settings.uContinuousPlaybackLookAhead = m_ContinuousPlaybackLookAhead;
settings.uMonitorQueuePoolSize = m_MonitorQueuePoolSize;
settings.uMaxHardwareTimeoutMs = m_MaximumHardwareTimeoutMs;
settings.bDebugOutOfRangeCheckEnabled = m_DebugOutOfRangeCheckEnabled;
settings.fDebugOutOfRangeLimit = m_DebugOutOfRangeLimit;
}
public virtual void CopyTo(AkPlatformInitSettings settings) { }
[UnityEngine.Tooltip("Determines whether to suspend audio during loss of focus of the editor or game.")]
public bool m_SuspendAudioDuringFocusLoss = true;
[UnityEngine.Tooltip("Determines whether to continue rendering audio while audio is suspended during focus loss. Only applicable if <b>Suspend Audio During Focus Loss</b> is enabled.")]
public bool m_RenderDuringFocusLoss;
[UnityEngine.Tooltip("Sets the sub-folder underneath UnityEngine.Application.persistentDataPath that will be used as the SoundBank base path. This is useful when the Init.bnk needs to be downloaded. Setting this to an empty string uses the typical SoundBank base path resolution. Setting this to \".\" uses UnityEngine.Application.persistentDataPath.")]
public string m_SoundBankPersistentDataPath;
[UnityEngine.Tooltip("Configures whether sub-folders are created in output folders. This needs to match the \"Create sub-folders for generated files\" SoundBank setting in Wwise Authoring.")]
public bool m_UseSubFoldersForGeneratedFiles;
[UnityEngine.Tooltip("Initial size of SBA portion of the Primary Memory Arena.")]
public uint m_MemoryPrimarySbaInitSize = 2097152;
[UnityEngine.Tooltip("Initial size of TLSF portion of the Primary Memory Arena.")]
public uint m_MemoryPrimaryTlsfInitSize = 2097152;
[UnityEngine.Tooltip("Size of each secondary span initialized for TLSF portion of the Primary Memory Arena.")]
public uint m_MemoryPrimaryTlsfSpanSize = 2097152;
[UnityEngine.Tooltip("Maximum amount of memory will be reserved for the Primary Memory Arena. A value of 0 will indicate no limit.")]
public uint m_MemoryPrimaryReservedLimit = 0;
[UnityEngine.Tooltip("Minimum size of allocations to be considered 'Huge' for the Primary Memory Arena. Huge allocations are put into standalone spans, separate from the TLSF spans")]
public uint m_MemoryPrimaryAllocSizeHuge = 2097152;
[UnityEngine.Tooltip("Initial size of TLSF portion of the Media Memory Arena.")]
public uint m_MemoryMediaTlsfInitSize = 2097152;
[UnityEngine.Tooltip("Size of each secondary span initialized for TLSF portion of the Media Memory Arena.")]
public uint m_MemoryMediaTlsfSpanSize = 2097152;
[UnityEngine.Tooltip("Maximum amount of memory will be reserved for the Media Memory Arena. A value of 0 will indicate no limit.")]
public uint m_MemoryMediaReservedLimit = 0;
[UnityEngine.Tooltip("Minimum size of allocations to be considered 'Huge' for the Media Memory Arena. Huge allocations are put into standalone spans, separate from the TLSF spans")]
public uint m_MemoryMediaAllocSizeHuge = 2097152;
[UnityEngine.Tooltip("Memory allocator debug level. For use under Audiokinetic Support supervision.")]
public uint m_MemoryDebugLevel = 0;
}
[System.Serializable]
public class AkCommonCommSettings
{
[UnityEngine.Tooltip("Size of the communication pool.")]
public uint m_PoolSize = 256 * 1024;
public static ushort DefaultDiscoveryBroadcastPort = 24024;
[UnityEngine.Tooltip("The port where the authoring application broadcasts \"Game Discovery\" requests to discover games running on the network. Default value: 24024. (Cannot be set to 0)")]
public ushort m_DiscoveryBroadcastPort = DefaultDiscoveryBroadcastPort;
[UnityEngine.Tooltip("The \"command\" channel port. Set to 0 to request a dynamic/ephemeral port.")]
public ushort m_CommandPort;
[UnityEngine.Tooltip("The \"notification\" channel port. Set to 0 to request a dynamic/ephemeral port.")]
public ushort m_NotificationPort;
[UnityEngine.Tooltip("Indicates whether or not to initialize the communication system. Some consoles have critical requirements for initialization of their communications system. Set to false only if your game already uses sockets before sound engine initialization.")]
public bool m_InitializeSystemComms = true;
[UnityEngine.Tooltip("The name used to identify this game within the authoring application. Leave empty to use \"UnityEngine.Application.productName\".")]
public string m_NetworkName;
[UnityEngine.Tooltip("HTCS communication can only be used with a Nintendo Switch Development Build")]
public AkCommunicationSettings.AkCommSystem m_commSystem = AkCommunicationSettings.AkCommSystem.AkCommSystem_Socket;
public virtual void CopyTo(AkCommunicationSettings settings)
{
settings.uPoolSize = m_PoolSize;
settings.uDiscoveryBroadcastPort = m_DiscoveryBroadcastPort;
settings.uCommandPort = m_CommandPort;
settings.bInitSystemLib = m_InitializeSystemComms;
settings.commSystem = m_commSystem;
string networkName = m_NetworkName;
if (string.IsNullOrEmpty(networkName))
networkName = UnityEngine.Application.productName;
#if UNITY_EDITOR
networkName += " (Editor)";
#endif
settings.szAppNetworkName = networkName;
}
public virtual void Validate() { }
}
public abstract class AkCommonPlatformSettings : AkBasePlatformSettings
{
protected abstract AkCommonUserSettings GetUserSettings();
protected abstract AkCommonAdvancedSettings GetAdvancedSettings();
protected abstract AkCommonCommSettings GetCommsSettings();
public override AkInitializationSettings AkInitializationSettings
{
get
{
var settings = base.AkInitializationSettings;
var userSettings = GetUserSettings();
userSettings.CopyTo(settings.deviceSettings);
userSettings.CopyTo(settings.streamMgrSettings);
userSettings.CopyTo(settings.initSettings);
userSettings.CopyTo(settings.platformSettings);
var advancedSettings = GetAdvancedSettings();
advancedSettings.CopyTo(settings.deviceSettings);
advancedSettings.CopyTo(settings.initSettings);
advancedSettings.CopyTo(settings.platformSettings);
settings.bUseSubFoldersForGeneratedFiles = advancedSettings.m_UseSubFoldersForGeneratedFiles;
settings.uMemoryPrimarySbaInitSize = advancedSettings.m_MemoryPrimarySbaInitSize;
settings.uMemoryPrimaryTlsfInitSize = advancedSettings.m_MemoryPrimaryTlsfInitSize;
settings.uMemoryPrimaryTlsfSpanSize = advancedSettings.m_MemoryPrimaryTlsfSpanSize;
settings.uMemoryPrimaryAllocSizeHuge = advancedSettings.m_MemoryPrimaryAllocSizeHuge;
settings.uMemoryPrimaryReservedLimit = advancedSettings.m_MemoryPrimaryReservedLimit;
settings.uMemoryMediaTlsfInitSize = advancedSettings.m_MemoryMediaTlsfInitSize;
settings.uMemoryMediaTlsfSpanSize = advancedSettings.m_MemoryMediaTlsfSpanSize;
settings.uMemoryMediaAllocSizeHuge = advancedSettings.m_MemoryMediaAllocSizeHuge;
settings.uMemoryMediaReservedLimit = advancedSettings.m_MemoryMediaReservedLimit;
settings.uMemDebugLevel = advancedSettings.m_MemoryDebugLevel;
return settings;
}
}
public override AkSpatialAudioInitSettings AkSpatialAudioInitSettings
{
get
{
var settings = base.AkSpatialAudioInitSettings;
GetUserSettings().CopyTo(settings);
return settings;
}
}
public override AkCallbackManager.InitializationSettings CallbackManagerInitializationSettings
{
get
{
return new AkCallbackManager.InitializationSettings { IsLoggingEnabled = GetUserSettings().m_EngineLogging };
}
}
public override string InitialLanguage
{
get { return GetUserSettings().m_StartupLanguage; }
}
public override bool IsDecodedBankEnabled
{
get { return GetUserSettings().m_IsDecodedBankEnabled; }
}
public override bool IsAutoBankEnabled
{
get { return GetUserSettings().m_IsAutoBankEnabled; }
set { GetUserSettings().m_IsAutoBankEnabled = value; }
}
public override bool LoadBanksAsynchronously
{
get { return GetAdvancedSettings().m_LoadBankAsynchronously; }
set { GetAdvancedSettings().m_LoadBankAsynchronously = value; }
}
public override string SoundBankPersistentDataPath
{
get { return GetAdvancedSettings().m_SoundBankPersistentDataPath; }
}
public override bool SuspendAudioDuringFocusLoss
{
get { return GetAdvancedSettings().m_SuspendAudioDuringFocusLoss; }
}
public override bool RenderDuringFocusLoss
{
get { return GetAdvancedSettings().m_RenderDuringFocusLoss; }
}
public override string SoundbankPath
{
get { return GetUserSettings().m_BasePath; }
}
public override bool UseSubFoldersForGeneratedFiles
{
get { return GetAdvancedSettings().m_UseSubFoldersForGeneratedFiles; }
}
public override uint MemoryDebugLevel
{
get { return GetAdvancedSettings().m_MemoryDebugLevel; }
}
public override float defaultListenerScalingFactor
{
get { return GetUserSettings().m_DefaultListenerScalingFactor; }
}
public override AkCommunicationSettings AkCommunicationSettings
{
get
{
var settings = base.AkCommunicationSettings;
GetCommsSettings().CopyTo(settings);
return settings;
}
}
#region parameter validation
#if UNITY_EDITOR
void OnValidate()
{
GetUserSettings().Validate();
GetCommsSettings().Validate();
}
#endif
#endregion
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 7b9556ae5b60a884593dac52ed024f34
@@ -0,0 +1,41 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
[System.AttributeUsage(System.AttributeTargets.Field, Inherited = true)]
public class AkEnumFlagAttribute : UnityEngine.PropertyAttribute
{
public System.Type Type;
public AkEnumFlagAttribute(System.Type type)
{
Type = type;
}
#if UNITY_EDITOR
[UnityEditor.CustomPropertyDrawer(typeof(AkEnumFlagAttribute))]
public class PropertyDrawer : UnityEditor.PropertyDrawer
{
public override void OnGUI(UnityEngine.Rect position, UnityEditor.SerializedProperty property, UnityEngine.GUIContent label)
{
UnityEditor.EditorGUI.BeginProperty(position, label, property);
var flagAttribute = (AkEnumFlagAttribute)attribute;
property.longValue = UnityEditor.EditorGUI.EnumFlagsField(position, new UnityEngine.GUIContent(label.text, AkUtilities.GetTooltip(property)), (System.Enum)System.Enum.ToObject(flagAttribute.Type, property.longValue)).GetHashCode();
UnityEditor.EditorGUI.EndProperty();
}
}
#endif
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: e5913d9e407fd604bb8f4538f8867cd1
@@ -0,0 +1,80 @@
using AK.Wwise.Unity.Logging;
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkLogger
{
// @todo sjl: Have SWIG specify the delegate's signature (possibly in AkSoundEngine) so that we can automatically determine the appropriate string marshaling.
[System.Runtime.InteropServices.UnmanagedFunctionPointer(System.Runtime.InteropServices.CallingConvention.StdCall)]
public delegate void ErrorLoggerInteropDelegate(
[System.Runtime.InteropServices.MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPStr)]
string message);
private static AkLogger ms_Instance = new AkLogger();
private ErrorLoggerInteropDelegate errorLoggerDelegate = WwiseInternalLogError;
private AkLogger()
{
if (ms_Instance == null)
{
ms_Instance = this;
AkUnitySoundEngine.SetErrorLogger(errorLoggerDelegate);
}
}
public static AkLogger Instance { get { return ms_Instance; } }
~AkLogger()
{
if (ms_Instance == this)
{
ms_Instance = null;
errorLoggerDelegate = null;
AkUnitySoundEngine.SetErrorLogger();
}
}
public void Init()
{
// used to force instantiation of this singleton
}
[AOT.MonoPInvokeCallback(typeof(ErrorLoggerInteropDelegate))]
public static void WwiseInternalLogError(string message)
{
WwiseLogger.Error(message);
}
public static void Message(string message)
{
WwiseLogger.LogFormat(message);
}
public static void Warning(string message)
{
WwiseLogger.Warning(message);
}
public static void Error(string message)
{
WwiseLogger.Error(message);
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 65f1f1ab106b8e9459d4773ed5ffc8db
@@ -0,0 +1,38 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkShowOnlyAttribute : UnityEngine.PropertyAttribute
{
#if UNITY_EDITOR
[UnityEditor.CustomPropertyDrawer(typeof(AkShowOnlyAttribute))]
public class PropertyDrawer : UnityEditor.PropertyDrawer
{
public override float GetPropertyHeight(UnityEditor.SerializedProperty property, UnityEngine.GUIContent label)
{
return UnityEditor.EditorGUI.GetPropertyHeight(property, label, true);
}
public override void OnGUI(UnityEngine.Rect position, UnityEditor.SerializedProperty property, UnityEngine.GUIContent label)
{
var saveEnabled = UnityEngine.GUI.enabled;
UnityEngine.GUI.enabled = false;
UnityEditor.EditorGUI.PropertyField(position, property, label, true);
UnityEngine.GUI.enabled = saveEnabled;
}
}
#endif // #if UNITY_EDITOR
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: dfed3f19ed8efc94baed86d7ee9c7b90
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: a8c1506e8b5fa4e4d8deb34d3e07caf2
@@ -0,0 +1,281 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if UNITY_ANDROID && !UNITY_EDITOR
using System;
#endif
using System.Runtime.InteropServices;
using AK.Wwise.Unity.Logging;
public class AkUnitySoundEngineInitialization
{
protected static AkUnitySoundEngineInitialization m_Instance;
public System.Action initializationDelegate;
public System.Action reInitializationDelegate;
public System.Action terminationDelegate;
public static AkUnitySoundEngineInitialization Instance
{
get
{
if (m_Instance == null)
{
m_Instance = new AkUnitySoundEngineInitialization();
}
return m_Instance;
}
}
public bool InitializeSoundEngine()
{
WwiseLogger.LogFormat("Wwise(R) SDK Version {0}.", AkUnitySoundEngine.WwiseVersion);
#if UNITY_ANDROID && ! UNITY_EDITOR
//Obtains the Android Java Object "currentActivity" in order to set it for the android io hook initialization
try
{
// Get the current Activity using AndroidJavaClass
using (var unityPlayer = new UnityEngine.AndroidJavaClass("com.unity3d.player.UnityPlayer"))
{
UnityEngine.AndroidJavaObject activity = unityPlayer.GetStatic<UnityEngine.AndroidJavaObject>("currentActivity");
IntPtr rawActivityPtr = activity.GetRawObject(); // Get the JNI pointer
// Pass the raw pointer to the native side
AkUnitySoundEngine.SetAndroidActivity(rawActivityPtr);
}
}
catch (Exception ex)
{
WwiseLogger.Error($"Failed to pass activity to native code: {ex.Message}");
}
#endif
#if UNITY_OPENHARMONY && !UNITY_EDITOR
//Obtains the OpenHarmony TS Object "applicationContext" in order to set it for the OpenHarmony io hook initialization
try
{
// Init using the current applicationContext via the AkUnitySoundEngineInitHelp.ts script
using (var akSoundEngineTs = new UnityEngine.OpenHarmonyJSObject("AkUnitySoundEngineInitHelper"))
{
akSoundEngineTs.Call("Init");
}
}
catch (System.Exception ex)
{
WwiseLogger.Error($"Failed to pass applicationContext to native code: {ex.Message}");
}
#endif
var activePlatformSettings = AkWwiseInitializationSettings.ActivePlatformSettings;
var initSettings = activePlatformSettings.AkInitializationSettings;
// DO NOT REMOVE until AkInitializationSettings.getCPtr(AkInitializationSettings obj) uses a safe handle (e.g. HandleRef)
var handle = GCHandle.Alloc(initSettings);
var initResult = AkUnitySoundEngine.Init(initSettings);
handle.Free();
if (initResult != AKRESULT.AK_Success)
{
WwiseLogger.Error($"Failed to initialize the sound engine. Reason: {initResult}");
AkUnitySoundEngine.Term();
return false;
}
var spatialAudioInitSettings = activePlatformSettings.AkSpatialAudioInitSettings;
// DO NOT REMOVE until AkSpatialAudioInitSettings.getCPtr(AkSpatialAudioInitSettings obj) uses a safe handle (e.g. HandleRef)
handle = GCHandle.Alloc(spatialAudioInitSettings);
if (AkUnitySoundEngine.InitSpatialAudio(spatialAudioInitSettings) != AKRESULT.AK_Success)
{
WwiseLogger.Warning("Failed to initialize spatial audio.");
}
handle.Free();
var communicationSettings = activePlatformSettings.AkCommunicationSettings;
// DO NOT REMOVE until AkCommunicationSettings.getCPtr(AkCommunicationSettings obj) uses a safe handle (e.g. HandleRef)
handle = GCHandle.Alloc(communicationSettings);
AkUnitySoundEngine.InitCommunication(communicationSettings);
handle.Free();
var akBasePathGetterInstance = AkBasePathGetter.Get();
var soundBankBasePath = akBasePathGetterInstance.SoundBankBasePath;
#if UNITY_OPENHARMONY && !UNITY_EDITOR
soundBankBasePath = "rawfile://" + soundBankBasePath;
#endif
if (string.IsNullOrEmpty(soundBankBasePath))
{
// this is a nearly impossible situation
WwiseLogger.Error("Couldn't find SoundBanks base path. Terminating sound engine.");
AkUnitySoundEngine.Term();
return false;
}
var persistentDataPath = akBasePathGetterInstance.PersistentDataPath;
var isBasePathSameAsPersistentPath = soundBankBasePath == persistentDataPath;
#if UNITY_ANDROID
var canSetBasePath = !isBasePathSameAsPersistentPath;
var canSetPersistentDataPath = true;
#else
var canSetBasePath = true;
var canSetPersistentDataPath = !isBasePathSameAsPersistentPath;
#endif
if (canSetBasePath && AkUnitySoundEngine.SetBasePath(soundBankBasePath) != AKRESULT.AK_Success)
{
#if !AK_WWISE_ADDRESSABLES
#if !UNITY_ANDROID || UNITY_EDITOR
#if UNITY_EDITOR
var format = "Failed to set SoundBanks base path to <{0}>. Make sure SoundBank path is correctly set under Edit > Project Settings > Wwise > Editor > Asset Management.";
#else
var format = "Failed to set SoundBanks base path to <{0}>. Make sure SoundBank path is correctly set under Edit > Project Settings > Wwise > Initialization.";
#endif
// It might be normal for SetBasePath to return AK_PathNotFound on Android. Silence the error log to avoid confusion.
WwiseLogger.ErrorFormat(format, soundBankBasePath);
#endif
#endif
}
if (canSetPersistentDataPath && !string.IsNullOrEmpty(persistentDataPath))
{
AkUnitySoundEngine.AddBasePath(persistentDataPath);
}
var decodedBankFullPath = akBasePathGetterInstance.DecodedBankFullPath;
if (!string.IsNullOrEmpty(decodedBankFullPath) && AkWwiseInitializationSettings.Instance.IsDecodedBankEnabled)
{
// AkUnitySoundEngine.SetDecodedBankPath creates the folders for writing to (if they don't exist)
AkUnitySoundEngine.SetDecodedBankPath(decodedBankFullPath);
// Adding decoded bank path last to ensure that it is the first one used when writing decoded banks.
AkUnitySoundEngine.AddBasePath(decodedBankFullPath);
}
AkUnitySoundEngine.SetCurrentLanguage(activePlatformSettings.InitialLanguage);
AkCallbackManager.Init(activePlatformSettings.CallbackManagerInitializationSettings);
WwiseLogger.Log("Sound engine initialized successfully.");
LoadInitBank();
initializationDelegate?.InvokeUnitySafe();
return true;
}
protected virtual void LoadInitBank()
{
AkBankManager.LoadInitBank();
}
protected virtual void ClearBanks()
{
AkUnitySoundEngine.ClearBanks();
}
protected virtual void ResetBanks()
{
AkBankManager.Reset();
}
public bool ResetSoundEngine(bool isInPlayMode)
{
if (isInPlayMode)
{
ClearBanks();
LoadInitBank();
}
AkCallbackManager.Init(AkWwiseInitializationSettings.ActivePlatformSettings.CallbackManagerInitializationSettings);
reInitializationDelegate?.InvokeUnitySafe();
return true;
}
public bool ShouldKeepSoundEngineEnabled()
{
#if UNITY_EDITOR
bool result = true;
if(UnityEditor.EditorApplication.isUpdating || UnityEditor.EditorApplication.isCompiling)
{
return false;
}
if (UnityEngine.Application.isPlaying)
{
return true;
}
if (!UnityEngine.Application.isPlaying)
{
result = AkWwiseEditorSettings.Instance.LoadSoundEngineInEditMode;
}
#if UNITY_2019_3_OR_NEWER
if(UnityEditor.EditorSettings.enterPlayModeOptionsEnabled)
{
result &= UnityEditor.EditorSettings.enterPlayModeOptions.HasFlag(UnityEditor.EnterPlayModeOptions.DisableDomainReload);
}
else
{
result = false;
}
#endif // UNITY_2019_3_OR_NEWER
return result;
#else
return false;
#endif // UNITY_EDITOR
}
public void ResetSoundEngine()
{
TerminateSoundEngine(forceReset : true);
if(ShouldKeepSoundEngineEnabled())
{
ResetSoundEngine(isInPlayMode : true);
InitializeSoundEngine();
}
}
public void TerminateSoundEngine()
{
TerminateSoundEngine(forceReset : false);
}
private void TerminateSoundEngine(bool forceReset)
{
if (!AkUnitySoundEngine.IsInitialized())
{
return;
}
if (ShouldKeepSoundEngineEnabled() && !forceReset)
{
return;
}
terminationDelegate?.InvokeUnitySafe();
AkUnitySoundEngine.Term();
// Make sure we have no callbacks left after Term. Some might be posted during termination.
AkCallbackManager.PostCallbacks();
AkCallbackManager.Term();
ResetBanks();
WwiseLogger.Log("Sound engine terminated successfully.");
}
}
#if WWISE_ADDRESSABLES_23_1_OR_LATER
[System.Obsolete(AkUnitySoundEngine.Ak_Sound_Engine_Init_Rename_2024_1_0)]
public class AkSoundEngineInitialization : AkUnitySoundEngineInitialization {}
#endif
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 6636436b46fd8894fbef982ed83bff22
@@ -0,0 +1,32 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
[System.Obsolete(AkUnitySoundEngine.Deprecation_2019_2_0)]
public class AkVector
{
private UnityEngine.Vector3 Vector = UnityEngine.Vector3.zero;
public void Zero() { Vector.Set(0, 0, 0); }
public float X { set { Vector.x = value; } get { return Vector.x; } }
public float Y { set { Vector.y = value; } get { return Vector.y; } }
public float Z { set { Vector.z = value; } get { return Vector.z; } }
public static implicit operator UnityEngine.Vector3(AkVector vector) { return vector.Vector; }
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 380d2298ccde79c4cb2f6e4f38009c51
@@ -0,0 +1,44 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using System.Runtime.InteropServices;
[StructLayout(LayoutKind.Sequential)]
public class AkVector64
{
public void Zero() {
X = 0.0;
Y = 0.0;
Z = 0.0;
}
public double X = 0.0;
public double Y = 0.0;
public double Z = 0.0;
public static implicit operator AkVector64(UnityEngine.Vector3 vector) {
AkVector64 ret = new AkVector64();
ret.X = vector.x;
ret.Y = vector.y;
ret.Z = vector.z;
return ret;
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 975a9355d97508f4b94c1c5ace8fcd80
@@ -0,0 +1,55 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
[System.Obsolete(AkUnitySoundEngine.Deprecation_2019_2_0)]
public class AkVertex
{
private UnityEngine.Vector3 Vector = UnityEngine.Vector3.zero;
public void Zero() { Vector.Set(0, 0, 0); }
public float X { set { Vector.x = value; } get { return Vector.x; } }
public float Y { set { Vector.y = value; } get { return Vector.y; } }
public float Z { set { Vector.z = value; } get { return Vector.z; } }
public static implicit operator UnityEngine.Vector3(AkVertex vector) { return vector.Vector; }
public AkVertex() { }
public AkVertex(float x, float y, float z) { Vector.Set(x, y, z); }
public void Clear() { Vector.Set(0, 0, 0); }
public static int GetSizeOf() { return sizeof(float) * 3; }
public void Clone(AkVertex other) { Vector = other.Vector; }
}
[System.Obsolete(AkUnitySoundEngine.Deprecation_2019_2_0)]
/// AkVertexArray is now deprecated. Users should instead use UnityEngine.Vector3[].
public class AkVertexArray : AkBaseArray<AkVertex>
{
public AkVertexArray(int count) : base(count) {}
protected override int StructureSize { get { return AkVertex.GetSizeOf(); } }
protected override AkVertex CreateNewReferenceFromIntPtr(System.IntPtr address) { return null; }
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkVertex other) {}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 339a3b41689a6df49a63c9649b9961a0
@@ -0,0 +1,814 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if !(UNITY_QNX) // Disable under unsupported platforms.
#if UNITY_EDITOR
using System;
using System.IO;
using UnityEditor;
using System.Linq;
using System.Xml.Serialization;
using UnityEngine;
using UnityEngine.Serialization;
using AK.Wwise.Unity.Logging;
[System.Serializable]
public class WwiseSettings
{
public const string Filename = "WwiseSettings.xml";
public static string GitRepositoryLink
{
get
{
string wwiseVersion = AkUnitySoundEngine.WwiseVersion;
string shortWwiseVersion = wwiseVersion.Substring(2, wwiseVersion.IndexOf("Build")-3); //-3 for the space and the 2 first character that are skipped.
string repositoryLink = "https://github.com/audiokinetic/WwiseUnityAddressables.git";
repositoryLink += $"#v{shortWwiseVersion}";
return repositoryLink;
}
}
public static string Path
{
get { return System.IO.Path.Combine(UnityEngine.Application.dataPath, Filename); }
}
public static bool Exists { get { return System.IO.File.Exists(Path); } }
public bool CopySoundBanksAsPreBuildStep = true;
public bool GenerateSoundBanksAsPreBuildStep = false;
public string WwiseStreamingAssetsPath = AkBasePathGetter.DefaultBasePath;
[FormerlySerializedAs("GeneratedSoundbanksPath")] public string RootOutputPath;
public bool CreatedPicker = false;
public bool CreateWwiseGlobal = true;
public bool CreateWwiseListener = true;
public bool ObjectReferenceAutoCleanup = true;
public bool LoadSoundEngineInEditMode = true;
public bool ShowMissingRigidBodyWarning = true;
public bool ShowSpatialAudioWarningMsg = true;
public string WwiseInstallationPathMac;
public string WwiseInstallationPathWindows;
public string WwiseProjectPath;
public bool UseWaapi = true;
public string WaapiPort = "8080";
public string WaapiIP = "127.0.0.1";
public bool AutoSyncWaapi = true;
public bool WaapiChangePending = false;
public bool InstallationWasRequested = false;
public bool UseGitRepository = true;
public string PackageSource = "";
public string AddressableBankFolder = "WwiseData/Bank";
public bool UseCustomBuildScript = false;
public string AddressableAssetBuilderPath = "Assets/AddressableAssetsData/DataBuilders/BuildScriptWwisePacked.asset";
public bool AutomaticallyUpdateExternalSourcesPath = false;
public string ExternalSourcesPath = "WwiseData/Bank";
public bool EnableUninstallationPrompt = true;
public bool DisableAsynchronousBankLoading = true;
public string XMLTranslatorTimeout = "0"; //Timeout (in ms) for error translator through SoundBanksInfo.xml. Set to 0 to disable.
public string WaapiTranslatorTimeout = "0"; //Timeout (in ms) for error translator through WAAPI. Set to 0 to disable.
[XmlIgnore]
public LogLevel LogLevel; // Do not serialize this setting, it is saved in its own Resource
[System.Xml.Serialization.XmlIgnore]
public string WwiseInstallationPath
{
#if UNITY_EDITOR_OSX
get { return WwiseInstallationPathMac; }
set { WwiseInstallationPathMac = value; }
#else
get { return WwiseInstallationPathWindows; }
set { WwiseInstallationPathWindows = value; }
#endif
}
internal static WwiseSettings LoadSettings()
{
var settings = new WwiseSettings();
try
{
var path = Path;
if (System.IO.File.Exists(path))
{
var xmlSerializer = new System.Xml.Serialization.XmlSerializer(typeof(WwiseSettings));
using (var xmlFileStream = new System.IO.FileStream(path, System.IO.FileMode.Open, System.IO.FileAccess.Read))
settings = xmlSerializer.Deserialize(xmlFileStream) as WwiseSettings;
}
else
{
var projectDir = System.IO.Path.GetDirectoryName(UnityEngine.Application.dataPath);
var foundWwiseProjects = System.IO.Directory.GetFiles(projectDir, "*.wproj", System.IO.SearchOption.AllDirectories);
if (foundWwiseProjects.Length > 0)
settings.WwiseProjectPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, foundWwiseProjects[0]);
else
settings.WwiseProjectPath = string.Empty;
settings.WwiseStreamingAssetsPath = AkBasePathGetter.DefaultBasePath;
}
}
catch
{
}
settings.LogLevel = WwiseLoggerSettings.Instance.LogLevel;
#if AK_WWISE_ADDRESSABLES && UNITY_ADDRESSABLES
settings.CheckGeneratedBanksPath();
#endif
return settings;
}
#if AK_WWISE_ADDRESSABLES && UNITY_ADDRESSABLES
public void CheckGeneratedBanksPath()
{
var fullRootOutputPath = AkUtilities.GetFullPath(UnityEngine.Application.dataPath, RootOutputPath);
var appDataPath = UnityEngine.Application.dataPath.Replace(System.IO.Path.AltDirectorySeparatorChar, System.IO.Path.DirectorySeparatorChar);
if (!fullRootOutputPath.Contains(appDataPath))
{
WwiseLogger.Warning("RootOutputPath is currently set to a path outside of the Assets folder. Generated SoundBanks will not be properly imported for Addressables. Please change this in Project Settings > Wwise Integration.");
}
}
#endif
public void SaveSettings()
{
try
{
var xmlDoc = new System.Xml.XmlDocument();
var xmlSerializer = new System.Xml.Serialization.XmlSerializer(GetType());
using (var xmlStream = new System.IO.MemoryStream())
{
var streamWriter = new System.IO.StreamWriter(xmlStream, System.Text.Encoding.UTF8);
xmlSerializer.Serialize(streamWriter, this);
xmlStream.Position = 0;
xmlDoc.Load(xmlStream);
xmlDoc.Save(Path);
}
}
catch
{
WwiseLogger.ErrorFormat("Unable to save settings to file <{0}>. Please ensure that this file path can be written to.", Path);
}
if (WwiseLoggerSettings.Instance.LogLevel != LogLevel)
{
WwiseLoggerSettings.Instance.LogLevel = LogLevel;
EditorUtility.SetDirty(WwiseLoggerSettings.Instance);
AssetDatabase.SaveAssetIfDirty(WwiseLoggerSettings.Instance);
}
}
}
public class AkWwiseEditorSettings
{
public static event System.Action OnWaapiSettingsChanged;
private static WwiseSettings s_Instance;
public static WwiseSettings Instance
{
get
{
if (s_Instance == null)
s_Instance = WwiseSettings.LoadSettings();
return s_Instance;
}
}
public static void Reload()
{
s_Instance = WwiseSettings.LoadSettings();
}
public static string WwiseProjectAbsolutePath
{
get { return AkUtilities.GetFullPath(UnityEngine.Application.dataPath, Instance.WwiseProjectPath); }
}
public static string GetRootOutputPath()
{
if (Instance == null)
return "";
if (string.IsNullOrEmpty(Instance.RootOutputPath))
{
MigrateRootOutputPath(AkUtilities.GetFullPath(UnityEngine.Application.dataPath, Instance.WwiseProjectPath));
}
return AkUtilities.GetFullPath(UnityEngine.Application.dataPath, Instance.RootOutputPath);
}
private static string FixTemporaryProjectRelativePath(string relativePath)
{
string fixedPath = relativePath;
int assetsIndex = relativePath.IndexOf("Assets");
if (assetsIndex == -1)
{
return fixedPath;
}
int slashIndex = relativePath.IndexOf("/", assetsIndex);
if (slashIndex != -1)
{
fixedPath = relativePath.Substring(slashIndex+1);
}
return fixedPath;
}
public static void MigrateRootOutputPath(string wwiseProjectPath)
{
if (string.IsNullOrEmpty(AkWwiseEditorSettings.Instance.RootOutputPath))
{
var doc = new System.Xml.XmlDocument { PreserveWhitespace = true };
doc.Load(wwiseProjectPath);
var Navigator = doc.CreateNavigator();
// Navigate the wproj file (XML format) to where our setting should be
var pathInXml = string.Format("/WwiseDocument/ProjectInfo/Project/PropertyList/Property[@Name='{0}']", "SoundBankHeaderFilePath");
var expression = System.Xml.XPath.XPathExpression.Compile(pathInXml);
var rootOutputPath = Navigator.SelectSingleNode(expression).GetAttribute("Value", "");
rootOutputPath = AkUtilities.GetFullPath(System.IO.Path.GetDirectoryName(wwiseProjectPath), rootOutputPath);
rootOutputPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, rootOutputPath);
rootOutputPath = FixTemporaryProjectRelativePath(rootOutputPath);
AkWwiseEditorSettings.Instance.RootOutputPath = rootOutputPath;
AkWwiseEditorSettings.Instance.SaveSettings();
WwiseLogger.Log($"MIGRATION: migrating RootOutputPath to {rootOutputPath}");
}
}
public static string WwiseScriptableObjectRelativePath
{
get { return System.IO.Path.Combine(System.IO.Path.Combine("Assets", "Wwise"), "ScriptableObjects"); }
}
#region GUI
#if UNITY_2018_3_OR_NEWER
class SettingsProvider : UnityEditor.SettingsProvider
#else
class EditorWindow : UnityEditor.EditorWindow
#endif
{
class Styles
{
public static string WwisePaths = "Wwise Paths";
public static UnityEngine.GUIContent WwiseProjectPath = new UnityEngine.GUIContent("Wwise Project Path", "Location of the Wwise project associated with this game. It is recommended to put it in the Unity Project root folder, outside the Assets folder.");
public static UnityEngine.GUIContent WwiseInstallationPath = new UnityEngine.GUIContent("Wwise Application Path", "Location of the Wwise application. This is required to generate the SoundBanks in Unity.");
public static UnityEngine.GUIContent WwiseRootOutputPathContent = new UnityEngine.GUIContent("Wwise Root Output Path", "Location of the Generated SoundBanks. This should be the same as the Root Output Path in Wwise.");
public static string AssetManagement = "Asset Management";
public static UnityEngine.GUIContent StreamingAssetsPath = new UnityEngine.GUIContent("Wwise StreamingAssets Path", "Location of the SoundBanks relative to (and within) the StreamingAssets folder.");
public static UnityEngine.GUIContent CopySoundBanksAsPreBuildStep = new UnityEngine.GUIContent("Copy SoundBanks at pre-Build step", "Copies the SoundBanks in the appropriate location for building and deployment. It is recommended to leave this box checked.");
public static UnityEngine.GUIContent GenerateSoundBanksAsPreBuildStep = new UnityEngine.GUIContent("Generate SoundBanks at pre-Build step", "Generates the SoundBanks before copying them during pre-Build step. It is recommended to leave this box unchecked if SoundBanks are generated on a specific build machine.");
public static string GlobalSettings = "Global Settings";
public static UnityEngine.GUIContent CreateWwiseGlobal = new UnityEngine.GUIContent("Create WwiseGlobal GameObject", "The WwiseGlobal object is a GameObject that contains the Initializing and Terminating scripts for the Wwise Sound Engine. In the Editor workflow, it is added to every scene, so that it can be properly previewed in the Editor. In the game, only one instance is created, in the first scene, and it is persisted throughout the game. It is recommended to leave this box checked.");
public static UnityEngine.GUIContent CreateWwiseListener = new UnityEngine.GUIContent("Add Listener to Main Camera", "In order for positioning to work, the AkAudioListener script needs to be attached to the main camera in every scene. If you wish for your listener to be attached to another GameObject, uncheck this box.");
public static UnityEngine.GUIContent ObjectReferenceAutoCleanup = new UnityEngine.GUIContent("Auto-delete WwiseObjectReferences", "Components that reference Wwise objects such as Events, Banks, and Busses track these references using WwiseObjectReference assets that are created in the Wwise/ScriptableObjects folder. If this option is checked and a Wwise Object has been removed from the Wwise Project, when parsing the Wwise project structure, the corresponding asset in the Wwise/ScriptableObjects folder will be deleted.");
public static UnityEngine.GUIContent LoadSoundEngineInEditMode = new UnityEngine.GUIContent("Load Sound Engine in Edit Mode", "Load the Sound Engine in Edit Mode. Disable this setting to verify the Sound Engine is properly enabled in-game.");
public static string InEditorWarnings = "In Editor Warnings";
public static UnityEngine.GUIContent ShowSpatialAudioWarningMsg = new UnityEngine.GUIContent("Show Spatial Audio Warnings", "Warnings will be displayed on Wwise components that are not configured for Spatial Audio to function properly. It is recommended to leave this box checked.");
public static string WaapiSection = "Wwise Authoring API (WAAPI)";
public static UnityEngine.GUIContent UseWaapi = new UnityEngine.GUIContent("Connect to WAAPI");
public static UnityEngine.GUIContent WaapiIP = new UnityEngine.GUIContent("WAAPI IP Address");
public static UnityEngine.GUIContent WaapiPort = new UnityEngine.GUIContent("WAAPI Port");
public static UnityEngine.GUIContent AutosyncSelection = new UnityEngine.GUIContent("Synchronize Selection");
public static string AddressableInstallerSection = "Wwise Addressable Installer";
public static UnityEngine.GUIContent UseGitRepository = new UnityEngine.GUIContent("Install Addressable from a git repository", "If true, will expect a git repository link to import the package, if false will install from a local folder.");
public static UnityEngine.GUIContent PackageSource = new UnityEngine.GUIContent("Package Source Path", "Can be a git repository link or a local folder depending on the setting above.");
public static UnityEngine.GUIContent AddressableBankFolder = new UnityEngine.GUIContent("Addressable Root Output Path", "Where the banks will be generated. The path should be relative to the Asset Folder");
public static UnityEngine.GUIContent UseCustomBuildScript = new UnityEngine.GUIContent("Use Custom Build Script", "If toggled on, specify a path to the custom build script in the AddressableAssetBuilderPath field. Otherwise the default Wwise Build script will be automatically created during the installation.");
public static UnityEngine.GUIContent AddressableAssetBuilderPath = new UnityEngine.GUIContent("Addressable Asset Build Path", "Where the custom asset builder is located.");
public static UnityEngine.GUIContent AutomaticallyUpdateExternalSourcesPath = new UnityEngine.GUIContent("Automatically Update External Sources Path", "If toggled on, the external sources path will be updated during the installation.");
public static UnityEngine.GUIContent ExternalSourcesPath = new UnityEngine.GUIContent("External Sources Path", "The new external sources path after the addressable package installation.");
public static UnityEngine.GUIContent EnableUninstallationPrompt = new UnityEngine.GUIContent("Enable Uninstallation Prompt", "If toggled on, you are not prompted to adjust the Asynchronous Bank Loading setting during uninstallation. Instead, the 'Disable Asynchronous Bank Loading On Uninstallation' setting determines bank behavior.");
public static UnityEngine.GUIContent DisableAsynchronousBankLoading = new UnityEngine.GUIContent("Disable Asynchronous Bank Loading On Uninstallation", "If toggled on, the Asynchronous Bank Loading will be disabled on uninstallation.");
public static string TranslatorSection = "Wwise Error Message Translator";
public static UnityEngine.GUIContent XMLTranslatorTimeout = new UnityEngine.GUIContent("XML Translator Timeout", "Maximum time (ms) taken to convert numeric ID in errors through SoundBankInfo.xml. Set to 0 to disable. Change will be applied next time play mode is entered.");
public static UnityEngine.GUIContent WaapiTranslatorTimeout = new UnityEngine.GUIContent("WAAPI Translator Timeout", "Maximum time (ms) taken to convert numeric ID in errors through WAAPI. Set to 0 to disable. Change will be applied next time play mode is entered.");
public static string LoggerSection = "Wwise Logger Settings";
public static UnityEngine.GUIContent WwiseLoggerLevel = new GUIContent("WwiseLogger Level", "Log Verbosity.");
private static UnityEngine.GUIStyle version;
public static UnityEngine.GUIStyle Version
{
get
{
if (version != null)
return version;
version = new UnityEngine.GUIStyle(UnityEditor.EditorStyles.whiteLargeLabel);
if (!UnityEngine.Application.HasProLicense())
{
version.active.textColor =
version.focused.textColor =
version.hover.textColor =
version.normal.textColor = UnityEngine.Color.black;
}
return version;
}
}
private static UnityEngine.GUIStyle textField;
public static UnityEngine.GUIStyle TextField
{
get
{
if (textField == null)
textField = new UnityEngine.GUIStyle("textfield");
return textField;
}
}
}
private static bool Ellipsis()
{
return UnityEngine.GUILayout.Button("...", UnityEngine.GUILayout.Width(30));
}
#if UNITY_2018_3_OR_NEWER
private SettingsProvider(string path) : base(path, UnityEditor.SettingsScope.Project) { }
[UnityEditor.SettingsProvider]
public static UnityEditor.SettingsProvider CreateWwiseIntegrationSettingsProvider()
{
return new SettingsProvider("Project/Wwise Integration") { keywords = GetSearchKeywordsFromGUIContentProperties<Styles>() };
}
public override void OnDeactivate()
{
base.OnDeactivate();
if(Instance.LoadSoundEngineInEditMode && !AkUnitySoundEngine.IsInitialized())
{
AkUnitySoundEngineInitialization.Instance.InitializeSoundEngine();
}
else if (!Instance.LoadSoundEngineInEditMode && AkUnitySoundEngine.IsInitialized())
{
AkUnitySoundEngineInitialization.Instance.TerminateSoundEngine();
}
}
private bool IsFolderWwiseApplicationPath(string path)
{
#if UNITY_EDITOR_OSX
return path.Contains("Wwise.app");
#else
string fullPath = Path.GetFullPath(Path.Combine(path, "Authoring\\x64\\Release\\bin\\Wwise.exe"));
return File.Exists(fullPath);
#endif
}
public override void OnGUI(string searchContext)
#else
[UnityEditor.MenuItem("Edit/Wwise Settings...", false, (int)AkWwiseWindowOrder.WwiseSettings)]
public static void Init()
{
// Get existing open window or if none, make a new one:
var window = GetWindow(typeof(EditorWindow));
window.position = new UnityEngine.Rect(100, 100, 850, 360);
window.titleContent = new UnityEngine.GUIContent("Wwise Settings");
}
private void OnGUI()
#endif
{
bool changed = false;
var labelWidth = UnityEditor.EditorGUIUtility.labelWidth;
UnityEditor.EditorGUIUtility.labelWidth += 100;
var settings = Instance;
UnityEngine.GUILayout.Label(string.Format("Wwise v{0} Settings.", AkUnitySoundEngine.WwiseVersion), Styles.Version);
UnityEngine.GUILayout.Label(Styles.WwisePaths, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.WwiseProjectPath);
UnityEditor.EditorGUILayout.SelectableLabel(settings.WwiseProjectPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
var OpenInPath = System.IO.Path.GetDirectoryName(AkUtilities.GetFullPath(UnityEngine.Application.dataPath, settings.WwiseProjectPath));
var WwiseProjectPathNew = UnityEditor.EditorUtility.OpenFilePanel("Select your Wwise Project", OpenInPath, "wproj");
if (WwiseProjectPathNew.Length != 0)
{
if (WwiseProjectPathNew.EndsWith(".wproj") == false)
{
UnityEditor.EditorUtility.DisplayDialog("Error", "Please select a valid .wproj file", "Ok");
}
else
{
settings.WwiseProjectPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, WwiseProjectPathNew);
changed = true;
}
}
}
}
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.WwiseInstallationPath);
UnityEditor.EditorGUILayout.SelectableLabel(settings.WwiseInstallationPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
#if UNITY_EDITOR_OSX
var path = UnityEditor.EditorUtility.OpenFilePanel("Select your Wwise application.", "/Applications/", "");
#else
var path = UnityEditor.EditorUtility.OpenFolderPanel("Select your Wwise application.", System.Environment.GetEnvironmentVariable("ProgramFiles(x86)"), "");
#endif
if (path != "" && !IsFolderWwiseApplicationPath(path))
{
EditorUtility.DisplayDialog("Wwise Application Path could not be set", $"{path} did not contain a Wwise Authoring application.", "OK");
}
else if (path.Length != 0)
{
settings.WwiseInstallationPath = System.IO.Path.GetFullPath(path);
changed = true;
}
}
}
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.WwiseRootOutputPathContent);
UnityEditor.EditorGUILayout.SelectableLabel(settings.RootOutputPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
#if UNITY_ADDRESSABLES && AK_WWISE_ADDRESSABLES
var OpenInPath = System.IO.Path.GetDirectoryName(settings.RootOutputPath);
var path = UnityEditor.EditorUtility.OpenFolderPanel("Select your generated SoundBanks destination folder", OpenInPath, settings.RootOutputPath.Substring(OpenInPath.Length + 1));
if (path.Length != 0)
{
if (path == UnityEngine.Application.dataPath)
{
UnityEditor.EditorUtility.DisplayDialog("Error", "The SoundBanks destination folder cannot be the 'Assets' folder.", "Ok");
}
else
{
var previousPath = settings.RootOutputPath;
if (previousPath != path)
{
settings.RootOutputPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
var projectPath = AkUtilities.GetFullPath(UnityEngine.Application.dataPath, settings.WwiseProjectPath);
var relPath = AkUtilities.MakeRelativePath(System.IO.Path.GetDirectoryName(projectPath), path);
if (!path.Contains(UnityEngine.Application.dataPath))
{
AkUtilities.SetWwiseRootOutputPath(projectPath, relPath);
}
else
{
AkUtilities.SetSoundbanksDestinationFoldersInWproj(projectPath, relPath);
var fullPreviousPath = AkUtilities.GetFullPath(UnityEngine.Application.dataPath, previousPath);
var appDataPath = UnityEngine.Application.dataPath.Replace(System.IO.Path.AltDirectorySeparatorChar, System.IO.Path.DirectorySeparatorChar);
if (!string.IsNullOrEmpty(previousPath) && System.IO.Directory.Exists(fullPreviousPath))
{
UnityEditor.AssetDatabase.Refresh();
if (fullPreviousPath.Contains(appDataPath))
{
var destination = System.IO.Path.Combine("Assets", settings.RootOutputPath);
AkUtilities.MoveAssetsFromDirectory(fullPreviousPath, destination, true);
}
else
{
AkUtilities.DirectoryCopy(fullPreviousPath, path, true);
}
UnityEditor.AssetDatabase.Refresh();
}
}
changed = true;
}
}
}
#else
var FullPath = AkUtilities.GetFullPath(UnityEngine.Application.streamingAssetsPath,
settings.WwiseStreamingAssetsPath);
var OpenInPath = System.IO.Path.GetDirectoryName(FullPath);
var path = UnityEditor.EditorUtility.OpenFolderPanel("Select your Root Output Path", OpenInPath, FullPath.Substring(OpenInPath.Length + 1));
if (path.Length != 0)
{
settings.RootOutputPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
changed = true;
}
#endif
}
}
#if !(AK_WWISE_ADDRESSABLES && UNITY_ADDRESSABLES)
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.StreamingAssetsPath);
UnityEditor.EditorGUILayout.SelectableLabel(settings.WwiseStreamingAssetsPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
var FullPath = AkUtilities.GetFullPath(UnityEngine.Application.streamingAssetsPath, settings.WwiseStreamingAssetsPath);
var OpenInPath = System.IO.Path.GetDirectoryName(FullPath);
var path = UnityEditor.EditorUtility.OpenFolderPanel("Select your SoundBanks destination folder", OpenInPath, FullPath.Substring(OpenInPath.Length + 1));
if (path.Length != 0)
{
var stremingAssetsIndex = UnityEngine.Application.dataPath.Split('/').Length;
var folders = path.Split('/');
if (folders.Length - 1 < stremingAssetsIndex || !string.Equals(folders[stremingAssetsIndex], "StreamingAssets", System.StringComparison.OrdinalIgnoreCase))
{
UnityEditor.EditorUtility.DisplayDialog("Error", "The SoundBank destination folder must be located within the Unity project 'StreamingAssets' folder.", "Ok");
}
else
{
var previousPath = settings.WwiseStreamingAssetsPath;
var newPath = AkUtilities.MakeRelativePath(UnityEngine.Application.streamingAssetsPath, path);
if (previousPath != newPath)
{
settings.WwiseStreamingAssetsPath = newPath;
AkWwiseInitializationSettings.Instance.UserSettings.m_BasePath = newPath;
changed = true;
}
}
}
}
}
#endif
}
#if !(AK_WWISE_ADDRESSABLES && UNITY_ADDRESSABLES)
UnityEngine.GUILayout.Label(Styles.AssetManagement, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEditor.EditorGUI.BeginChangeCheck();
settings.CopySoundBanksAsPreBuildStep = UnityEditor.EditorGUILayout.Toggle(Styles.CopySoundBanksAsPreBuildStep, settings.CopySoundBanksAsPreBuildStep);
UnityEngine.GUI.enabled = settings.CopySoundBanksAsPreBuildStep;
settings.GenerateSoundBanksAsPreBuildStep = UnityEditor.EditorGUILayout.Toggle(Styles.GenerateSoundBanksAsPreBuildStep, settings.GenerateSoundBanksAsPreBuildStep);
UnityEngine.GUI.enabled = true;
if (UnityEditor.EditorGUI.EndChangeCheck())
changed = true;
}
#endif
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.GlobalSettings, UnityEditor.EditorStyles.boldLabel);
UnityEditor.EditorGUI.BeginChangeCheck();
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
settings.CreateWwiseGlobal = UnityEditor.EditorGUILayout.Toggle(Styles.CreateWwiseGlobal, settings.CreateWwiseGlobal);
settings.CreateWwiseListener = UnityEditor.EditorGUILayout.Toggle(Styles.CreateWwiseListener, settings.CreateWwiseListener);
settings.ObjectReferenceAutoCleanup = UnityEditor.EditorGUILayout.Toggle(Styles.ObjectReferenceAutoCleanup, settings.ObjectReferenceAutoCleanup);
settings.LoadSoundEngineInEditMode = UnityEditor.EditorGUILayout.Toggle(Styles.LoadSoundEngineInEditMode, settings.LoadSoundEngineInEditMode);
}
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.InEditorWarnings, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
settings.ShowSpatialAudioWarningMsg = UnityEditor.EditorGUILayout.Toggle(Styles.ShowSpatialAudioWarningMsg, settings.ShowSpatialAudioWarningMsg);
}
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.WaapiSection, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
bool shouldFireDelegate = false;
settings.UseWaapi = UnityEditor.EditorGUILayout.Toggle(Styles.UseWaapi, settings.UseWaapi);
UnityEngine.GUI.enabled = settings.UseWaapi;
string newWaapiIP = UnityEditor.EditorGUILayout.TextField(Styles.WaapiIP, settings.WaapiIP);
if (newWaapiIP != settings.WaapiIP)
{
settings.WaapiIP = newWaapiIP;
settings.WaapiChangePending = true;
}
string newWaapiPort = UnityEditor.EditorGUILayout.TextField(Styles.WaapiPort, settings.WaapiPort);
if (newWaapiPort != settings.WaapiPort)
{
settings.WaapiPort = newWaapiPort;
settings.WaapiChangePending = true;
}
if (settings.WaapiChangePending &&
(UnityEngine.Event.current.keyCode == UnityEngine.KeyCode.Return ||
UnityEngine.Event.current.keyCode == UnityEngine.KeyCode.KeypadEnter))
{
shouldFireDelegate = true;
settings.WaapiChangePending = false;
}
settings.AutoSyncWaapi = UnityEditor.EditorGUILayout.Toggle(Styles.AutosyncSelection, settings.AutoSyncWaapi);
UnityEngine.GUI.enabled = true;
if (shouldFireDelegate)
{
AkWwiseEditorSettings.OnWaapiSettingsChanged?.Invoke();
}
}
if (settings.WaapiChangePending)
{
UnityEditor.EditorGUILayout.HelpBox("Changes to WAAPI settings detected. Press the ENTER key to apply changes and reattempt connection.", UnityEditor.MessageType.Warning);
}
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.AddressableInstallerSection, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
settings.UseGitRepository = UnityEditor.EditorGUILayout.Toggle(Styles.UseGitRepository, settings.UseGitRepository);
if (!settings.UseGitRepository)
{
if (settings.PackageSource.StartsWith("https://"))
{
settings.PackageSource = "";
}
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.PackageSource);
UnityEditor.EditorGUILayout.SelectableLabel(settings.PackageSource, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
#if UNITY_EDITOR_OSX
var path = UnityEditor.EditorUtility.OpenFilePanel("Select your Wwise Addressable source.", "/Applications/", "");
#else
var path = UnityEditor.EditorUtility.OpenFolderPanel("Select your Wwise Addressable source.", System.Environment.GetEnvironmentVariable("ProgramFiles(x86)"), "");
#endif
if (path.Length != 0)
{
settings.PackageSource = System.IO.Path.GetFullPath(path);
changed = true;
}
}
}
}
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.AddressableBankFolder);
UnityEditor.EditorGUILayout.SelectableLabel(settings.AddressableBankFolder, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
var FullPath = AkUtilities.GetFullPath(UnityEngine.Application.dataPath,settings.RootOutputPath);
var OpenInPath = System.IO.Path.GetDirectoryName(FullPath);
var path = UnityEditor.EditorUtility.OpenFolderPanel(
"Select Addressable Bank folder", OpenInPath,
FullPath.Substring(OpenInPath.Length + 1));
if (path.Length != 0)
{
if (!path.Contains(UnityEngine.Application.dataPath))
{
UnityEditor.EditorUtility.DisplayDialog("Error",
"The SoundBanks destination folder must be located within the Unity project 'Assets' folder.",
"Ok");
}
else if (path == UnityEngine.Application.dataPath)
{
UnityEditor.EditorUtility.DisplayDialog("Error",
"The SoundBanks destination folder cannot be the 'Assets' folder.", "Ok");
}
else
{
settings.AddressableBankFolder = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
changed = true;
}
}
}
}
settings.UseCustomBuildScript = UnityEditor.EditorGUILayout.Toggle(Styles.UseCustomBuildScript, settings.UseCustomBuildScript);
if (settings.UseCustomBuildScript)
{
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.AddressableAssetBuilderPath);
UnityEditor.EditorGUILayout.SelectableLabel(settings.AddressableAssetBuilderPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
var path = UnityEditor.EditorUtility.OpenFilePanel("Select the Addressable Asset Builder Path.", UnityEngine.Application.dataPath, "asset");
if (path.Length != 0)
{
if (!path.Contains(UnityEngine.Application.dataPath))
{
UnityEditor.EditorUtility.DisplayDialog("Error", "The SoundBanks destination folder must be located within the Unity project 'Assets' folder.", "Ok");
}
else if (path == UnityEngine.Application.dataPath)
{
UnityEditor.EditorUtility.DisplayDialog("Error", "The SoundBanks destination folder cannot be the 'Assets' folder.", "Ok");
}
else
{
settings.AddressableAssetBuilderPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
changed = true;
}
}
}
}
}
settings.AutomaticallyUpdateExternalSourcesPath = UnityEditor.EditorGUILayout.Toggle(Styles.AutomaticallyUpdateExternalSourcesPath, settings.AutomaticallyUpdateExternalSourcesPath);
if (settings.AutomaticallyUpdateExternalSourcesPath)
{
using (new UnityEngine.GUILayout.HorizontalScope())
{
UnityEditor.EditorGUILayout.PrefixLabel(Styles.ExternalSourcesPath);
UnityEditor.EditorGUILayout.SelectableLabel(settings.ExternalSourcesPath, Styles.TextField, UnityEngine.GUILayout.Height(17));
if (Ellipsis())
{
var path = UnityEditor.EditorUtility.OpenFolderPanel(
"Select External Sources folder", UnityEngine.Application.dataPath,
"");
if (path.Length != 0)
{
if (!path.Contains(UnityEngine.Application.dataPath))
{
UnityEditor.EditorUtility.DisplayDialog("Error",
"The External Sources destination folder must be located within the Unity project 'Assets' folder.",
"Ok");
}
else if (path == UnityEngine.Application.dataPath)
{
UnityEditor.EditorUtility.DisplayDialog("Error",
"The External Sources destination folder cannot be the 'Assets' folder.", "Ok");
}
else
{
settings.ExternalSourcesPath = AkUtilities.MakeRelativePath(UnityEngine.Application.dataPath, path);
changed = true;
}
}
}
}
}
settings.EnableUninstallationPrompt = UnityEditor.EditorGUILayout.Toggle(Styles.EnableUninstallationPrompt, settings.EnableUninstallationPrompt);
if (!settings.EnableUninstallationPrompt)
{
settings.DisableAsynchronousBankLoading = UnityEditor.EditorGUILayout.Toggle(Styles.DisableAsynchronousBankLoading, settings.DisableAsynchronousBankLoading);
}
}
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.TranslatorSection, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
settings.XMLTranslatorTimeout = UnityEditor.EditorGUILayout.TextField(Styles.XMLTranslatorTimeout, settings.XMLTranslatorTimeout);
settings.WaapiTranslatorTimeout = UnityEditor.EditorGUILayout.TextField(Styles.WaapiTranslatorTimeout, settings.WaapiTranslatorTimeout);
}
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEngine.GUILayout.Label(Styles.LoggerSection, UnityEditor.EditorStyles.boldLabel);
using (new UnityEngine.GUILayout.VerticalScope("box"))
{
settings.LogLevel =
(LogLevel)UnityEditor.EditorGUILayout.EnumPopup(Styles.WwiseLoggerLevel, settings.LogLevel);
}
if (UnityEditor.EditorGUI.EndChangeCheck())
changed = true;
UnityEngine.GUILayout.Space(UnityEditor.EditorGUIUtility.standardVerticalSpacing);
UnityEditor.EditorGUIUtility.labelWidth = labelWidth;
if (changed)
{
settings.SaveSettings();
}
}
#endregion
}
}
#endif // UNITY_EDITOR
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: b6b04487901e2764b9e76a2f36afb1de
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 787172c9fd87bf84d95c5feee04a83f1
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 6c0b87b115b2f754d9ff0f392b4a132b
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkAcousticSurfaceArray : AkBaseArray<AkAcousticSurface>
{
public AkAcousticSurfaceArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkAcousticSurface_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkAcousticSurface_Clear(address);
}
protected override AkAcousticSurface CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkAcousticSurface(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkAcousticSurface other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkAcousticSurface_Clone(address, AkAcousticSurface.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 29823a51368682240af45110e887f9ac
@@ -0,0 +1,148 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkAuxSendArray : System.IDisposable
{
private const int MAX_COUNT = 4;
private readonly int SIZE_OF_AKAUXSENDVALUE = AkUnitySoundEnginePINVOKE.CSharp_AkAuxSendValue_GetSizeOf();
private System.IntPtr m_Buffer;
private int m_Count;
public AkAuxSendArray()
{
m_Buffer = System.Runtime.InteropServices.Marshal.AllocHGlobal(MAX_COUNT * SIZE_OF_AKAUXSENDVALUE);
m_Count = 0;
}
public AkAuxSendValue this[int index]
{
get
{
if (index >= m_Count)
throw new System.IndexOutOfRangeException("Out of range access in AkAuxSendArray");
return new AkAuxSendValue(GetObjectPtr(index), false);
}
}
public bool isFull
{
get { return m_Count >= MAX_COUNT || m_Buffer == System.IntPtr.Zero; }
}
public void Dispose()
{
if (m_Buffer != System.IntPtr.Zero)
{
System.Runtime.InteropServices.Marshal.FreeHGlobal(m_Buffer);
m_Buffer = System.IntPtr.Zero;
m_Count = 0;
}
}
~AkAuxSendArray()
{
Dispose();
}
public void Reset()
{
m_Count = 0;
}
public bool Add(UnityEngine.GameObject in_listenerGameObj, uint in_AuxBusID, float in_fValue)
{
if (isFull)
return false;
AkUnitySoundEnginePINVOKE.CSharp_AkAuxSendValue_Set(GetObjectPtr(m_Count),
AkUnitySoundEngine.GetAkGameObjectID(in_listenerGameObj), in_AuxBusID, in_fValue);
m_Count++;
return true;
}
public bool Add(uint in_AuxBusID, float in_fValue)
{
if (isFull)
return false;
AkUnitySoundEnginePINVOKE.CSharp_AkAuxSendValue_Set(GetObjectPtr(m_Count), AkUnitySoundEngine.AK_INVALID_GAME_OBJECT,
in_AuxBusID, in_fValue);
m_Count++;
return true;
}
public bool Contains(UnityEngine.GameObject in_listenerGameObj, uint in_AuxBusID)
{
if (m_Buffer == System.IntPtr.Zero)
return false;
for (var i = 0; i < m_Count; i++)
{
if (AkUnitySoundEnginePINVOKE.CSharp_AkAuxSendValue_IsSame(GetObjectPtr(i),
AkUnitySoundEngine.GetAkGameObjectID(in_listenerGameObj), in_AuxBusID))
return true;
}
return false;
}
public bool Contains(uint in_AuxBusID)
{
if (m_Buffer == System.IntPtr.Zero)
return false;
for (var i = 0; i < m_Count; i++)
{
if (AkUnitySoundEnginePINVOKE.CSharp_AkAuxSendValue_IsSame(GetObjectPtr(i), AkUnitySoundEngine.AK_INVALID_GAME_OBJECT, in_AuxBusID))
return true;
}
return false;
}
public AKRESULT SetValues(UnityEngine.GameObject gameObject)
{
return (AKRESULT) AkUnitySoundEnginePINVOKE.CSharp_SetGameObjectAuxSendValues(AkUnitySoundEngine.GetAkGameObjectID(gameObject), m_Buffer, (uint) m_Count);
}
public AKRESULT GetValues(UnityEngine.GameObject gameObject)
{
uint count = MAX_COUNT;
var res = (AKRESULT) AkUnitySoundEnginePINVOKE.CSharp_GetGameObjectAuxSendValues(AkUnitySoundEngine.GetAkGameObjectID(gameObject), m_Buffer, ref count);
m_Count = (int) count;
return res;
}
public System.IntPtr GetBuffer()
{
return m_Buffer;
}
public int Count()
{
return m_Count;
}
private System.IntPtr GetObjectPtr(int index)
{
return (System.IntPtr) (m_Buffer.ToInt64() + SIZE_OF_AKAUXSENDVALUE * index);
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 52f83b558da6d564ea9c62ef22463b93
@@ -0,0 +1,88 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public abstract class AkBaseArray<T> : System.IDisposable
{
public AkBaseArray(int capacity)
{
m_Buffer = System.Runtime.InteropServices.Marshal.AllocHGlobal(capacity * StructureSize);
if (m_Buffer != System.IntPtr.Zero)
{
Capacity = capacity;
for (var index = 0; index < capacity; ++index)
DefaultConstructAtIntPtr(GetObjectPtr(index));
}
}
public void Dispose()
{
if (m_Buffer != System.IntPtr.Zero)
{
for (var index = 0; index < Capacity; ++index)
ReleaseAllocatedMemoryFromReferenceAtIntPtr(GetObjectPtr(index));
System.Runtime.InteropServices.Marshal.FreeHGlobal(m_Buffer);
m_Buffer = System.IntPtr.Zero;
Capacity = 0;
}
}
~AkBaseArray() { Dispose(); }
public int Capacity { get; private set; }
public virtual int Count() { return Capacity; }
protected abstract int StructureSize { get; }
/// <summary>
/// This method is called for each element of the array when the array is constructed. It should be used to clear the memory associated with an element so that it will be seen as if it had been default constructed.
/// </summary>
/// <param name="address">The address of the element</param>
protected virtual void DefaultConstructAtIntPtr(System.IntPtr address) { }
/// <summary>
/// This method is called for each element of the array when the array is disposed. It should be used to delete memory allocated by elements.
/// </summary>
/// <param name="address">The address of the element</param>
protected virtual void ReleaseAllocatedMemoryFromReferenceAtIntPtr(System.IntPtr address) { }
protected abstract T CreateNewReferenceFromIntPtr(System.IntPtr address);
protected abstract void CloneIntoReferenceFromIntPtr(System.IntPtr address, T other);
public T this[int index]
{
get { return CreateNewReferenceFromIntPtr(GetObjectPtr(index)); }
set { CloneIntoReferenceFromIntPtr(GetObjectPtr(index), value); }
}
public System.IntPtr GetBuffer() { return m_Buffer; }
private System.IntPtr m_Buffer;
protected System.IntPtr GetObjectPtr(int index)
{
if (index >= Capacity)
throw new System.IndexOutOfRangeException("Out of range access in " + GetType().Name);
return (System.IntPtr)(m_Buffer.ToInt64() + StructureSize * index);
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 273008a43f0d8a24cb3297ddea8ad275
@@ -0,0 +1,140 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using System.Runtime.InteropServices;
/// <summary>
/// Represents a native array of AkChannelEmitters to be used with <see cref="AkUnitySoundEngine.SetMultiplePositions(UnityEngine.GameObject,AkChannelEmitterArray,ushort,AkMultiPositionType)"/>
/// </summary>
public class AkChannelEmitterArray : System.IDisposable
{
/// <summary>
/// C# representation of an AkChannelEmitter struct
/// </summary>
[StructLayout(LayoutKind.Sequential)]
private struct NativeAkChannelEmitter
{
/// Orientation of the emitter
/// We are making the assumption throughout that sizeof(AkVector) == sizeof(UnityEngine.Vector3)
public UnityEngine.Vector3 orientationFront;
/// Top orientation of the emitter
public UnityEngine.Vector3 orientationTop;
/// Position of the emitter. Shouldn't use AkVector64 because it is a class...
public double position_x;
public double position_y;
public double position_z;
/// Channels to which the above position applies.
public uint uInputChannels;
}
/// <summary>
/// Pointer to the start of the unmanaged memory buffer.
/// </summary>
public System.IntPtr m_Buffer;
private uint m_MaxCount;
private static readonly int NativeStructSize = Marshal.SizeOf<NativeAkChannelEmitter>();
private static readonly int OffFront = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.orientationFront));
private static readonly int OffTop = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.orientationTop));
private static readonly int OffPosX = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.position_x));
private static readonly int OffPosY = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.position_y));
private static readonly int OffPosZ = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.position_z));
private static readonly int OffMask = (int)Marshal.OffsetOf(typeof(NativeAkChannelEmitter), nameof(NativeAkChannelEmitter.uInputChannels));
public AkChannelEmitterArray(uint in_Count)
{
m_Buffer = Marshal.AllocHGlobal((int)(in_Count * NativeStructSize));
m_MaxCount = in_Count;
Count = 0;
}
/// <summary>
/// Gets the number of emitters currently added to the array.
/// </summary>
public uint Count { get; private set; }
public void Dispose()
{
System.GC.SuppressFinalize(this);
if (m_Buffer != System.IntPtr.Zero)
{
Marshal.FreeHGlobal(m_Buffer);
m_Buffer = System.IntPtr.Zero;
m_MaxCount = 0;
}
}
~AkChannelEmitterArray()
{
Dispose();
}
// <summary>
/// Resets the iterator and the count to zero, allowing the array to be reused without reallocating memory.
/// </summary>
public void Reset()
{
Count = 0;
}
/// <summary>
/// Adds a new emitter configuration to the array.
/// </summary>
/// <param name="in_Pos">The position of the emitter.</param>
/// <param name="in_Forward">The forward orientation of the emitter.</param>
/// <param name="in_Top">The top orientation of the emitter.</param>
/// <param name="in_ChannelMask">The bitmask representing the channels, see <see cref="AkChannelConfig"/></param>
/// <exception cref="System.IndexOutOfRangeException">Thrown if the array is already full.</exception>
public void Add(AkVector64 in_Pos, UnityEngine.Vector3 in_Forward, UnityEngine.Vector3 in_Top,
uint in_ChannelMask)
{
if (Count >= m_MaxCount)
throw new System.IndexOutOfRangeException("Out of range access in AkChannelEmitterArray");
// OPTIMIZATION. Since we don't use unsafe, and we want to avoid boxing via Marshal.StructureToPtr, the only solution is to write members individually.
System.IntPtr pItem = m_Buffer + (int)(Count * NativeStructSize);
// Orientation Front
Marshal.WriteInt32(pItem, OffFront + 0, System.BitConverter.SingleToInt32Bits(in_Forward.x));
Marshal.WriteInt32(pItem, OffFront + 4, System.BitConverter.SingleToInt32Bits(in_Forward.y));
Marshal.WriteInt32(pItem, OffFront + 8, System.BitConverter.SingleToInt32Bits(in_Forward.z));
// Orientation Top
Marshal.WriteInt32(pItem, OffTop + 0, System.BitConverter.SingleToInt32Bits(in_Top.x));
Marshal.WriteInt32(pItem, OffTop + 4, System.BitConverter.SingleToInt32Bits(in_Top.y));
Marshal.WriteInt32(pItem, OffTop + 8, System.BitConverter.SingleToInt32Bits(in_Top.z));
// Position - Direct 64-bit writes from the struct fields
Marshal.WriteInt64(pItem, OffPosX, System.BitConverter.DoubleToInt64Bits(in_Pos.X));
Marshal.WriteInt64(pItem, OffPosY, System.BitConverter.DoubleToInt64Bits(in_Pos.Y));
Marshal.WriteInt64(pItem, OffPosZ, System.BitConverter.DoubleToInt64Bits(in_Pos.Z));
// Mask
Marshal.WriteInt32(pItem, OffMask, (int)in_ChannelMask);
Count++;
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: e896b051a9adc7b45a029bcb8ccae585
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkDeviceDescriptionArray : AkBaseArray<AkDeviceDescription>
{
public AkDeviceDescriptionArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkDeviceDescription_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkDeviceDescription_Clear(address);
}
protected override AkDeviceDescription CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkDeviceDescription(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkDeviceDescription other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkDeviceDescription_Clone(address, AkDeviceDescription.getCPtr(other));
}
}
#endif
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 12fd93885c4219c43835a911a97ee616
@@ -0,0 +1,40 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkDiffractionPathInfoArray : AkBaseArray<AkDiffractionPathInfo>
{
public AkDiffractionPathInfoArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkDiffractionPathInfo_GetSizeOf(); }
}
protected override AkDiffractionPathInfo CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkDiffractionPathInfo(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkDiffractionPathInfo other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkDiffractionPathInfo_Clone(address, AkDiffractionPathInfo.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 8b1b6ad2b17678940949137ac5e6d09d
@@ -0,0 +1,50 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkExternalSourceInfoArray : AkBaseArray<AkExternalSourceInfo>
{
public AkExternalSourceInfoArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkExternalSourceInfo_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkExternalSourceInfo_Clear(address);
}
protected override void ReleaseAllocatedMemoryFromReferenceAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkExternalSourceInfo_szFile_set(address, null);
}
protected override AkExternalSourceInfo CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkExternalSourceInfo(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkExternalSourceInfo other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkExternalSourceInfo_Clone(address, AkExternalSourceInfo.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 90e793f3f25e5ec4aa4a88fa08a5e1a3
@@ -0,0 +1,88 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkMIDIPostArray
{
private readonly int m_Count;
private readonly int SIZE_OF = AkUnitySoundEnginePINVOKE.CSharp_AkMIDIPost_GetSizeOf();
private System.IntPtr m_Buffer = System.IntPtr.Zero;
public AkMIDIPostArray(int size)
{
m_Count = size;
m_Buffer = System.Runtime.InteropServices.Marshal.AllocHGlobal(m_Count * SIZE_OF);
}
public AkMIDIPost this[int index]
{
get
{
if (index >= m_Count)
throw new System.IndexOutOfRangeException("Out of range access in AkMIDIPostArray");
return new AkMIDIPost(GetObjectPtr(index), false);
}
set
{
if (index >= m_Count)
throw new System.IndexOutOfRangeException("Out of range access in AkMIDIPostArray");
AkUnitySoundEnginePINVOKE.CSharp_AkMIDIPost_Clone(GetObjectPtr(index), AkMIDIPost.getCPtr(value));
}
}
~AkMIDIPostArray()
{
System.Runtime.InteropServices.Marshal.FreeHGlobal(m_Buffer);
m_Buffer = System.IntPtr.Zero;
}
public void PostOnEvent(uint in_eventID, UnityEngine.GameObject gameObject)
{
var gameObjectID = AkUnitySoundEngine.GetAkGameObjectID(gameObject);
AkUnitySoundEngine.PreGameObjectAPICall(gameObject, gameObjectID);
AkUnitySoundEnginePINVOKE.CSharp_PostMIDIOnEvent__SWIG_3(in_eventID, gameObjectID, m_Buffer, (ushort) m_Count);
}
public void PostOnEvent(uint in_eventID, UnityEngine.GameObject gameObject, int count)
{
if (count >= m_Count)
throw new System.IndexOutOfRangeException("Out of range access in AkMIDIPostArray");
var gameObjectID = AkUnitySoundEngine.GetAkGameObjectID(gameObject);
AkUnitySoundEngine.PreGameObjectAPICall(gameObject, gameObjectID);
AkUnitySoundEnginePINVOKE.CSharp_PostMIDIOnEvent__SWIG_3(in_eventID, gameObjectID, m_Buffer, (ushort) count);
}
public System.IntPtr GetBuffer()
{
return m_Buffer;
}
public int Count()
{
return m_Count;
}
private System.IntPtr GetObjectPtr(int index)
{
return (System.IntPtr) (m_Buffer.ToInt64() + SIZE_OF * index);
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 03991e0847903f84389f0a3ac4b141b1
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkObjectInfoArray : AkBaseArray<AkObjectInfo>
{
public AkObjectInfoArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkObjectInfo_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkObjectInfo_Clear(address);
}
protected override AkObjectInfo CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkObjectInfo(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkObjectInfo other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkObjectInfo_Clone(address, AkObjectInfo.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 3801e24873004414fb73fed9894a37ff
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkObstructionOcclusionValuesArray : AkBaseArray<AkObstructionOcclusionValues>
{
public AkObstructionOcclusionValuesArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkObstructionOcclusionValues_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkObstructionOcclusionValues_Clear(address);
}
protected override AkObstructionOcclusionValues CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkObstructionOcclusionValues(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkObstructionOcclusionValues other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkObstructionOcclusionValues_Clone(address, AkObstructionOcclusionValues.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 72a2119a96a89a148922b20c464225b4
@@ -0,0 +1,94 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkPositionArray : System.IDisposable
{
public System.IntPtr m_Buffer;
private System.IntPtr m_Current;
private uint m_MaxCount;
public AkPositionArray(uint in_Count)
{
m_Buffer = System.Runtime.InteropServices.Marshal.AllocHGlobal((int) in_Count * (sizeof(float) * 6 + sizeof(double) * 3));
m_Current = m_Buffer;
m_MaxCount = in_Count;
Count = 0;
}
public uint Count { get; private set; }
public void Dispose()
{
if (m_Buffer != System.IntPtr.Zero)
{
System.Runtime.InteropServices.Marshal.FreeHGlobal(m_Buffer);
m_Buffer = System.IntPtr.Zero;
m_MaxCount = 0;
}
}
~AkPositionArray()
{
Dispose();
}
public void Reset()
{
m_Current = m_Buffer;
Count = 0;
}
public void Add(AkVector64 in_Pos, UnityEngine.Vector3 in_Forward, UnityEngine.Vector3 in_Top)
{
if (Count >= m_MaxCount)
throw new System.IndexOutOfRangeException("Out of range access in AkPositionArray");
//Marshal doesn't do floats. So copy the bytes themselves. Grrr.
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Forward.x), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Forward.y), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Forward.z), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Top.x), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Top.y), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt32(m_Current,
System.BitConverter.ToInt32(System.BitConverter.GetBytes(in_Top.z), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(float));
System.Runtime.InteropServices.Marshal.WriteInt64(m_Current,
System.BitConverter.ToInt64(System.BitConverter.GetBytes(in_Pos.X), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(double));
System.Runtime.InteropServices.Marshal.WriteInt64(m_Current,
System.BitConverter.ToInt64(System.BitConverter.GetBytes(in_Pos.Y), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(double));
System.Runtime.InteropServices.Marshal.WriteInt64(m_Current,
System.BitConverter.ToInt64(System.BitConverter.GetBytes(in_Pos.Z), 0));
m_Current = (System.IntPtr) (m_Current.ToInt64() + sizeof(double));
Count++;
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: d2dac2bb7af1f3c4e99c5ca1a9d13c79
@@ -0,0 +1,40 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkReflectionPathInfoArray : AkBaseArray<AkReflectionPathInfo>
{
public AkReflectionPathInfoArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkReflectionPathInfo_GetSizeOf(); }
}
protected override AkReflectionPathInfo CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkReflectionPathInfo(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkReflectionPathInfo other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkReflectionPathInfo_Clone(address, AkReflectionPathInfo.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 2374fa8a43260374da73abedbead7f98
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkSourceSettingsArray : AkBaseArray<AkSourceSettings>
{
public AkSourceSettingsArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkSourceSettings_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkSourceSettings_Clear(address);
}
protected override AkSourceSettings CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkSourceSettings(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkSourceSettings other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkSourceSettings_Clone(address, AkSourceSettings.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 21b3d946f71e1874f8dea6257b64f9ea
@@ -0,0 +1,45 @@
#if !(UNITY_QNX) // Disable under unsupported platforms.
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public class AkTriangleArray : AkBaseArray<AkTriangle>
{
public AkTriangleArray(int count) : base(count)
{
}
protected override int StructureSize
{
get { return AkUnitySoundEnginePINVOKE.CSharp_AkTriangle_GetSizeOf(); }
}
protected override void DefaultConstructAtIntPtr(System.IntPtr address)
{
AkUnitySoundEnginePINVOKE.CSharp_AkTriangle_Clear(address);
}
protected override AkTriangle CreateNewReferenceFromIntPtr(System.IntPtr address)
{
return new AkTriangle(address, false);
}
protected override void CloneIntoReferenceFromIntPtr(System.IntPtr address, AkTriangle other)
{
AkUnitySoundEnginePINVOKE.CSharp_AkTriangle_Clone(address, AkTriangle.getCPtr(other));
}
}
#endif // #if !(UNITY_QNX) // Disable under unsupported platforms.
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 959e9847839cf2c44917926e95e6b0cc
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 42c7bf98edbc1b94aa8b870abbfd95c3
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,55 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if UNITY_EDITOR_OSX || (UNITY_STANDALONE_OSX && !UNITY_EDITOR)
public partial class AkBasePathGetter
{
static string DefaultPlatformName = "Mac";
public static void AdjustFullBasePathForPlatform(ref string fullBasePath)
{
fullBasePath = System.IO.Path.Combine(UnityEngine.Application.streamingAssetsPath, fullBasePath);
}
public static string GetPersistentDataPath()
{
return UnityEngine.Application.persistentDataPath;
}
public static bool InitBankExists(string tempSoundBankBasePath)
{
return System.IO.File.Exists(System.IO.Path.Combine(tempSoundBankBasePath, "Init.bnk"));
}
public static string GetDecodedBankPath()
{
return System.IO.Path.Combine(Instance.SoundBankBasePath, DecodedBankFolder);
}
}
#endif
#if UNITY_EDITOR
[UnityEditor.InitializeOnLoad]
public partial class AkMacBasePathGetter
{
static AkMacBasePathGetter()
{
AkBasePathGetter.AddTargetPlatform(UnityEditor.BuildTarget.StandaloneOSX, "Mac");
}
}
#endif
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 8af240862ecc27c4eb7f0417d3b6e373
@@ -0,0 +1,92 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if (UNITY_STANDALONE_OSX && !UNITY_EDITOR) || UNITY_EDITOR_OSX
public partial class AkCommonUserSettings
{
partial void SetSampleRate(AkPlatformInitSettings settings)
{
settings.uSampleRate = m_SampleRate;
}
protected partial string GetPluginPath()
{
#if UNITY_EDITOR_OSX
return System.IO.Path.GetFullPath(AkUtilities.GetPathInPackage("Runtime/Plugins/Mac/DSP"));
#else
return System.IO.Path.Combine(UnityEngine.Application.dataPath, "Plugins" + System.IO.Path.DirectorySeparatorChar);
#endif
}
}
#endif
public class AkMacSettings : AkWwiseInitializationSettings.PlatformSettings
{
#if UNITY_EDITOR
[UnityEditor.InitializeOnLoadMethod]
private static void AutomaticPlatformRegistration()
{
if (UnityEditor.AssetDatabase.IsAssetImportWorkerProcess())
{
return;
}
RegisterPlatformSettingsClass<AkMacSettings>("Mac");
}
#endif // UNITY_EDITOR
[System.Serializable]
public class PlatformAdvancedSettings : AkCommonAdvancedSettings
{
[UnityEngine.Tooltip("Number of Apple Spatial Audio point sources to allocate for 3D audio use (each point source is a system audio object).")]
public uint NumSpatialAudioPointSources = 128;
[UnityEngine.Tooltip("Print debug information related to audio device initialization in the system log.")]
public bool VerboseSystemOutput = false;
public override void CopyTo(AkPlatformInitSettings settings)
{
#if (UNITY_STANDALONE_OSX && !UNITY_EDITOR) || UNITY_EDITOR_OSX
settings.uNumSpatialAudioPointSources = NumSpatialAudioPointSources;
settings.bVerboseSystemOutput = VerboseSystemOutput;
#endif
}
}
protected override AkCommonUserSettings GetUserSettings()
{
return UserSettings;
}
protected override AkCommonAdvancedSettings GetAdvancedSettings()
{
return AdvancedSettings;
}
protected override AkCommonCommSettings GetCommsSettings()
{
return CommsSettings;
}
[UnityEngine.HideInInspector]
public AkCommonUserSettings UserSettings;
[UnityEngine.HideInInspector]
public PlatformAdvancedSettings AdvancedSettings;
[UnityEngine.HideInInspector]
public AkCommonCommSettings CommsSettings;
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: d7f19a53744848c4d8d5b31cd1ca1c27
@@ -0,0 +1,36 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public partial class AkUnitySoundEngine
{
#if UNITY_EDITOR_OSX || (UNITY_STANDALONE_OSX && !UNITY_EDITOR)
/// <summary>
/// Converts "AkOSChar*" C-strings to C# strings.
/// </summary>
/// <param name="ptr">"AkOSChar*" memory pointer passed to C# as an IntPtr.</param>
/// <returns>Converted string.</returns>
public static string StringFromIntPtrOSString(System.IntPtr ptr)
{
return StringFromIntPtrString(ptr);
}
public static bool PlatformSupportsDecodeBank()
{
return true;
}
#endif
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 64321e2f6e664f2478c1ec074e7d3426
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 270d55b21246e824eaeb28b1fdbb9e01
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,24 @@
{
"name": "Ak.Wwise.Api.WAAPI",
"rootNamespace": "",
"references": [
"AK.Wwise.Unity.API.WwiseTypes",
"AK.Wwise.Unity.API",
"AK.Wwise.Unity.Utilities",
"AK.Wwise.Unity.Logging"
],
"includePlatforms": [],
"excludePlatforms": [
"Lumin",
"Stadia"
],
"allowUnsafeCode": false,
"overrideReferences": false,
"precompiledReferences": [],
"autoReferenced": true,
"defineConstraints": [
"!UNITY_SERVER"
],
"versionDefines": [],
"noEngineReferences": false
}
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: eb0dcd37a0eb0aa4bbeb9c8d634123b2
AssemblyDefinitionImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,136 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
/// <summary>
/// The Waapi Client provides a core interface to Waapi using strings only. You will need to provide your own JSON serialization.
/// </summary>
internal class AkWaapiClient
{
public Wamp wamp;
public event Wamp.DisconnectedHandler Disconnected;
/// <summary>Connect to a running instance of Wwise Authoring.</summary>
/// <param name="uri">URI to connect. Usually the WebSocket protocol (ws:) followed by the hostname and port, followed by waapi.</param>
/// <example>Connect("ws://localhost:8080/waapi")</example>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
public async System.Threading.Tasks.Task Connect(
string uri = "ws://localhost:8080/waapi",
int timeout = System.Int32.MaxValue)
{
if (wamp == null)
wamp = new Wamp();
wamp.Disconnected += Wamp_Disconnected;
await wamp.Connect(uri, timeout);
}
public void CancelConnectionAttempt()
{
wamp.CancelCurrentConnection();
}
private void Wamp_Disconnected()
{
if (Disconnected != null)
{
Disconnected();
}
}
/// <summary>Close the connection.</summary>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
public async System.Threading.Tasks.Task Close(
int timeout = System.Int32.MaxValue)
{
if (wamp == null)
throw new Wamp.WampNotConnectedException("WAMP connection is not established");
await wamp.Close(timeout);
wamp.Disconnected -= Wamp_Disconnected;
wamp = null;
}
/// <summary>
/// Return true if the client is connected and ready for operations.
/// </summary>
public bool IsConnected()
{
if (wamp == null)
return false;
return wamp.IsConnected();
}
/// <summary>Call a WAAPI remote procedure. Refer to WAAPI reference documentation for a list of URIs and their arguments and options.</summary>
/// <param name="uri">The URI of the remote procedure.</param>
/// <param name="args">The arguments of the remote procedure.</param>
/// <param name="options">The options the remote procedure.</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
/// <returns>A JSON string with the result of the Remote Procedure Call.</returns>
public async System.Threading.Tasks.Task<string> Call(
string uri,
string args = "{}",
string options = "{}",
int timeout = System.Int32.MaxValue)
{
if (wamp == null)
throw new Wamp.WampNotConnectedException("WAMP connection is not established");
if (args == null)
args = "{}";
if (options == null)
options = "{}";
return await wamp.Call(uri, args, options, timeout);
}
/// <summary>Subscribe to WAAPI topic. Refer to WAAPI reference documentation for a list of topics and their options.</summary>
/// <param name="topic">The topic to which subscribe.</param>
/// <param name="options">The options the subscription.</param>
/// <param name="publishHandler/// ">The delegate function to call when the topic is published.</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
/// <returns>Subscription id, that you can use to unsubscribe.</returns>
public async System.Threading.Tasks.Task<uint> Subscribe(
string topic,
string options,
Wamp.PublishHandler publishHandler,
int timeout = System.Int32.MaxValue)
{
if (wamp == null)
throw new Wamp.WampNotConnectedException("WAMP connection is not established");
if (options == null)
options = "{}";
return await wamp.Subscribe(topic, options, publishHandler, timeout);
}
/// <summary>Unsubscribe from a subscription.</summary>
/// <param name="subscriptionId">The subscription id received from the initial subscription.</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
public async System.Threading.Tasks.Task Unsubscribe(
uint subscriptionId,
int timeout = System.Int32.MaxValue)
{
if (wamp == null)
throw new Wamp.WampNotConnectedException("WAMP connection is not established");
await wamp.Unsubscribe(subscriptionId, timeout);
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 4c99a7e15178a14418317de1b1951076
@@ -0,0 +1,590 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using System.Collections.Generic;
using System.Collections.ObjectModel;
/// <summary>
/// Base class for Json serializable objects.
/// Implements implicit cast to string using UnityEngine.JsonUtility.ToJson.
/// </summary>
[System.Serializable]
public class JsonSerializable
{
public static implicit operator string(JsonSerializable o) => UnityEngine.JsonUtility.ToJson(o);
}
/// <summary>
/// Abstract base class for WAAPI command arguments.
/// </summary>
[System.Serializable]
public abstract class Args : JsonSerializable
{
}
/// <summary>
/// WAAPI arguments containing a WAQL string.
/// </summary>
[System.Serializable]
public class WaqlArgs : Args
{
public string waql;
public WaqlArgs(string query)
{
waql = query;
}
}
/// <summary>
/// WAAPI arguments containing an object identfier.
/// </summary>
[System.Serializable]
public class ArgsObject : Args
{
public string @object;
public ArgsObject(string objectId)
{
@object = objectId;
}
}
/// <summary>
/// WAAPI arguments containing an object identfier and new value used when renaming an object.
/// </summary>
[System.Serializable]
public class ArgsRename : Args
{
public string @object;
public string value;
public ArgsRename(string objectId, string value)
{
@object = objectId;
this.value = value;
}
}
/// <summary>
/// WAAPI arguments containing an object identfier and name used when deleting an object.
/// </summary>
[System.Serializable]
public class ArgsDisplayName : Args
{
public string displayName;
public ArgsDisplayName(string displayName)
{
this.displayName = displayName;
}
}
/// <summary>
/// WAAPI arguments containing an object identfier and command field.
/// Used by AkWaapiUtilities.SelectObjectInAuthoringAsync().
/// </summary>
[System.Serializable]
public class ArgsCommand : Args
{
public string[] @objects;
public string command;
public ArgsCommand(string c, string[] objectIds)
{
command = c;
objects = objectIds;
}
}
/// <summary>
/// WAAPI arguments containing an Event identfier and transport ID.
/// Used to toggle Event playback.
/// </summary>
[System.Serializable]
public class ArgsPlay : Args
{
public string action;
public int transport;
public ArgsPlay(string a, int t) { action = a; transport = t; }
}
/// <summary>
/// WAAPI arguments containing a transport ID.
/// Used to specify transports in transport-specific commands.
/// </summary>
[System.Serializable]
public class ArgsTransport : Args
{
public int transport;
public ArgsTransport(int t) { transport = t; }
}
/// <summary>
/// Abstract base class for WAAPI command options.
/// </summary>
[System.Serializable]
public class Options : JsonSerializable
{
}
/// <summary>
/// WAAPI options to specify the names of fields to return in a WAAPI request returning WwiseObjects.
/// </summary>
[System.Serializable]
public class ReturnOptions : Options
{
public string[] @return;
public ReturnOptions(string [] infokeys)
{
@return = infokeys;
}
}
/// <summary>
/// WAAPI options used to specify the transport ID when subscribing.
/// </summary>
[System.Serializable]
public class TransportOptions : Options
{
public int transport;
public TransportOptions(int id)
{
transport = id;
}
}
/// <summary>
/// Used to deserialize the response from an ak.wwise.core.transport.create command.
/// Contains the transport ID.
/// </summary>
[System.Serializable]
public class ReturnTransport : JsonSerializable
{
public int transport;
}
/// <summary>
/// Used to deserialize transport-state information receieved from the transport.stateChanged topic.
/// </summary>
[System.Serializable]
public class TransportState : JsonSerializable
{
public string gameObject;
public string state;
public string @object;
public int transport;
}
/// <summary>
/// Used to deserialize WAAPI error messages.
/// </summary>
[System.Serializable]
public class ErrorMessage : JsonSerializable
{
public string message;
public ErrorDetails details;
}
/// <summary>
/// Used to deserialize details in WAAPI error messages.
/// </summary>
[System.Serializable]
public class ErrorDetails : JsonSerializable
{
public string [] reasons;
public string procedureUri;
}
/// <summary>
/// Class used to deserialize a WAAPI response containing Wwise objects.
/// </summary>
[System.Serializable]
public class ReturnWwiseObjects : JsonSerializable
{
public List<WwiseObjectInfoJsonObject> @return;
}
[System.Serializable]
public class PingWwiseObject : JsonSerializable
{
public bool isAvailable;
}
/// <summary>
/// Generic class to deserialize a WAAPI response containing Wwise objects with custom return options.
/// </summary>
[System.Serializable]
public class ReturnWwiseObjects<T> : JsonSerializable
{
public List<T> @return;
}
/// <summary>
/// Class used to deserialize selected Wwise objects published on the ak.wwise.ui.selectionChanged topic.
/// </summary>
[System.Serializable]
public class SelectedWwiseObjects : JsonSerializable
{
public List<WwiseObjectInfoJsonObject> objects;
}
/// <summary>
/// Used to deserialize information published on the ak.wwise.core.@object.nameChanged topic.
/// </summary>
[System.Serializable]
public class WwiseRenameInfo : JsonSerializable
{
public WwiseObjectInfoJsonObject @object;
public string newName;
public string oldName;
public WwiseObjectInfo objectInfo;
public void ParseInfo()
{
objectInfo = @object;
}
}
/// <summary>
/// Used to deserialize information published on the ak.wwise.core.@object.childAdded and ak.wwise.core.@object.childRemoved topics.
/// </summary>
[System.Serializable]
public class WwiseChildModifiedInfo : JsonSerializable
{
public WwiseObjectInfoJsonObject parent;
public WwiseObjectInfoJsonObject child;
public WwiseObjectInfo parentInfo;
public WwiseObjectInfo childInfo;
public void ParseInfo()
{
parentInfo = parent;
childInfo = child;
}
}
/// <summary>
/// Used to deserialize information from a request for a Wwise object.
/// Implements an implicit cast to WwiseObjectInfo.
/// </summary>
[System.Serializable]
public class WwiseObjectInfoJsonObject : System.IComparable
{
public string id;
public WwiseObjectInfoParent parent;
public string name;
public string type;
public int childrenCount;
public string path;
public string filePath;
public string workunitType;
public string soundbankBnkFilePath;
public static implicit operator WwiseObjectInfo(WwiseObjectInfoJsonObject info)
{
return ToObjectInfo(info);
}
public static WwiseObjectInfo ToObjectInfo(WwiseObjectInfoJsonObject info)
{
var type = info.type == null ? "" : info.type;
var wutype = info.workunitType == null ? "" : info.workunitType;
var objectType = WaapiHelper.GetWwiseObjectTypeFromString(type.ToLower(), wutype.ToLower());
var parentID = info.parent.id == null ? System.Guid.Empty : System.Guid.Parse(info.parent.id);
var objectGuid = info.id == null ? System.Guid.Empty : System.Guid.Parse(info.id);
return new WwiseObjectInfo
{
objectGUID = objectGuid,
name = info.name,
type = objectType,
childrenCount = info.childrenCount,
path = info.path,
workUnitType = wutype,
parentID = parentID,
filePath = info.filePath,
soundbankBnkFilePath = info.soundbankBnkFilePath
};
}
public int CompareTo(object obj)
{
if (obj is WwiseObjectInfoJsonObject)
{
string objPath = (obj as WwiseObjectInfoJsonObject).path;
if (objPath.Contains(path))
{
return -1;
}
else if (path.Contains(objPath))
{
return 1;
}
return path.Length < objPath.Length ? -1 : 1;
}
return 0;
}
}
/// <summary>
/// Contains the GUID of the returned object's parent.
/// </summary>
[System.Serializable]
public class WwiseObjectInfoParent
{
public string id;
}
/// <summary>
/// Class containing the information returned by a WAAPI request for an object.
/// </summary>
[System.Serializable]
public struct WwiseObjectInfo
{
public System.Guid objectGUID;
public System.Guid parentID;
public string name;
public WwiseObjectType type;
public int childrenCount;
public string path;
public string workUnitType;
public string filePath;
public string soundbankBnkFilePath;
}
[System.Serializable]
public struct WwiseStructureChangeParentChange
{
public WwiseObjectInfoJsonObject newParent;
public WwiseObjectInfoJsonObject oldParent;
}
[System.Serializable]
public struct WwiseStructureChangeNameChange
{
public string newName;
public string oldName;
}
[System.Serializable]
public struct WwiseStructureChangeChange
{
public string type;
public WwiseStructureChangeNameChange nameChange;
public WwiseStructureChangeParentChange parentChange;
}
[System.Serializable]
public struct WwiseStructureChanged
{
public WwiseObjectInfoJsonObject @object;
public List<WwiseStructureChangeChange> changes;
void ParseInfo()
{
}
}
[System.Serializable]
public struct WwiseStructureObjects
{
public List<WwiseStructureChanged>objects;
void ParseInfo()
{
}
}
/// <summary>
/// Contains a helper function GetWwiseObjectTypeFromString.
/// </summary>
public static class WaapiHelper
{
public static WwiseObjectType GetWwiseObjectTypeFromString(string typeString, string workUnitType)
{
if (!WaapiKeywords.typeStringDict.ContainsKey(typeString))
return WwiseObjectType.None;
if (workUnitType != string.Empty)
{
if (workUnitType == "folder")
{
return WaapiKeywords.typeStringDict["physicalfolder"];
}
return WaapiKeywords.typeStringDict[typeString];
}
return WaapiKeywords.typeStringDict[typeString];
}
}
/// <summary>
/// Contains fields for specific WAAPI keywords.
/// </summary>
public class WaapiKeywords
{
public const string ACTION = "action";
public const string ANCESTORS = "ancestors";
public const string AT = "@";
public const string AUX_BUSSES = "auxBusses";
public const string BACK_SLASH = "\\";
public const string BANK_DATA = "bankData";
public const string BANK_INFO = "bankInfo";
public const string CHILD = "child";
public const string CHILDREN = "children";
public const string CHILDREN_COUNT = "childrenCount";
public const string CLASSID = "classId";
public const string COMMAND = "command";
public const string DATA = "data";
public const string DELETE_ITEMS = "Delete Items";
public const string DESCENDANTS = "descendants";
public const string DISPLAY_NAME = "displayName";
public const string DRAG_DROP_ITEMS = "Drag Drop Items";
public const string EVENT = "event";
public const string EVENTS = "events";
public const string FILEPATH = "filePath";
public const string FIND_IN_PROJECT_EXPLORER = "FindInProjectExplorerSyncGroup1";
public const string FOLDER = "Folder";
public const string FROM = "from";
public const string ID = "id";
public const string INCLUSIONS = "inclusions";
public const string INFO_FILE = "infoFile";
public const string IS_CONNECTED = "isConnected";
public const string LANGUAGE = "language";
public const string LANGUAGES = "languages";
public const string MAX = "max";
public const string MAX_RADIUS_ATTENUATION = "audioSource:maxRadiusAttenuation";
public const string MESSSAGE = "message";
public const string MIN = "min";
public const string NAME = "name";
public const string NAMECONTAINS = "name:contains";
public const string NEW = "new";
public const string NEW_NAME = "newName";
public const string NOTES = "notes";
public const string OBJECT = "object";
public const string OBJECTS = "objects";
public const string OF_TYPE = "ofType";
public const string OLD_NAME = "oldName";
public const string PARENT = "parent";
public const string PATH = "path";
public const string PHYSICAL_FOLDER = "PhysicalFolder";
public const string PLATFORM = "platform";
public const string PLATFORMS = "platforms";
public const string PLAY = "play";
public const string PLAYING = "playing";
public const string PLAYSTOP = "playStop";
public const string PLUGININFO_OPTIONS = "pluginInfo";
public const string PLUGININFO_RESPONSE = "PluginInfo";
public const string PROJECT = "Project";
public const string PROPERTY = "property";
public const string RADIUS = "radius";
public const string RANGE = "range";
public const string REBUILD = "rebuild";
public const string REBUILDINITBANK = "rebuildInitBank";
public const string REDO = "Redo";
public const string RESTRICTION = "restriction";
public const string RETURN = "return";
public const string SEARCH = "search";
public const string SELECT = "select";
public const string SIZE = "size";
public const string SKIP_LANGUAGES = "skipLanguages";
public const string SOUNDBANK = "soundbank";
public const string SOUNDBANKS = "soundbanks";
public const string STATE = "state";
public const string STOP = "stop";
public const string STOPPED = "stopped";
public const string STRUCTURE = "structure";
public const string TRANSFORM = "transform";
public const string TRANSPORT = "transport";
public const string TYPE = "type";
public const string UI = "ui";
public const string UNDO = "Undo";
public const string VALUE = "value";
public const string VOLUME = "Volume";
public const string WHERE = "where";
public const string WORKUNIT_TYPE = "workunit:type";
public const string WRITETODISK = "writeToDisk";
public const string OPEN_SOUNDBANK_FOLDER = "OpenContainingFolderSoundbank";
public const string OPEN_WORKUNIT_FOLDER = "OpenContainingFolderWorkUnit";
public const string OPEN_WAV_FOLDER = "OpenContainingFolderWAV";
/// <summary>
/// Maps WwiseObjectType to strings.
/// </summary>
public static ReadOnlyDictionary<WwiseObjectType, string> WwiseObjectTypeStrings = new ReadOnlyDictionary<WwiseObjectType, string>(new Dictionary<WwiseObjectType, string>()
{
{WwiseObjectType.None, "None"},
{WwiseObjectType.AuxBus, "AuxiliaryBus"},
{WwiseObjectType.Bus, "Bus"},
{WwiseObjectType.Event, "Event"},
{WwiseObjectType.Folder, "Folder"},
{WwiseObjectType.PhysicalFolder, "PhysicalFolder"},
{WwiseObjectType.Project, "Project"},
{WwiseObjectType.Soundbank, "SoundBank"},
{WwiseObjectType.State, "State"},
{WwiseObjectType.StateGroup, "StateGroup"},
{WwiseObjectType.Switch, "Switch"},
{WwiseObjectType.SwitchGroup, "SwitchGroup"},
{WwiseObjectType.WorkUnit, "WorkUnit"},
{WwiseObjectType.GameParameter, "Game Parametr"},
{WwiseObjectType.Trigger, "Trigger"},
{WwiseObjectType.AcousticTexture, "AcousticTexture"}
});
/// <summary>
/// Maps root folder names to displayed strings.
/// </summary>
public static ReadOnlyDictionary<string, string> FolderDisplaynames = new ReadOnlyDictionary<string, string>(new Dictionary<string, string>()
{
{"Busses", "Auxiliary Busses" },
{ "Events", "Events"},
{ "States", "States"},
{ "SoundBanks", "SoundBanks"},
{ "Switches", "Switches"},
{ "Triggers", "Triggers"},
{ "Virtual Acoustics", "Virtual Acoustics"},
});
/// <summary>
/// Maps strings to WwiseObjectType.
/// </summary>
public static ReadOnlyDictionary<string, WwiseObjectType> typeStringDict = new ReadOnlyDictionary<string, WwiseObjectType>(new Dictionary<string, WwiseObjectType>()
{
["auxbus"] = WwiseObjectType.AuxBus,
["bus"] = WwiseObjectType.Bus,
["event"] = WwiseObjectType.Event,
["folder"] = WwiseObjectType.Folder,
["physicalfolder"] = WwiseObjectType.PhysicalFolder,
["soundbank"] = WwiseObjectType.Soundbank,
["project"] = WwiseObjectType.Project,
["state"] = WwiseObjectType.State,
["stategroup"] = WwiseObjectType.StateGroup,
["switch"] = WwiseObjectType.Switch,
["switchgroup"] = WwiseObjectType.SwitchGroup,
["workunit"] = WwiseObjectType.WorkUnit,
["gameparameter"] = WwiseObjectType.GameParameter,
["trigger"] = WwiseObjectType.Trigger,
["acoustictexture"] = WwiseObjectType.AcousticTexture
});
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: b1824479e8e1c3f46b22c405d767ebec
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 61263ded45bd05548bbc41e8cb595283
@@ -0,0 +1,330 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
/// <summary>URI strings to use in WAAPI calls. For a complete description, refer to the official Wwise SDK documentation.</summary>
public class ak
{
public class soundengine
{
/// <summary>Set multiple positions for a single game object. Setting multiple positions for a single game object is a way to simulate multiple emission sources while using the resources of only one voice. This can be used to simulate wall openings, area sounds, or multiple objects emitting the same sound in the same area. See <tt>AK::SoundEngine::SetMultiplePositions</tt>.</summary>
public const string setMultiplePositions = "ak.soundengine.setMultiplePositions";
/// <summary>Set the scaling factor of a game object. Modify the attenuation computations on this game object to simulate sounds with a larger or smaller area of effect. See <tt>AK::SoundEngine::SetScalingFactor</tt>.</summary>
public const string setScalingFactor = "ak.soundengine.setScalingFactor";
/// <summary>Asynchronously post an Event to the sound engine (by event ID). See <tt>AK::SoundEngine::PostEvent</tt>.</summary>
public const string postEvent = "ak.soundengine.postEvent";
/// <summary>Set the value of a real-time parameter control. See <tt>AK::SoundEngine::SetRTPCValue</tt>.</summary>
public const string setRTPCValue = "ak.soundengine.setRTPCValue";
/// <summary>Set a game object's obstruction and occlusion levels. This function is used to affect how an object should be heard by a specific listener. See <tt>AK::SoundEngine::SetObjectObstructionAndOcclusion</tt>.</summary>
public const string setObjectObstructionAndOcclusion = "ak.soundengine.setObjectObstructionAndOcclusion";
/// <summary>Set a single game object's active listeners. By default, all new game objects have no listeners active, but this behavior can be overridden with <tt>SetDefaultListeners()</tt>. Inactive listeners are not computed. See <tt>AK::SoundEngine::SetListeners</tt>.</summary>
public const string setListeners = "ak.soundengine.setListeners";
/// <summary>Execute an action on all nodes that are referenced in the specified event in an action of type play. See <tt>AK::SoundEngine::ExecuteActionOnEvent</tt>.</summary>
public const string executeActionOnEvent = "ak.soundengine.executeActionOnEvent";
/// <summary>Set a listener's spatialization parameters. This lets you define listener-specific volume offsets for each audio channel. See <tt>AK::SoundEngine::SetListenerSpatialization</tt>.</summary>
public const string setListenerSpatialization = "ak.soundengine.setListenerSpatialization";
/// <summary>Reset the value of a real-time parameter control to its default value, as specified in the Wwise project. See <tt>AK::SoundEngine::ResetRTPCValue</tt>.</summary>
public const string resetRTPCValue = "ak.soundengine.resetRTPCValue";
/// <summary>Unregister a game object. Registering a game object twice does nothing. Unregistering it once unregisters it no matter how many times it has been registered. Unregistering a game object while it is in use is allowed, but the control over the parameters of this game object is lost. For example, say a sound associated with this game object is a 3D moving sound. It will stop moving when the game object is unregistered, and there will be no way to regain control over the game object. See <tt>AK::SoundEngine::UnregisterGameObj</tt>.</summary>
public const string unregisterGameObj = "ak.soundengine.unregisterGameObj";
/// <summary>Stop the current content, associated to the specified playing ID, from playing. See <tt>AK::SoundEngine::StopPlayingID</tt>.</summary>
public const string stopPlayingID = "ak.soundengine.stopPlayingID";
/// <summary>Set the Auxiliary Busses to route the specified game object. See <tt>AK::SoundEngine::SetGameObjectAuxSendValues</tt>.</summary>
public const string setGameObjectAuxSendValues = "ak.soundengine.setGameObjectAuxSendValues";
/// <summary>Seek inside all playing objects that are referenced in Play Actions of the specified Event. See <tt>AK::SoundEngine::SeekOnEvent</tt>.</summary>
public const string seekOnEvent = "ak.soundengine.seekOnEvent";
/// <summary>Register a game object. Registering a game object twice does nothing. Unregistering it once unregisters it no matter how many times it has been registered. See <tt>AK::SoundEngine::RegisterGameObj</tt>.</summary>
public const string registerGameObj = "ak.soundengine.registerGameObj";
/// <summary>Set a the default active listeners for all subsequent game objects that are registered. See <tt>AK::SoundEngine::SetDefaultListeners</tt>.</summary>
public const string setDefaultListeners = "ak.soundengine.setDefaultListeners";
/// <summary>Set the position of a game object. See <tt>AK::SoundEngine::SetPosition</tt>.</summary>
public const string setPosition = "ak.soundengine.setPosition";
/// <summary>Display a message in the profiler's Capture Log view.</summary>
public const string postMsgMonitor = "ak.soundengine.postMsgMonitor";
/// <summary>Set the output bus volume (direct) to be used for the specified game object. See <tt>AK::SoundEngine::SetGameObjectOutputBusVolume</tt>.</summary>
public const string setGameObjectOutputBusVolume = "ak.soundengine.setGameObjectOutputBusVolume";
/// <summary>Set the State of a Switch Group. See <tt>AK::SoundEngine::SetSwitch</tt>.</summary>
public const string setSwitch = "ak.soundengine.setSwitch";
/// <summary>Stop playing the current content associated to the specified game object ID. If no game object is specified, all sounds will be stopped. See <tt>AK::SoundEngine::StopAll</tt>.</summary>
public const string stopAll = "ak.soundengine.stopAll";
/// <summary>Post the specified Trigger. See <tt>AK::SoundEngine::PostTrigger</tt>.</summary>
public const string postTrigger = "ak.soundengine.postTrigger";
public class error
{
public const string invalid_playing_id = "ak.soundengine.invalid_playing_id";
public const string wrong_volumeOffsets_length = "ak.soundengine.wrong_volumeOffsets_length";
}
}
public class wwise
{
public class error
{
public const string invalid_arguments = "ak.wwise.invalid_arguments";
public const string invalid_options = "ak.wwise.invalid_options";
public const string invalid_json = "ak.wwise.invalid_json";
public const string invalid_object = "ak.wwise.invalid_object";
public const string invalid_property = "ak.wwise.invalid_property";
public const string invalid_reference = "ak.wwise.invalid_reference";
public const string invalid_query = "ak.wwise.query.invalid_query";
public const string file_error = "ak.wwise.file_error";
public const string unavailable = "ak.wwise.unavailable";
public const string unexpected_error = "ak.wwise.unexpected_error";
public const string locked = "ak.wwise.locked";
public const string connection_failed = "ak.wwise.connection_failed";
public const string already_connected = "ak.wwise.already_connected";
public const string wwise_console = "ak.wwise.wwise_console";
}
public class debug
{
/// <summary>Private use only.</summary>
public const string testAssert = "ak.wwise.debug.testAssert";
/// <summary>Sent when an assert has failed. This is only available with Debug builds.</summary>
public const string assertFailed = "ak.wwise.debug.assertFailed";
/// <summary>Enable or disable the automation mode for Wwise. This reduces the potential interruptions caused by message boxes and dialogs. For instance, enabling the automation mode silently accepts: project migration, project load log, EULA acceptance, project licence display and generic message boxes.</summary>
public const string enableAutomationMode = "ak.wwise.debug.enableAutomationMode";
/// <summary>Enables debug assertions. Every call to enableAsserts with false increments the ref count. Calling with true will decrement the ref count. This is only available with Debug builds.</summary>
public const string enableAsserts = "ak.wwise.debug.enableAsserts";
}
public class core
{
public class audioSourcePeaks
{
/// <summary>Get the min/max peak pairs, in a given region of an audio source, as a collection of binary strings (one per channel). The strings are base-64 encoded 16-bit signed int arrays, with min and max values being interleaved. If getCrossChannelPeaks is true, there will be only one binary string representing peaks across all channels globally.</summary>
public const string getMinMaxPeaksInRegion = "ak.wwise.core.audioSourcePeaks.getMinMaxPeaksInRegion";
/// <summary>Get the min/max peak pairs in the entire trimmed region of an audio source, for each channel, as an array of binary strings (one per channel). The strings are base-64 encoded 16-bit signed int arrays, with min and max values being interleaved. If getCrossChannelPeaks is true, there will be only one binary string representing peaks across all channels globally.</summary>
public const string getMinMaxPeaksInTrimmedRegion = "ak.wwise.core.audioSourcePeaks.getMinMaxPeaksInTrimmedRegion";
}
public class remote
{
/// <summary>Retrieves the connection status.</summary>
public const string getConnectionStatus = "ak.wwise.core.remote.getConnectionStatus";
/// <summary>Retrieves all consoles available for connecting Wwise Authoring to a Sound Engine instance.</summary>
public const string getAvailableConsoles = "ak.wwise.core.remote.getAvailableConsoles";
/// <summary>Disconnects the Wwise Authoring application from a connected Wwise Sound Engine running executable.</summary>
public const string disconnect = "ak.wwise.core.remote.disconnect";
/// <summary>Connects the Wwise Authoring application to a Wwise Sound Engine running executable. The host must be running code with communication enabled.</summary>
public const string connect = "ak.wwise.core.remote.connect";
}
public class log
{
/// <summary>Sent when an item is added to the log. This could be used to retrieve items added to the SoundBank generation log. To retrieve the complete log, refer to ak.wwise.core.log.get.</summary>
public const string itemAdded = "ak.wwise.core.log.itemAdded";
/// <summary>Retrieve the latest log for a specific channel. Refer to ak.wwise.core.log.itemadded to be notified when an item is added to the log.</summary>
public const string get = "ak.wwise.core.log.get";
}
/// <summary>Retrieve global Wwise information.</summary>
public const string getInfo = "ak.wwise.core.getInfo";
public class @object
{
/// <summary>Sent when an object reference is changed.</summary>
public const string referenceChanged = "ak.wwise.core.object.referenceChanged";
/// <summary>Moves an object to the given parent. Returns the moved object.</summary>
public const string move = "ak.wwise.core.object.move";
/// <summary>Sent when an attenuation curve's link/unlink is changed.</summary>
public const string attenuationCurveLinkChanged = "ak.wwise.core.object.attenuationCurveLinkChanged";
/// <summary>Sent when an object is added as a child to another object.</summary>
public const string childAdded = "ak.wwise.core.object.childAdded";
/// <summary>Retrieves the list of all object types registered in Wwise's object model.</summary>
public const string getTypes = "ak.wwise.core.object.getTypes";
/// <summary>Sent when the watched property of an object changes.</summary>
public const string propertyChanged = "ak.wwise.core.object.propertyChanged";
/// <summary>Creates an object of type 'type', as a child of 'parent'. Refer to ak.wwise.core.audio.import to import audio files to Wwise.</summary>
public const string create = "ak.wwise.core.object.create";
/// <summary>Performs a query, returns specified data for each object in query result.</summary>
public const string get = "ak.wwise.core.object.get";
/// <summary>Sent prior to an object's deletion.</summary>
public const string preDeleted = "ak.wwise.core.object.preDeleted";
/// <summary>Sent when an object is renamed. Publishes the object which the name was changed.</summary>
public const string nameChanged = "ak.wwise.core.object.nameChanged";
/// <summary>Sent following an object's deletion.</summary>
public const string postDeleted = "ak.wwise.core.object.postDeleted";
/// <summary>Sent when the object's notes are changed.</summary>
public const string notesChanged = "ak.wwise.core.object.notesChanged";
/// <summary>Retrieves information about an object property.</summary>
public const string getPropertyInfo = "ak.wwise.core.object.getPropertyInfo";
/// <summary>Renames an object.</summary>
public const string setName = "ak.wwise.core.object.setName";
/// <summary>Sets the object's notes.</summary>
public const string setNotes = "ak.wwise.core.object.setNotes";
/// <summary>Sets the specified attenuation curve for a given attenuation object.</summary>
public const string setAttenuationCurve = "ak.wwise.core.object.setAttenuationCurve";
/// <summary>Sets a property value of an object for a specific platform. Refer to ak.wwise.core.object.setreference to set a reference to an object.</summary>
public const string setProperty = "ak.wwise.core.object.setProperty";
/// <summary>Copies an object to the given parent.</summary>
public const string copy = "ak.wwise.core.object.copy";
/// <summary>Return true if a property is enabled based on the values of the properties it depends on.</summary>
public const string isPropertyEnabled = "ak.wwise.core.object.isPropertyEnabled";
/// <summary>Sets the randomizer values of a property of an object for a specific platform.</summary>
public const string setRandomizer = "ak.wwise.core.object.setRandomizer";
/// <summary>Sets an object's reference value.</summary>
public const string setReference = "ak.wwise.core.object.setReference";
/// <summary>Sent when an attenuation curve is changed.</summary>
public const string attenuationCurveChanged = "ak.wwise.core.object.attenuationCurveChanged";
/// <summary>Sent when an object is created.</summary>
public const string created = "ak.wwise.core.object.created";
/// <summary>Sent when an object is removed from the children of another object.</summary>
public const string childRemoved = "ak.wwise.core.object.childRemoved";
/// <summary>Retrieves the list of property and reference names for an object.</summary>
public const string getPropertyNames = "ak.wwise.core.object.getPropertyNames";
/// <summary>Gets the specified attenuation curve for a given attenuation object.</summary>
public const string getAttenuationCurve = "ak.wwise.core.object.getAttenuationCurve";
/// <summary>Sent when one or many curves are changed.</summary>
public const string curveChanged = "ak.wwise.core.object.curveChanged";
/// <summary>Deletes the specified object.</summary>
public const string delete = "ak.wwise.core.object.delete";
/// <summary>Retrieves the list of property and reference names for an object.</summary>
public const string getPropertyAndReferenceNames = "ak.wwise.core.object.getPropertyAndReferenceNames";
/// <summary>Retrieves the list of operation made to objects.</summary>
public const string structureChanged = "ak.wwise.core.object.structureChanged";
/// <summary>Verify if WAAPI is currently available.</summary>
public const string ping = "ak.wwise.core.ping";
}
public class undo
{
/// <summary>Ends the last undo group.</summary>
public const string endGroup = "ak.wwise.core.undo.endGroup";
/// <summary>Cancels the last undo group. Please note that this does not revert the operations made since the last ak.wwise.core.undo.begingroup call.</summary>
public const string cancelGroup = "ak.wwise.core.undo.cancelGroup";
/// <summary>Begins an undo group. Make sure to call ak.wwise.core.undo.endgroup exactly once for every ak.wwise.core.beginUndoGroup call you make. Calls to ak.wwise.core.undo.beginGroup can be nested.</summary>
public const string beginGroup = "ak.wwise.core.undo.beginGroup";
}
public class profiler
{
/// <summary>Returns the current time of the specified profiler cursor in milliseconds.</summary>
public const string getCursorTime = "ak.wwise.core.profiler.getCursorTime";
/// <summary>Start the profiler capture and return the time at the beginning of the capture in milliseconds.</summary>
public const string startCapture = "ak.wwise.core.profiler.startCapture";
/// <summary>Retrieves all parameters affecting voice volume, highpass and lowpass for a voice path, resolved from pipeline IDs.</summary>
public const string getVoiceContributions = "ak.wwise.core.profiler.getVoiceContributions";
/// <summary>Retrieves the voices at a specific profiler capture time.</summary>
public const string getVoices = "ak.wwise.core.profiler.getVoices";
/// <summary>Retrieves the busses at a specific profiler capture time.</summary>
public const string getBusses = "ak.wwise.core.profiler.getBusses";
/// <summary>Stop the profiler capture and return the time at the end of the capture in milliseconds.</summary>
public const string stopCapture = "ak.wwise.core.profiler.stopCapture";
}
public class project
{
/// <summary>Sent when the after the project is completely closed.</summary>
public const string postClosed = "ak.wwise.core.project.postClosed";
/// <summary>Sent when the project has been successfully loaded.</summary>
public const string loaded = "ak.wwise.core.project.loaded";
/// <summary>Sent when the project begins closing.</summary>
public const string preClosed = "ak.wwise.core.project.preClosed";
/// <summary>Saves the current project.</summary>
public const string save = "ak.wwise.core.project.save";
/// <summary>Sent when the project has been saved.</summary>
public const string saved = "ak.wwise.core.project.saved";
}
public class transport
{
/// <summary>Gets the state of the given transport object.</summary>
public const string getState = "ak.wwise.core.transport.getState";
/// <summary>Sent when the transport's state has changed.</summary>
public const string stateChanged = "ak.wwise.core.transport.stateChanged";
/// <summary>Creates a transport object for the given Wwise object. The return transport object can be used to play, stop, pause and resume the Wwise object via the other transport functions.</summary>
public const string create = "ak.wwise.core.transport.create";
/// <summary>Returns the list of transport objects.</summary>
public const string getList = "ak.wwise.core.transport.getList";
/// <summary>Destroys the given transport object.</summary>
public const string destroy = "ak.wwise.core.transport.destroy";
/// <summary>Executes an action on the given transport object, or all transports if no transport is specified.</summary>
public const string executeAction = "ak.wwise.core.transport.executeAction";
}
public class soundbank
{
/// <summary>Retrieves a SoundBank's inclusion list.</summary>
public const string getInclusions = "ak.wwise.core.soundbank.getInclusions";
/// <summary>Sent when a single SoundBank is generated. This could be sent multiple times during SoundBank generation, for every SoundBank generated and for every platform. To generate SoundBanks, refer to ak.wwise.ui.commands.execute with one of the SoundBank generation commands.</summary>
public const string generated = "ak.wwise.core.soundbank.generated";
/// <summary>Modifies a SoundBank's inclusion list. The 'operation' argument determines how the 'inclusions' argument modifies the SoundBank's inclusion list; 'inclusions' may be added to / removed from / replace the SoundBank's inclusion list.</summary>
public const string setInclusions = "ak.wwise.core.soundbank.setInclusions";
/// <summary>Generate the soundbanks.</summary>
public const string generate = "ak.wwise.core.soundbank.generate";
}
public class audio
{
/// <summary>Create Wwise objects and import audio files. This function is using the same importation processor available through the Tab Delimited import in the Audio File Importer. The function returns an array of all objects created, replaced or re-used. Use the options to specify how the objects are returned.</summary>
public const string import = "ak.wwise.core.audio.import";
/// <summary>Scripted object creation and audio file import from a tab-delimited file.</summary>
public const string importTabDelimited = "ak.wwise.core.audio.importTabDelimited";
/// <summary>Sent at the end of an import operation.</summary>
public const string imported = "ak.wwise.core.audio.imported";
}
public class switchContainer
{
/// <summary>Remove an assignment between a Switch Container's child and a State.</summary>
public const string removeAssignment = "ak.wwise.core.switchContainer.removeAssignment";
/// <summary>Returns the list of assignments between a Switch Container's children and states.</summary>
public const string getAssignments = "ak.wwise.core.switchContainer.getAssignments";
/// <summary>Sent when an assignment is removed from a Switch Container.</summary>
public const string assignmentRemoved = "ak.wwise.core.switchContainer.assignmentRemoved";
/// <summary>Assign a Switch Container's child to a Switch. This is the equivalent of doing a drag&drop of the child to a state in the Assigned Objects view. The child is always added at the end for each state.</summary>
public const string addAssignment = "ak.wwise.core.switchContainer.addAssignment";
/// <summary>Sent when an assignment is added to a Switch Container.</summary>
public const string assignmentAdded = "ak.wwise.core.switchContainer.assignmentAdded";
}
public class plugin
{
/// <summary>Retrieves the list of all object types registered in Wwise's object model.</summary>
public const string getList = "ak.wwise.core.plugin.getList";
/// <summary>Retrieves information about an object property.</summary>
public const string getProperty = "ak.wwise.core.plugin.getProperty";
/// <summary>Retrieves the list of property and reference names for an object.</summary>
public const string getProperties = "ak.wwise.core.plugin.getProperties";
}
}
public class ui
{
public class project
{
/// <summary>Closes the current project.</summary>
public const string close = "ak.wwise.ui.project.close";
/// <summary>Opens a project, specified by path. Please refer to ak.wwise.core.project.loaded for further explanations on how to be notified when the operation has completed.</summary>
public const string open = "ak.wwise.ui.project.open";
}
/// <summary>Bring Wwise main window to foreground. Refer to SetForegroundWindow and AllowSetForegroundWindow on MSDN for more information on the restrictions. Refer to ak.wwise.core.getInfo to obtain the Wwise process ID for AllowSetForegroundWindow.</summary>
public const string bringToForeground = "ak.wwise.ui.bringToForeground";
public class commands
{
/// <summary>Unregister an array of add-on UI commands.</summary>
public const string unregister = "ak.wwise.ui.commands.unregister";
/// <summary>Sent when a command is executed. The objects for which the command is executed are sent in the publication.</summary>
public const string executed = "ak.wwise.ui.commands.executed";
/// <summary>Executes a command. Some commands can take a list of objects as parameter.</summary>
public const string execute = "ak.wwise.ui.commands.execute";
/// <summary>Register an array of add-on commands. Registered commands remain until the Wwise process is terminated. Refer to to ak.wwise.ui.commands.executed.</summary>
public const string register = "ak.wwise.ui.commands.register";
/// <summary>Get the list of commands.</summary>
public const string getCommands = "ak.wwise.ui.commands.getCommands";
}
/// <summary>Retrieves the list of objects currently selected by the user in the active view.</summary>
public const string getSelectedObjects = "ak.wwise.ui.getSelectedObjects";
/// <summary>Sent when the selection changes in the project.</summary>
public const string selectionChanged = "ak.wwise.ui.selectionChanged";
}
public class waapi
{
/// <summary>Retrieve the list of topics to which a client can subscribe.</summary>
public const string getTopics = "ak.wwise.waapi.getTopics";
/// <summary>Retrieve the list of functions.</summary>
public const string getFunctions = "ak.wwise.waapi.getFunctions";
/// <summary>Retrieve the JSON schema of a Waapi URI.</summary>
public const string getSchema = "ak.wwise.waapi.getSchema";
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 12890b20cf960be489806d648435d24c
@@ -0,0 +1,592 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
using System.Linq;
/// <summary>
/// WAMP protocol implementation using only strings and regular expressions. This implements only a subset of the WAMP feature set and is only compatible with Wwise.
/// </summary>
public class Wamp
{
/// <summary>Exception thrown during WAMP operations when the timeout is reached.</summary>
public class TimeoutException : System.Exception
{
public TimeoutException(string message)
: base(message)
{
}
}
public class WampNotConnectedException : System.Exception
{
public WampNotConnectedException(string message)
: base(message)
{
}
}
/// <summary>Exception thrown during WAMP operations.</summary>
public class ErrorException : System.Exception
{
internal string Json { get; set; }
internal Messages MessageId { get; set; }
internal int RequestId { get; set; }
internal string Uri { get; set; }
public ErrorException(string message)
: base(message)
{
}
public static ErrorException FromResponse(string response)
{
// [ERROR, CALL, CALL.Request|id, Details|dict, Error|uri, Arguments|list, ArgumentsKw|dict]
string pattern = @"^\[\s*8,\s*(\d+)\s*,\s*(\d+)\s*,\s*\{\s*\}\s*,\s*""([^,\s]+)""\s*,\[\s*\]\s*,\s*(\{)";
var match = System.Text.RegularExpressions.Regex.Match(response, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (match.Groups.Count != 5)
throw new ErrorException("Invalid ERROR message.");
Messages messageId = (Messages)int.Parse(match.Groups[1].Value);
int requestId = int.Parse(match.Groups[2].Value);
string uri = match.Groups[3].Value;
string json = response.Substring(match.Groups[4].Index, response.Length - match.Groups[4].Index - 1);
return new ErrorException($"Error {uri} in {messageId.ToString()} operation.")
{
Json = json,
MessageId = messageId,
RequestId = requestId,
Uri = uri
};
}
}
/// <summary>Messages ids defined by the WAMP protocol</summary>
internal enum Messages : int
{
HELLO = 1,
WELCOME = 2,
GOODBYE = 6,
ERROR = 8,
SUBSCRIBE = 32,
SUBSCRIBED = 33,
UNSUBSCRIBE = 34,
UNSUBSCRIBED = 35,
EVENT = 36,
CALL = 48,
RESULT = 50
}
/// <summary>Encapsulate a response from the server.</summary>
private class Response
{
public Messages MessageId { get; set; }
public int RequestId { get; set; }
public int ContextSpecificResultId { get; set; }
public uint SubscriptionId { get; set; }
public string Json { get; set; }
}
/// <summary>Publish events are delegates registered with Subscribe.</summary>
public delegate void PublishHandler(string json);
public delegate void DisconnectedHandler();
public event DisconnectedHandler Disconnected;
private System.Net.WebSockets.ClientWebSocket ws;
private int sessionId = 0;
private int currentRequestId = 0;
private System.Threading.CancellationTokenSource stopServerTokenSource = new System.Threading.CancellationTokenSource();
private System.Threading.Tasks.TaskCompletionSource<Response> taskCompletion = new System.Threading.Tasks.TaskCompletionSource<Response>();
private System.Collections.Concurrent.ConcurrentDictionary<uint, PublishHandler> subscriptions = new System.Collections.Concurrent.ConcurrentDictionary<uint, PublishHandler>();
private async System.Threading.Tasks.Task Send(string msg, int timeout)
{
try
{
using (var cts = new System.Threading.CancellationTokenSource(timeout))
{
var segment = new System.ArraySegment<byte>(System.Text.Encoding.UTF8.GetBytes(msg));
await ws.SendAsync(segment, System.Net.WebSockets.WebSocketMessageType.Text, true, cts.Token);
}
}
catch (System.Threading.Tasks.TaskCanceledException)
{
throw new TimeoutException("Timeout when sending message.");
}
}
/// <summary>Parse a WAMP message from the server.</summary>
private Response Parse(string msg)
{
const string msgTypePattern = @"^\[\s*(\d+)";
var match = System.Text.RegularExpressions.Regex.Match(msg, msgTypePattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (match.Groups.Count != 2)
throw new ErrorException("Error while parsing response from server.");
Messages messageId = (Messages)int.Parse(match.Groups[1].Value);
switch (messageId)
{
case Messages.WELCOME:
return ParseWelcome(msg);
case Messages.GOODBYE:
return ParseGoodbye(msg);
case Messages.SUBSCRIBED:
return ParseSubscribed(msg);
case Messages.UNSUBSCRIBED:
return ParseUnsubscribed(msg);
case Messages.EVENT:
return ParseEvent(msg);
case Messages.RESULT:
return ParseResult(msg);
case Messages.ERROR:
throw ErrorException.FromResponse(msg);
default:
throw new ErrorException("Unexpected result from server.");
}
}
private static Response ParseResult(string msg)
{
// [RESULT, CALL.Request|id, Details|dict, YIELD.Arguments|list, YIELD.ArgumentsKw | dict]
const string pattern = @"^\[\s*50,\s*(\d+)\s*,\s*\{\s*\}\s*,\s*\[\s*\]\s*,\s*(\{)";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (!match.Success || match.Groups.Count != 3)
throw new ErrorException("Invalid RESULT message.");
return new Response()
{
MessageId = Messages.RESULT,
RequestId = (int.Parse(match.Groups[1].Value)),
Json = msg.Substring(match.Groups[2].Index, msg.Length - match.Groups[2].Index - 1)
};
}
private static Response ParseSubscribed(string msg)
{
// [SUBSCRIBED, SUBSCRIBE.Request|id, Subscription|id]
const string pattern = @"^\[\s*33,\s*(\d+)\s*,\s*(\d+)\s*]$";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (!match.Success || match.Groups.Count != 3)
throw new ErrorException("Invalid SUBSCRIBED message.");
return new Response()
{
MessageId = Messages.SUBSCRIBED,
RequestId = (int.Parse(match.Groups[1].Value)),
//ContextSpecificResultId = (int.Parse(match.Groups[2].Value))
SubscriptionId = (uint.Parse(match.Groups[2].Value))
};
}
private static Response ParseUnsubscribed(string msg)
{
// [UNSUBSCRIBED, UNSUBSCRIBE.Request|id]
const string pattern = @"^\[\s*35,\s*(\d+)\s*]$";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (!match.Success || match.Groups.Count != 2)
throw new ErrorException("Invalid UNSUBSCRIBED message.");
return new Response()
{
MessageId = Messages.UNSUBSCRIBED,
RequestId = (int.Parse(match.Groups[1].Value))
};
}
private static Response ParseGoodbye(string msg)
{
// [GOODBYE, Details|dict, Reason|uri]
const string pattern = @"^\[\s*6";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (!match.Success || match.Groups.Count != 1)
throw new ErrorException("Invalid GOODBYE message.");
return new Response()
{
MessageId = Messages.GOODBYE
};
}
private static Response ParseWelcome(string msg)
{
// [WELCOME, Session|id, Details|dict]
const string pattern = @"^\[\s*2,\s*(\d+)";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (!match.Success || match.Groups.Count != 2)
throw new ErrorException("Invalid WELCOME message.");
return new Response()
{
MessageId = Messages.WELCOME,
RequestId = 0,
ContextSpecificResultId = (int.Parse(match.Groups[1].Value))
};
}
private static Response ParseEvent(string msg)
{
// [EVENT, SUBSCRIBED.Subscription|id, PUBLISHED.Publication|id, Details|dict, PUBLISH.Arguments|list, PUBLISH.ArgumentKw|dict]
const string pattern = @"^\[\s*36,\s*(\d+)\s*,\s*(\d+)\s*,\s*\{\s*\}\s*,\s*\[\s*\]\s*,\s*(\{)";
var match = System.Text.RegularExpressions.Regex.Match(msg, pattern, System.Text.RegularExpressions.RegexOptions.Singleline);
if (match.Groups.Count != 4)
throw new ErrorException("Invalid EVENT message.");
return new Response()
{
MessageId = Messages.EVENT,
RequestId = (int.Parse(match.Groups[2].Value)),
ContextSpecificResultId = (int.Parse(match.Groups[1].Value)),
Json = msg.Substring(match.Groups[3].Index, msg.Length - match.Groups[3].Index - 1)
};
}
private async System.Threading.Tasks.Task<Response> ReceiveMessage()
{
// Receive one web socket message
System.Collections.Generic.List<System.Collections.Generic.IEnumerable<byte>> segments = new System.Collections.Generic.List<System.Collections.Generic.IEnumerable<byte>>();
try
{
while (true)
{
byte[] buffer = new byte[4096];
var segment = new System.ArraySegment<byte>(buffer, 0, buffer.Length);
System.Net.WebSockets.WebSocketReceiveResult rcvResult = await ws.ReceiveAsync(segment, stopServerTokenSource.Token);
// Accumulate the byte arrays in a list, we will join them later
segments.Add(segment.Skip(segment.Offset).Take(rcvResult.Count));
if (rcvResult.EndOfMessage)
break;
}
}
catch (System.Net.WebSockets.WebSocketException e)
{
throw e.InnerException;
}
catch (System.Exception)
{
throw new ErrorException("Error receiving response from server.");
}
try
{
byte[] bytes = segments.SelectMany(t => t).ToArray<byte>();
string msg = System.Text.Encoding.UTF8.GetString(bytes);
return Parse(msg);
}
catch (ErrorException e)
{
// Dispatch already built error
throw e;
}
catch (System.Exception)
{
throw new ErrorException("Error while parsing response from server.");
}
}
/// <summary>
/// Wait for the next response
/// </summary>
/// <returns>The response from the server.</returns>
private async System.Threading.Tasks.Task<Response> Receive(int timeout)
{
System.Threading.Tasks.Task task = await System.Threading.Tasks.Task.WhenAny(
taskCompletion.Task,
System.Threading.Tasks.Task.Delay(timeout));
if (task != taskCompletion.Task)
{
taskCompletion = new System.Threading.Tasks.TaskCompletionSource<Response>();
// Timeout reached
throw new TimeoutException("Timeout when receiving message.");
}
if (task.Exception != null)
{
taskCompletion = new System.Threading.Tasks.TaskCompletionSource<Response>();
if (task.Exception.InnerException.InnerException != null)
throw task.Exception.InnerException.InnerException;
throw task.Exception;
}
var result = taskCompletion.Task.Result;
// Since we can't re-use the task completion, create a new one for the next message
taskCompletion = new System.Threading.Tasks.TaskCompletionSource<Response>();
return result;
}
/// <summary>
/// Wait for the next response and do some validation on the response
/// </summary>
/// <param name="message">What message to expect</param>
/// <param name="requestId">What request id to expect</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise exception when timeout is reached.</param>
/// <returns></returns>
private async System.Threading.Tasks.Task<Response> ReceiveExpect(Messages message, int requestId, int timeout)
{
// Should receive the expected message or ERROR
Response response = await Receive(timeout);
if (response.MessageId != message)
throw new ErrorException($"{message.ToString()}: invalid response. Did not receive expected answer.");
if (response.RequestId != requestId)
throw new ErrorException($"{message.ToString()}: invalid request id for result.");
return response;
}
public System.Threading.CancellationTokenSource _connectionTokenSource;
/// <summary>
/// Connect to the specified host, handshake and prepare the listening task.
/// </summary>
/// <param name="host">The URI of the host, usually something like ws://host:port</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise exception when timeout is reached.</param>
/// <returns></returns>
internal async System.Threading.Tasks.Task Connect(string host, int timeout)
{
try
{
System.Uri uri = new System.Uri(host);
_connectionTokenSource = new System.Threading.CancellationTokenSource(timeout);
// Connect
if (ws == null)
ws = new System.Net.WebSockets.ClientWebSocket();
await ws.ConnectAsync(uri, _connectionTokenSource.Token);
{
// [HELLO, Realm|uri, Details|dict]
await Send($"[{(int)Messages.HELLO},\"realm1\"]", timeout);
}
StartListen();
{
// Should receive the WELCOME
Response response = await ReceiveExpect(Messages.WELCOME, 0, timeout);
sessionId = response.ContextSpecificResultId;
}
}
catch (System.Net.WebSockets.WebSocketException e)
{
ws.Dispose();
ws = new System.Net.WebSockets.ClientWebSocket();
throw new ErrorException(e.ToString());
}
catch (System.Exception e)
{
throw new ErrorException(e.ToString());
}
}
/// <summary>
/// Forcefully cancel the connection attempt to the host
/// </summary>
public void CancelCurrentConnection()
{
if (_connectionTokenSource != null)
{
_connectionTokenSource.Cancel();
}
}
/// <summary>
/// Tell the connection state of the WebSocket client.
/// </summary>
/// <returns>Return true if the connection is open and ready.</returns>
internal bool IsConnected()
{
if (ws == null)
return false;
return ws.State == System.Net.WebSockets.WebSocketState.Open;
}
internal System.Net.WebSockets.WebSocketState SocketState()
{
if (ws == null) return System.Net.WebSockets.WebSocketState.None;
return ws.State;
}
/// <summary>Close the connection.</summary>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise exception when timeout is reached.</param>
internal async System.Threading.Tasks.Task Close(int timeout)
{
// [GOODBYE, Details|dict, Reason|uri]
try
{
await Send($"[{(int)Messages.GOODBYE},{{}},\"bye_from_csharp_client\"]", timeout);
Response response = await ReceiveExpect(Messages.GOODBYE, 0, timeout);
stopServerTokenSource.Cancel();
using (var cts = new System.Threading.CancellationTokenSource(timeout))
{
await ws.CloseOutputAsync(System.Net.WebSockets.WebSocketCloseStatus.NormalClosure, "wamp_close", cts.Token);
}
}
catch (System.Net.WebSockets.WebSocketException)
{
ws.Dispose();
stopServerTokenSource.Cancel();
}
}
private void ProcessEvent(Response message)
{
int subscriptionId = message.ContextSpecificResultId;
PublishHandler publishEvent = null;
if (!subscriptions.TryGetValue((uint)subscriptionId, out publishEvent))
throw new ErrorException("UNSUBSCRIBE: unknown subscription id.");
publishEvent(message.Json);
}
private void StartListen()
{
// Start the receive task, that will remain running for the whole connection
System.Threading.CancellationToken ct = stopServerTokenSource.Token;
var task = System.Threading.Tasks.Task.Factory.StartNew(() =>
{
ct.ThrowIfCancellationRequested();
while (true)
{
try
{
System.Threading.Tasks.Task<Response> receiveTask = ReceiveMessage();
receiveTask.Wait();
if (receiveTask.Result.MessageId == Messages.EVENT)
ProcessEvent(receiveTask.Result);
else if (taskCompletion != null)
taskCompletion.SetResult(receiveTask.Result);
else
throw new ErrorException("Received WAMP message that we did not expect.");
if (ct.IsCancellationRequested)
{
break;
}
}
catch (System.Exception e)
{
if (e.InnerException.GetType() == typeof(System.Net.WebSockets.WebSocketException))
{
var exception = e.InnerException as System.Net.WebSockets.WebSocketException;
if (exception.WebSocketErrorCode == System.Net.WebSockets.WebSocketError.ConnectionClosedPrematurely)
{
if (taskCompletion != null)
taskCompletion.SetException(e);
OnDisconnect();
return;
}
}
if (ws.State != System.Net.WebSockets.WebSocketState.Open)
{
OnDisconnect();
return;
}
// Signal the exception to the other thread and continue to listen
if (taskCompletion != null)
taskCompletion.SetException(e);
}
}
}, stopServerTokenSource.Token);
}
private void OnDisconnect()
{
if (Disconnected != null)
{
Disconnected();
}
}
/// <summary>
/// Invoke an RPC function from the uri
/// </summary>
/// <param name="uri">URI of the function</param>
/// <param name="args">Arguments</param>
/// <param name="options">Options</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise exception when Waapi.TimeoutException is reached.</param>
/// <returns></returns>
internal async System.Threading.Tasks.Task<string> Call(string uri, string args, string options, int timeout)
{
int requestId = ++currentRequestId;
// [CALL, Request|id, Options|dict, Procedure|uri, Arguments|list, ArgumentsKw|dict]
await Send($"[{(int)Messages.CALL},{requestId},{options},\"{uri}\",[],{args}]", timeout);
// Should receive the RESULT or ERROR
Response response = await ReceiveExpect(Messages.RESULT, requestId, timeout);
return response.Json;
}
/// <summary>
/// Subscribe to a WAMP topic.
/// </summary>
/// <param name="topic">The topic to which subscribe.</param>
/// <param name="options">The options the subscription.</param>
/// <param name="publishEvent">The delegate function to call when the topic is published.</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
/// <returns>Subscription id, that you can use to unsubscribe.</returns>
internal async System.Threading.Tasks.Task<uint> Subscribe(string topic, string options, PublishHandler publishEvent, int timeout)
{
int requestId = ++currentRequestId;
// [SUBSCRIBE, Request|id, Options|dict, Topic|uri]
await Send($"[{(int)Messages.SUBSCRIBE},{requestId},{options},\"{topic}\"]", timeout);
// Should receive the SUBSCRIBED or ERROR
Response response = await ReceiveExpect(Messages.SUBSCRIBED, requestId, timeout);
subscriptions.TryAdd(response.SubscriptionId, publishEvent);
return response.SubscriptionId;
}
/// <summary>Unsubscribe from a subscription.</summary>
/// <param name="subscriptionId">The subscription id received from the initial subscription.</param>
/// <param name="timeout">The maximum timeout in milliseconds for the function to execute. Will raise Waapi.TimeoutException when timeout is reached.</param>
internal async System.Threading.Tasks.Task Unsubscribe(uint subscriptionId, int timeout)
{
int requestId = ++currentRequestId;
// [UNSUBSCRIBE, Request|id, SUBSCRIBED.Subscription|id]
await Send($"[{(int)Messages.UNSUBSCRIBE},{requestId},{subscriptionId}]", timeout);
Response response = await ReceiveExpect(Messages.UNSUBSCRIBED, requestId, timeout);
PublishHandler oldEvent;
subscriptions.TryRemove(subscriptionId, out oldEvent);
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 8a97d980ceabe2f48a3ad5246ddcc562
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 3a5db7798fd4706409203f052abdbe02
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,36 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
public partial class AkUnitySoundEngine
{
#if UNITY_EDITOR_WIN || (UNITY_STANDALONE_WIN && !UNITY_EDITOR)
/// <summary>
/// Converts "AkOSChar*" C-strings to C# strings.
/// </summary>
/// <param name="ptr">"AkOSChar*" memory pointer passed to C# as an IntPtr.</param>
/// <returns>Converted string.</returns>
public static string StringFromIntPtrOSString(System.IntPtr ptr)
{
return StringFromIntPtrWString(ptr);
}
public static bool PlatformSupportsDecodeBank()
{
return true;
}
#endif
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 03848137b5830de4eb86a3ed15714883
@@ -0,0 +1,55 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if UNITY_EDITOR_WIN || (UNITY_STANDALONE_WIN && !UNITY_EDITOR)
public partial class AkBasePathGetter
{
static string DefaultPlatformName = "Windows";
public static void AdjustFullBasePathForPlatform(ref string fullBasePath)
{
fullBasePath = System.IO.Path.Combine(UnityEngine.Application.streamingAssetsPath, fullBasePath);
}
public static string GetPersistentDataPath()
{
return UnityEngine.Application.persistentDataPath;
}
public static bool InitBankExists(string tempSoundBankBasePath)
{
return System.IO.File.Exists(System.IO.Path.Combine(tempSoundBankBasePath, "Init.bnk"));
}
public static string GetDecodedBankPath()
{
return System.IO.Path.Combine(Instance.SoundBankBasePath, DecodedBankFolder);
}
}
#endif
#if UNITY_EDITOR
[UnityEditor.InitializeOnLoad]
public partial class AkWindowsBasePathGetter
{
static AkWindowsBasePathGetter()
{
AkBasePathGetter.AddTargetPlatform(UnityEditor.BuildTarget.StandaloneWindows, "Windows");
AkBasePathGetter.AddTargetPlatform(UnityEditor.BuildTarget.StandaloneWindows64, "Windows");
}
}
#endif
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: cd7b372b06246d64182e25dd0943d2b2
@@ -0,0 +1,113 @@
/*******************************************************************************
The content of this file includes portions of the proprietary AUDIOKINETIC Wwise
Technology released in source code form as part of the game integration package.
The content of this file may not be used without valid licenses to the
AUDIOKINETIC Wwise Technology.
Note that the use of the game engine is subject to the Unity(R) Terms of
Service at https://unity3d.com/legal/terms-of-service
License Usage
Licensees holding valid licenses to the AUDIOKINETIC Wwise Technology may use
this file in accordance with the end user license agreement provided with the
software or, alternatively, in accordance with the terms contained
in a written agreement between you and Audiokinetic Inc.
Copyright (c) 2026 Audiokinetic Inc.
*******************************************************************************/
#if (UNITY_STANDALONE_WIN && !UNITY_EDITOR) || UNITY_EDITOR_WIN
#if UNITY_STANDALONE_WIN
using AK.Wwise.Unity.Logging;
#endif
public partial class AkCommonUserSettings
{
partial void SetSampleRate(AkPlatformInitSettings settings)
{
settings.uSampleRate = m_SampleRate;
}
protected partial string GetPluginPath()
{
#if UNITY_EDITOR_WIN
return System.IO.Path.GetFullPath(AkUtilities.GetPathInPackage(@"Runtime\Plugins\Windows\x86_64\DSP"));
#elif UNITY_STANDALONE_WIN
string potentialPath = System.IO.Path.Combine(UnityEngine.Application.dataPath, "Plugins" + System.IO.Path.DirectorySeparatorChar);
string architectureName = "x86";
#if UNITY_64
architectureName += "_64";
#endif
if(System.IO.File.Exists(System.IO.Path.Combine(potentialPath, "AkUnitySoundEngine.dll")))
{
return potentialPath;
}
else if(System.IO.File.Exists(System.IO.Path.Combine(potentialPath, architectureName, "AkUnitySoundEngine.dll")))
{
return System.IO.Path.Combine(potentialPath, architectureName);
}
else
{
WwiseLogger.Log("Cannot find Wwise plugin path");
return null;
}
#else
return System.IO.Path.Combine(UnityEngine.Application.dataPath, "Plugins" + System.IO.Path.DirectorySeparatorChar);
#endif
}
}
#endif
public class AkWindowsSettings : AkWwiseInitializationSettings.PlatformSettings
{
#if UNITY_EDITOR
[UnityEditor.InitializeOnLoadMethod]
private static void AutomaticPlatformRegistration()
{
if (UnityEditor.AssetDatabase.IsAssetImportWorkerProcess())
{
return;
}
RegisterPlatformSettingsClass<AkWindowsSettings>("Windows");
}
#endif // UNITY_EDITOR
protected override AkCommonUserSettings GetUserSettings()
{
return UserSettings;
}
protected override AkCommonAdvancedSettings GetAdvancedSettings()
{
return AdvancedSettings;
}
protected override AkCommonCommSettings GetCommsSettings()
{
return CommsSettings;
}
[System.Serializable]
public class PlatformAdvancedSettings : AkCommonAdvancedSettings
{
[UnityEngine.Tooltip("Maximum number of System Audio Objects to reserve. Other processes will not be able to use them. Default is 128.")]
public uint MaxSystemAudioObjects = 128;
public override void CopyTo(AkPlatformInitSettings settings)
{
#if (UNITY_STANDALONE_WIN && !UNITY_EDITOR) || UNITY_EDITOR_WIN
settings.uMaxSystemAudioObjects = MaxSystemAudioObjects;
#endif
}
}
[UnityEngine.HideInInspector]
public AkCommonUserSettings UserSettings;
[UnityEngine.HideInInspector]
public PlatformAdvancedSettings AdvancedSettings;
[UnityEngine.HideInInspector]
public AkCommonCommSettings CommsSettings;
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 60c68bd91426f234c9ccc932c90b9ddf