feat: support asset bundle
This commit is contained in:
@@ -59,3 +59,6 @@ crashlytics-build.properties
|
|||||||
# Temporary auto-generated Android Assets
|
# Temporary auto-generated Android Assets
|
||||||
/Assets/StreamingAssets/aa.meta
|
/Assets/StreamingAssets/aa.meta
|
||||||
/Assets/StreamingAssets/aa/*
|
/Assets/StreamingAssets/aa/*
|
||||||
|
|
||||||
|
/Assets/StreamingAssets/
|
||||||
|
/Assets/StreamingAssets.meta
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
fileFormatVersion: 2
|
fileFormatVersion: 2
|
||||||
guid: ad7387f41068f465fbabd034439fbd89
|
guid: ad7387f41068f465fbabd034439fbd89
|
||||||
|
labels:
|
||||||
|
- Audio
|
||||||
folderAsset: yes
|
folderAsset: yes
|
||||||
DefaultImporter:
|
DefaultImporter:
|
||||||
externalObjects: {}
|
externalObjects: {}
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
fileFormatVersion: 2
|
fileFormatVersion: 2
|
||||||
guid: 07dda0761dca5405ebf092d473b8e0e3
|
guid: 07dda0761dca5405ebf092d473b8e0e3
|
||||||
|
labels:
|
||||||
|
- Audio
|
||||||
folderAsset: yes
|
folderAsset: yes
|
||||||
DefaultImporter:
|
DefaultImporter:
|
||||||
externalObjects: {}
|
externalObjects: {}
|
||||||
|
|||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 0d356a0e07bd4566b4e303a87d7e3545
|
||||||
|
timeCreated: 1778817283
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
using System;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
|
namespace OCES
|
||||||
|
{
|
||||||
|
public class AssetBundleAssetProvider : IAssetProvider
|
||||||
|
{
|
||||||
|
readonly AssetBundle m_assetBundle;
|
||||||
|
|
||||||
|
public AssetBundleAssetProvider(string bundleFilePath)
|
||||||
|
{
|
||||||
|
this.m_assetBundle = AssetBundle.LoadFromFile(bundleFilePath);
|
||||||
|
if (this.m_assetBundle is null)
|
||||||
|
{
|
||||||
|
Debug.LogError($"[OCES] 无法加载: {bundleFilePath}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public T Load<T>(string path) where T : UnityEngine.Object
|
||||||
|
{
|
||||||
|
return this.m_assetBundle.LoadAsset<T>(path);
|
||||||
|
}
|
||||||
|
public ResourceRequest LoadAsync<T>(string path) where T : UnityEngine.Object
|
||||||
|
{
|
||||||
|
return this.m_assetBundle.LoadAssetAsync<T>(path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 12e6fce897c74d9fbb347666d13123d1
|
||||||
|
timeCreated: 1778817328
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 94c95f233df548289406144c77e05d0b
|
||||||
|
timeCreated: 1778828249
|
||||||
@@ -0,0 +1,107 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using UnityEngine;
|
||||||
|
using UnityEditor;
|
||||||
|
|
||||||
|
namespace OCES.Editor
|
||||||
|
{
|
||||||
|
public static class AssetBundleBuilder
|
||||||
|
{
|
||||||
|
static string BuildBundle(string bundleName, string outputDir, BuildTarget buildTarget, params string[] sourceDirs)
|
||||||
|
{
|
||||||
|
// 1. 收集所有文件(递归)
|
||||||
|
List<string> assetNames = new();
|
||||||
|
List<string> addressableNames = new();
|
||||||
|
|
||||||
|
foreach (string dir in sourceDirs)
|
||||||
|
{
|
||||||
|
if (!Directory.Exists(dir))
|
||||||
|
{
|
||||||
|
Debug.LogWarning($"[AssetBundleBuilder] 目录不存在,跳过: {dir}");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
string[] files = Directory.GetFiles(dir, "*.*", SearchOption.AllDirectories);
|
||||||
|
foreach (string file in files)
|
||||||
|
{
|
||||||
|
if (file.EndsWith(".meta")) continue;
|
||||||
|
if (file.EndsWith(".DS_Store")) continue;
|
||||||
|
if (file.StartsWith("._")) continue;
|
||||||
|
if (file.EndsWith(".pkf")) continue;
|
||||||
|
|
||||||
|
string assetPath = file.Replace("\\", "/");
|
||||||
|
assetNames.Add(assetPath);
|
||||||
|
|
||||||
|
string relative = assetPath.Replace("Assets/Resources/", "");
|
||||||
|
string withoutExt = Path.ChangeExtension(relative, null);
|
||||||
|
addressableNames.Add(withoutExt);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (assetNames.Count == 0)
|
||||||
|
{
|
||||||
|
return $"[AssetBundleBuilder] {bundleName}: 无文件";
|
||||||
|
}
|
||||||
|
Directory.CreateDirectory(outputDir);
|
||||||
|
|
||||||
|
// 2. 构建
|
||||||
|
AssetBundleBuild build = new()
|
||||||
|
{
|
||||||
|
assetBundleName = bundleName + ".ab",
|
||||||
|
assetNames = assetNames.ToArray(),
|
||||||
|
addressableNames = addressableNames.ToArray()
|
||||||
|
};
|
||||||
|
|
||||||
|
AssetBundleManifest manifest = BuildPipeline.BuildAssetBundles(
|
||||||
|
outputDir,
|
||||||
|
new[] { build },
|
||||||
|
BuildAssetBundleOptions.None,
|
||||||
|
buildTarget);
|
||||||
|
|
||||||
|
return !manifest ? $"[{bundleName}.ab] 构建失败"
|
||||||
|
: $"[AssetBundleBuilder] {bundleName}.ab 构建完成,包含 {assetNames.Count} 个资源";
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
internal static string BuildBundles(
|
||||||
|
bool buildAudio, string audioBundlePath,
|
||||||
|
bool buildHaptic, string hapticBundlePath,
|
||||||
|
BuildTarget buildTarget)
|
||||||
|
{
|
||||||
|
string log = "";
|
||||||
|
|
||||||
|
if (buildAudio)
|
||||||
|
log += BuildBundleFromPath(audioBundlePath, buildTarget,
|
||||||
|
"Assets/Resources/Audios",
|
||||||
|
"Assets/Resources/AudioData") + "\n";
|
||||||
|
|
||||||
|
if (buildHaptic)
|
||||||
|
log += BuildBundleFromPath(hapticBundlePath, buildTarget,
|
||||||
|
"Assets/Resources/Haptics",
|
||||||
|
"Assets/Resources/HapticData") + "\n";
|
||||||
|
|
||||||
|
AssetDatabase.Refresh();
|
||||||
|
return log.TrimEnd('\n');
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 根据配置中的相对路径构建单个 Bundle。
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="relativePath">配置中的路径,如 "Bundles/audios.ab"</param>
|
||||||
|
/// <param name="target"></param>
|
||||||
|
/// <param name="sourceDirs"></param>
|
||||||
|
public static string BuildBundleFromPath(
|
||||||
|
string relativePath, BuildTarget target, params string[] sourceDirs)
|
||||||
|
{
|
||||||
|
// 解析路径 → 输出目录 + Bundle 名
|
||||||
|
string fullPath = Path.Combine(Application.streamingAssetsPath, relativePath);
|
||||||
|
string outputDir = Path.GetDirectoryName(fullPath);
|
||||||
|
string bundleName = Path.GetFileNameWithoutExtension(fullPath);
|
||||||
|
|
||||||
|
return string.IsNullOrEmpty(bundleName)
|
||||||
|
? $"[AssetBundleBuilder] 无效路径: {relativePath}"
|
||||||
|
: BuildBundle(bundleName, outputDir, target, sourceDirs);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: c370f95cedb246969a5831a5bda067c2
|
||||||
|
timeCreated: 1778828259
|
||||||
@@ -0,0 +1,131 @@
|
|||||||
|
using System.Linq;
|
||||||
|
using OCES.Audio;
|
||||||
|
using OCES.Haptic;
|
||||||
|
using UnityEngine;
|
||||||
|
using UnityEditor;
|
||||||
|
|
||||||
|
namespace OCES.Editor
|
||||||
|
{
|
||||||
|
public class AssetBundleBuilderWindow : EditorWindow
|
||||||
|
{
|
||||||
|
bool m_buildAudio = true;
|
||||||
|
bool m_buildHaptic = true;
|
||||||
|
int m_targetIndex;
|
||||||
|
string m_audioBundleSourcePath;
|
||||||
|
string m_hapticBundleSourcePath;
|
||||||
|
|
||||||
|
string m_log = "";
|
||||||
|
Vector2 m_scrollPos;
|
||||||
|
|
||||||
|
// Settings 资源路径
|
||||||
|
const string k_audioSettingsPath = "Assets/Settings/AudioExtendSettings.asset";
|
||||||
|
const string k_hapticSettingsPath = "Assets/Settings/HapticSettings.asset";
|
||||||
|
|
||||||
|
static readonly (BuildTarget target, string label)[] s_platforms =
|
||||||
|
{
|
||||||
|
(BuildTarget.Android, "Android"),
|
||||||
|
(BuildTarget.iOS, "iOS"),
|
||||||
|
(BuildTarget.StandaloneOSX, "macOS"),
|
||||||
|
(BuildTarget.StandaloneWindows64, "Windows (x64)"),
|
||||||
|
(BuildTarget.StandaloneLinux64, "Linux (x64)"),
|
||||||
|
};
|
||||||
|
|
||||||
|
static readonly string[] s_platformLabels = s_platforms.Select(p => p.label).ToArray();
|
||||||
|
|
||||||
|
[MenuItem("Tools/OCES/Asset Bundle Builder")]
|
||||||
|
public static void ShowWindow()
|
||||||
|
{
|
||||||
|
AssetBundleBuilderWindow window = GetWindow<AssetBundleBuilderWindow>(
|
||||||
|
false, "Bundle Builder", true);
|
||||||
|
window.minSize = new Vector2(360, 400);
|
||||||
|
window.Show();
|
||||||
|
}
|
||||||
|
|
||||||
|
void OnEnable()
|
||||||
|
{
|
||||||
|
// 默认选中当前 Player 平台
|
||||||
|
BuildTarget current = EditorUserBuildSettings.activeBuildTarget;
|
||||||
|
for (int i = 0; i < s_platforms.Length; i++)
|
||||||
|
{
|
||||||
|
if (s_platforms[i].target != current)
|
||||||
|
continue;
|
||||||
|
this.m_targetIndex = i;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 兜底:Android
|
||||||
|
this.m_targetIndex = 13;
|
||||||
|
}
|
||||||
|
|
||||||
|
void OnGUI()
|
||||||
|
{
|
||||||
|
GUILayout.Space(10);
|
||||||
|
|
||||||
|
// ── Bundle 选择 ──
|
||||||
|
EditorGUILayout.LabelField("Bundles to Build", EditorStyles.boldLabel);
|
||||||
|
this.m_buildAudio = EditorGUILayout.ToggleLeft("Audio Bundle (audios.ab)", this.m_buildAudio);
|
||||||
|
this.m_buildHaptic = EditorGUILayout.ToggleLeft("Haptic Bundle (haptic.ab)", this.m_buildHaptic);
|
||||||
|
|
||||||
|
GUILayout.Space(10);
|
||||||
|
|
||||||
|
// ── 平台选择 ──
|
||||||
|
EditorGUILayout.LabelField("Target Platform", EditorStyles.boldLabel);
|
||||||
|
this.m_targetIndex = EditorGUILayout.Popup(this.m_targetIndex, s_platformLabels);
|
||||||
|
|
||||||
|
// ── 输出路径预览 ──
|
||||||
|
AudioExtendSettings audioSettings =
|
||||||
|
AssetDatabase.LoadAssetAtPath<AudioExtendSettings>(k_audioSettingsPath);
|
||||||
|
HapticSettings hapticSettings =
|
||||||
|
AssetDatabase.LoadAssetAtPath<HapticSettings>(k_hapticSettingsPath);
|
||||||
|
|
||||||
|
if (audioSettings && this.m_buildAudio)
|
||||||
|
EditorGUILayout.LabelField(
|
||||||
|
$" Audio → {Application.streamingAssetsPath}/{audioSettings.audioBundlePath}",
|
||||||
|
EditorStyles.miniLabel);
|
||||||
|
|
||||||
|
if (hapticSettings && this.m_buildHaptic)
|
||||||
|
EditorGUILayout.LabelField(
|
||||||
|
$" Haptic → {Application.streamingAssetsPath}/{hapticSettings.hapticBundlePath}",
|
||||||
|
EditorStyles.miniLabel);
|
||||||
|
|
||||||
|
if (!audioSettings && !hapticSettings)
|
||||||
|
EditorGUILayout.HelpBox(
|
||||||
|
$"未找到 Settings 资产。\n 请初始化对应系统。",
|
||||||
|
MessageType.Warning);
|
||||||
|
|
||||||
|
GUILayout.Space(10);
|
||||||
|
|
||||||
|
// ── 构建按钮 ──
|
||||||
|
bool canBuild = (this.m_buildAudio || this.m_buildHaptic)
|
||||||
|
&& (audioSettings || !this.m_buildAudio)
|
||||||
|
&& (hapticSettings || !this.m_buildHaptic);
|
||||||
|
|
||||||
|
EditorGUI.BeginDisabledGroup(!canBuild);
|
||||||
|
if (GUILayout.Button("Build", GUILayout.Height(32)))
|
||||||
|
{
|
||||||
|
string result = AssetBundleBuilder.BuildBundles(this.m_buildAudio,
|
||||||
|
audioSettings ? audioSettings.audioBundlePath : "", this.m_buildHaptic,
|
||||||
|
hapticSettings != null ? hapticSettings.hapticBundlePath : "",
|
||||||
|
s_platforms[this.m_targetIndex].target);
|
||||||
|
this.m_log += result + "\n";
|
||||||
|
}
|
||||||
|
EditorGUI.EndDisabledGroup();
|
||||||
|
|
||||||
|
GUILayout.Space(10);
|
||||||
|
|
||||||
|
// ── 日志区 ──
|
||||||
|
EditorGUILayout.LabelField("Build Log", EditorStyles.boldLabel);
|
||||||
|
this.m_scrollPos = EditorGUILayout.BeginScrollView(this.m_scrollPos,
|
||||||
|
GUILayout.ExpandHeight(true));
|
||||||
|
EditorGUILayout.TextArea(this.m_log,
|
||||||
|
GUILayout.ExpandHeight(true));
|
||||||
|
EditorGUILayout.EndScrollView();
|
||||||
|
|
||||||
|
// 底部清空日志按钮
|
||||||
|
if (string.IsNullOrEmpty(this.m_log))
|
||||||
|
return;
|
||||||
|
GUILayout.Space(4);
|
||||||
|
if (GUILayout.Button("Clear Log", GUILayout.Width(80)))
|
||||||
|
this.m_log = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: f327fedaa18441e2bf347cf46810592d
|
||||||
|
timeCreated: 1778829708
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
using System;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
|
namespace OCES
|
||||||
|
{
|
||||||
|
public interface IAssetProvider
|
||||||
|
{
|
||||||
|
T Load<T>(string path) where T : UnityEngine.Object;
|
||||||
|
ResourceRequest LoadAsync<T>(string path) where T : UnityEngine.Object;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 35a140a1c75444b49ad470726512b817
|
||||||
|
timeCreated: 1778815286
|
||||||
+29
-2
@@ -2,6 +2,7 @@ using System;
|
|||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using JetBrains.Annotations;
|
using JetBrains.Annotations;
|
||||||
|
using OCES.Audio;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
using Object = UnityEngine.Object;
|
using Object = UnityEngine.Object;
|
||||||
|
|
||||||
@@ -11,6 +12,12 @@ namespace OCES
|
|||||||
{
|
{
|
||||||
readonly Dictionary<string, Object> m_cachedObjects = new();
|
readonly Dictionary<string, Object> m_cachedObjects = new();
|
||||||
readonly Dictionary<string, List<Action<Object>>> m_pendingCallbacks = new();
|
readonly Dictionary<string, List<Action<Object>>> m_pendingCallbacks = new();
|
||||||
|
IAssetProvider m_assetProvider;
|
||||||
|
|
||||||
|
public void SetProvider(IAssetProvider assetProvider)
|
||||||
|
{
|
||||||
|
this.m_assetProvider = assetProvider;
|
||||||
|
}
|
||||||
|
|
||||||
[CanBeNull]
|
[CanBeNull]
|
||||||
internal T LoadSync<T>(string path) where T : Object
|
internal T LoadSync<T>(string path) where T : Object
|
||||||
@@ -19,8 +26,18 @@ namespace OCES
|
|||||||
{
|
{
|
||||||
return cachedObject as T;
|
return cachedObject as T;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
T newObject;
|
||||||
|
if (this.m_assetProvider is not null)
|
||||||
|
{
|
||||||
|
newObject = this.m_assetProvider.Load<T>(path);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
newObject = Resources.Load<T>(path);
|
||||||
|
Debug.LogWarning($"[ResourceLoader] No IAssetProvider set, falling back to Resources.Load for '{path}'");
|
||||||
|
}
|
||||||
|
|
||||||
T newObject = Resources.Load<T>(path);
|
|
||||||
this.m_cachedObjects.Add(path, newObject);
|
this.m_cachedObjects.Add(path, newObject);
|
||||||
return newObject;
|
return newObject;
|
||||||
}
|
}
|
||||||
@@ -40,7 +57,17 @@ namespace OCES
|
|||||||
}
|
}
|
||||||
|
|
||||||
this.m_pendingCallbacks[path] = new List<Action<Object>> { obj => onComplete?.Invoke(obj as T) };
|
this.m_pendingCallbacks[path] = new List<Action<Object>> { obj => onComplete?.Invoke(obj as T) };
|
||||||
ResourceRequest newRequest = Resources.LoadAsync<T>(path);
|
ResourceRequest newRequest;
|
||||||
|
if (this.m_assetProvider is not null)
|
||||||
|
{
|
||||||
|
newRequest = this.m_assetProvider.LoadAsync<T>(path);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
newRequest = Resources.LoadAsync<T>(path);
|
||||||
|
Debug.LogWarning($"[ResourceLoader] No IAssetProvider set, falling back to Resources.Load for '{path}'");
|
||||||
|
}
|
||||||
|
|
||||||
StartCoroutine(HandleAsyncLoadCompletion(path, newRequest));
|
StartCoroutine(HandleAsyncLoadCompletion(path, newRequest));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
using System;
|
||||||
|
using UnityEngine;
|
||||||
|
|
||||||
|
namespace OCES
|
||||||
|
{
|
||||||
|
public class ResourcesAssetProvider : IAssetProvider
|
||||||
|
{
|
||||||
|
public T Load<T>(string path) where T : UnityEngine.Object
|
||||||
|
{
|
||||||
|
return Resources.Load<T>(path);
|
||||||
|
}
|
||||||
|
public ResourceRequest LoadAsync<T>(string path) where T : UnityEngine.Object
|
||||||
|
{
|
||||||
|
return Resources.LoadAsync<T>(path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,3 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: e5c672cc770b4032bfcd888f36766b45
|
||||||
|
timeCreated: 1778817303
|
||||||
@@ -12,7 +12,7 @@ namespace OCES.Audio
|
|||||||
public class AudioExtendSettings : ScriptableObject
|
public class AudioExtendSettings : ScriptableObject
|
||||||
{
|
{
|
||||||
// ========== Resource Paths ==========
|
// ========== Resource Paths ==========
|
||||||
[Header("Resource Paths")]
|
[Header("Resources")]
|
||||||
[Tooltip("Resources 子目录:音频配置文件(.bytes)")]
|
[Tooltip("Resources 子目录:音频配置文件(.bytes)")]
|
||||||
public string audioConfigPath = "AudioData";
|
public string audioConfigPath = "AudioData";
|
||||||
|
|
||||||
@@ -22,6 +22,9 @@ namespace OCES.Audio
|
|||||||
[Tooltip("Resources 路径:AudioMixer 资产")]
|
[Tooltip("Resources 路径:AudioMixer 资产")]
|
||||||
public string audioMixerPath = "Audios/Master";
|
public string audioMixerPath = "Audios/Master";
|
||||||
|
|
||||||
|
public bool useAssetBundle = false;
|
||||||
|
public string audioBundlePath = "Bundles/audios.ab";
|
||||||
|
|
||||||
// ========== AudioMixer Group Paths ==========
|
// ========== AudioMixer Group Paths ==========
|
||||||
[Header("AudioMixer Groups")]
|
[Header("AudioMixer Groups")]
|
||||||
public string sfxGroupPath = "Master/Regular/SFX";
|
public string sfxGroupPath = "Master/Regular/SFX";
|
||||||
|
|||||||
@@ -288,6 +288,17 @@ namespace OCES.Audio
|
|||||||
DontDestroyOnLoad(gameObject);
|
DontDestroyOnLoad(gameObject);
|
||||||
|
|
||||||
this.ResourceLoader = gameObject.AddComponent<ResourceLoader>();
|
this.ResourceLoader = gameObject.AddComponent<ResourceLoader>();
|
||||||
|
|
||||||
|
if (AudioExtendSettings.Instance.useAssetBundle)
|
||||||
|
{
|
||||||
|
string bundlePath = Path.Combine(Application.streamingAssetsPath,
|
||||||
|
AudioExtendSettings.Instance.audioBundlePath);
|
||||||
|
this.ResourceLoader.SetProvider(new AssetBundleAssetProvider(bundlePath));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this.ResourceLoader.SetProvider(new ResourcesAssetProvider());
|
||||||
|
}
|
||||||
|
|
||||||
string audioConfigPath = AudioExtendSettings.Instance.audioConfigPath;
|
string audioConfigPath = AudioExtendSettings.Instance.audioConfigPath;
|
||||||
|
|
||||||
@@ -388,8 +399,6 @@ namespace OCES.Audio
|
|||||||
AudioObject childContainer = this.m_audioObjects.GetMappingResult(switchContainer.Id, currentStateValue);
|
AudioObject childContainer = this.m_audioObjects.GetMappingResult(switchContainer.Id, currentStateValue);
|
||||||
return childContainer ?? this.m_audioObjects.GetDefaultSwitchOrFallback(switchContainer);
|
return childContainer ?? this.m_audioObjects.GetDefaultSwitchOrFallback(switchContainer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class AudioConfigLoader
|
public static class AudioConfigLoader
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ namespace OCES.Audio.Editor
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
[MenuItem("Tools/Audio/Create AudioExtendSettings Asset")]
|
[MenuItem("Tools/OCES/Audio/Create AudioExtendSettings Asset")]
|
||||||
static void CreateDefaultAsset()
|
static void CreateDefaultAsset()
|
||||||
{
|
{
|
||||||
if (!AssetDatabase.IsValidFolder("Assets/Settings"))
|
if (!AssetDatabase.IsValidFolder("Assets/Settings"))
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ namespace OCES.Audio
|
|||||||
get { return Path.Combine(Application.dataPath, "Resources", AudioExtendSettings.Instance.audioConfigPath); }
|
get { return Path.Combine(Application.dataPath, "Resources", AudioExtendSettings.Instance.audioConfigPath); }
|
||||||
}
|
}
|
||||||
|
|
||||||
[MenuItem("Tools/Audio/Apply Audio Import Settings")]
|
[MenuItem("Tools/OCES/Audio/Apply Audio Import Settings")]
|
||||||
public static void RunFromMenu()
|
public static void RunFromMenu()
|
||||||
{
|
{
|
||||||
if (EditorUtility.DisplayDialog(
|
if (EditorUtility.DisplayDialog(
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ namespace OCES.Haptic.Editor
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
[MenuItem("Tools/Haptic/Create Haptic Settings Asset")]
|
[MenuItem("Tools/OCES/Haptic/Create Haptic Settings Asset")]
|
||||||
static void CreateDefaultAsset()
|
static void CreateDefaultAsset()
|
||||||
{
|
{
|
||||||
if (!AssetDatabase.IsValidFolder("Assets/Settings"))
|
if (!AssetDatabase.IsValidFolder("Assets/Settings"))
|
||||||
|
|||||||
@@ -15,6 +15,9 @@ namespace OCES.Haptic
|
|||||||
[Tooltip("Resources 子目录:触感资源文件(.haptic)")]
|
[Tooltip("Resources 子目录:触感资源文件(.haptic)")]
|
||||||
public string hapticResourcePath = "Haptics/";
|
public string hapticResourcePath = "Haptics/";
|
||||||
|
|
||||||
|
public bool useAssetBundle = false;
|
||||||
|
public string hapticBundlePath = "Bundles/haptics.ab";
|
||||||
|
|
||||||
public static HapticSettings Instance { get; internal set; }
|
public static HapticSettings Instance { get; internal set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
using Lofelt.NiceVibrations;
|
using Lofelt.NiceVibrations;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
|
|
||||||
@@ -117,6 +118,16 @@ namespace OCES.Haptic
|
|||||||
DontDestroyOnLoad(gameObject);
|
DontDestroyOnLoad(gameObject);
|
||||||
|
|
||||||
this.ResourceLoader = gameObject.AddComponent<ResourceLoader>();
|
this.ResourceLoader = gameObject.AddComponent<ResourceLoader>();
|
||||||
|
if (HapticSettings.Instance.useAssetBundle)
|
||||||
|
{
|
||||||
|
string bundlePath = Path.Combine(Application.streamingAssetsPath,
|
||||||
|
HapticSettings.Instance.hapticBundlePath);
|
||||||
|
this.ResourceLoader.SetProvider(new AssetBundleAssetProvider(bundlePath));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this.ResourceLoader.SetProvider(new ResourcesAssetProvider());
|
||||||
|
}
|
||||||
|
|
||||||
this.m_hapticObjects = HapticConfigLoader.Load<HapticObjectConfig>(HapticSettings.Instance.hapticConfigPath + "HapticObject");
|
this.m_hapticObjects = HapticConfigLoader.Load<HapticObjectConfig>(HapticSettings.Instance.hapticConfigPath + "HapticObject");
|
||||||
this.IsHapticSupported = DeviceCapabilities.isVersionSupported;
|
this.IsHapticSupported = DeviceCapabilities.isVersionSupported;
|
||||||
|
|||||||
@@ -15,6 +15,8 @@ MonoBehaviour:
|
|||||||
audioConfigPath: AudioData
|
audioConfigPath: AudioData
|
||||||
audioResourcePath: Audios
|
audioResourcePath: Audios
|
||||||
audioMixerPath: Audios/Master
|
audioMixerPath: Audios/Master
|
||||||
|
useAssetBundle: 1
|
||||||
|
audioBundlePath: Bundles/audios.ab
|
||||||
sfxGroupPath: Master/Regular/SFX
|
sfxGroupPath: Master/Regular/SFX
|
||||||
voiceGroupPath: Master/Regular/Voice
|
voiceGroupPath: Master/Regular/Voice
|
||||||
accentSfxGroupPath: Master/SFX_Accent
|
accentSfxGroupPath: Master/SFX_Accent
|
||||||
|
|||||||
@@ -14,3 +14,5 @@ MonoBehaviour:
|
|||||||
m_EditorClassIdentifier:
|
m_EditorClassIdentifier:
|
||||||
hapticConfigPath: HapticData/
|
hapticConfigPath: HapticData/
|
||||||
hapticResourcePath: Haptics/
|
hapticResourcePath: Haptics/
|
||||||
|
useAssetBundle: 0
|
||||||
|
hapticBundlePath: Bundles/haptics.ab
|
||||||
|
|||||||
@@ -0,0 +1,3 @@
|
|||||||
|
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
|
||||||
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=lofelt/@EntryIndexedValue">True</s:Boolean></wpf:ResourceDictionary>
|
||||||
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Lofelt/@EntryIndexedValue">True</s:Boolean></wpf:ResourceDictionary>
|
||||||
Reference in New Issue
Block a user