• UnityDOTS备忘


    Unity DOTS中创建一个AssetBundle并将其用作Entity

    1. 创建一个新的Unity项目,并确保已启用DOTS功能。

    2. 创建一个AssetBundle,可以通过在Project视图中右键单击文件夹并选择“Create > AssetBundle”来创建。

    3. 将您想要转换为Entity的资源(例如模型、纹理等)拖放到AssetBundle中。

    4. 创建一个新的C#脚本,用于加载AssetBundle并将其转换为Entity。以下是一个示例代码:

    System间的数

    using Unity.Entities;
    using Unity.Transforms;
    using Unity.Rendering;
    using UnityEngine;
    using Unity.Mathematics;

    public class AssetBundleToEntity : MonoBehaviour
    {
        public GameObject prefab;
        public Material material;

        void Start()
        {
            var entityManager = World.DefaultGameObjectInjectionWorld.EntityManager;

            var entityPrefab = GameObjectConversionUtility.ConvertGameObjectHierarchy(prefab, World.Active);

            Entity entity = entityManager.Instantiate(entityPrefab);

            entityManager.AddComponentData(entity, new Translation { Value = new float3(0, 0, 0) });

            entityManager.AddSharedComponentData(entity, new RenderMesh
            {
                material = material,
                mesh = entityManager.GetSharedComponentData(entityPrefab).mesh
            });
        }
    }

    据传递

    动态加载代码

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEngine;
    using Unity.Entities;
    using Unity.Transforms;
    using Unity.Rendering;
    using Unity.Mathematics;

    public class DynamicAssetBundleLoading : MonoBehaviour
    {
        public string assetBundlePath;
        public string assetName;
        public Material material;

        IEnumerator Start()
        {
            AssetBundleCreateRequest request = AssetBundle.LoadFromFileAsync(assetBundlePath);
            yield return request;

            AssetBundle assetBundle = request.assetBundle;

            AssetBundleRequest assetRequest = assetBundle.LoadAssetAsync(assetName);
            yield return assetRequest;

            GameObject prefab = assetRequest.asset as GameObject;

            var entityManager = World.DefaultGameObjectInjectionWorld.EntityManager;

            var entityPrefab = GameObjectConversionUtility.ConvertGameObjectHierarchy(prefab, World.Active);

            Entity entity = entityManager.Instantiate(entityPrefab);

            entityManager.AddComponentData(entity, new Translation { Value = new float3(0, 0, 0) });

            entityManager.AddSharedComponentData(entity, new RenderMesh
            {
                material = material,
                mesh = entityManager.GetSharedComponentData(entityPrefab).mesh
            });

            assetBundle.Unload(false);
        }
    }

    释放Entity

    using Unity.Entities;
    using Unity.Transforms;
    using Unity.Rendering;
    using UnityEngine;

    public class ReleaseEntity : MonoBehaviour
    {
        EntityManager entityManager;

        void Start()
        {
            entityManager = World.DefaultGameObjectInjectionWorld.EntityManager;

            // 创建Entity
            Entity entity = entityManager.CreateEntity();

            // 添加组件数据
            entityManager.AddComponentData(entity, new Translation { Value = new float3(0, 0, 0) });

            // 添加SharedComponent数据
            entityManager.AddSharedComponentData(entity, new RenderMesh
            {
                material = GetComponent().material,
                mesh = GetComponent().sharedMesh
            });
        }

        void OnDestroy()
        {
            // 释放Entity
            entityManager.DestroyEntity(entity);

            // 释放相关的GameObject和AssetBundle引用
            Destroy(gameObject);
            Resources.UnloadUnusedAssets();
        }
    }

    System以MonoBehaviour数据事件通知

    在Unity的Data-Oriented Technology Stack (DOTS)中,如果您希望在ECS系统中的Job执行完毕后通知MonoBehaviour或外部代码,可以使用Unity的Events系统或自定义事件系统来实现通信。以下是一种常见的方法:

    1. 使用Unity的Events系统:
      • 在MonoBehaviour中定义一个事件,当事件被触发时通知外部代码。
      • 在ECS系统中,创建一个System,在System中检查Job是否执行完毕,并在适当的时机触发MonoBehaviour中定义的事件。
      • using Unity.Entities;
        using UnityEngine;
        using UnityEngine.Events;

        public class JobCompletedEvent : MonoBehaviour
        {
            public UnityEvent onJobCompleted;

            public void TriggerJobCompletedEvent()
            {
                onJobCompleted.Invoke();
            }
        }

        public class JobCompletionSystem : ComponentSystem
        {
            protected override void OnUpdate()
            {
                // 检查Job是否执行完毕
                if (jobCompleted)
                {
                    // 获取JobCompletedEvent组件
                    JobCompletedEvent jobCompletedEvent = FindObjectOfType();

                    // 触发事件通知外部代码
                    jobCompletedEvent?.TriggerJobCompletedEvent();
                }
            }
        }

      • 自定义事件系统:
        • 创建一个自定义的事件系统,允许ECS系统和MonoBehaviour之间进行通信。
        • 在ECS系统中,触发自定义事件来通知MonoBehaviour或外部代码。
        • using Unity.Entities;
          using UnityEngine;

          public class CustomEventSystem : ComponentSystem
          {
              public delegate void JobCompletedEventHandler();
              public static event JobCompletedEventHandler OnJobCompleted;

              protected override void OnUpdate()
              {
                  // 检查Job是否执行完毕
                  if (jobCompleted)
                  {
                      // 触发自定义事件通知外部代码
                      OnJobCompleted?.Invoke();
                  }
              }
          }

    2. IBufferElementData

      要将DynamicBuffer与Entity关联,我们只需要定义需要的IBufferElementData,而不是DynamicBuffer本身,使用GenerateAuthoringComponent属性会自动帮我们生成DynamicBuffer并添加到Entity上,这里需要注意一下,下面定义一个简单的IBufferElementData看一下吧:

      1. using Unity.Entities;
      2. [GenerateAuthoringComponent]
      3. public struct IntBufferElement : IBufferElementData
      4. {
      5. public int Value;
      6. }

     添加与释放

    1. EntityManager.AddComponent<IntBufferElement>(yourEntity);
    2. EntityManager.RemoveComponent<IntBufferElement>(yourEntity);
  • 相关阅读:
    Linux- POSIX共享内存对象
    Ubuntu搭建团队文档协作在线平台
    【2021集创赛】Arm杯二等奖-基于Arm核的智慧病房手势识别方案
    网课、会议投屏自动截屏软件推荐 —— 使用定时自动截屏软件,自动截屏网课、会议投屏,方便回顾、整理
    Moka人事:实现无代码开发的API连接,打通电商平台与用户运营系统
    G1D21-作业-AttacKG&SVM&kg_book&偷懒哈哈哈
    JVM调优
    刷题日记【第十二篇】-笔试必刷题【洗牌+MP3光标位置+年终奖+迷宫问题】
    项目日历是什么?如何规划?
    秋招校招,什么是群面?
  • 原文地址:https://blog.csdn.net/wanzhihui0000/article/details/138040000