protected unsafe override void UpdateRenderState() { ImGuiNative.igGetStyle()->WindowRounding = 0; ImGuiNative.igGetStyle()->ColumnsMinSpacing = 1; var leftFrameSize = new Vector2(NativeWindow.Width - 10, NativeWindow.Height); ImGui.SetNextWindowSize(leftFrameSize, SetCondition.Always); ImGui.SetNextWindowPosCenter(SetCondition.Always); ImGui.BeginWindow("Assembly Browser Main Window", WindowFlags.NoResize | WindowFlags.NoTitleBar | WindowFlags.NoMove | WindowFlags.ShowBorders | WindowFlags.MenuBar | WindowFlags.NoScrollbar); DrawTopMenuBar(); ImGuiNative.igColumns(2, "MainLayoutColumns", true); // Left panel ImGui.BeginChildFrame (_leftFrameId, new Vector2(ImGuiNative.igGetColumnWidth(0), ImGui.GetWindowHeight() - 40), WindowFlags.ShowBorders | WindowFlags.HorizontalScrollbar); DrawAssemblyListView(); ImGui.EndChildFrame(); // Right panel ImGuiNative.igNextColumn(); Vector2 rightFrameSize = new Vector2(ImGuiNative.igGetColumnWidth(1), ImGui.GetWindowHeight() - 40); ImGui.BeginChildFrame(_rightFrameID, rightFrameSize, WindowFlags.ShowBorders | WindowFlags.HorizontalScrollbar); DrawRightFrame(rightFrameSize); ImGui.EndChildFrame(); ImGui.EndWindow(); }
private bool DrawSceneOptionLabel(string sceneName, StageCompletionInfo sci) { bool result = false; if (ImGui.BeginChildFrame((uint)sceneName.GetHashCode(), new Vector2(0, 175), WindowFlags.ShowBorders)) { if (ImGui.BeginChildFrame(0, new Vector2(150, 0), WindowFlags.Default)) { if (ImGui.Button(sceneName, new Vector2(-1, -1))) { result = true; } } ImGui.EndChildFrame(); ImGui.SameLine(); if (ImGui.BeginChildFrame(1, new Vector2(-1, -0), WindowFlags.Default)) { ImGui.Text($"Points: {sci.MaxPointsCollected} / {sci.MaxPointsPossible}"); ImGui.Text($"Any%%: {sci.FastestCompletionAny} seconds"); ImGui.Text($"100%%: {sci.FastestCompletionFull} seconds"); } ImGui.EndChildFrame(); } ImGui.EndChildFrame(); return(result); }
private void DrawUiActions() { var toolbarSize = NVector2.UnitY * (ImGui.GetTextLineHeightWithSpacing() + ImGui.GetStyle().ItemSpacing.Y * 2); ImGui.Text($"{ImGuiEx.IcoMoon.HammerIcon} Actions"); ImGui.BeginChildFrame(1, toolbarSize); { if (ImGuiEx.DelegateButton("New project", $"{ImGuiEx.IcoMoon.HammerIcon}", "New project")) { _state = new State(); ResetEditor(_state); } ImGui.SameLine(); if (ImGuiEx.DelegateButton("Save project", $"{ImGuiEx.IcoMoon.FloppyDiskIcon}", "Save project")) { _openFdDefinition = ImGuiEx.CreateFilePickerDefinition(Assembly.GetExecutingAssembly() .Location, "Save", ".json"); ImGui.OpenPopup("Save project"); } DoPopup("Save project", ref _openFdDefinition, () => { var json = JsonSerializer.Serialize(_state, CreateJsonSerializerOptions(_state.PropertyDefinitions)); File.WriteAllText(_openFdDefinition.SelectedRelativePath, json); }); ImGui.SameLine(); if (ImGuiEx.DelegateButton("Open project", $"{ImGuiEx.IcoMoon.FolderOpenIcon}", "Open project")) { _openFdDefinition = ImGuiEx.CreateFilePickerDefinition(Assembly.GetExecutingAssembly() .Location, "Open", ".json"); ImGui.OpenPopup("Open project"); } DoPopup("Open project", ref _openFdDefinition, () => { // load json var json = File.ReadAllText(_openFdDefinition.SelectedRelativePath); using var jsonDocument = JsonDocument.Parse(json); var propJson = jsonDocument.RootElement.GetProperty(nameof(_state.PropertyDefinitions)).ToString(); var properties = JsonSerializer.Deserialize <Dictionary <string, Property> >(propJson, CreateJsonSerializerOptions()); var newState = JsonSerializer.Deserialize <State>(json, CreateJsonSerializerOptions(properties)); // clean animator and sprites/textures ResetEditor(newState, false); _state = newState; }); ImGui.SameLine(); } ImGui.EndChildFrame(); }
private bool DrawFolder(ref string selected) { bool result = false; ImGui.Text("Current Folder: " + CurrentFolder); if (ImGui.BeginChildFrame(1, new Vector2(0, 300), WindowFlags.Default)) { DirectoryInfo di = new DirectoryInfo(CurrentFolder); if (di.Exists) { if (di.Parent != null) { ImGui.PushStyleColor(ColorTarget.Text, new System.Numerics.Vector4(1, 1, 0, 1)); if (ImGui.Selectable("../", false, SelectableFlags.DontClosePopups)) { CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } foreach (var dict in di.GetDirectories()) { ImGui.PushStyleColor(ColorTarget.Text, new System.Numerics.Vector4(1, 1, 0, 1)); if (ImGui.Selectable(dict.Name + "/", false, SelectableFlags.DontClosePopups)) { CurrentFolder = dict.FullName; } ImGui.PopStyleColor(); } foreach (var file in di.GetFiles("*.filter")) { bool isSelected = SelectedFile == file.FullName; if (ImGui.Selectable(file.Name, isSelected, SelectableFlags.DontClosePopups)) { SelectedFile = file.FullName; selected = SelectedFile; result = true; } } } } ImGui.EndChildFrame(); return(result); }
public static void DoEntityCreatorModal(string[] textureNames, Action <string, string> onCreatePressed) { var open_create_sprite = true; var ch = ImGui.GetContentRegionAvail(); var frameHeight = ch.Y - (ImGui.GetTextLineHeight() + ImGui.GetStyle().WindowPadding.Y * 1.5f); if (ImGui.BeginPopupModal("Create entity", ref open_create_sprite, ImGuiWindowFlags.NoResize)) { ImGui.BeginChildFrame(1337, NVector2.UnitX * 400 + NVector2.UnitY * frameHeight); ImGui.InputText("Entity name", ref spriteName, 64); ImGui.ListBox("Textures", ref selectedTexture, textureNames, textureNames.Length); ImGui.EndChildFrame(); if (ImGui.Button("Create entity##2")) { onCreatePressed?.Invoke(spriteName, textureNames[selectedTexture]); ImGui.CloseCurrentPopup(); } ImGui.EndPopup(); } }
public override void Render() { this.Wizard.NextButton.Enabled = true; this.Wizard.PreviousButton.Visble = false; this.Wizard.NextButton.Title = "Home"; Vector2 size = ImGui.GetWindowSize(); ImGui.PushItemWidth(size.X - 16); ImGui.PopItemWidth(); ImGui.Spacing(); if (ImGui.BeginChildFrame(1, new Vector2(200, size.Y - 24), ImGuiWindowFlags.None)) { var directories = new List <string>(); if (!this.currentFolder.Equals(this.rootFolder, StringComparison.CurrentCultureIgnoreCase)) { directories.Add(".."); } directories.AddRange(Directory.GetDirectories(this.currentFolder)); foreach (string directory in directories) { Vector2 iconPosition = ImGui.GetWindowPos() + ImGui.GetCursorPos(); iconPosition.Y -= ImGui.GetScrollY(); float lineHeight = ImGui.GetTextLineHeight(); ImGui.SetCursorPosX(lineHeight * 2); if (ImGui.Selectable(Path.GetFileName(directory), false, ImGuiSelectableFlags.DontClosePopups)) { this.currentFile = null; this.currentFolder = directory.Equals("..") ? Path.GetFullPath(Path.Combine(this.currentFolder, "..")) : directory; } GenerateFolderIcon(iconPosition, lineHeight); } string[] files = Directory.GetFiles(this.currentFolder); foreach (string file in files) { Vector2 iconPosition = ImGui.GetWindowPos() + ImGui.GetCursorPos(); iconPosition.Y -= ImGui.GetScrollY(); float lineHeight = ImGui.GetTextLineHeight(); ImGui.SetCursorPosX(lineHeight * 2); if (ImGui.Selectable(Path.GetFileName(file), string.Equals(file, this.currentFile, StringComparison.CurrentCultureIgnoreCase), ImGuiSelectableFlags.DontClosePopups)) { ApplicationManager.ClearImageCache(); this.currentFile = file; this.expectedImageInfo = this.LoadExpected(file); this.actualImageInfo = this.LoadActualImage(file); } GenerateFileIcon(iconPosition, lineHeight); } ImGui.EndChildFrame(); } ImGui.SameLine(); if (ImGui.BeginChildFrame(2, new Vector2(size.X - 224, size.Y - 24), ImGuiWindowFlags.None)) { ImGui.Text("Expected Image"); if (this.expectedImageInfo.TexturePtr != IntPtr.Zero) { ImGui.Image(this.expectedImageInfo.TexturePtr, this.expectedImageInfo.Size); } else if (this.expectedImageInfo.ErrorMessage != null) { ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(1, 0, 0, 1)); ImGui.TextWrapped(this.expectedImageInfo.ErrorMessage); ImGui.PopStyleColor(); } ImGui.Spacing(); ImGui.Text("Actual Image"); if (this.actualImageInfo.TexturePtr != IntPtr.Zero) { ImGui.Image(this.actualImageInfo.TexturePtr, this.actualImageInfo.Size); } else if (this.actualImageInfo.ErrorMessage != null) { ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(1, 0, 0, 1)); ImGui.TextWrapped(this.actualImageInfo.ErrorMessage); ImGui.PopStyleColor(); } ImGui.Spacing(); if (ImGui.Button("Compare")) { this.OpenCompare(this.expectedImageInfo.TempFilePath, this.actualImageInfo.TempFilePath); } ImGui.EndChildFrame(); } }
public void Draw() { if (_consoleVisible && ImGui.Begin("Console", ref _consoleVisible, ImGuiWindowFlags.NoCollapse)) { var textHeight = ImGuiNative.igGetTextLineHeight(); var contentMin = ImGui.GetWindowContentRegionMin(); var contentMax = ImGui.GetWindowContentRegionMax(); var wrapWidth = contentMax.X - contentMin.X; //Leave some space at the bottom var maxHeight = contentMax.Y - contentMin.Y - (textHeight * 3); //Display as input text area to allow text selection ImGui.InputTextMultiline("##consoleText", ref _consoleText, _maxConsoleChars, new Vector2(wrapWidth, maxHeight), ImGuiInputTextFlags.ReadOnly, null); //Scroll to bottom when new text is added ImGuiNative.igBeginGroup(); var id = ImGui.GetID("##consoleText"); ImGui.BeginChildFrame(id, new Vector2(wrapWidth, maxHeight), ImGuiWindowFlags.None); switch (_textAdded) { case TextAdded.Yes: { _textAdded = TextAdded.ApplyScroll; break; } case TextAdded.ApplyScroll: { _textAdded = TextAdded.No; var yPos = ImGuiNative.igGetScrollMaxY(); ImGuiNative.igSetScrollY(yPos); break; } } ImGui.EndChildFrame(); ImGuiNative.igEndGroup(); ImGui.Text("Command:"); ImGui.SameLine(); //Max width for the input ImGui.PushItemWidth(-1); if (ImGui.InputText("##consoleInput", _consoleInputBuffer, (uint)_consoleInputBuffer.Length, ImGuiInputTextFlags.EnterReturnsTrue, null)) { //Needed since GetString doesn't understand null terminated strings var stringLength = StringUtils.NullTerminatedByteLength(_consoleInputBuffer); if (stringLength > 0) { var commandText = Encoding.UTF8.GetString(_consoleInputBuffer, 0, stringLength); _logger.Information($"] {commandText}"); _client.CommandContext.QueueCommands(commandText); } Array.Fill <byte>(_consoleInputBuffer, 0, 0, stringLength); } ImGui.PopItemWidth(); ImGui.End(); } }
public static bool BeginChildFrame(uint id, Vector2 size, ImGuiWindowFlags flags) { return(ImGui.BeginChildFrame(id, size, flags)); }
public FilePickerResult Draw() { ImGui.Text("Current Folder: " + Path.GetFileName(RootFolder) + CurrentFolder.Replace(RootFolder, "")); var result = FilePickerResult.Unfinished; if (ImGui.BeginChildFrame(1, new Vector2(400, 400))) { var di = new DirectoryInfo(CurrentFolder); if (di.Exists) { var yellow = new Vector4(1, 1, 0, 1); if (di.Parent != null && CurrentFolder != RootFolder) { ImGui.PushStyleColor(ImGuiCol.Text, yellow); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } var fileSystemEntries = GetFileSystemEntries(di.FullName); foreach (var fse in fileSystemEntries) { if (Directory.Exists(fse)) { var name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, yellow); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = fse; } ImGui.PopStyleColor(); } else { var name = Path.GetFileName(fse); bool isSelected = SelectedFile == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { SelectedFile = fse; } if (ImGui.IsMouseDoubleClicked(0)) { result = FilePickerResult.Finished; ImGui.CloseCurrentPopup(); } } } } } ImGui.EndChildFrame(); if (ImGui.Button("Cancel")) { result = FilePickerResult.Cancelled; ImGui.CloseCurrentPopup(); } if (OnlyAllowFolders) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = FilePickerResult.Finished; SelectedFile = CurrentFolder; ImGui.CloseCurrentPopup(); } } else if (SelectedFile != null) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = FilePickerResult.Finished; ImGui.CloseCurrentPopup(); } } return(result); }
public bool Draw() { ImGui.Text("Current Folder: " + Path.GetFileName(RootFolder) + CurrentFolder.Replace(RootFolder, "")); bool result = false; if (ImGui.BeginChildFrame(1, new Num.Vector2(500, 400))) { DirectoryInfo di = new DirectoryInfo(CurrentFolder); if (di.Exists) { if (di.Parent != null && (!DontAllowTraverselBeyondRootFolder || CurrentFolder != RootFolder)) { ImGui.PushStyleColor(ImGuiCol.Text, Color.Yellow.PackedValue); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } List <string> fileSystemEntries = GetFileSystemEntries(di.FullName); foreach (string fse in fileSystemEntries) { if (Directory.Exists(fse)) { string name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, Color.Yellow.PackedValue); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = fse; } ImGui.PopStyleColor(); } else { string name = Path.GetFileName(fse); bool isSelected = SelectedFile == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { SelectedFile = fse; } if (ImGui.IsMouseDoubleClicked(0)) { result = true; ImGui.CloseCurrentPopup(); } } } } } ImGui.EndChildFrame(); if (ImGui.Button("Cancel")) { result = false; RemoveFilePicker(this); ImGui.CloseCurrentPopup(); } if (OnlyAllowFolders) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = true; SelectedFile = CurrentFolder; ImGui.CloseCurrentPopup(); } } else if (SelectedFile != null) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = true; ImGui.CloseCurrentPopup(); } } return(result); }
private static bool DrawFolder(ref string selected, string[] extensions = null) { var currentDirectory = Directory.Exists(selected) ? selected : (new FileInfo(selected)).DirectoryName; ImGui.Text("Current Folder: " + currentDirectory); if (ImGui.BeginChildFrame(1, DefaultFilePickerSize, ImGuiWindowFlags.ChildMenu)) { DirectoryInfo di = new DirectoryInfo(currentDirectory); if (di.Exists) { if (di.Parent != null) { ImGui.PushStyleColor(ImGuiCol.Text, RgbaFloat.Yellow.ToVector4()); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { selected = di.Parent.FullName; } ImGui.PopStyleColor(); } foreach (var fse in Directory.EnumerateFileSystemEntries(di.FullName)) { if (Directory.Exists(fse)) { string name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, RgbaFloat.Yellow.ToVector4()); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { selected = fse; } ImGui.PopStyleColor(); } else { var ext = Path.GetExtension(fse); if (extensions == null || extensions.Contains(ext)) { var name = Path.GetFileName(fse); bool isSelected = selected == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { selected = fse; } } } } } } ImGui.EndChildFrame(); var fileName = Directory.Exists(selected) ? "" : (new FileInfo(selected)).Name; ImGui.InputText("Name", ref fileName, 64); selected = Directory.Exists(selected) ? (new DirectoryInfo(selected)).FullName + "\\" + fileName : (new FileInfo(selected)).DirectoryName + "\\" + fileName; ImGui.SameLine(); if (ImGui.Button("Okay")) { ImGui.CloseCurrentPopup(); return(true); } ImGui.SameLine(); if (ImGui.Button("Cancel")) { ImGui.CloseCurrentPopup(); return(false); } return(false); }
private bool DrawFolder() { bool result = false; DirectoryInfo di = new DirectoryInfo(currentFolder); if (di.Exists) { float availY = ImGui.GetContentRegionAvail().Y; if (ImGui.BeginChildFrame(1, new System.Numerics.Vector2(160.0f, availY - 30.0f))) { var drives = DriveInfo.GetDrives(); ImGui.Text("Drives"); ImGui.Separator(); foreach (var drive in drives) { if (ImGui.Selectable(drive.Name + $" ({drive.VolumeLabel})")) { SelectedFile = null; currentFolder = drive.Name; UpdateDisplay(drive.Name); } } ImGui.EndChildFrame(); } ImGui.SameLine(); if (ImGui.BeginChildFrame(2, new System.Numerics.Vector2(0, availY - 30.0f))) { //file picker ImGui.PushStyleColor(ImGuiCol.Text, new System.Numerics.Vector4(1.0f, 1.0f, 0.0f, 1.0f)); if (di.Parent != null && ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { currentFolder = di.Parent.FullName; SelectedFile = null; UpdateDisplay(di.Parent.FullName); } foreach (var f in displayFolders) { string name = Path.GetFileName(f); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { currentFolder = f; SelectedFile = null; UpdateDisplay(f); } } ImGui.PopStyleColor(); foreach (var f in displayFiles) { string name = Path.GetFileName(f); if (ImGui.Selectable(name, SelectedFile == f, ImGuiSelectableFlags.DontClosePopups)) { SelectedFile = f; } } ImGui.EndChildFrame(); } } float availX = ImGui.GetContentRegionMax().X; ImGui.SetNextItemWidth(availX - 144.0f); string dis = string.IsNullOrEmpty(SelectedFile) ? currentFolder : SelectedFile; ImGui.InputText(string.Empty, ref dis, 32786); if (ImGui.IsKeyDown(ImGui.GetKeyIndex(ImGuiKey.Enter))) { if (Directory.Exists(dis)) { currentFolder = dis; UpdateDisplay(dis); } else if (File.Exists(dis)) { SelectedFile = dis; currentFolder = Path.GetDirectoryName(dis); UpdateDisplay(currentFolder); } else { ImGui.OpenPopup("path-invalid"); } } if (ImGui.BeginPopup("path-invalid", ImGuiWindowFlags.NoTitleBar)) { ImGui.Text("Specified path does not exist!"); ImGui.EndPopup(); } ImGui.SameLine(); if (ImGui.Button("Open", new System.Numerics.Vector2(60.0f, 0.0f)) && !string.IsNullOrEmpty(SelectedFile) && File.Exists(SelectedFile)) { result = true; ImGui.CloseCurrentPopup(); } ImGui.SameLine(); if (ImGui.Button("Cancel", new System.Numerics.Vector2(60.0f, 0.0f))) { result = false; ImGui.CloseCurrentPopup(); } return(result); }
private static void HandleType(SettingsHolder holder, object type, string propertyInfo) { switch (type) { case ButtonNode buttonNode: holder.DrawDelegate = () => { if (ImGui.Button(holder.Unique)) { buttonNode.OnPressed(); } }; return; case null: case EmptyNode _: holder.DrawDelegate = () => { }; return; case HotkeyNode hotkeyNode: holder.DrawDelegate = () => { var str = $"{holder.Name} {hotkeyNode.Value}##{hotkeyNode.Value}"; var popupOpened = true; if (ImGui.Button(str)) { ImGui.OpenPopup(str); popupOpened = true; } if (!ImGui.BeginPopupModal(str, ref popupOpened, ImGuiWindowFlags.NoTitleBar | ImGuiWindowFlags.NoResize | ImGuiWindowFlags.NoCollapse)) { return; } if (Input.GetKeyState(Keys.Escape)) { ImGui.CloseCurrentPopup(); ImGui.EndPopup(); return; } foreach (var key in Enum.GetValues(typeof(Keys))) { if (!Input.GetKeyState((Keys)key)) { continue; } hotkeyNode.Value = (Keys)key; ImGui.CloseCurrentPopup(); break; } ImGui.Text($"Press new key to change '{hotkeyNode.Value}' or Esc for exit."); ImGui.EndPopup(); }; return; case ToggleNode toggleNode: holder.DrawDelegate = () => { var isChecked = toggleNode.Value; ImGui.Checkbox(holder.Unique, ref isChecked); toggleNode.Value = isChecked; }; return; case ColorNode colorNode: holder.DrawDelegate = () => { var color = colorNode.Value.ToVector4().ToVector4Num(); if (ImGui.ColorEdit4(holder.Unique, ref color, ImGuiColorEditFlags.NoInputs | ImGuiColorEditFlags.AlphaBar | ImGuiColorEditFlags.AlphaPreviewHalf)) { colorNode.Value = color.ToSharpColor(); } }; return; case ListNode listNode: holder.DrawDelegate = () => { if (!ImGui.BeginCombo(holder.Unique, listNode.Value)) { return; } foreach (var value in listNode.Values) { if (!ImGui.Selectable(value)) { continue; } listNode.Value = value; break; } ImGui.EndCombo(); }; return; case FileNode fileNode: holder.DrawDelegate = () => { if (!ImGui.TreeNode(holder.Unique)) { return; } var value = fileNode.Value; if (ImGui.BeginChildFrame(1, new Vector2(0f, 300f))) { var directoryInfo = new DirectoryInfo("config"); if (directoryInfo.Exists) { var files = directoryInfo.GetFiles(); foreach (var fileInfo in files) { if (ImGui.Selectable(fileInfo.Name, value == fileInfo.FullName)) { fileNode.Value = fileInfo.FullName; } } } ImGui.EndChildFrame(); } ImGui.TreePop(); }; return; case RangeNode <int> iRangeNode: holder.DrawDelegate = () => { var value = iRangeNode.Value; ImGui.SliderInt(holder.Unique, ref value, iRangeNode.Min, iRangeNode.Max); iRangeNode.Value = value; }; return; case RangeNode <float> fRangeNode: holder.DrawDelegate = () => { var value = fRangeNode.Value; ImGui.SliderFloat(holder.Unique, ref value, fRangeNode.Min, fRangeNode.Max); fRangeNode.Value = value; }; return; case RangeNode <long> lRangeNode: holder.DrawDelegate = () => { var value = (int)lRangeNode.Value; ImGui.SliderInt(holder.Unique, ref value, (int)lRangeNode.Min, (int)lRangeNode.Max); lRangeNode.Value = value; }; return; case RangeNode <Vector2> vRangeNode: holder.DrawDelegate = () => { var value = vRangeNode.Value; ImGui.SliderFloat2(holder.Unique, ref value, vRangeNode.Min.X, vRangeNode.Max.X); vRangeNode.Value = value; }; return; case TextNode textNode: holder.DrawDelegate = () => { var value = textNode.Value; ImGui.InputText(holder.Unique, ref value, 200); textNode.Value = value; }; return; } DebugWindow.LogDebug( $"SettingsParser => DrawDelegate not auto-generated for '{propertyInfo}'."); }
private static void HandleType(MenuAttribute menuAttribute, SettingsHolder holder, object type) { switch (type) { case ButtonNode n: holder.DrawDelegate = () => { if (ImGui.Button(holder.Unique)) { n.OnPressed(); } }; break; case EmptyNode n: break; case HotkeyNode n: holder.DrawDelegate = () => { var holderName = $"{holder.Name} {n.Value}##{n.Value}"; var open = true; if (ImGui.Button(holderName)) { ImGui.OpenPopup(holderName); open = true; } if (ImGui.BeginPopupModal(holderName, ref open, (ImGuiWindowFlags)35)) { if (Input.GetKeyState(Keys.Escape)) { ImGui.CloseCurrentPopup(); ImGui.EndPopup(); return; } foreach (var key in Enum.GetValues(typeof(Keys))) { var keyState = Input.GetKeyState((Keys)key); if (keyState) { n.Value = (Keys)key; ImGui.CloseCurrentPopup(); break; } } ImGui.Text($" Press new key to change '{n.Value}' or Esc for exit."); ImGui.EndPopup(); } }; break; case ToggleNode n: holder.DrawDelegate = () => { var value = n.Value; ImGui.Checkbox(holder.Unique, ref value); n.Value = value; }; break; case ColorNode n: holder.DrawDelegate = () => { var vector4 = n.Value.ToVector4().ToVector4Num(); if (ImGui.ColorEdit4(holder.Unique, ref vector4, ImGuiColorEditFlags.AlphaBar | ImGuiColorEditFlags.NoInputs | ImGuiColorEditFlags.AlphaPreviewHalf)) { n.Value = vector4.ToSharpColor(); } }; break; case ListNode n: holder.DrawDelegate = () => { if (ImGui.BeginCombo(holder.Unique, n.Value)) { foreach (var t in n.Values) { if (ImGui.Selectable(t)) { n.Value = t; ImGui.EndCombo(); return; } } ImGui.EndCombo(); } }; break; case FileNode n: holder.DrawDelegate = () => { if (ImGui.TreeNode(holder.Unique)) { var selected = n.Value; if (ImGui.BeginChildFrame(1, new Vector2(0, 300))) { var di = new DirectoryInfo("config"); if (di.Exists) { foreach (var file in di.GetFiles()) { if (ImGui.Selectable(file.Name, selected == file.FullName)) { n.Value = file.FullName; } } } ImGui.EndChildFrame(); } ImGui.TreePop(); } }; break; case RangeNode <int> n: holder.DrawDelegate = () => { var r = n.Value; ImGui.SliderInt(holder.Unique, ref r, n.Min, n.Max); n.Value = r; }; break; case RangeNode <float> n: holder.DrawDelegate = () => { var r = n.Value; ImGui.SliderFloat(holder.Unique, ref r, n.Min, n.Max); n.Value = r; }; break; case RangeNode <long> n: holder.DrawDelegate = () => { var r = (int)n.Value; ImGui.SliderInt(holder.Unique, ref r, (int)n.Min, (int)n.Max); n.Value = r; }; break; case RangeNode <Vector2> n: holder.DrawDelegate = () => { var vect = n.Value; ImGui.SliderFloat2(holder.Unique, ref vect, n.Min.X, n.Max.X); n.Value = vect; }; break; case TextNode n: holder.DrawDelegate = () => { var input = n.Value; ImGui.InputText(holder.Unique, ref input, 200); n.Value = input; }; break; default: DebugWindow.LogDebug($"{type} not supported for menu now. Ask developers to add this type."); break; } }
public void Submit() { Vector2 windowSize = new Vector2(440, 240); float quickLinks = 0.25f; float entries = 1f - quickLinks; if (ImGui.Begin(Title, ImGuiWindowFlags.AlwaysAutoResize)) { ImGui.Text(CurrentDirectory); SubmitQuickLinks(); ImGui.SameLine(); if (ImGui.BeginChild("fs-entries", new Vector2(windowSize.X * entries, windowSize.Y), true)) { if (ImGui.Selectable("..")) { // .. directory to move backwards. ChangeDirectory(BackOneDirectory(CurrentDirectory)); } foreach (string entry in CurrentDirectoryEntries) { FileAttributes attr = File.GetAttributes(entry); if (attr.HasFlag(FileAttributes.Directory)) { ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(0, 1, 1, 1f)); } else { ImGui.PushStyleColor(ImGuiCol.Text, new Vector4(1, 1, 0, 1f)); } if (PassFileTypeFilter(entry, fileTypeOptions[selectedFileType])) { if (ImGui.Selectable(Path.GetFileName(entry), SelectedFiles.Contains(entry))) { if (attr.HasFlag(FileAttributes.Directory)) { ChangeDirectory(entry); } else { switch (DialogType) { case FileDialogType.SaveFile: // Do nothing break; case FileDialogType.SelectFile: if (!SelectedFiles.Contains(entry)) { if (SelectedFiles.Count > 0) { SelectedFiles[0] = entry; } else { SelectedFiles.Add(entry); } } else { SelectedFiles.Clear(); } break; case FileDialogType.SelectMultipleFiles: ToggleSelection(entry); break; } } } } ImGui.PopStyleColor(); } ImGui.EndChild(); if (DialogType == FileDialogType.SaveFile) { ImGui.SetNextItemWidth(windowSize.X - 100); ImGui.InputText("", ref saveFileName, 50); } else { if (ImGui.BeginChildFrame(2, new Vector2(windowSize.X - 100, 20), ImGuiWindowFlags.NoScrollbar)) { ImGui.Text(GetSelectedFilesAsString(new Vector2(windowSize.X - 100, 20))); ImGui.EndChildFrame(); } } ImGui.SameLine(); ImGui.SetNextItemWidth(100); ImGui.Combo("", ref selectedFileType, fileTypeOptions, fileTypeOptions.Length, 5); if (ImGui.Button("Close")) { SelectedFiles.Clear(); IsDone = true; } ImGui.SameLine(); string submitButton = DialogType != FileDialogType.SaveFile ? "Select" : "Save"; if (ImGui.Button(submitButton)) { IsDone = true; if (DialogType == FileDialogType.SaveFile) { SelectedFiles.Add(CurrentDirectory + @$ "/{saveFileName}{fileTypeOptions[0]}"); } } } ImGui.End(); } }
public static bool BeginChildFrame(uint id, Vector2 size) { return(ImGui.BeginChildFrame(id, size)); }
public static bool DoFilePicker(ref FilePickerDefinition fpDef) { ImGui.Text(Path.GetFileName(fpDef.RootFolder) + fpDef.CurrentFolder.Replace(fpDef.RootFolder, "")); bool result = false; var ch = ImGui.GetContentRegionAvail(); var frameHeight = ch.Y - (ImGui.GetTextLineHeight() * 2 + ImGui.GetStyle().WindowPadding.Y * 3.5f); if (ImGui.BeginChildFrame(1, new Vector2(0, frameHeight), ImGuiWindowFlags.ChildWindow | ImGuiWindowFlags.NoResize)) { var di = new DirectoryInfo(fpDef.CurrentFolder); if (di.Exists) { if (di.Parent != null && fpDef.CurrentFolder != fpDef.RootFolder) { ImGui.PushStyleColor(ImGuiCol.Text, Color.Yellow.PackedValue); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { fpDef.CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } var fileSystemEntries = GetFileSystemEntries(ref fpDef, di.FullName); foreach (var fse in fileSystemEntries) { if (Directory.Exists(fse)) { var name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, Color.Yellow.PackedValue); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { fpDef.CurrentFolder = fse; } ImGui.PopStyleColor(); } else { var name = Path.GetFileName(fse); bool isSelected = fpDef.SelectedAbsolutePath == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { fpDef.SelectedAbsolutePath = fse; } if (ImGui.IsMouseDoubleClicked(0) && ImGui.IsItemHovered()) { result = true; ImGui.CloseCurrentPopup(); } } } } } ImGui.EndChildFrame(); if (fpDef.OnlyAllowFolders) { fpDef.SelectedAbsolutePath = fpDef.CurrentFolder; fpDef.SelectedRelativePath = fpDef.SelectedAbsolutePath.Substring(fpDef.executingPath.Length + 1); } else { if (!string.IsNullOrEmpty(fpDef.SelectedAbsolutePath)) { fpDef.SelectedRelativePath = fpDef.SelectedAbsolutePath.Substring(fpDef.executingPath.Length + 1); fpDef.SelectedFileName = Path.GetFileName(fpDef.SelectedAbsolutePath); } ImGui.SetNextItemWidth(ch.X); string fileName = fpDef.SelectedFileName ?? string.Empty; ImGui.InputText(String.Empty, ref fileName, 64); if (!string.IsNullOrEmpty(fileName)) { fpDef.SelectedAbsolutePath = Path.Combine(fpDef.CurrentFolder, fileName); fpDef.SelectedRelativePath = Path.Combine(Path.GetDirectoryName(fpDef.SelectedRelativePath), fileName); } } if (ImGui.Button("Cancel")) { result = false; ImGui.CloseCurrentPopup(); } if (fpDef.SelectedAbsolutePath != null) { ImGui.SameLine(); if (ImGui.Button(fpDef.ActionButtonLabel)) { result = true; ImGui.CloseCurrentPopup(); } } return(result); }
unsafe void Layout() { if (!CursorDefault.consoleIsOpen) { //ImGui.ShowDemoWindow(); return; } ImGui.SetNextWindowSize(new Vector2(Screen.width, 200)); ImGui.SetNextWindowPos(new Vector2(0, 0)); if (ImGui.Begin("window", ImGuiWindowFlags.NoResize | ImGuiWindowFlags.NoMove | ImGuiWindowFlags.NoTitleBar | ImGuiWindowFlags.MenuBar | ImGuiWindowFlags.NoSavedSettings)) { ImGui.Separator(); if (ImGui.BeginMenuBar()) { ImGui.Checkbox("Errors", ref showErrors); ImGui.Checkbox("Warnings", ref showWarnings); ImGui.Checkbox("Info", ref showInfo); ImGui.Spacing(); ImGui.Checkbox("Timestamps", ref timestamps); ImGui.EndMenuBar(); } ImGui.PushStyleVar(ImGuiStyleVar.ItemSpacing, new Vector2(0, 0)); ImGui.PushStyleVar(ImGuiStyleVar.FramePadding, Vector2.one); if (ImGui.BeginChildFrame(1, ImGui.GetWindowSize() - new Vector2(0, 60))) { uint idx = 0; foreach (var log in inst.logs) { string str = timestamps ? log.logStr : log.logStrNoTimestamp; ImGui.PushStyleVar(ImGuiStyleVar.ItemInnerSpacing, Vector2.zero); TimeSpan diff = DateTime.Now - log.time; float alpha = 1 - Mathf.Clamp01((float)diff.TotalSeconds - (float)CmdFadeTime.TotalSeconds); Vector4 col = Vector4.one; if (log.logType == LogType.Assert || log.logType == LogType.Exception) { col = new Vector4(.6f, 0, 0, 1); } if (log.logType == LogType.Error) { col = new Vector4(1, 0, 0, 1); } if (log.logType == LogType.Warning) { col = new Vector4(1, 1, .3f, 1); } if (log.logType == LogType.Log) { col = new Vector4(1, 1, 1, 1); } ImGui.PushStyleColor(ImGuiCol.Button, new Vector4(1, 1, 1, 0.1f * alpha)); ImGui.PushStyleColor(ImGuiCol.Text, col); Vector2 size = new Vector2(ImGui.GetWindowWidth(), ImGui.CalcTextSize(str).y + 3); ImGui.PushStyleVar(ImGuiStyleVar.ButtonTextAlign, new Vector2(0f, 0.5f)); bool show = ((log.logType == LogType.Assert || log.logType == LogType.Exception) && showErrors) || (log.logType == LogType.Error && showErrors) || (log.logType == LogType.Warning && showWarnings) || (log.logType == LogType.Log && showInfo); if (show) { if (ImGui.Button(str, size)) { log.isOpen = !log.isOpen; } if (ImGui.BeginPopupContextItem($"expand_log_{idx}")) { ImGui.Checkbox("Stack trace", ref log.isOpen); if (ImGui.Selectable("Copy...")) { if (log.isOpen) { ImGui.SetClipboardText($"{str}\n{log.stackTrace}"); } else { ImGui.SetClipboardText(str); } inst.PushStatus("Copied!"); } ImGui.EndPopup(); } if (log.isOpen) { ImGui.Text(log.stackTrace); } } ImGui.PopStyleColor(); ImGui.PopStyleColor(); ImGui.PopStyleVar(); ImGui.PopStyleVar(); idx++; } inst.scrollToBottom = ImGui.GetScrollY() >= ImGui.GetScrollMaxY(); if (inst.scrollToBottom) { ImGui.SetScrollHereY(1.0f); } ImGui.EndChildFrame(); } ImGui.PopStyleVar(); ImGui.PopStyleVar(); ImGui.Spacing(); ImGuiInputTextCallback cb = (ImGuiInputTextCallbackData * data) => { ImGuiInputTextCallbackDataPtr ptr = new ImGuiInputTextCallbackDataPtr(data); if (desiredConsoleInput != null) { ptr.DeleteChars(0, ptr.BufTextLen); ptr.InsertChars(0, desiredConsoleInput); desiredConsoleInput = null; } return(ptr.BufTextLen); }; if (ImGui.InputTextWithHint("", ">", ref consoleInput, 150, ImGuiInputTextFlags.EnterReturnsTrue | ImGuiInputTextFlags.CallbackAlways, cb)) { bool didRun = ComReg.RunCom(consoleInput); //if (history.Count == 0 || history[history.Count - 1] != consoleInput) if (didRun) { history.Add(consoleInput); } consoleInput = ""; historyLogIndex = -1; ImGui.SetKeyboardFocusHere(); } if (FocusText) { ImGui.SetKeyboardFocusHere(-1); FocusText = false; } if (consoleInput.Contains("`")) //hack { consoleInput = consoleInput.Replace("`", ""); } ImGui.SameLine(); inst.DrawStatusImgui(); ImGui.End(); } }
private void DrawConsole() { if (_consoleVisible && ImGui.BeginWindow("Console", ref _consoleVisible, WindowFlags.NoCollapse)) { var textHeight = ImGuiNative.igGetTextLineHeight(); var contentMin = ImGui.GetWindowContentRegionMin(); var contentMax = ImGui.GetWindowContentRegionMax(); var wrapWidth = contentMax.X - contentMin.X; //Leave some space at the bottom var maxHeight = contentMax.Y - contentMin.Y - (textHeight * 3); //Convert the text to UTF8 //Acount for null terminator var byteCount = Encoding.UTF8.GetByteCount(_consoleText) + 1; //Resize on demand if (_consoleTextUTF8 == null || _consoleTextUTF8.Length < byteCount) { _consoleTextUTF8 = new byte[byteCount]; } var bytesWritten = StringUtils.EncodeNullTerminatedString(Encoding.UTF8, _consoleText, _consoleTextUTF8); //Display as input text area to allow text selection var pinnedBuffer = GCHandle.Alloc(_consoleTextUTF8, GCHandleType.Pinned); var bufferAddress = pinnedBuffer.AddrOfPinnedObject(); ImGui.InputTextMultiline("##consoleText", bufferAddress, (uint)bytesWritten + 1, new Vector2(wrapWidth, maxHeight), InputTextFlags.ReadOnly, null); //Scroll to bottom when new text is added ImGuiNative.igBeginGroup(); var id = ImGui.GetID("##consoleText"); ImGui.BeginChildFrame(id, new Vector2(wrapWidth, maxHeight), WindowFlags.Default); switch (_textAdded) { case TextAdded.Yes: { _textAdded = TextAdded.ApplyScroll; break; } case TextAdded.ApplyScroll: { _textAdded = TextAdded.No; var yPos = ImGuiNative.igGetScrollMaxY(); ImGuiNative.igSetScrollY(yPos); break; } } ImGui.EndChildFrame(); ImGuiNative.igEndGroup(); pinnedBuffer.Free(); ImGui.Text("Command:"); ImGui.SameLine(); //Max width for the input ImGui.PushItemWidth(-1); if (ImGui.InputText("##consoleInput", _consoleInputBuffer, (uint)_consoleInputBuffer.Length, InputTextFlags.EnterReturnsTrue, null)) { //Needed since GetString doesn't understand null terminated strings var stringLength = StringUtils.NullTerminatedByteLength(_consoleInputBuffer); if (stringLength > 0) { var commandText = Encoding.UTF8.GetString(_consoleInputBuffer, 0, stringLength); _logger.Information($"] {commandText}"); _engine.CommandContext.QueueCommands(commandText); } Array.Fill <byte>(_consoleInputBuffer, 0, 0, stringLength); } ImGui.PopItemWidth(); ImGui.EndWindow(); } }
private void DrawUiHierarchyFrame() { var size = ImGui.GetContentRegionAvail(); var itemSpacing = ImGui.GetStyle().ItemSpacing + NVector2.UnitY * 4; ImGui.PushStyleVar(ImGuiStyleVar.ItemSpacing, itemSpacing); ImGui.Text($"{ImGuiEx.IcoMoon.ListIcon} Hierarchy"); ImGui.BeginChildFrame(2, size - NVector2.UnitY * 256); { // create sprite bool itemHovered = false; ImGui.Text($"{ImGuiEx.IcoMoon.ImagesIcon} Entities"); ImGui.SameLine(); if (_state.Textures.Count > 0) { if (ImGui.SmallButton($"{ImGuiEx.IcoMoon.PlusIcon}##1")) { ImGui.OpenPopup("Create entity"); ImGuiEx.DoEntityCreatorReset(); } } else { ImGuiEx.DisabledButton($"{ImGuiEx.IcoMoon.PlusIcon}"); } ImGuiEx.DoEntityCreatorModal(_state.Textures.Keys.ToArray(), (name, selectedTexture) => { Entity entity = new Entity(name, selectedTexture); var propDef = _state.PropertyDefinitions[POSITION_PROPERTY]; entity.SetCurrentPropertyValue(propDef, propDef.CreateInstance()); _state.Animator.CreateTrack(propDef.Type, name, POSITION_PROPERTY); var fiPropDef = _state.PropertyDefinitions[FRAMEINDEX_PROPERTY]; entity.SetCurrentPropertyValue(fiPropDef, fiPropDef.CreateInstance()); _state.Animator.CreateTrack(fiPropDef.Type, name, FRAMEINDEX_PROPERTY); _state.Entities[entity.Id] = entity; }); // show all created entities ImGui.Indent(); foreach (var entity in _state.Entities.Values) { bool selected = selectedEntityId == entity.Id; ImGui.Selectable(entity.Id, ref selected); if (selected) { selectedTextureId = string.Empty; selectedEntityId = entity.Id; } if (ImGui.IsItemHovered()) { itemHovered = true; hoveredentityId = entity.Id; } } ImGui.Unindent(); if (!itemHovered) { hoveredentityId = string.Empty; } // Add textures ImGui.Text($"{ImGuiEx.IcoMoon.TextureIcon} Textures"); ImGui.SameLine(); if (ImGui.SmallButton($"{ImGuiEx.IcoMoon.PlusIcon}##2")) { _openFdDefinition = ImGuiEx.CreateFilePickerDefinition(Assembly.GetExecutingAssembly() .Location, "Open", ".png"); ImGui.OpenPopup("Load texture"); } DoPopup("Load texture", ref _openFdDefinition, () => { var key = Path.GetFileNameWithoutExtension(_openFdDefinition.SelectedFileName); if (!_state.Textures.ContainsKey(key)) { var path = _openFdDefinition.SelectedRelativePath; var texture = Texture2D.FromFile(GraphicsDevice, path); _state.Textures[key] = new TextureFrame(texture, path, new NVector2(32, 32), new NVector2(16, 16)); } }); // show all loaded textures ImGui.Indent(); foreach (var texture in _state.Textures.Keys) { bool selected = selectedTextureId == texture; ImGui.Selectable(texture, ref selected); if (selected) { selectedEntityId = string.Empty; selectedTextureId = texture; } } ImGui.Unindent(); ImGui.TreePop(); } ImGui.EndChildFrame(); ImGui.PopStyleVar(); }
private bool DrawFolder(ref string selected, bool returnOnSelection = false) { _keepPopup = true; ImGui.Text("Current Folder: " + CurrentFolder); bool result = false; if (ImGui.BeginChildFrame(1, new Num.Vector2(0, 220), ImGuiWindowFlags.Modal /*WindowFlags.Default*/)) { DirectoryInfo di = new DirectoryInfo(CurrentFolder); if (di.Exists) { if (di.Parent != null) { ImGui.PushStyleColor(ImGuiCol.Text, new Num.Vector4(1, 1, 0, 1) /*RgbaFloat.Yellow.ToVector4()*/); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } foreach (var fse in Directory.EnumerateFileSystemEntries(di.FullName)) { if (Directory.Exists(fse)) { string name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, new Num.Vector4(1, 1, 0, 1)); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = fse; } ImGui.PopStyleColor(); } else { string name = Path.GetFileName(fse); bool isSelected = SelectedFile == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { SelectedFile = fse; if (returnOnSelection) { result = true; selected = SelectedFile; } } if (ImGui.IsMouseDoubleClicked(0)) { result = true; selected = SelectedFile; ImGui.CloseCurrentPopup(); _menuAction = string.Empty; } } } } } ImGui.EndChildFrame(); if (ImGui.Button("Cancel")) { result = false; ImGui.CloseCurrentPopup(); _menuAction = string.Empty; } if (SelectedFile != null) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = true; selected = SelectedFile; ImGui.CloseCurrentPopup(); _menuAction = string.Empty; } } return(result); }
private void DrawUiProperties() { void InsertKeyframe(string entityId, string propertyId) { var entity = _state.Entities[entityId]; var propDef = _state.PropertyDefinitions[propertyId]; var trackId = _state.Animator.GetTrackKey(entityId, propertyId); var value = entity.GetCurrentPropertyValue <object>(propDef); _state.Animator.InsertKeyframe(trackId, value); } ImGui.Text($"{ImGuiEx.IcoMoon.EqualizerIcon} Properties"); ImGui.BeginChildFrame(3, NVector2.UnitY * 208); if (!string.IsNullOrEmpty(selectedEntityId)) { var selectedEntity = _state.Entities[selectedEntityId]; var tempEntityName = ImGuiEx.SavedInput(String.Empty, selectedEntity.Id); ImGui.SameLine(); if (ImGui.Button("Rename") && !_state.Entities.ContainsKey(tempEntityName)) { RenameEntity(selectedEntity, tempEntityName); ImGuiEx.ResetSavedInput(); } ImGui.Separator(); ImGui.Columns(2); ImGui.SetColumnWidth(0, 28); if (ImGui.Button($"{ImGuiEx.IcoMoon.KeyIcon}##group")) { foreach (var propertyId in selectedEntity) { InsertKeyframe(selectedEntityId, propertyId); } } ImGui.NextColumn(); ImGui.Text("All properties"); ImGui.Separator(); ImGui.NextColumn(); var keyframeButtonId = 0; foreach (var propertyId in selectedEntity) { ImGui.PushID(keyframeButtonId++); if (ImGui.Button($"{ImGuiEx.IcoMoon.KeyIcon}")) { InsertKeyframe(selectedEntityId, propertyId); } ImGui.PopID(); ImGui.NextColumn(); var propDefinition = _state.PropertyDefinitions[propertyId]; switch (propertyId) { case POSITION_PROPERTY: Vector2 value = selectedEntity.GetCurrentPropertyValue <Vector2>(propDefinition); var pos = new NVector2(value.X, value.Y); ImGui.DragFloat2(propertyId, ref pos); value.X = pos.X; value.Y = pos.Y; selectedEntity.SetCurrentPropertyValue(propDefinition, value); break; case FRAMEINDEX_PROPERTY: int frameIndex = selectedEntity.GetCurrentPropertyValue <int>(propDefinition); var texture = _state.Textures[selectedEntity.TextureId]; int framesX = (int)(texture.Width / texture.FrameSize.X); int framesY = (int)(texture.Height / texture.FrameSize.Y); ImGui.SliderInt(propertyId, ref frameIndex, 0, framesX * framesY - 1); selectedEntity.SetCurrentPropertyValue(propDefinition, frameIndex); break; } ImGui.NextColumn(); } } else if (!string.IsNullOrEmpty(selectedTextureId)) { var scale = 2f; var selectedTexture = _state.Textures[selectedTextureId]; var currentFrameSize = selectedTexture.FrameSize; var currentPivot = selectedTexture.Pivot; ImGui.DragFloat2("Framesize", ref currentFrameSize); ImGui.DragFloat2("Pivot", ref currentPivot); selectedTexture.FrameSize = currentFrameSize; selectedTexture.Pivot = currentPivot; var scaledFrameSize = currentFrameSize * scale; var scaledPivot = currentPivot * scale; ImGui.BeginChildFrame(2, NVector2.UnitY * 154f); var contentSize = ImGui.GetContentRegionAvail(); var center = ImGui.GetCursorScreenPos() + contentSize * 0.5f; var frameStart = center - scaledFrameSize * 0.5f; // draw frame size var drawList = ImGui.GetWindowDrawList(); drawList.AddRect(frameStart, frameStart + scaledFrameSize, Color.GreenYellow.PackedValue); // horizontal line drawList.AddLine(center - NVector2.UnitX * scaledFrameSize * 0.5f, center + NVector2.UnitX * scaledFrameSize * 0.5f, Color.ForestGreen.PackedValue); // vertical line drawList.AddLine(center - NVector2.UnitY * scaledFrameSize * 0.5f, center + NVector2.UnitY * scaledFrameSize * 0.5f, Color.ForestGreen.PackedValue); // draw pivot drawList.AddCircleFilled(frameStart + scaledPivot, 4, Color.White.PackedValue); ImGui.EndChildFrame(); } ImGui.EndChildFrame(); }
private unsafe void SubmitGui() { //ImGui.SetNextWindowSize(new System.Numerics.Vector2(Width, Height), SetCondition.FirstUseEver); //ImGui.SetNextWindowPosCenter(SetCondition.Always); ImGui.BeginWindow("Test", ref _windowOpen, WindowFlags.NoResize | WindowFlags.NoTitleBar | WindowFlags.NoMove); ImGui.BeginMainMenuBar(); if (ImGui.BeginMenu("File")) { if (ImGui.MenuItem("Menu item", "", false, true)) { } ImGui.EndMenu(); } if (ImGui.BeginMenu("Edit")) { if (ImGui.MenuItem("Edit", "", false, true)) { } ImGui.EndMenu(); } if (ImGui.BeginMenu("View")) { if (ImGui.Checkbox("Wireframe Mode", ref _wireframeEnabled)) { Console.WriteLine("Wireframe Mode:" + _wireframeEnabled); } ImGui.EndMenu(); } if (ImGui.BeginMenu("Options")) { if (ImGui.Checkbox("Debug Mode", ref _debugEnabled)) { } ImGui.EndMenu(); } if (ImGui.BeginMenu("Tools")) { if (ImGui.MenuItem("Edit", "", false, true)) { } ImGui.EndMenu(); } if (ImGui.BeginMenu("Windows")) { ImGui.EndMenu(); } if (ImGui.BeginMenu("Help")) { if (ImGui.MenuItem("Edit", "", false, true)) { } ImGui.EndMenu(); } if (_debugEnabled) { if (ImGui.BeginMenu("Debug")) { if (ImGui.MenuItem("Console")) { showConsole = !showConsole; } if (ImGui.MenuItem("OpenGL Console")) { showOpenGLConsole = !showOpenGLConsole; } ImGui.EndMenu(); } } ImGui.EndMainMenuBar(); //ImGui.SetNextWindowPos(new Vector2(0, 20), SetCondition.Always); //ImGui.SetNextWindowSize(new Vector2(Width, 30), SetCondition.Always); ImGui.PushStyleVar(StyleVar.WindowPadding, new Vector2(5f, 5f)); ImGui.BeginWindow("inner window", WindowFlags.NoMove | WindowFlags.NoTitleBar | WindowFlags.NoResize | WindowFlags.NoScrollbar | WindowFlags.NoScrollWithMouse); if (ImGui.Button("Btn1", new Vector2(50, 25))) { } ImGui.SameLine(); if (ImGui.Button("Btn2")) { } ImGui.EndWindow(); ImGui.PopStyleVar(); ImGui.BeginChildFrame(1, new Vector2(50, 50), WindowFlags.AlwaysAutoResize); ImGui.Text("Outside"); ImGui.Separator(); ImGui.Spacing(); ImGui.Spacing(); ImGui.Spacing(); ImGui.Spacing(); ImGui.Spacing(); ImGui.Text("Seperator"); ImGui.EndWindow(); if (showConsole) { ImGui.BeginWindow("Console", ref showConsole, WindowFlags.Default); ImGui.Text(stringWriter.ToString()); ImGui.EndWindow(); } if (showOpenGLConsole) { ImGui.BeginWindow("OpenGL Console", ref showOpenGLConsole, WindowFlags.Default); //Create callback GetGlDebugMessages(); ImGui.EndWindow(); } }
public static bool Sequencer(SequenceInterface sequence, ref int currentFrame, ref bool expanded, ref int selectedEntry, ref int firstFrame, SEQUENCER_OPTIONS sequenceOptions) { var ret = false; var io = ImGui.GetIO(); var cx = (int)(io.MousePos.X); var cy = (int)(io.MousePos.Y); var legendWidth = 120; var deleteAnimationEntry = -1; var duplicateAnimationEntry = -1; var insertAnimationEntry = -1; var ItemHeight = 20; var popupOpened = false; var sequenceCount = sequence.ItemCount; if (sequenceCount == 0) { return(false); } ImGui.BeginGroup(); var draw_list = ImGui.GetWindowDrawList(); var canvas_pos = ImGui.GetCursorScreenPos(); // ImDrawList API uses screen coordinates! var canvas_size = ImGui.GetContentRegionAvail(); // Resize canvas to what's available int firstFrameUsed = firstFrame; int controlHeight = sequenceCount * ItemHeight; for (int i = 0; i < sequenceCount; i++) { controlHeight += sequence.GetCustomHeight(i); } int frameCount = Math.Max(sequence.FrameMax - sequence.FrameMin, 1); // ImVector<CustomDraw> customDraws; // ImVector<CustomDraw> compactCustomDraws; var customDraws = new List <CustomDraw>(); var compactCustomDraws = new List <CustomDraw>(); // zoom in/out int visibleFrameCount = (int)Math.Floor((canvas_size.X - legendWidth) / framePixelWidth); float barWidthRatio = Math.Min(visibleFrameCount / (float)frameCount, 1f); float barWidthInPixels = barWidthRatio * (canvas_size.X - legendWidth); var regionRect = new ImRect(canvas_pos, canvas_pos + canvas_size); if (ImGui.IsWindowFocused() && io.KeyAlt && io.MouseDown[2]) { if (!panningView) { panningViewSource = io.MousePos; panningView = true; panningViewFrame = firstFrame; } firstFrame = panningViewFrame - (int)((io.MousePos.X - panningViewSource.X) / framePixelWidth); firstFrame = Math.Clamp(firstFrame, sequence.FrameMin, sequence.FrameMax - visibleFrameCount); } if (panningView && !io.MouseDown[2]) { panningView = false; } framePixelWidthTarget = Math.Clamp(framePixelWidthTarget, 0.1f, 50f); framePixelWidth = Lerp(framePixelWidth, framePixelWidthTarget, 0.33f); frameCount = sequence.FrameMax - sequence.FrameMin; if (visibleFrameCount >= frameCount) { firstFrame = sequence.FrameMin; } // -- if (!expanded) { ImGui.InvisibleButton("canvas", new Vector2(canvas_size.X - canvas_pos.X, (float)ItemHeight)); draw_list.AddRectFilled(canvas_pos, new Vector2(canvas_size.X + canvas_pos.X, canvas_pos.Y + ItemHeight), 0xFF3D3837, 0); var tmps = $"{frameCount} Frames / {sequenceCount} entries"; draw_list.AddText(new Vector2(canvas_pos.X + 26, canvas_pos.Y + 2), 0xFFFFFFFF, tmps); } else { bool hasScrollBar = true; /* * int framesPixelWidth = int(frameCount * framePixelWidth); * if ((framesPixelWidth + legendWidth) >= canvas_size.X) * { * hasScrollBar = true; * } */ // test scroll area var headerSize = new Vector2(canvas_size.X, (float)ItemHeight); var scrollBarSize = new Vector2(canvas_size.X, 14f); ImGui.InvisibleButton("topBar", headerSize); draw_list.AddRectFilled(canvas_pos, canvas_pos + headerSize, 0xFFFF0000, 0); Vector2 childFramePos = ImGui.GetCursorScreenPos(); var childFrameSize = new Vector2(canvas_size.X, canvas_size.Y - 8f - headerSize.Y - (hasScrollBar ? scrollBarSize.Y : 0)); ImGui.PushStyleColor(ImGuiCol.FrameBg, 0); ImGui.BeginChildFrame(889, childFrameSize); sequence.focused = ImGui.IsWindowFocused(); ImGui.InvisibleButton("contentBar", new Vector2(canvas_size.X, (float)(controlHeight))); Vector2 contentMin = ImGui.GetItemRectMin(); Vector2 contentMax = ImGui.GetItemRectMax(); var contentRect = new ImRect(contentMin, contentMax); float contentHeight = contentMax.Y - contentMin.Y; // full background draw_list.AddRectFilled(canvas_pos, canvas_pos + canvas_size, 0xFF242424, 0); // current frame top var topRect = new ImRect(new Vector2(canvas_pos.X + legendWidth, canvas_pos.Y), new Vector2(canvas_pos.X + canvas_size.X, canvas_pos.Y + ItemHeight)); if (!MovingCurrentFrame && !MovingScrollBar && movingEntry == -1 && sequenceOptions.HasFlag(SEQUENCER_OPTIONS.SEQUENCER_CHANGE_FRAME) && currentFrame >= 0 && topRect.Contains(io.MousePos) && io.MouseDown[0]) { MovingCurrentFrame = true; } if (MovingCurrentFrame) { if (true) { currentFrame = (int)((io.MousePos.X - topRect.Min.X) / framePixelWidth) + firstFrameUsed; if (currentFrame < sequence.FrameMin) { currentFrame = sequence.FrameMin; } if (currentFrame >= sequence.FrameMax) { currentFrame = sequence.FrameMax; } } if (!io.MouseDown[0]) { MovingCurrentFrame = false; } } // Draw header controls on the left draw_list.AddRectFilled(canvas_pos, new Vector2(canvas_size.X + canvas_pos.X, canvas_pos.Y + ItemHeight), 0xFF3D3837, 0); if (sequenceOptions.HasFlag(SEQUENCER_OPTIONS.SEQUENCER_ADD)) { const uint PauseColor = 0xFFf1c40f; const uint LoopColor = 0xFF0fc4f1; var nextButtonPosition = new Vector2(canvas_pos.X + legendWidth - ItemHeight, canvas_pos.Y + 2); if (SequencerButton(draw_list, nextButtonPosition, 'P', sequence.IsPaused, PauseColor)) { Tooltip(sequence.IsPaused ? "Resume" : "Pause"); if (io.MouseReleased[0]) { sequence.IsPaused = !sequence.IsPaused; } } nextButtonPosition.X -= ButtonDistance; if (SequencerButton(draw_list, nextButtonPosition, 'L', sequence.ForceLoop, LoopColor)) { Tooltip("Force loop"); if (io.MouseReleased[0]) { sequence.ForceLoop = !sequence.ForceLoop; } } nextButtonPosition.X -= ButtonDistance; if (SequencerButton(draw_list, nextButtonPosition, 'A', false, ColorWhite)) { Tooltip("Add new animation"); if (io.MouseReleased[0]) { insertAnimationEntry = sequence.ItemCount; } } } //header frame number and lines const int MinimumDistanceBetweenElements = 100; int modFrameCount = 5; // after how many frames should print the frame number int frameStep = 1; while ((modFrameCount * framePixelWidth) < MinimumDistanceBetweenElements) { modFrameCount *= 2; frameStep *= 2; } ; int halfModFrameCount = modFrameCount / 2; Action <int, int> drawLine = (int i, int regionHeight) => { const uint TextColor = 0xFFBBBBBB; bool baseIndex = ((i % modFrameCount) == 0) || (i == sequence.FrameMax || i == sequence.FrameMin); bool halfIndex = (i % halfModFrameCount) == 0; int px = (int)canvas_pos.X + (int)(i * framePixelWidth) + legendWidth - (int)(firstFrameUsed * framePixelWidth); int tiretStart = baseIndex ? 4 : (halfIndex ? 10 : 14); int tiretEnd = baseIndex ? regionHeight : ItemHeight; if (px <= (canvas_size.X + canvas_pos.X) && px >= (canvas_pos.X + legendWidth)) { draw_list.AddLine(new Vector2((float)px, canvas_pos.Y + (float)tiretStart), new Vector2((float)px, canvas_pos.Y + (float)tiretEnd - 1), 0xFF606060, 1); draw_list.AddLine(new Vector2((float)px, canvas_pos.Y + (float)ItemHeight), new Vector2((float)px, canvas_pos.Y + (float)regionHeight - 1), 0x30606060, 1); } if (baseIndex && px >= (canvas_pos.X + legendWidth)) { draw_list.AddText(new Vector2((float)px + 3f, canvas_pos.Y), TextColor, $"{i}"); } }; for (int i = sequence.FrameMin; i <= sequence.FrameMax; i += frameStep) { drawLine(i, ItemHeight); } drawLine(sequence.FrameMin, ItemHeight); drawLine(sequence.FrameMax, ItemHeight); /* * draw_list.AddLine(canvas_pos, new Vector2(canvas_pos.X, canvas_pos.Y + controlHeight), 0xFF000000, 1); * draw_list.AddLine(new Vector2(canvas_pos.X, canvas_pos.Y + ItemHeight), new Vector2(canvas_size.X, canvas_pos.Y + ItemHeight), 0xFF000000, 1); */ // clip content draw_list.PushClipRect(childFramePos, childFramePos + childFrameSize); // draw item names in the legend rect on the left for (int i = 0, customHeight = 0; i < sequenceCount; i++) { var animation = sequence.GetAnimation(i); var tPos = new Vector2(contentMin.X + 3, contentMin.Y + i * ItemHeight + 2 + customHeight); var tEndPos = new Vector2(contentMin.X + 3 + legendWidth, contentMin.Y + (i + 1) * ItemHeight + 2 + customHeight); var canMouseClickOnRow = new ImRect(tPos, tEndPos).Contains(io.MousePos) && io.MousePos.Y > childFramePos.Y && io.MousePos.Y <= childFramePos.Y + childFrameSize.Y && ImGui.IsWindowFocused(); if (canMouseClickOnRow && io.MouseDown[0] && ImGui.IsWindowHovered()) { selectedEntry = i; } draw_list.AddText(tPos, 0xFFFFFFFF, animation.Name ?? $"#{i + 1}"); if (sequenceOptions.HasFlag(SEQUENCER_OPTIONS.SEQUENCER_DEL)) { var isAnimationVisible = sequence.IsVisible(i); var buttonPos = new Vector2(contentMin.X + legendWidth - ButtonDistance + 2 - 10, tPos.Y + 2); if (SequencerButton(draw_list, buttonPos, 'H', !isAnimationVisible, 0xff15208f) && canMouseClickOnRow) { Tooltip("Hide animation"); if (io.MouseReleased[0]) { sequence.SetVisibility(i, !isAnimationVisible); } } var isFocused = sequence.IsFocus(i); buttonPos.X -= ButtonDistance; if (SequencerButton(draw_list, buttonPos, 'S', isFocused, 0xff69992f) && canMouseClickOnRow) { Tooltip("Display only this animation"); if (io.MouseReleased[0]) { if (isFocused) { sequence.ResetFocus(); } else { sequence.SetFocus(i); } } } buttonPos.X -= ButtonDistance; if (SequencerButton(draw_list, buttonPos, 'D', false, ColorWhite) && canMouseClickOnRow) { Tooltip("Duplicate animation"); if (io.MouseReleased[0]) { duplicateAnimationEntry = i; } } buttonPos.X -= ButtonDistance; if (SequencerButton(draw_list, buttonPos, 'R', false, ColorWhite) && canMouseClickOnRow) { Tooltip("Remove animation"); if (io.MouseReleased[0]) { deleteAnimationEntry = i; } } } customHeight += sequence.GetCustomHeight(i); } // clipping rect so items bars are not visible in the legend on the left when scrolled // // slots background for (int i = 0, customHeight = 0; i < sequenceCount; i++) { // Draw as a zebra background uint col = (i & 1) != 0 ? 0xFF3A3636 : 0xFF413D3D; var localCustomHeight = sequence.GetCustomHeight(i); Vector2 pos = new Vector2(contentMin.X + legendWidth, contentMin.Y + ItemHeight * i + 1 + customHeight); Vector2 sz = new Vector2(canvas_size.X + canvas_pos.X, pos.Y + ItemHeight - 1 + localCustomHeight); if (!popupOpened && cy >= pos.Y && cy < pos.Y + (ItemHeight + localCustomHeight) && movingEntry == -1 && cx > contentMin.X && cx < contentMin.X + canvas_size.X) { col += 0x80201008; pos.X -= legendWidth; } draw_list.AddRectFilled(pos, sz, col, 0); customHeight += localCustomHeight; } draw_list.PushClipRect(childFramePos + new Vector2((float)(legendWidth), 0f), childFramePos + childFrameSize); // vertical frame lines in content area Action <int, int> drawLineContent = (int i, int regionHeight) => { int px = (int)canvas_pos.X + (int)(i * framePixelWidth) + legendWidth - (int)(firstFrameUsed * framePixelWidth); int tiretStart = (int)(contentMin.Y); int tiretEnd = (int)(contentMax.Y); if (px <= (canvas_size.X + canvas_pos.X) && px >= (canvas_pos.X + legendWidth)) { //draw_list.AddLine(new Vector2((float)px, canvas_pos.Y + (float)tiretStart), new Vector2((float)px, canvas_pos.Y + (float)tiretEnd - 1), 0xFF606060, 1); draw_list.AddLine(new Vector2((float)(px), (float)(tiretStart)), new Vector2((float)(px), (float)(tiretEnd)), 0x30606060, 1); } }; for (int i = sequence.FrameMin; i <= sequence.FrameMax; i += frameStep) { drawLineContent(i, (int)(contentHeight)); } drawLineContent(sequence.FrameMin, (int)(contentHeight)); drawLineContent(sequence.FrameMax, (int)(contentHeight)); // selection bool selected = (selectedEntry >= 0); if (selected) { // draw background differently if selected var customHeight = 0; for (int i = 0; i < selectedEntry; i++) { customHeight += sequence.GetCustomHeight(i); } ; draw_list.AddRectFilled( new Vector2(contentMin.X, contentMin.Y + ItemHeight * selectedEntry + customHeight), new Vector2(contentMin.X + canvas_size.X, contentMin.Y + ItemHeight * (selectedEntry + 1) + customHeight), 0x801080FF, 1f); } // slots for (int i = 0, customHeight = 0; i < sequenceCount; i++) { var animation = sequence.GetAnimation(i); var localCustomHeight = sequence.GetCustomHeight(i); Vector2 pos = new Vector2(contentMin.X + legendWidth - firstFrameUsed * framePixelWidth, contentMin.Y + ItemHeight * i + 1 + customHeight); var slotP1 = new Vector2(pos.X + animation.FrameStart * framePixelWidth, pos.Y + 2); var slotP2 = new Vector2(pos.X + animation.FrameEnd * framePixelWidth + framePixelWidth, pos.Y + ItemHeight - 2); var slotP3 = new Vector2(pos.X + animation.FrameEnd * framePixelWidth + framePixelWidth, pos.Y + ItemHeight - 2 + localCustomHeight); uint slotColor = animation.Color | 0xFF000000; uint slotColorHalf = (animation.Color & 0xFFFFFF) | 0x40000000; if (slotP1.X <= (canvas_size.X + contentMin.X) && slotP2.X >= (contentMin.X + legendWidth)) { draw_list.AddRectFilled(slotP1, slotP3, slotColorHalf, 2); draw_list.AddRectFilled(slotP1, slotP2, slotColor, 2); } if (new ImRect(slotP1, slotP2).Contains(io.MousePos) && io.MouseDoubleClicked[0]) { sequence.DoubleClick(i); } var rects = new ImRect[] { new ImRect(slotP1, new Vector2(slotP1.X + AnimationBarSideSelectionWidth, slotP2.Y)), new ImRect(new Vector2(slotP2.X - AnimationBarSideSelectionWidth, slotP1.Y), slotP2), new ImRect(slotP1, slotP2) }; var quadColor = new uint[] { 0xFFFFFFFF, 0xFFFFFFFF, slotColor + (selected ? 0u : 0x202020u) }; if (movingEntry == -1 && (sequenceOptions.HasFlag(SEQUENCER_OPTIONS.SEQUENCER_EDIT_STARTEND))) // TODOFOCUS && backgroundRect.Contains(io.MousePos)) { const uint AnimationResizeHoverColor = 0xFFFFFFFFu; uint AnimationBarHoverColor = slotColor + 0x202020; var animBarLeftRect = new ImRect(slotP1, new Vector2(slotP1.X + AnimationBarSideSelectionWidth, slotP2.Y)); var animBarRightRect = new ImRect(new Vector2(slotP2.X - AnimationBarSideSelectionWidth, slotP1.Y), slotP2); var animBarRect = new ImRect(slotP1, slotP2); var animationBarPartSelection = AnimationBarPart.None; if (animBarLeftRect.Contains(io.MousePos)) { animationBarPartSelection = AnimationBarPart.SelectionLeft; draw_list.AddRectFilled(animBarLeftRect.Min, animBarLeftRect.Max, AnimationResizeHoverColor, 2); } else if (animBarRightRect.Contains(io.MousePos)) { animationBarPartSelection = AnimationBarPart.SelectionRight; draw_list.AddRectFilled(animBarRightRect.Min, animBarRightRect.Max, AnimationResizeHoverColor, 2); } else if (animBarRect.Contains(io.MousePos)) { animationBarPartSelection = AnimationBarPart.Bar; draw_list.AddRectFilled(animBarRect.Min, animBarRect.Max, AnimationBarHoverColor, 2); } if (ImGui.IsMouseClicked(0) && animationBarPartSelection != AnimationBarPart.None) { if (!new ImRect(childFramePos, childFramePos + childFrameSize).Contains(io.MousePos)) { continue; } if (!MovingScrollBar && !MovingCurrentFrame) { movingEntry = i; movingPos = cx; movingPart = animationBarPartSelection; sequence.BeginEdit(movingEntry); break; } } } // custom draw if (localCustomHeight > 0) { var rp = new Vector2(canvas_pos.X, contentMin.Y + ItemHeight * i + 1 + customHeight); var customRect = new ImRect(rp + new Vector2(legendWidth - (firstFrameUsed - sequence.FrameMin - 0.5f) * framePixelWidth, (float)(ItemHeight)), rp + new Vector2(legendWidth + (sequence.FrameMax - firstFrameUsed - 0.5f + 2f) * framePixelWidth, (float)(localCustomHeight + ItemHeight))); var clippingRect = new ImRect(rp + new Vector2((float)(legendWidth), (float)(ItemHeight)), rp + new Vector2(canvas_size.X, (float)(localCustomHeight + ItemHeight))); var legendRect = new ImRect(rp + new Vector2(0f, (float)(ItemHeight)), rp + new Vector2((float)(legendWidth), (float)(localCustomHeight))); var legendClippingRect = new ImRect(canvas_pos + new Vector2(0f, (float)(ItemHeight)), canvas_pos + new Vector2((float)(legendWidth), (float)(localCustomHeight + ItemHeight))); customDraws.Add(new CustomDraw { index = i, customRect = customRect, legendRect = legendRect, clippingRect = clippingRect, legendClippingRect = legendClippingRect }); } else { var rp = new Vector2(canvas_pos.X, contentMin.Y + ItemHeight * i + customHeight); var customRect = new ImRect(rp + new Vector2(legendWidth - (firstFrameUsed - sequence.FrameMin - 0.5f) * framePixelWidth, (float)(0f)), rp + new Vector2(legendWidth + (sequence.FrameMax - firstFrameUsed - 0.5f + 2f) * framePixelWidth, (float)(ItemHeight))); var clippingRect = new ImRect(rp + new Vector2((float)(legendWidth), (float)(0f)), rp + new Vector2(canvas_size.X, (float)(ItemHeight))); compactCustomDraws.Add(new CustomDraw { index = i, customRect = customRect, legendRect = new ImRect(), clippingRect = clippingRect, legendClippingRect = new ImRect() }); } customHeight += localCustomHeight; } // moving if (/*backgroundRect.Contains(io.MousePos) && */ movingEntry >= 0) { ImGui.CaptureMouseFromApp(); int diffFrame = (int)((cx - movingPos) / framePixelWidth); if (Math.Abs(diffFrame) > 0) { var animation = sequence.GetAnimation(movingEntry); selectedEntry = movingEntry; if (movingPart.HasFlag(AnimationBarPart.SelectionLeft)) { animation.FrameStart += diffFrame; } if (movingPart.HasFlag(AnimationBarPart.SelectionRight)) { animation.FrameEnd += diffFrame; } if (animation.FrameStart < 0) { if (movingPart.HasFlag(AnimationBarPart.SelectionRight)) { animation.FrameEnd -= animation.FrameStart; } animation.FrameStart = 0; } if (movingPart.HasFlag(AnimationBarPart.SelectionLeft) && animation.FrameStart > animation.FrameEnd) { animation.FrameStart = animation.FrameEnd; } if (movingPart.HasFlag(AnimationBarPart.SelectionRight) && animation.FrameEnd < animation.FrameStart) { animation.FrameEnd = animation.FrameStart; } movingPos += (int)(diffFrame * framePixelWidth); } if (!io.MouseDown[0]) { // single select if (/*diffFrame != 0 &&*/ movingPart != 0) { selectedEntry = movingEntry; ret = true; } movingEntry = -1; sequence.EndEdit(); } } // cursor if (currentFrame >= firstFrame && currentFrame <= sequence.FrameMax) { const float cursorWidth = 8f; float cursorOffset = contentMin.X + legendWidth + (currentFrame - firstFrameUsed) * framePixelWidth + framePixelWidth / 2 - cursorWidth * 0.5f; draw_list.AddLine(new Vector2(cursorOffset, canvas_pos.Y), new Vector2(cursorOffset, contentMax.Y), 0xA02A2AFF, cursorWidth); draw_list.AddText(new Vector2(cursorOffset + 10, canvas_pos.Y + 2), 0xFF2A2AFF, $"{currentFrame}"); } draw_list.PopClipRect(); draw_list.PopClipRect(); foreach (var customDraw in customDraws) { sequence.CustomDraw(customDraw.index, draw_list, customDraw.customRect, customDraw.legendRect, customDraw.clippingRect, customDraw.legendClippingRect); } foreach (var customDraw in compactCustomDraws) { sequence.CustomDrawCompact(customDraw.index, draw_list, customDraw.customRect, customDraw.clippingRect); } // copy paste if (sequenceOptions.HasFlag(SEQUENCER_OPTIONS.SEQUENCER_COPYPASTE)) { var rectCopy = new ImRect(new Vector2(contentMin.X + 100, canvas_pos.Y + 2) , new Vector2(contentMin.X + 100 + 30, canvas_pos.Y + ItemHeight - 2)); bool inRectCopy = rectCopy.Contains(io.MousePos); uint copyColor = inRectCopy ? 0xFF1080FF : 0xFF000000; draw_list.AddText(rectCopy.Min, copyColor, "Copy"); var rectPaste = new ImRect(new Vector2(contentMin.X + 140, canvas_pos.Y + 2) , new Vector2(contentMin.X + 140 + 30, canvas_pos.Y + ItemHeight - 2)); bool inRectPaste = rectPaste.Contains(io.MousePos); uint pasteColor = inRectPaste ? 0xFF1080FF : 0xFF000000; draw_list.AddText(rectPaste.Min, pasteColor, "Paste"); if (inRectCopy && io.MouseReleased[0]) { sequence.Copy(); } if (inRectPaste && io.MouseReleased[0]) { sequence.Paste(); } } // ImGui.EndChildFrame(); ImGui.PopStyleColor(); if (hasScrollBar) { ImGui.InvisibleButton("scrollBar", scrollBarSize); Vector2 scrollBarMin = ImGui.GetItemRectMin(); Vector2 scrollBarMax = ImGui.GetItemRectMax(); // ratio = number of frames visible in control / number to total frames float startFrameOffset = ((float)(firstFrameUsed - sequence.FrameMin) / (float)frameCount) * (canvas_size.X - legendWidth); var scrollBarA = new Vector2(scrollBarMin.X + legendWidth, scrollBarMin.Y - 2); var scrollBarB = new Vector2(scrollBarMin.X + canvas_size.X, scrollBarMax.Y - 1); draw_list.AddRectFilled(scrollBarA, scrollBarB, 0xFF222222, 0); var scrollBarRect = new ImRect(scrollBarA, scrollBarB); bool inScrollBar = scrollBarRect.Contains(io.MousePos); draw_list.AddRectFilled(scrollBarA, scrollBarB, 0xFF101010, 8); var scrollBarC = new Vector2(scrollBarMin.X + legendWidth + startFrameOffset, scrollBarMin.Y); var scrollBarD = new Vector2(scrollBarMin.X + legendWidth + barWidthInPixels + startFrameOffset, scrollBarMax.Y - 2); draw_list.AddRectFilled(scrollBarC, scrollBarD, (inScrollBar || MovingScrollBar) ? 0xFF606060 : 0xFF505050, 6); float handleRadius = (scrollBarMax.Y - scrollBarMin.Y) / 2; var barHandleLeft = new ImRect(scrollBarC, new Vector2(scrollBarC.X + 14, scrollBarD.Y)); var barHandleRight = new ImRect(new Vector2(scrollBarD.X - 14, scrollBarC.Y), scrollBarD); bool onLeft = barHandleLeft.Contains(io.MousePos); bool onRight = barHandleRight.Contains(io.MousePos); draw_list.AddRectFilled(barHandleLeft.Min, barHandleLeft.Max, (onLeft || sizingLBar) ? 0xFFAAAAAA : 0xFF666666, 6); draw_list.AddRectFilled(barHandleRight.Min, barHandleRight.Max, (onRight || sizingRBar) ? 0xFFAAAAAA : 0xFF666666, 6); var scrollBarThumb = new ImRect(scrollBarC, scrollBarD); if (sizingRBar) { if (!io.MouseDown[0]) { sizingRBar = false; } else { // Resize scrollbar from the right float barNewWidth = Math.Max(barWidthInPixels + io.MouseDelta.X, MinBarWidth); float barRatio = barNewWidth / barWidthInPixels; framePixelWidthTarget = framePixelWidth = framePixelWidth / barRatio; int newVisibleFrameCount = (int)((canvas_size.X - legendWidth) / framePixelWidthTarget); int lastFrame = firstFrame + newVisibleFrameCount; if (lastFrame > sequence.FrameMax) { framePixelWidthTarget = framePixelWidth = (canvas_size.X - legendWidth) / (float)(sequence.FrameMax - firstFrame); } } } else if (sizingLBar) { if (!io.MouseDown[0]) { sizingLBar = false; } else { // Resize scrollbar from the left if (Math.Abs(io.MouseDelta.X) > FLT_EPSILON) { float barNewWidth = Math.Max(barWidthInPixels - io.MouseDelta.X, MinBarWidth); float barRatio = barNewWidth / barWidthInPixels; float previousFramePixelWidthTarget = framePixelWidthTarget; framePixelWidthTarget = framePixelWidth = framePixelWidth / barRatio; int newVisibleFrameCount = (int)(visibleFrameCount / barRatio); int newFirstFrame = firstFrame + newVisibleFrameCount - visibleFrameCount; newFirstFrame = Math.Clamp(newFirstFrame, sequence.FrameMin, Math.Max(sequence.FrameMax - visibleFrameCount, sequence.FrameMin)); if (newFirstFrame == firstFrame) { framePixelWidth = framePixelWidthTarget = previousFramePixelWidthTarget; } else { firstFrame = newFirstFrame; } } } } else { if (MovingScrollBar) { if (!io.MouseDown[0]) { MovingScrollBar = false; } else { float framesPerPixelInBar = barWidthInPixels / (float)visibleFrameCount; firstFrame = (int)((io.MousePos.X - panningViewSource.X) / framesPerPixelInBar) - panningViewFrame; firstFrame = Math.Clamp(firstFrame, sequence.FrameMin, Math.Max(sequence.FrameMax - visibleFrameCount, sequence.FrameMin)); } } else { if (scrollBarThumb.Contains(io.MousePos) && ImGui.IsMouseClicked(0) && !MovingCurrentFrame && movingEntry == -1) { MovingScrollBar = true; panningViewSource = io.MousePos; panningViewFrame = firstFrame; } if (!sizingRBar && onRight && ImGui.IsMouseClicked(0)) { sizingRBar = true; } if (!sizingLBar && onLeft && ImGui.IsMouseClicked(0)) { sizingLBar = true; } } } } } ImGui.EndGroup(); if (regionRect.Contains(io.MousePos)) { bool overCustomDraw = false; foreach (var custom in customDraws) { if (custom.customRect.Contains(io.MousePos)) { overCustomDraw = true; } } if (overCustomDraw) { } else { //frameOverCursor = *firstFrame + (int)(visibleFrameCount * ((io.MousePos.X - (float)legendWidth - canvas_pos.X) / (canvas_size.X - legendWidth))); ////frameOverCursor = max(min(*firstFrame - visibleFrameCount / 2, frameCount - visibleFrameCount), 0); ///**firstFrame -= frameOverCursor; //*firstFrame *= framePixelWidthTarget / framePixelWidth; //*firstFrame += frameOverCursor;*/ //if (io.MouseWheel < -FLT_EPSILON) //{ // *firstFrame -= frameOverCursor; // *firstFrame = int(*firstFrame * 1.1f); // framePixelWidthTarget *= 0.9f; // *firstFrame += frameOverCursor; //} //if (io.MouseWheel > FLT_EPSILON) //{ // *firstFrame -= frameOverCursor; // *firstFrame = int(*firstFrame * 0.9f); // framePixelWidthTarget *= 1.1f; // *firstFrame += frameOverCursor; //} } } if (expanded) { bool overExpanded = SequencerAddDelButton(draw_list, new Vector2(canvas_pos.X + 2, canvas_pos.Y + 2), !expanded); if (overExpanded && io.MouseReleased[0]) { expanded = !expanded; } } if (deleteAnimationEntry >= 0) { sequence.RemoveAnimation(deleteAnimationEntry); if ((selectedEntry == deleteAnimationEntry || selectedEntry >= sequence.ItemCount)) { selectedEntry = -1; } } if (duplicateAnimationEntry >= 0) { sequence.DuplicateAnimation(duplicateAnimationEntry); } if (insertAnimationEntry >= 0) { sequence.AddAnimation(); } return(ret); }
public static void Parse(ISettings settings, List <ISettingsHolder> draws, int id = -1) { if (settings == null) { DebugWindow.LogError("Cant parse null settings."); return; } var props = settings.GetType().GetProperties(); foreach (var property in props) { if (property.GetCustomAttribute <IgnoreMenuAttribute>() != null) { continue; } var menuAttribute = property.GetCustomAttribute <MenuAttribute>(); var isSettings = property.PropertyType.GetInterfaces().ContainsF(typeof(ISettings)); if (property.Name == "Enable" && menuAttribute == null) { continue; } if (menuAttribute == null) { menuAttribute = new MenuAttribute(Regex.Replace(property.Name, "(\\B[A-Z])", " $1")); } var holder = new SettingsHolder { Name = menuAttribute.MenuName, Tooltip = menuAttribute.Tooltip, ID = menuAttribute.index == -1 ? MathHepler.Randomizer.Next(int.MaxValue) : menuAttribute.index }; if (isSettings) { var innerSettings = (ISettings)property.GetValue(settings); if (menuAttribute.index != -1) { holder.Type = HolderChildType.Tab; draws.Add(holder); Parse(innerSettings, draws, menuAttribute.index); var parent = GetAllDrawers(draws).Find(x => x.ID == menuAttribute.parentIndex); parent?.Children.Add(holder); } else { Parse(innerSettings, draws); } continue; } var type = property.GetValue(settings); if (menuAttribute.parentIndex != -1) { var parent = GetAllDrawers(draws).Find(x => x.ID == menuAttribute.parentIndex); parent?.Children.Add(holder); } else if (id != -1) { var parent = GetAllDrawers(draws).Find(x => x.ID == id); parent?.Children.Add(holder); } else { draws.Add(holder); } switch (type) { case ButtonNode n: holder.DrawDelegate = () => { if (ImGui.Button(holder.Unique)) { n.OnPressed(); } }; break; case EmptyNode n: break; case HotkeyNode n: holder.DrawDelegate = () => { var holderName = $"{holder.Name} {n.Value}##{n.Value}"; var open = true; if (ImGui.Button(holderName)) { ImGui.OpenPopup(holderName); open = true; } if (ImGui.BeginPopupModal(holderName, ref open, (ImGuiWindowFlags)35)) { if (Input.GetKeyState(Keys.Escape)) { ImGui.CloseCurrentPopup(); ImGui.EndPopup(); return; } foreach (var key in Enum.GetValues(typeof(Keys))) { var keyState = Input.GetKeyState((Keys)key); if (keyState) { n.Value = (Keys)key; ImGui.CloseCurrentPopup(); break; } } ImGui.Text($" Press new key to change '{n.Value}' or Esc for exit."); ImGui.EndPopup(); } }; break; case ToggleNode n: holder.DrawDelegate = () => { var value = n.Value; ImGui.Checkbox(holder.Unique, ref value); n.Value = value; }; break; case ColorNode n: holder.DrawDelegate = () => { var vector4 = n.Value.ToVector4().ToVector4Num(); if (ImGui.ColorEdit4(holder.Unique, ref vector4, ImGuiColorEditFlags.AlphaBar | ImGuiColorEditFlags.NoInputs | ImGuiColorEditFlags.AlphaPreviewHalf)) { n.Value = vector4.ToSharpColor(); } }; break; case ListNode n: holder.DrawDelegate = () => { if (ImGui.BeginCombo(holder.Unique, n.Value)) { foreach (var t in n.Values) { if (ImGui.Selectable(t)) { n.Value = t; ImGui.EndCombo(); return; } } ImGui.EndCombo(); } }; break; case FileNode n: holder.DrawDelegate = () => { if (ImGui.TreeNode(holder.Unique)) { var selected = n.Value; if (ImGui.BeginChildFrame(1, new Vector2(0, 300))) { var di = new DirectoryInfo("config"); if (di.Exists) { foreach (var file in di.GetFiles()) { if (ImGui.Selectable(file.Name, selected == file.FullName)) { n.Value = file.FullName; } } } ImGui.EndChildFrame(); } ImGui.TreePop(); } }; break; case RangeNode <int> n: holder.DrawDelegate = () => { var r = n.Value; ImGui.SliderInt(holder.Unique, ref r, n.Min, n.Max); n.Value = r; }; break; case RangeNode <float> n: holder.DrawDelegate = () => { var r = n.Value; ImGui.SliderFloat(holder.Unique, ref r, n.Min, n.Max); n.Value = r; }; break; case RangeNode <long> n: holder.DrawDelegate = () => { var r = (int)n.Value; ImGui.SliderInt(holder.Unique, ref r, (int)n.Min, (int)n.Max); n.Value = r; }; break; case RangeNode <Vector2> n: holder.DrawDelegate = () => { var vect = n.Value; ImGui.SliderFloat2(holder.Unique, ref vect, n.Min.X, n.Max.X); n.Value = vect; }; break; default: Core.Logger.Warning($"{type} not supported for menu now. Ask developers to add this type."); break; } } }
private static void HandleType(SettingsHolder holder, object type, string propertyInfo) { switch (type) { case ButtonNode buttonNode: holder.DrawDelegate = () => { if (ImGui.Button(holder.Unique)) { buttonNode.OnPressed(); } }; return; case null: case EmptyNode _: holder.DrawDelegate = () => { }; return; case HotkeyNode hotkeyNode: holder.DrawDelegate = () => { var str = $"{holder.Name} {hotkeyNode.Value}##{hotkeyNode.Value}"; if (ImGui.Button(str)) { // Clear async buffer state Input.ClearAsyncBuffer(); // Begin pop up ImGui.OpenPopup(str); } // Create modal var popupOpened = true; if (ImGui.BeginPopupModal(str, ref popupOpened, ImGuiWindowFlags.NoTitleBar | ImGuiWindowFlags.NoResize | ImGuiWindowFlags.NoCollapse)) { ButtonPopupVisible = true; } else { return; } // Close popup if escape was pressed if (Input.GetKeyState(Keys.Escape)) { ImGui.CloseCurrentPopup(); ImGui.EndPopup(); ButtonPopupVisible = false; return; } // Get prssed keys Keys key = Input.GetPressedKeys(true); // If a key was pressed, set value and close popup if ((key & Keys.KeyCode) != Keys.None) { // Set the node's value to the keys that were pressed and close the popup hotkeyNode.Value = key; ImGui.CloseCurrentPopup(); ButtonPopupVisible = false; } // End popup ImGui.Text($"Press new key to change '{hotkeyNode.Value}' or Esc for exit."); ImGui.EndPopup(); }; return; case ToggleNode toggleNode: holder.DrawDelegate = () => { var isChecked = toggleNode.Value; ImGui.Checkbox(holder.Unique, ref isChecked); toggleNode.Value = isChecked; }; return; case ColorNode colorNode: holder.DrawDelegate = () => { var color = colorNode.Value.ToVector4().ToVector4Num(); if (ImGui.ColorEdit4(holder.Unique, ref color, ImGuiColorEditFlags.NoInputs | ImGuiColorEditFlags.AlphaBar | ImGuiColorEditFlags.AlphaPreviewHalf)) { colorNode.Value = color.ToSharpColor(); } }; return; case ListNode listNode: holder.DrawDelegate = () => { if (!ImGui.BeginCombo(holder.Unique, listNode.Value)) { return; } foreach (var value in listNode.Values) { if (!ImGui.Selectable(value)) { continue; } listNode.Value = value; break; } ImGui.EndCombo(); }; return; case FileNode fileNode: holder.DrawDelegate = () => { if (!ImGui.TreeNode(holder.Unique)) { return; } var value = fileNode.Value; if (ImGui.BeginChildFrame(1, new Vector2(0f, 300f))) { var directoryInfo = new DirectoryInfo("config"); if (directoryInfo.Exists) { var files = directoryInfo.GetFiles(); foreach (var fileInfo in files) { if (ImGui.Selectable(fileInfo.Name, value == fileInfo.FullName)) { fileNode.Value = fileInfo.FullName; } } } ImGui.EndChildFrame(); } ImGui.TreePop(); }; return; case RangeNode <int> iRangeNode: holder.DrawDelegate = () => { var value = iRangeNode.Value; ImGui.SliderInt(holder.Unique, ref value, iRangeNode.Min, iRangeNode.Max); iRangeNode.Value = value; }; return; case RangeNode <float> fRangeNode: holder.DrawDelegate = () => { var value = fRangeNode.Value; ImGui.SliderFloat(holder.Unique, ref value, fRangeNode.Min, fRangeNode.Max); fRangeNode.Value = value; }; return; case RangeNode <long> lRangeNode: holder.DrawDelegate = () => { var value = (int)lRangeNode.Value; ImGui.SliderInt(holder.Unique, ref value, (int)lRangeNode.Min, (int)lRangeNode.Max); lRangeNode.Value = value; }; return; case RangeNode <Vector2> vRangeNode: holder.DrawDelegate = () => { var value = vRangeNode.Value; ImGui.SliderFloat2(holder.Unique, ref value, vRangeNode.Min.X, vRangeNode.Max.X); vRangeNode.Value = value; }; return; case TextNode textNode: holder.DrawDelegate = () => { var value = textNode.Value; ImGui.InputText(holder.Unique, ref value, 200); textNode.Value = value; }; return; } }
private bool DrawFolder(ref string selected, bool returnOnSelection = false) { ImGui.Text("Current Folder: " + CurrentFolder); bool result = false; if (ImGui.BeginChildFrame(1, DefaultFilePickerSize, ImGuiWindowFlags.ChildMenu)) { DirectoryInfo di = new DirectoryInfo(CurrentFolder); if (di.Exists) { if (di.Parent != null) { ImGui.PushStyleColor(ImGuiCol.Text, RgbaFloat.Yellow.ToVector4()); if (ImGui.Selectable("../", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = di.Parent.FullName; } ImGui.PopStyleColor(); } foreach (var fse in Directory.EnumerateFileSystemEntries(di.FullName)) { if (Directory.Exists(fse)) { string name = Path.GetFileName(fse); ImGui.PushStyleColor(ImGuiCol.Text, RgbaFloat.Yellow.ToVector4()); if (ImGui.Selectable(name + "/", false, ImGuiSelectableFlags.DontClosePopups)) { CurrentFolder = fse; } ImGui.PopStyleColor(); } else if (!PickDirectory) { var ext = Path.GetExtension(fse); if (Extensions == null || Extensions.Contains(ext)) { var name = Path.GetFileName(fse); bool isSelected = SelectedFile == fse; if (ImGui.Selectable(name, isSelected, ImGuiSelectableFlags.DontClosePopups)) { SelectedFile = fse; if (returnOnSelection) { result = true; selected = SelectedFile; } } } } } } } ImGui.EndChildFrame(); if (PickDirectory) { if (ImGui.Button("Select")) { result = true; selected = CurrentFolder; ImGui.CloseCurrentPopup(); } } else { if (ImGui.Button("Cancel")) { result = false; ImGui.CloseCurrentPopup(); } if (SelectedFile != null) { ImGui.SameLine(); if (ImGui.Button("Open")) { result = true; selected = SelectedFile; ImGui.CloseCurrentPopup(); } } } return(result); }
public override void OnInspectorGUI() { var gameObject = target as GameObject; if (gameObject == null) { return; } ImGui.BeginChildFrame(0, new Vector2(ImGui.GetWindowWidth(), 25f), WindowFlags.NoScrollbar); { ImGui.Columns(2, "Tags and Layers Columns", false); var tagIndex = gameObject.tagIndex; if (ImGui.Combo("Tag", ref tagIndex, TagLayerManager.instanceTags.ToArray())) { gameObject.tagIndex = tagIndex; } ImGui.SameLine(); if (ImGui.Button(" + ")) { TagLayerManager.Select(); } ImGui.NextColumn(); ImGui.SetColumnOffset(1, ImGui.GetWindowContentRegionWidth() * 0.4f); var layerIndex = gameObject.layerIndex; if (ImGui.Combo("Layer", ref layerIndex, TagLayerManager.instanceLayers.ToArray())) { gameObject.layerIndex = layerIndex; } ImGui.SameLine(); if (ImGui.Button(" + ")) { TagLayerManager.Select(); } } ImGui.EndChildFrame(); var components = gameObject.GetComponents <Component>().ToList(); foreach (var component in components) { ImGui.PushID(component.id); { if (DrawCollapsingHeader(component)) { var componentType = component.GetType(); if (s_ComponentEditors.TryGetValue(componentType, out Inspector editor)) { editor.target = component; editor.OnInspectorGUI(); } else if (componentType.IsGenericType) { var foundEditor = false; foreach (var keyValuePair in s_ComponentEditors) { var underlyingType = componentType.GetGenericTypeDefinition(); if (underlyingType != keyValuePair.Key) { continue; } keyValuePair.Value.target = component; keyValuePair.Value.OnInspectorGUI(); foundEditor = true; break; } if (!foundEditor) { s_DefaultInspector.target = component; s_DefaultInspector.OnInspectorGUI(); } } else { s_DefaultInspector.target = component; s_DefaultInspector.OnInspectorGUI(); } } } ImGui.PopID(); } ImGui.LabelText("", ""); ImGui.Columns(3, "Add Component Column", false); { ImGui.NextColumn(); if (ImGui.Button( "Add Component", new Vector2(ImGui.GetColumnWidth(ImGui.GetColumnIndex()) - 15f, 0))) { ImGui.OpenPopup("Add Component Popup"); } if (ImGui.BeginPopup("Add Component Popup")) { foreach (var type in Assembly.GetCallingAssembly().GetTypes()) { if (!typeof(Component).IsAssignableFrom(type) || type.IsAbstract) { continue; } if (ImGui.MenuItem(type.Name)) { gameObject.AddComponent(type); } } ImGui.EndPopup(); } } }