Example #1
0
        private static unsafe void SubmitEntitiesWindow(EntityAdmin admin, Dictionary <Entity, List <int> > entityToComponentGroups)
        {
            ImGui.Begin("Entities and Components");

            bool createEntity = SubmitAddComponent("Create Entity", out Type componentType);

            Entity entityToDestroy = SelectedEntityComponent as Entity;
            bool   disabled        = entityToDestroy == null;

            if (disabled)
            {
                Util.ImGuiUtil.BeginDisable();
            }
            if (ImGui.Button("Destroy Entity") && !disabled)
            {
                admin.DestroyEntity(entityToDestroy);
            }
            if (disabled)
            {
                Util.ImGuiUtil.EndDisable();
            }

            ImGui.Separator();
            ImGui.BeginChild("scrolling", Vector2.Zero, false, ImGuiWindowFlags.HorizontalScrollbar);

            var entities = EntityAdminUtil.GetEntities(admin);

            foreach (var entity in entities)
            {
                var components = entity.Components;

                ImGuiTreeNodeFlags nodeFlags = ImGuiTreeNodeFlags.OpenOnArrow | ImGuiTreeNodeFlags.OpenOnDoubleClick | ImGuiTreeNodeFlags.SpanAvailWidth; // OpenOnDoubleClick doesn't seem to work. Not sure why.
                if (entity.Components.Count == 0)
                {
                    nodeFlags |= ImGuiTreeNodeFlags.Leaf;
                }
                if (entity == SelectedEntityComponent)
                {
                    nodeFlags |= ImGuiTreeNodeFlags.Selected;
                    if (scrollEntitiesView)
                    {
                        ImGui.SetScrollHereY();
                    }
                }

                if (entity.HasComponent <DontDestroyOnClear>(true))
                {
                    ImGui.PushFont(ImGuiController.BoldFont);
                }
                if (!entity.IsActive)
                {
                    ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(0.5f, 0.5f, 0.5f, 1f));
                }
                bool errorInEntity = false;
                for (int i = 0; i < components.Count; i++)
                {
                    if (!RequiresSystem.HasECSSystemForType(components[i].GetType(), HostHelper.GameSystems, out _))
                    {
                        errorInEntity = true;
                    }
                    if (components[i] == SelectedEntityComponent)
                    {
                        ImGui.SetNextItemOpen(true);
                    }
                }
                string componentGroupsText = string.Empty;
                if (entityToComponentGroups.ContainsKey(entity))
                {
                    foreach (int groupNum in entityToComponentGroups[entity])
                    {
                        componentGroupsText = $"({groupNum}){componentGroupsText}";
                    }
                    if (entityToComponentGroups[entity].Count() > 1)
                    {
                        errorInEntity = true;
                    }
                }
                if (errorInEntity)
                {
                    ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(1f, 0f, 0f, 1f));
                }
                string entityTransformText = !entity.HasComponent <Transform>(true) ? "~ " : "";
                string entityLabelText     = $"{componentGroupsText}{entityTransformText}{entity.Name}";
                bool   expanded            = ImGui.TreeNodeEx(entity.Guid.ToString(), nodeFlags, entityLabelText);
                if (errorInEntity)
                {
                    ImGui.PopStyleColor();
                }
                if (!entity.IsActive)
                {
                    ImGui.PopStyleColor();
                }
                if (entity.HasComponent <DontDestroyOnClear>(true))
                {
                    ImGui.PopFont();
                }

                if (ImGui.IsItemClicked())
                {
                    SelectedEntityComponent = entity;
                    scrollSceneGraphView    = true;
                }

                if (ImGui.BeginDragDropSource())
                {
                    ImGui.SetDragDropPayload(PAYLOAD_STRING, IntPtr.Zero, 0); // Payload is needed to trigger BeginDragDropTarget()
                    draggedObject = entity;
                    ImGui.Text(entity.Name);
                    ImGui.EndDragDropSource();
                }

                if (expanded)
                {
                    for (int i = 0; i < components.Count; i++)
                    {
                        Component component = components[i];
                        nodeFlags = ImGuiTreeNodeFlags.Leaf | ImGuiTreeNodeFlags.SpanAvailWidth | ImGuiTreeNodeFlags.NoTreePushOnOpen; // This last one means that you can't do aImGui.TreePop(); or things will be messed up.
                        if (component == SelectedEntityComponent)
                        {
                            nodeFlags |= ImGuiTreeNodeFlags.Selected;
                            if (scrollEntitiesView)
                            {
                                ImGui.SetScrollHereY();
                            }
                        }
                        if (!component.IsActive)
                        {
                            ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(0.5f, 0.5f, 0.5f, 1f));
                        }
                        bool hasRequiredSystems = RequiresSystem.HasECSSystemForType(component.GetType(), HostHelper.GameSystems, out _);
                        if (!hasRequiredSystems)
                        {
                            ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(1f, 0f, 0f, 1f));
                        }
                        ImGui.TreeNodeEx(component.Guid.ToString(), nodeFlags, component.Name);
                        if (!hasRequiredSystems)
                        {
                            ImGui.PopStyleColor();
                        }
                        if (!component.IsActive)
                        {
                            ImGui.PopStyleColor();
                        }
                        if (ImGui.IsItemClicked())
                        {
                            SelectedEntityComponent = component;
                            scrollSceneGraphView    = true;
                        }
                        if (ImGui.BeginDragDropSource())
                        {
                            ImGui.SetDragDropPayload(PAYLOAD_STRING, IntPtr.Zero, 0); // Payload is needed to trigger BeginDragDropTarget()
                            draggedObject = component;
                            ImGui.Text(component.Name);
                            ImGui.EndDragDropSource();
                        }
                    }
                    ImGui.TreePop();
                }
            }

            scrollEntitiesView = false;
            if (createEntity)
            {
                var entity = admin.CreateEntity($"{componentType.Name}'s Entity");
                SelectedEntityComponent = admin.AddComponent(entity, componentType);
                scrollEntitiesView      = true; // For some reason this doesn't work half the time -_- Not sure why...
            }

            ImGui.End();
        }