From 68eb8b9f212db01edde27d1805abefd53df2100f Mon Sep 17 00:00:00 2001 From: Wojtek Figat Date: Fri, 30 Aug 2024 12:58:12 +0200 Subject: [PATCH] Fix properties editor labels positioning #2530 #2609 --- .../CustomEditors/Editors/CollectionEditor.cs | 22 ++++++++++++++----- .../CustomEditors/Editors/GenericEditor.cs | 12 +++++----- .../Editors/LocalizedStringEditor.cs | 6 ++--- .../Container/PropertiesListElement.cs | 9 ++------ .../GUI/CheckablePropertyNameLabel.cs | 2 ++ .../CustomEditors/GUI/PropertiesList.cs | 15 ++++++++++--- .../CustomEditors/GUI/PropertyNameLabel.cs | 13 +++++++++++ .../CustomEditors/LayoutElementsContainer.cs | 15 ++++++++++++- 8 files changed, 68 insertions(+), 26 deletions(-) diff --git a/Source/Editor/CustomEditors/Editors/CollectionEditor.cs b/Source/Editor/CustomEditors/Editors/CollectionEditor.cs index 7c0670010..5f0ad17c4 100644 --- a/Source/Editor/CustomEditors/Editors/CollectionEditor.cs +++ b/Source/Editor/CustomEditors/Editors/CollectionEditor.cs @@ -53,7 +53,7 @@ namespace FlaxEditor.CustomEditors.Editors Index = index; SetupContextMenu += OnSetupContextMenu; - _arrangeButtonRect = new Rectangle(2, 3, 12, 12); + _arrangeButtonRect = new Rectangle(2, 4, 12, 12); // Extend margin of the label to support a dragging handle. Margin m = Margin; @@ -75,7 +75,7 @@ namespace FlaxEditor.CustomEditors.Editors b = menu.AddButton("Move down", OnMoveDownClicked); b.Enabled = Index + 1 < Editor.Count && !Editor._readOnly; - + b = menu.AddButton("Remove", OnRemoveClicked); b.Enabled = !Editor._readOnly; } @@ -88,13 +88,12 @@ namespace FlaxEditor.CustomEditors.Editors _arrangeButtonInUse = false; } - /// public override void Draw() { base.Draw(); - var style = FlaxEngine.GUI.Style.Current; + var style = FlaxEngine.GUI.Style.Current; var mousePosition = PointFromScreen(Input.MouseScreenPosition); var dragBarColor = _arrangeButtonRect.Contains(mousePosition) ? style.Foreground : style.ForegroundGrey; Render2D.DrawSprite(FlaxEditor.Editor.Instance.Icons.DragBar12, _arrangeButtonRect, _arrangeButtonInUse ? Color.Orange : dragBarColor); @@ -104,6 +103,14 @@ namespace FlaxEditor.CustomEditors.Editors } } + /// + protected override void OnSizeChanged() + { + base.OnSizeChanged(); + + _arrangeButtonRect.Y = (Height - _arrangeButtonRect.Height) * 0.5f; + } + private bool ArrangeAreaCheck(out int index, out Rectangle rect) { var child = Editor.ChildrenEditors[0]; @@ -278,10 +285,10 @@ namespace FlaxEditor.CustomEditors.Editors public override void Draw() { base.Draw(); + if (_canReorder) { var style = FlaxEngine.GUI.Style.Current; - var mousePosition = PointFromScreen(Input.MouseScreenPosition); var dragBarColor = _arrangeButtonRect.Contains(mousePosition) ? style.Foreground : style.ForegroundGrey; Render2D.DrawSprite(FlaxEditor.Editor.Instance.Icons.DragBar12, _arrangeButtonRect, _arrangeButtonInUse ? Color.Orange : dragBarColor); @@ -519,6 +526,7 @@ namespace FlaxEditor.CustomEditors.Editors (elementType.GetProperties().Length == 1 && elementType.GetFields().Length == 0) || elementType.Equals(new ScriptType(typeof(JsonAsset))) || elementType.Equals(new ScriptType(typeof(SettingsBase))); + bool prevWasNestedPropertiesList = false; for (int i = 0; i < size; i++) { // Apply spacing @@ -538,6 +546,7 @@ namespace FlaxEditor.CustomEditors.Editors itemLabel.LinkedEditor = itemLayout.Object(new ListValueContainer(elementType, i, Values, attributes), overrideEditor); if (_readOnly && itemLayout.Children.Count > 0) GenericEditor.OnReadOnlyProperty(itemLayout); + prevWasNestedPropertiesList = false; } else if (_displayType == CollectionAttribute.DisplayType.Header || (_displayType == CollectionAttribute.DisplayType.Default && !single)) { @@ -547,6 +556,7 @@ namespace FlaxEditor.CustomEditors.Editors cdp.CustomControl.LinkedEditor = itemLayout.Object(new ListValueContainer(elementType, i, Values, attributes), overrideEditor); if (_readOnly && itemLayout.Children.Count > 0) GenericEditor.OnReadOnlyProperty(itemLayout); + prevWasNestedPropertiesList = false; } } } @@ -663,7 +673,7 @@ namespace FlaxEditor.CustomEditors.Editors cloned[i] = tmp; } } - + SetValue(cloned); } diff --git a/Source/Editor/CustomEditors/Editors/GenericEditor.cs b/Source/Editor/CustomEditors/Editors/GenericEditor.cs index 1eb1c5f90..343ac917d 100644 --- a/Source/Editor/CustomEditors/Editors/GenericEditor.cs +++ b/Source/Editor/CustomEditors/Editors/GenericEditor.cs @@ -560,19 +560,19 @@ namespace FlaxEditor.CustomEditors.Editors internal static void OnReadOnlyProperty(LayoutElementsContainer itemLayout, int labelIndex = -1) { - PropertiesListElement list = null; + PropertiesList list = null; int firstChildControlIndex = 0; bool disableSingle = true; var control = itemLayout.Children[itemLayout.Children.Count - 1]; if (control is GroupElement group && group.Children.Count > 0) { - list = group.Children[0] as PropertiesListElement; + list = (group.Children[0] as PropertiesListElement)?.Properties; disableSingle = false; // Disable all nested editors } else if (control is PropertiesListElement list1 && labelIndex != -1) { - list = list1; - firstChildControlIndex = list.Labels[labelIndex].FirstChildControlIndex; + list = list1.Labels[labelIndex].FirstChildControlContainer ?? list1.Properties; + firstChildControlIndex = list1.Labels[labelIndex].FirstChildControlIndex; } else if (control?.Control != null) { @@ -582,10 +582,10 @@ namespace FlaxEditor.CustomEditors.Editors if (list != null) { // Disable controls added to the editor - var count = list.Properties.Children.Count; + var count = list.Children.Count; for (int j = firstChildControlIndex; j < count; j++) { - var child = list.Properties.Children[j]; + var child = list.Children[j]; if (disableSingle && child is PropertyNameLabel) break; diff --git a/Source/Editor/CustomEditors/Editors/LocalizedStringEditor.cs b/Source/Editor/CustomEditors/Editors/LocalizedStringEditor.cs index 5fe374337..efa6581f5 100644 --- a/Source/Editor/CustomEditors/Editors/LocalizedStringEditor.cs +++ b/Source/Editor/CustomEditors/Editors/LocalizedStringEditor.cs @@ -33,10 +33,10 @@ namespace FlaxEditor.CustomEditors.Editors if (layout.Children.Count == 0) return; var propList = layout.Children[layout.Children.Count - 1] as PropertiesListElement; - if (propList == null || propList.Children.Count != 2) + if (propList == null || propList.Children.Count < 2) return; - var idElement = propList.Children[0] as TextBoxElement; - var valueElement = propList.Children[1] as TextBoxElement; + var idElement = propList.Children[propList.Children.Count - 2] as TextBoxElement; + var valueElement = propList.Children[propList.Children.Count - 1] as TextBoxElement; if (idElement == null || valueElement == null) return; _idElement = idElement; diff --git a/Source/Editor/CustomEditors/Elements/Container/PropertiesListElement.cs b/Source/Editor/CustomEditors/Elements/Container/PropertiesListElement.cs index 0862200da..c7705b336 100644 --- a/Source/Editor/CustomEditors/Elements/Container/PropertiesListElement.cs +++ b/Source/Editor/CustomEditors/Elements/Container/PropertiesListElement.cs @@ -53,13 +53,7 @@ namespace FlaxEditor.CustomEditors.Elements internal void OnAddProperty(string name, string tooltip) { - var label = new PropertyNameLabel(name) - { - Parent = Properties, - TooltipText = tooltip, - FirstChildControlIndex = Properties.Children.Count - }; - Labels.Add(label); + OnAddProperty(new PropertyNameLabel(name), tooltip); } internal void OnAddProperty(PropertyNameLabel label, string tooltip) @@ -88,6 +82,7 @@ namespace FlaxEditor.CustomEditors.Elements public override void ClearLayout() { base.ClearLayout(); + Labels.Clear(); } } diff --git a/Source/Editor/CustomEditors/GUI/CheckablePropertyNameLabel.cs b/Source/Editor/CustomEditors/GUI/CheckablePropertyNameLabel.cs index 3cd8b57c1..0ce5f441e 100644 --- a/Source/Editor/CustomEditors/GUI/CheckablePropertyNameLabel.cs +++ b/Source/Editor/CustomEditors/GUI/CheckablePropertyNameLabel.cs @@ -58,6 +58,8 @@ namespace FlaxEditor.CustomEditors.GUI // Update child controls enabled state if (FirstChildControlIndex >= 0 && Parent is PropertiesList propertiesList) { + if (FirstChildControlContainer != null) + propertiesList = FirstChildControlContainer; var controls = propertiesList.Children; var labels = propertiesList.Element.Labels; var thisIndex = labels.IndexOf(this); diff --git a/Source/Editor/CustomEditors/GUI/PropertiesList.cs b/Source/Editor/CustomEditors/GUI/PropertiesList.cs index 208dc64e6..25580c503 100644 --- a/Source/Editor/CustomEditors/GUI/PropertiesList.cs +++ b/Source/Editor/CustomEditors/GUI/PropertiesList.cs @@ -245,16 +245,25 @@ namespace FlaxEditor.CustomEditors.GUI for (int i = 0; i < count; i++) { var label = _element.Labels[i]; + var container = label.FirstChildControlContainer ?? this; if (label.FirstChildControlIndex < 0) yStarts[i] = 0; - else if (_children.Count <= label.FirstChildControlIndex) + else if (container.ChildrenCount <= label.FirstChildControlIndex) yStarts[i] = y; + else if (label.FirstChildControlContainer != null) + { + var firstChild = label.FirstChildControlContainer.Children[label.FirstChildControlIndex]; + yStarts[i] = firstChild.PointToParent(this, Float2.Zero).Y; + if (i == count - 1) + yStarts[i + 1] = firstChild.PointToParent(this, firstChild.Size).Y; + } else { - yStarts[i] = _children[label.FirstChildControlIndex].Top; + var firstChild = _children[label.FirstChildControlIndex]; + yStarts[i] = firstChild.Top; if (i == count - 1) - yStarts[i + 1] = _children[label.FirstChildControlIndex].Bottom; + yStarts[i + 1] = firstChild.Bottom; } } diff --git a/Source/Editor/CustomEditors/GUI/PropertyNameLabel.cs b/Source/Editor/CustomEditors/GUI/PropertyNameLabel.cs index 035c90fe9..1301be318 100644 --- a/Source/Editor/CustomEditors/GUI/PropertyNameLabel.cs +++ b/Source/Editor/CustomEditors/GUI/PropertyNameLabel.cs @@ -30,6 +30,11 @@ namespace FlaxEditor.CustomEditors.GUI /// internal int FirstChildControlIndex; + /// + /// Helper value used by the to draw property names in a proper area. + /// + internal PropertiesList FirstChildControlContainer; + /// /// The linked custom editor (shows the label property). /// @@ -154,8 +159,16 @@ namespace FlaxEditor.CustomEditors.GUI public override void OnDestroy() { SetupContextMenu = null; + LinkedEditor = null; + FirstChildControlContainer = null; base.OnDestroy(); } + + /// + public override string ToString() + { + return Text.ToString(); + } } } diff --git a/Source/Editor/CustomEditors/LayoutElementsContainer.cs b/Source/Editor/CustomEditors/LayoutElementsContainer.cs index 0ec88238e..427b8bf74 100644 --- a/Source/Editor/CustomEditors/LayoutElementsContainer.cs +++ b/Source/Editor/CustomEditors/LayoutElementsContainer.cs @@ -666,7 +666,20 @@ namespace FlaxEditor.CustomEditors } var property = AddPropertyItem(name, tooltip); - return property.Object(values, editor); + int start = property.Properties.Children.Count; + var result = property.Object(values, editor); + + // Special case when properties list is nested into another properties list (eg. array of structures or LocalizedString editor) + if (this is PropertiesListElement thisPropertiesList && + editor.ParentEditor != null && + editor.ParentEditor.LinkedLabel != null && + editor.ParentEditor.LinkedLabel.FirstChildControlContainer == null) + { + editor.ParentEditor.LinkedLabel.FirstChildControlIndex = start; + editor.ParentEditor.LinkedLabel.FirstChildControlContainer = property.Properties; + } + + return result; } ///