赞
踩
在多次打包尝试中,不断的切换打包名称和打包类型成了一件很麻烦的事情,而且还要区分类型进行文件夹管理,于是就诞生了写一个打包工具的想法。
VisionOSSettings
成员类型 | 成员名称 | 描述 | 作用 |
---|---|---|---|
字段 | k_SettingsKey | 用于存储和检索VisionOSSettings 实例的键。 | 用于在Player设置中保存和加载配置数据。 |
字段 | k_HandTrackingUsageTooltip | 手部追踪用途描述的提示信息。 | 用于在请求手部追踪授权时向用户展示的描述信息。 |
字段 | k_WorldSensingUsageTooltip | 世界感知用途描述的提示信息。 | 用于在请求世界感知授权时向用户展示的描述信息。 |
枚举 | AppMode | 定义应用程序的模式:虚拟现实(VR )、混合现实(MR )或窗口化(Windowed )。 | 用于设置应用程序的初始模式。 |
字段 | m_AppMode | 应用程序的初始模式。 | 用于获取或设置应用程序的初始模式。 |
字段 | m_HandsTrackingUsageDescription | 手部追踪用途的描述。 | 用于提供手部追踪用途的描述,将添加到生成的visionOS Player Xcode项目的Info.plist文件中。 |
字段 | m_WorldSensingUsageDescription | 世界感知用途的描述。 | 用于提供世界感知用途的描述,将添加到生成的visionOS Player Xcode项目的Info.plist文件中。 |
属性 | appMode | 获取或设置应用程序的模式。 | 用于获取或设置m_AppMode 字段的值。 |
属性 | handsTrackingUsageDescription | 获取或设置手部追踪用途的描述。 | 用于获取或设置m_HandsTrackingUsageDescription 字段的值。 |
属性 | worldSensingUsageDescription | 获取或设置世界感知用途的描述。 | 用于获取或设置m_WorldSensingUsageDescription 字段的值。 |
方法 | GetOrCreateSettings | 获取当前选中的设置,或者如果没有设置则创建默认设置。 | 用于获取或创建VisionOSSettings 实例。 |
属性 | currentSettings | 获取或设置用于Player构建的VisionOSSettings 。 | 用于获取或设置当前的VisionOSSettings 实例。 |
方法 | TrySelect | 尝试选择当前的VisionOSSettings 实例。 | 用于将当前的VisionOSSettings 实例设置为活动对象。 |
方法 | GetSerializedSettings | 获取VisionOSSettings 的序列化对象。 | 用于创建VisionOSSettings 实例的SerializedObject 。 |
这个文件是通过Package Manager的Add Package By Name导入com.unity.polyspatial
才会出现,文件位置是:"Assets/XR/Settings/VisionOSSettings.asset"
,。
VisionOSSettings
方法以下是读取配置文件的代码:
/// <summary>
/// 加载关于VisionOS的配置参数
/// </summary>
private void LoadSettings()
{
var configPath = "Assets/XR/Settings/VisionOSSettings.asset";
_visionOSSettings = AssetDatabase.LoadAssetAtPath<VisionOSSettings>(configPath);
}
这段代码提供了一个下拉菜单,让开发者在Unity编辑器中选择VisionOS项目的构建类型:实机(Device)或模拟器(Simulator)。选择结果会更新项目的构建设置,确保生成的应用适配目标平台。
PlayerSettings.VisionOS.sdkVersion =
(VisionOSSdkVersion)EditorGUILayout.EnumPopup(PlayerSettings.VisionOS.sdkVersion);
以及选择的版本的枚举类型:
/// <summary>
/// <para>支持的VisionOS SDK版本</para>
/// </summary>
public enum VisionOSSdkVersion
{
/// <summary>
/// <para>设备SDK</para>
/// </summary>
Device,
/// <summary>
/// <para>模拟器SDK</para>
/// </summary>
Simulator,
}
InitBuildScenes
用于初始化场景的默认列表,DrawSceneOptions
在编辑器中提供界面让用户自定义每个场景的构建配置并保存。
/// <summary> /// 初始化构建项目的参数 /// </summary> private void InitBuildScenes() { _sceneConfigs = new Dictionary<string, VisionOSSettings.AppMode>(); foreach (var editorBuildSettingsScene in EditorBuildSettings.scenes) _sceneConfigs.Add(editorBuildSettingsScene.path, VisionOSSettings.AppMode.MR); } /// <summary> /// 绘制所有场景的配置项 /// </summary> private void DrawSceneOptions() { GUILayout.Space(5f); GUILayout.Label("场景类型配置选择:"); GUILayout.BeginVertical("HelpBox"); for (int i = 0; i < EditorBuildSettings.scenes.Length; i++) { var editorBuildSetting = EditorBuildSettings.scenes[i]; GUILayout.BeginHorizontal(); GUILayout.Label(editorBuildSetting.path, GUILayout.Width(250f)); _sceneConfigs[editorBuildSetting.path] = (VisionOSSettings.AppMode)EditorGUILayout.EnumPopup(_sceneConfigs[editorBuildSetting.path]); GUILayout.EndHorizontal(); } GUILayout.EndVertical(); if (GUILayout.Button("保存配置")) SaveLocalData(); }
这段代码用于构建VisionOS项目,通过选择匹配的场景并指定输出路径。OnClickBuildVisionOSProject
触发构建流程,GetEnabledScenes
获取要包含的场景。
/// <summary> /// 点击构建VisionOS项目 /// </summary> private void OnClickBuildVisionOSProject() { _outputXcodeProject = $"{_outputPath}/{_visionOSAppMode}/{PlayerSettings.VisionOS.sdkVersion}/{DateTime.Now:yyMMddHHmm}"; if (!Directory.Exists(_outputXcodeProject)) Directory.CreateDirectory(_outputXcodeProject); var scenes = GetEnabledScenes(); if (scenes.Length == 0) _exceptionMessage = "没有满足条件的场景"; var buildXcodeProjectPath = Path.Combine(_outputXcodeProject, ""); if (!string.IsNullOrEmpty(_exceptionMessage)) return; var result = BuildPipeline.BuildPlayer(new BuildPlayerOptions { scenes = scenes, locationPathName = buildXcodeProjectPath, target = BuildTarget.VisionOS, options = BuildOptions.None }); } /// <summary> /// 获取当前已激活场景 /// </summary> /// <returns>符合当前打包模式的场景列表</returns> private string[] GetEnabledScenes() { var scenes = new List<string>(); for (var i = 0; i < EditorBuildSettings.scenes.Length; i++) { var scenePath = EditorBuildSettings.scenes[i].path; if (_sceneConfigs[scenePath] == _visionOSAppMode) scenes.Add(scenePath); } return scenes.ToArray(); }
using System; using System.Collections.Generic; using System.IO; using Newtonsoft.Json; using Unity.VisualScripting; using UnityEditor; using UnityEditor.XR.VisionOS; using UnityEngine; using UnityEngine.XR; public class VisionProBuildingWindow : EditorWindow { private VisionOSSettings _visionOSSettings; private VisionOSSettings.AppMode _visionOSAppMode; private string _outputPath, _outputXcodeProject; private Dictionary<string, VisionOSSettings.AppMode> _sceneConfigs; private string[] _editorBuildSettingsScenes; private string _exceptionMessage; [MenuItem("Window/Tools/VisionProBuildingWindow")] private static void ShowWindow() { var window = GetWindow(typeof(VisionProBuildingWindow)); window.titleContent = new GUIContent("设置VisionOS导出选项"); } private void Awake() { InitWindowData(); LoadSettings(); } private void InitWindowData() { InitLocalData(); InitOutputParams(); } private void InitOutputParams() { _outputPath = $"{Application.dataPath.Replace("/Assets", "")}/Out"; } /// <summary> /// 初始化本地存储的配置数据 /// </summary> private void InitLocalData() { var data = EditorPrefs.GetString($"{nameof(VisionProBuildingWindow)}.EnableScene"); if (string.IsNullOrEmpty(data)) InitBuildScenes(); else _sceneConfigs = JsonConvert.DeserializeObject<Dictionary<string, VisionOSSettings.AppMode>>(data); } /// <summary> /// 初始化构建项目的参数 /// </summary> private void InitBuildScenes() { _sceneConfigs = new Dictionary<string, VisionOSSettings.AppMode>(); foreach (var editorBuildSettingsScene in EditorBuildSettings.scenes) _sceneConfigs.Add(editorBuildSettingsScene.path, VisionOSSettings.AppMode.MR); } /// <summary> /// 保存本地存储的配置数据 /// </summary> private void SaveLocalData() { EditorPrefs.SetString( $"{nameof(VisionProBuildingWindow)}.EnableScene", JsonConvert.SerializeObject(_sceneConfigs)); } private void OnFocus() { InitWindowData(); } /// <summary> /// 加载关于VisionOS的配置参数 /// </summary> private void LoadSettings() { var configPath = "Assets/XR/Settings/VisionOSSettings.asset"; _visionOSSettings = AssetDatabase.LoadAssetAtPath<VisionOSSettings>(configPath); } /// <summary> /// 切换当前VisionOS打包显示类型 /// </summary> /// <param name="appMode">1=VR,2=MR,3=Windowed</param> private void SwitchVisionOSMode(VisionOSSettings.AppMode appMode) { if (_visionOSSettings == null) return; if (_visionOSSettings.appMode == appMode) return; _visionOSSettings.appMode = appMode; EditorUtility.SetDirty(_visionOSSettings); AssetDatabase.SaveAssetIfDirty(_visionOSSettings); } private void OnGUI() { DrawProjectOptions(); DrawSceneOptions(); DrawBuildOptions(); } /// <summary> /// 绘制项目的 /// </summary> private void DrawProjectOptions() { GUILayout.BeginHorizontal(); GUILayout.Label("当前选择的打包类型", GUILayout.Width(150f)); PlayerSettings.VisionOS.sdkVersion = (VisionOSSdkVersion)EditorGUILayout.EnumPopup(PlayerSettings.VisionOS.sdkVersion); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); GUILayout.Label("当前输出的打包路径", GUILayout.Width(150f)); GUILayout.Label(_outputXcodeProject); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); GUILayout.Label("当前选中的打包模式", GUILayout.Width(150f)); _visionOSAppMode = (VisionOSSettings.AppMode)EditorGUILayout.EnumPopup(_visionOSAppMode); SwitchVisionOSMode(_visionOSAppMode); GUILayout.EndHorizontal(); } /// <summary> /// 绘制所有场景的配置项 /// </summary> private void DrawSceneOptions() { GUILayout.Space(5f); GUILayout.Label("场景类型配置选择:"); GUILayout.BeginVertical("HelpBox"); for (int i = 0; i < EditorBuildSettings.scenes.Length; i++) { var editorBuildSetting = EditorBuildSettings.scenes[i]; GUILayout.BeginHorizontal(); GUILayout.Label(editorBuildSetting.path, GUILayout.Width(250f)); _sceneConfigs[editorBuildSetting.path] = (VisionOSSettings.AppMode)EditorGUILayout.EnumPopup(_sceneConfigs[editorBuildSetting.path]); GUILayout.EndHorizontal(); } GUILayout.EndVertical(); if (GUILayout.Button("保存配置")) SaveLocalData(); } /// <summary> /// 绘制Build参数选项和按钮 /// </summary> private void DrawBuildOptions() { GUILayout.Space(5f); GUILayout.BeginHorizontal(); GUILayout.FlexibleSpace(); if (GUILayout.Button("开始创建工程", GUILayout.Width(200f), GUILayout.Height(60f))) OnClickBuildVisionOSProject(); GUILayout.FlexibleSpace(); GUILayout.EndHorizontal(); if (string.IsNullOrEmpty(_exceptionMessage)) return; GUILayout.BeginHorizontal("HelpBox"); GUILayout.Label($"{_exceptionMessage}"); GUILayout.EndHorizontal(); } /// <summary> /// 点击构建VisionOS项目 /// </summary> private void OnClickBuildVisionOSProject() { _outputXcodeProject = $"{_outputPath}/{_visionOSAppMode}/{PlayerSettings.VisionOS.sdkVersion}/{DateTime.Now:yyMMddHHmm}"; if (!Directory.Exists(_outputXcodeProject)) Directory.CreateDirectory(_outputXcodeProject); var scenes = GetEnabledScenes(); if (scenes.Length == 0) _exceptionMessage = "没有满足条件的场景"; var buildXcodeProjectPath = Path.Combine(_outputXcodeProject, ""); if (!string.IsNullOrEmpty(_exceptionMessage)) return; var result = BuildPipeline.BuildPlayer(new BuildPlayerOptions { scenes = scenes, locationPathName = buildXcodeProjectPath, target = BuildTarget.VisionOS, options = BuildOptions.None }); } /// <summary> /// 获取当前已激活场景 /// </summary> /// <returns>符合当前打包模式的场景列表</returns> private string[] GetEnabledScenes() { var scenes = new List<string>(); for (var i = 0; i < EditorBuildSettings.scenes.Length; i++) { var scenePath = EditorBuildSettings.scenes[i].path; if (_sceneConfigs[scenePath] == _visionOSAppMode) scenes.Add(scenePath); } return scenes.ToArray(); } }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。