mirror of
https://github.com/space-wizards/RobustToolbox.git
synced 2026-02-14 19:29:36 +01:00
WPF layout (#1581)
This commit is contained in:
committed by
GitHub
parent
771a256925
commit
583b7ebf38
@@ -29,9 +29,9 @@ namespace Robust.Build.Tasks
|
||||
public static Parser<char, float[]> Thickness { get; }
|
||||
= SkipWhitespaces.Then(
|
||||
OneOf(
|
||||
Try(Single1.Select(c => new[] {c})),
|
||||
Try(Single4.Select(c => new[] {c.Item1, c.Item2, c.Item3, c.Item4})),
|
||||
Try(Single2.Select(c => new[] {c.Item1, c.Item2})),
|
||||
Try(Single4.Select(c => new[] {c.Item1, c.Item2, c.Item3, c.Item4}))
|
||||
Try(Single1.Select(c => new[] {c}))
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
32
Robust.Client.Injectors/RXamlColorAstNode.cs
Normal file
32
Robust.Client.Injectors/RXamlColorAstNode.cs
Normal file
@@ -0,0 +1,32 @@
|
||||
using System.Reflection.Emit;
|
||||
using XamlX.Ast;
|
||||
using XamlX.Emit;
|
||||
using XamlX.IL;
|
||||
using XamlX.TypeSystem;
|
||||
|
||||
namespace Robust.Build.Tasks
|
||||
{
|
||||
internal class RXamlColorAstNode
|
||||
: XamlAstNode, IXamlAstValueNode, IXamlAstILEmitableNode
|
||||
{
|
||||
private readonly IXamlMethod _method;
|
||||
private readonly string _color;
|
||||
|
||||
public RXamlColorAstNode(IXamlLineInfo lineInfo, RXamlWellKnownTypes types, string color) : base(lineInfo)
|
||||
{
|
||||
_color = color;
|
||||
Type = new XamlAstClrTypeReference(lineInfo, types.Color, false);
|
||||
_method = types.ColorFromXaml;
|
||||
}
|
||||
|
||||
public IXamlAstTypeReference Type { get; }
|
||||
|
||||
public XamlILNodeEmitResult Emit(XamlEmitContext<IXamlILEmitter, XamlILNodeEmitResult> context, IXamlILEmitter codeGen)
|
||||
{
|
||||
codeGen.Ldstr(_color);
|
||||
codeGen.EmitCall(_method);
|
||||
|
||||
return XamlILNodeEmitResult.Type(0, Type.GetClrType());
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -13,6 +13,10 @@ namespace Robust.Build.Tasks
|
||||
public IXamlConstructor Vector2ConstructorFull { get; }
|
||||
public IXamlType Vector2i { get; }
|
||||
public IXamlConstructor Vector2iConstructorFull { get; }
|
||||
public IXamlType Thickness { get; }
|
||||
public IXamlConstructor ThicknessConstructorFull { get; }
|
||||
public IXamlType Color { get; }
|
||||
public IXamlMethod ColorFromXaml { get; }
|
||||
|
||||
public RXamlWellKnownTypes(TransformerConfiguration cfg)
|
||||
{
|
||||
@@ -23,6 +27,7 @@ namespace Robust.Build.Tasks
|
||||
|
||||
(Vector2, Vector2ConstructorFull) = GetNumericTypeInfo("Robust.Shared.Maths.Vector2", Single, 2);
|
||||
(Vector2i, Vector2iConstructorFull) = GetNumericTypeInfo("Robust.Shared.Maths.Vector2i", Int32, 2);
|
||||
(Thickness, ThicknessConstructorFull) = GetNumericTypeInfo("Robust.Shared.Maths.Thickness", Single, 4);
|
||||
|
||||
(IXamlType, IXamlConstructor) GetNumericTypeInfo(string name, IXamlType componentType, int componentCount)
|
||||
{
|
||||
@@ -31,6 +36,12 @@ namespace Robust.Build.Tasks
|
||||
|
||||
return (type, ctor);
|
||||
}
|
||||
|
||||
Color = cfg.TypeSystem.GetType("Robust.Shared.Maths.Color");
|
||||
ColorFromXaml = Color.GetMethod(new FindMethodMethodSignature("FromXaml", Color, XamlIlTypes.String)
|
||||
{
|
||||
IsStatic = true
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -329,6 +329,77 @@ namespace Robust.Build.Tasks
|
||||
return true;
|
||||
}
|
||||
|
||||
if (type.Equals(types.Thickness))
|
||||
{
|
||||
var foo = MathParsing.Thickness.Parse(text);
|
||||
|
||||
if (!foo.Success)
|
||||
throw new XamlLoadException($"Unable to parse \"{text}\" as a Thickness", node);
|
||||
|
||||
var val = foo.Value;
|
||||
float[] full;
|
||||
if (val.Length == 1)
|
||||
{
|
||||
var u = val[0];
|
||||
full = new[] {u, u, u, u};
|
||||
}
|
||||
else if (val.Length == 2)
|
||||
{
|
||||
var h = val[0];
|
||||
var v = val[1];
|
||||
full = new[] {h, v, h, v};
|
||||
}
|
||||
else // 4
|
||||
{
|
||||
full = val;
|
||||
}
|
||||
|
||||
result = new RXamlSingleVecLikeConstAstNode(
|
||||
node,
|
||||
types.Thickness, types.ThicknessConstructorFull,
|
||||
types.Single, full);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (type.Equals(types.Thickness))
|
||||
{
|
||||
var foo = MathParsing.Thickness.Parse(text);
|
||||
|
||||
if (!foo.Success)
|
||||
throw new XamlLoadException($"Unable to parse \"{text}\" as a Thickness", node);
|
||||
|
||||
var val = foo.Value;
|
||||
float[] full;
|
||||
if (val.Length == 1)
|
||||
{
|
||||
var u = val[0];
|
||||
full = new[] {u, u, u, u};
|
||||
}
|
||||
else if (val.Length == 2)
|
||||
{
|
||||
var h = val[0];
|
||||
var v = val[1];
|
||||
full = new[] {h, v, h, v};
|
||||
}
|
||||
else // 4
|
||||
{
|
||||
full = val;
|
||||
}
|
||||
|
||||
result = new RXamlSingleVecLikeConstAstNode(
|
||||
node,
|
||||
types.Thickness, types.ThicknessConstructorFull,
|
||||
types.Single, full);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (type.Equals(types.Color))
|
||||
{
|
||||
// TODO: Interpret these colors at XAML compile time instead of at runtime.
|
||||
result = new RXamlColorAstNode(node, types, text);
|
||||
return true;
|
||||
}
|
||||
|
||||
result = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -481,6 +481,8 @@ namespace Robust.Client.Console.Commands
|
||||
{
|
||||
_writeNode(root, 0, writer);
|
||||
}
|
||||
|
||||
shell.WriteLine("Saved guidump");
|
||||
}
|
||||
|
||||
private static void _writeNode(Control control, int indents, TextWriter writer)
|
||||
@@ -542,7 +544,7 @@ namespace Robust.Client.Console.Commands
|
||||
|
||||
public void Execute(IConsoleShell shell, string argStr, string[] args)
|
||||
{
|
||||
var window = new SS14Window { CustomMinimumSize = (500, 400)};
|
||||
var window = new SS14Window { MinSize = (500, 400)};
|
||||
var tabContainer = new TabContainer();
|
||||
window.Contents.AddChild(tabContainer);
|
||||
var scroll = new ScrollContainer();
|
||||
@@ -562,7 +564,7 @@ namespace Robust.Client.Console.Commands
|
||||
optionButton.OnItemSelected += eventArgs => optionButton.SelectId(eventArgs.Id);
|
||||
vBox.AddChild(optionButton);
|
||||
|
||||
var tree = new Tree { SizeFlagsVertical = Control.SizeFlags.FillExpand };
|
||||
var tree = new Tree { VerticalExpand = true };
|
||||
var root = tree.CreateItem();
|
||||
root.Text = "Honk!";
|
||||
var child = tree.CreateItem();
|
||||
@@ -599,7 +601,7 @@ namespace Robust.Client.Console.Commands
|
||||
{
|
||||
grid.AddChild(new Button
|
||||
{
|
||||
CustomMinimumSize = (50, 50),
|
||||
MinSize = (50, 50),
|
||||
Text = $"{x}, {y}"
|
||||
});
|
||||
}
|
||||
@@ -631,6 +633,29 @@ namespace Robust.Client.Console.Commands
|
||||
}
|
||||
});
|
||||
|
||||
tabContainer.AddChild(new HSplitContainer
|
||||
{
|
||||
Children =
|
||||
{
|
||||
new PanelContainer
|
||||
{
|
||||
PanelOverride = new StyleBoxFlat {BackgroundColor = Color.Red},
|
||||
Children =
|
||||
{
|
||||
new Label{ Text = "FOOBARBAZ"},
|
||||
}
|
||||
},
|
||||
new PanelContainer
|
||||
{
|
||||
PanelOverride = new StyleBoxFlat {BackgroundColor = Color.Blue},
|
||||
Children =
|
||||
{
|
||||
new Label{ Text = "FOOBARBAZ"},
|
||||
}
|
||||
},
|
||||
}
|
||||
});
|
||||
|
||||
window.OpenCentered();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,8 +20,6 @@ namespace Robust.Client.Console
|
||||
{
|
||||
private readonly IReflectionManager _reflectionManager;
|
||||
|
||||
protected override Vector2? CustomSize => (300, 300);
|
||||
|
||||
private readonly VBoxContainer _watchesVBox;
|
||||
private readonly LineEdit _addWatchEdit;
|
||||
private readonly Button _addWatchButton;
|
||||
@@ -37,12 +35,12 @@ namespace Robust.Client.Console
|
||||
|
||||
var mainVBox = new VBoxContainer
|
||||
{
|
||||
CustomMinimumSize = (500, 300),
|
||||
MinSize = (500, 300),
|
||||
Children =
|
||||
{
|
||||
(_watchesVBox = new VBoxContainer
|
||||
{
|
||||
SizeFlagsVertical = SizeFlags.FillExpand
|
||||
VerticalExpand = true
|
||||
}),
|
||||
new HBoxContainer
|
||||
{
|
||||
@@ -50,7 +48,7 @@ namespace Robust.Client.Console
|
||||
{
|
||||
(_addWatchEdit = new HistoryLineEdit
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = Loc.GetString("Add watch (C# interactive)")
|
||||
}),
|
||||
(_addWatchButton = new Button
|
||||
@@ -66,6 +64,8 @@ namespace Robust.Client.Console
|
||||
_addWatchEdit.OnTextEntered += _ => AddWatch();
|
||||
|
||||
Contents.AddChild(mainVBox);
|
||||
|
||||
SetSize = (300, 300);
|
||||
}
|
||||
|
||||
private void AddWatch()
|
||||
@@ -113,7 +113,7 @@ namespace Robust.Client.Console
|
||||
{
|
||||
(_outputLabel = new Label
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
ClipText = true
|
||||
}),
|
||||
(delButton = new Button
|
||||
@@ -176,7 +176,7 @@ namespace Robust.Client.Console
|
||||
{
|
||||
Text = message,
|
||||
ClipText = true,
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
HorizontalExpand = true
|
||||
},
|
||||
(delButton = new Button {Text = Loc.GetString("Remove")})
|
||||
}
|
||||
|
||||
@@ -1,30 +1,54 @@
|
||||
using System;
|
||||
using JetBrains.Annotations;
|
||||
using Robust.Shared.Maths;
|
||||
using Robust.Shared.Utility;
|
||||
using Robust.Shared.ViewVariables;
|
||||
|
||||
namespace Robust.Client.UserInterface
|
||||
{
|
||||
// Code and design heavily inspired by WPF/Avalonia.
|
||||
|
||||
public partial class Control
|
||||
{
|
||||
public event Action<Control>? OnMinimumSizeChanged;
|
||||
|
||||
private Vector2 _size;
|
||||
|
||||
[ViewVariables] internal Vector2? PreviousMeasure;
|
||||
[ViewVariables] internal UIBox2? PreviousArrange;
|
||||
|
||||
private float _sizeFlagsStretchRatio = 1;
|
||||
private Vector2? _calculatedMinimumSize;
|
||||
private Vector2 _customMinimumSize;
|
||||
private SizeFlags _sizeFlagsHorizontal = SizeFlags.Fill;
|
||||
private SizeFlags _sizeFlagsVertical = SizeFlags.Fill;
|
||||
private bool _layoutDirty;
|
||||
|
||||
private float _minWidth;
|
||||
private float _minHeight;
|
||||
private float _setWidth = float.NaN;
|
||||
private float _setHeight = float.NaN;
|
||||
private float _maxWidth = float.PositiveInfinity;
|
||||
private float _maxHeight = float.PositiveInfinity;
|
||||
|
||||
private bool _horizontalExpand;
|
||||
private bool _verticalExpand;
|
||||
private HAlignment _horizontalAlignment;
|
||||
private VAlignment _verticalAlignment;
|
||||
private Thickness _margin;
|
||||
private bool _isLayoutUpdateOverrideUsed;
|
||||
private bool _measuring;
|
||||
|
||||
[ViewVariables] public Vector2 DesiredSize { get; private set; }
|
||||
[ViewVariables] public Vector2i DesiredPixelSize => (Vector2i) (DesiredSize * UIScale);
|
||||
[ViewVariables] public bool IsMeasureValid { get; private set; }
|
||||
[ViewVariables] public bool IsArrangeValid { get; private set; }
|
||||
|
||||
[ViewVariables]
|
||||
public Thickness Margin
|
||||
{
|
||||
get => _margin;
|
||||
set => _margin = value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Called when the <see cref="UIScale"/> for this control changes.
|
||||
/// </summary>
|
||||
protected internal virtual void UIScaleChanged()
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -56,7 +80,6 @@ namespace Robust.Client.UserInterface
|
||||
|
||||
_size = value;
|
||||
Resized();
|
||||
UpdateLayout();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -179,12 +202,36 @@ namespace Robust.Client.UserInterface
|
||||
/// Horizontal size flags for container layout.
|
||||
/// </summary>
|
||||
[ViewVariables]
|
||||
[Obsolete("Use HorizontalAlignment and HorizontalExpand instead.")]
|
||||
public SizeFlags SizeFlagsHorizontal
|
||||
{
|
||||
get => _sizeFlagsHorizontal;
|
||||
get
|
||||
{
|
||||
var flags = HorizontalAlignment switch
|
||||
{
|
||||
HAlignment.Stretch => SizeFlags.Fill,
|
||||
HAlignment.Left => SizeFlags.None,
|
||||
HAlignment.Center => SizeFlags.ShrinkCenter,
|
||||
HAlignment.Right => SizeFlags.ShrinkEnd,
|
||||
_ => throw new ArgumentOutOfRangeException()
|
||||
};
|
||||
|
||||
if (_horizontalExpand)
|
||||
flags |= SizeFlags.Expand;
|
||||
|
||||
return flags;
|
||||
}
|
||||
set
|
||||
{
|
||||
_sizeFlagsHorizontal = value;
|
||||
HorizontalExpand = (value & SizeFlags.Expand) != 0;
|
||||
HorizontalAlignment = (value & ~SizeFlags.Expand) switch
|
||||
{
|
||||
SizeFlags.None => HAlignment.Left,
|
||||
SizeFlags.Fill => HAlignment.Stretch,
|
||||
SizeFlags.ShrinkCenter => HAlignment.Center,
|
||||
SizeFlags.ShrinkEnd => HAlignment.Right,
|
||||
_ => throw new ArgumentOutOfRangeException()
|
||||
};
|
||||
|
||||
Parent?.UpdateLayout();
|
||||
}
|
||||
@@ -193,18 +240,87 @@ namespace Robust.Client.UserInterface
|
||||
/// <summary>
|
||||
/// Vertical size flags for container layout.
|
||||
/// </summary>
|
||||
[Obsolete("Use VerticalAlignment and VerticalExpand instead.")]
|
||||
[ViewVariables]
|
||||
public SizeFlags SizeFlagsVertical
|
||||
{
|
||||
get => _sizeFlagsVertical;
|
||||
get
|
||||
{
|
||||
var flags = _verticalAlignment switch
|
||||
{
|
||||
VAlignment.Stretch => SizeFlags.Fill,
|
||||
VAlignment.Top => SizeFlags.None,
|
||||
VAlignment.Center => SizeFlags.ShrinkCenter,
|
||||
VAlignment.Bottom => SizeFlags.ShrinkEnd,
|
||||
_ => throw new ArgumentOutOfRangeException()
|
||||
};
|
||||
|
||||
if (_verticalExpand)
|
||||
flags |= SizeFlags.Expand;
|
||||
|
||||
return flags;
|
||||
}
|
||||
set
|
||||
{
|
||||
_sizeFlagsVertical = value;
|
||||
VerticalExpand = (value & SizeFlags.Expand) != 0;
|
||||
VerticalAlignment = (value & ~SizeFlags.Expand) switch
|
||||
{
|
||||
SizeFlags.None => VAlignment.Top,
|
||||
SizeFlags.Fill => VAlignment.Stretch,
|
||||
SizeFlags.ShrinkCenter => VAlignment.Center,
|
||||
SizeFlags.ShrinkEnd => VAlignment.Bottom,
|
||||
_ => throw new ArgumentOutOfRangeException()
|
||||
};
|
||||
|
||||
Parent?.UpdateLayout();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public HAlignment HorizontalAlignment
|
||||
{
|
||||
get => _horizontalAlignment;
|
||||
set
|
||||
{
|
||||
_horizontalAlignment = value;
|
||||
InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public VAlignment VerticalAlignment
|
||||
{
|
||||
get => _verticalAlignment;
|
||||
set
|
||||
{
|
||||
_verticalAlignment = value;
|
||||
InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public bool HorizontalExpand
|
||||
{
|
||||
get => _horizontalExpand;
|
||||
set
|
||||
{
|
||||
_horizontalExpand = value;
|
||||
Parent?.InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public bool VerticalExpand
|
||||
{
|
||||
get => _verticalExpand;
|
||||
set
|
||||
{
|
||||
_verticalExpand = value;
|
||||
Parent?.InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Stretch ratio used to give shared of the available space in case multiple siblings are set to expand
|
||||
/// in a container
|
||||
@@ -225,12 +341,12 @@ namespace Robust.Client.UserInterface
|
||||
|
||||
_sizeFlagsStretchRatio = value;
|
||||
|
||||
Parent?.UpdateLayout();
|
||||
Parent?.InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A combination of <see cref="CustomMinimumSize" /> and <see cref="CalculateMinimumSize" />,
|
||||
/// A combination of <see cref="MinSize" /> and <see cref="CalculateMinimumSize" />,
|
||||
/// Whichever is greater.
|
||||
/// Use this for whenever you need the *actual* minimum size of something.
|
||||
/// </summary>
|
||||
@@ -238,24 +354,13 @@ namespace Robust.Client.UserInterface
|
||||
/// This is in virtual pixels.
|
||||
/// </remarks>
|
||||
/// <seealso cref="CombinedPixelMinimumSize"/>
|
||||
[ViewVariables]
|
||||
public Vector2 CombinedMinimumSize
|
||||
{
|
||||
get
|
||||
{
|
||||
if (!_calculatedMinimumSize.HasValue)
|
||||
{
|
||||
_updateMinimumSize();
|
||||
DebugTools.Assert(_calculatedMinimumSize.HasValue);
|
||||
}
|
||||
|
||||
return Vector2.ComponentMax(CustomMinimumSize, _calculatedMinimumSize!.Value);
|
||||
}
|
||||
}
|
||||
[Obsolete("Use DesiredSize and Measure()")]
|
||||
public Vector2 CombinedMinimumSize => DesiredSize;
|
||||
|
||||
/// <summary>
|
||||
/// The <see cref="CombinedMinimumSize"/>, in physical pixels.
|
||||
/// </summary>
|
||||
[Obsolete("Use DesiredSize and Measure()")]
|
||||
public Vector2i CombinedPixelMinimumSize => (Vector2i) (CombinedMinimumSize * UIScale);
|
||||
|
||||
/// <summary>
|
||||
@@ -264,24 +369,95 @@ namespace Robust.Client.UserInterface
|
||||
/// <seealso cref="CalculateMinimumSize" />
|
||||
/// <seealso cref="CombinedMinimumSize" />
|
||||
[ViewVariables]
|
||||
[Obsolete("Use MinSize instead.")]
|
||||
public Vector2 CustomMinimumSize
|
||||
{
|
||||
get => _customMinimumSize;
|
||||
get => (_minWidth, _minHeight);
|
||||
set => (MinWidth, MinHeight) = Vector2.ComponentMax(Vector2.Zero, value);
|
||||
}
|
||||
|
||||
public Vector2 MinSize
|
||||
{
|
||||
get => (_minWidth, _minHeight);
|
||||
set => (MinWidth, MinHeight) = Vector2.ComponentMax(Vector2.Zero, value);
|
||||
}
|
||||
|
||||
public Vector2 SetSize
|
||||
{
|
||||
get => (_setWidth, _setHeight);
|
||||
set => (SetWidth, SetHeight) = value;
|
||||
}
|
||||
|
||||
public Vector2 MaxSize
|
||||
{
|
||||
get => (_maxWidth, _maxHeight);
|
||||
set => (MaxWidth, MaxHeight) = value;
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float MinWidth
|
||||
{
|
||||
get => _minWidth;
|
||||
set
|
||||
{
|
||||
_customMinimumSize = Vector2.ComponentMax(Vector2.Zero, value);
|
||||
MinimumSizeChanged();
|
||||
_minWidth = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
private void _updateMinimumSize()
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float MinHeight
|
||||
{
|
||||
if (_stylingDirty)
|
||||
get => _minHeight;
|
||||
set
|
||||
{
|
||||
ForceRunStyleUpdate();
|
||||
_minHeight = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
_calculatedMinimumSize = Vector2.ComponentMax(Vector2.Zero, CalculateMinimumSize());
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float SetWidth
|
||||
{
|
||||
get => _setWidth;
|
||||
set
|
||||
{
|
||||
_setWidth = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float SetHeight
|
||||
{
|
||||
get => _setHeight;
|
||||
set
|
||||
{
|
||||
_setHeight = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float MaxWidth
|
||||
{
|
||||
get => _maxWidth;
|
||||
set
|
||||
{
|
||||
_maxWidth = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)]
|
||||
public float MaxHeight
|
||||
{
|
||||
get => _maxHeight;
|
||||
set
|
||||
{
|
||||
_maxHeight = value;
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -289,27 +465,31 @@ namespace Robust.Client.UserInterface
|
||||
/// Do NOT call this directly to get the minimum size for layout purposes!
|
||||
/// Use <see cref="CombinedMinimumSize" /> for the ACTUAL minimum size.
|
||||
/// </summary>
|
||||
[Obsolete("Implement MeasureOverride instead")]
|
||||
protected virtual Vector2 CalculateMinimumSize()
|
||||
{
|
||||
var min = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
min = Vector2.ComponentMax(min, child.CombinedMinimumSize);
|
||||
}
|
||||
return min;
|
||||
return Vector2.Zero;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Tells the GUI system that the minimum size of this control may have changed,
|
||||
/// so that say containers will re-sort it if necessary.
|
||||
/// </summary>
|
||||
[Obsolete("Use InvalidateMeasure()")]
|
||||
public void MinimumSizeChanged()
|
||||
{
|
||||
_calculatedMinimumSize = null;
|
||||
OnMinimumSizeChanged?.Invoke(this);
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
Parent?.MinimumSizeChanged();
|
||||
UpdateLayout();
|
||||
public void InvalidateMeasure()
|
||||
{
|
||||
if (!IsMeasureValid)
|
||||
return;
|
||||
|
||||
IsMeasureValid = false;
|
||||
IsArrangeValid = false;
|
||||
|
||||
UserInterfaceManagerInternal.QueueMeasureUpdate(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -320,89 +500,241 @@ namespace Robust.Client.UserInterface
|
||||
/// where running the deferred layout updating system in the UI manager can be annoying.
|
||||
/// If you are forced to use this in regular code, you have found a bug.
|
||||
/// </remarks>
|
||||
[Obsolete("Call Arrange manually for unit tests or call Measure manually for early measures.")]
|
||||
public void ForceRunLayoutUpdate()
|
||||
{
|
||||
DoLayoutUpdate();
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.ForceRunLayoutUpdate();
|
||||
}
|
||||
// TODO: Fix or remove this
|
||||
if (PreviousArrange.HasValue)
|
||||
Arrange(PreviousArrange.Value);
|
||||
}
|
||||
|
||||
protected void UpdateLayout()
|
||||
public void InvalidateArrange()
|
||||
{
|
||||
if (_layoutDirty)
|
||||
if (!IsArrangeValid)
|
||||
{
|
||||
// Already queued for a layout update, don't bother.
|
||||
return;
|
||||
}
|
||||
|
||||
_layoutDirty = true;
|
||||
UserInterfaceManagerInternal.QueueLayoutUpdate(this);
|
||||
IsArrangeValid = false;
|
||||
UserInterfaceManagerInternal.QueueArrangeUpdate(this);
|
||||
}
|
||||
|
||||
protected void FitChildInPixelBox(Control child, UIBox2i pixelBox)
|
||||
[Obsolete("Use InvalidateArrange()")]
|
||||
protected void UpdateLayout()
|
||||
{
|
||||
var topLeft = pixelBox.TopLeft / UIScale;
|
||||
var bottomRight = pixelBox.BottomRight / UIScale;
|
||||
|
||||
FitChildInBox(child, new UIBox2(topLeft, bottomRight));
|
||||
InvalidateArrange();
|
||||
}
|
||||
|
||||
protected void FitChildInBox(Control child, UIBox2 box)
|
||||
public void Measure(Vector2 availableSize)
|
||||
{
|
||||
DebugTools.Assert(child.Parent == this);
|
||||
if (!IsMeasureValid || PreviousMeasure != availableSize)
|
||||
{
|
||||
IsMeasureValid = true;
|
||||
var desired = MeasureCore(availableSize);
|
||||
|
||||
var (minX, minY) = child.CombinedMinimumSize;
|
||||
var newPosX = box.Left;
|
||||
var newSizeX = minX;
|
||||
if (desired.X < 0 || desired.Y < 0 || !float.IsFinite(desired.X) || !float.IsFinite(desired.Y))
|
||||
throw new InvalidOperationException("Invalid size returned from Measure()");
|
||||
|
||||
if ((child.SizeFlagsHorizontal & SizeFlags.ShrinkEnd) != 0)
|
||||
{
|
||||
newPosX += (box.Width - minX);
|
||||
}
|
||||
else if ((child.SizeFlagsHorizontal & SizeFlags.ShrinkCenter) != 0)
|
||||
{
|
||||
newPosX += (box.Width - minX) / 2;
|
||||
}
|
||||
else if ((child.SizeFlagsHorizontal & SizeFlags.Fill) != 0)
|
||||
{
|
||||
newSizeX = Math.Max(box.Width, newSizeX);
|
||||
}
|
||||
var prev = DesiredSize;
|
||||
DesiredSize = desired;
|
||||
PreviousMeasure = availableSize;
|
||||
|
||||
var newPosY = box.Top;
|
||||
var newSizeY = minY;
|
||||
|
||||
if ((child.SizeFlagsVertical & SizeFlags.ShrinkEnd) != 0)
|
||||
{
|
||||
newPosY += (box.Height - minY);
|
||||
if (prev != desired && Parent != null && !Parent._measuring)
|
||||
Parent?.InvalidateMeasure();
|
||||
}
|
||||
else if ((child.SizeFlagsVertical & SizeFlags.ShrinkCenter) != 0)
|
||||
{
|
||||
newPosY += (box.Height - minY) / 2;
|
||||
}
|
||||
else if ((child.SizeFlagsVertical & SizeFlags.Fill) != 0)
|
||||
{
|
||||
newSizeY = Math.Max(box.Height, newSizeY);
|
||||
}
|
||||
|
||||
child.Position = new Vector2(newPosX, newPosY);
|
||||
child.Size = new Vector2(newSizeX, newSizeY);
|
||||
}
|
||||
|
||||
internal void DoLayoutUpdate()
|
||||
protected virtual Vector2 MeasureCore(Vector2 availableSize)
|
||||
{
|
||||
if (!Visible)
|
||||
return default;
|
||||
|
||||
if (_stylingDirty)
|
||||
ForceRunStyleUpdate();
|
||||
|
||||
var withoutMargin = _margin.Deflate(availableSize);
|
||||
|
||||
var constrained = ApplySizeConstraints(this, withoutMargin);
|
||||
|
||||
Vector2 measured;
|
||||
try
|
||||
{
|
||||
_measuring = true;
|
||||
measured = Vector2.ComponentMax(
|
||||
MeasureOverride(constrained),
|
||||
// For the time being keep the old CalculateMinimumSize around.
|
||||
#pragma warning disable 618
|
||||
CalculateMinimumSize());
|
||||
#pragma warning restore 618
|
||||
}
|
||||
finally
|
||||
{
|
||||
_measuring = false;
|
||||
}
|
||||
|
||||
if (!float.IsNaN(SetWidth))
|
||||
{
|
||||
measured.X = SetWidth;
|
||||
}
|
||||
|
||||
measured.X = Math.Clamp(measured.X, MinWidth, MaxWidth);
|
||||
|
||||
if (!float.IsNaN(SetHeight))
|
||||
{
|
||||
measured.Y = SetHeight;
|
||||
}
|
||||
|
||||
measured.Y = Math.Clamp(measured.Y, MinHeight, MaxHeight);
|
||||
|
||||
measured = _margin.Inflate(measured);
|
||||
return Vector2.ComponentMin(measured, availableSize);
|
||||
}
|
||||
|
||||
protected virtual Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var min = Vector2.Zero;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.Measure(availableSize);
|
||||
min = Vector2.ComponentMax(min, child.DesiredSize);
|
||||
}
|
||||
|
||||
return min;
|
||||
}
|
||||
|
||||
public void ArrangePixel(UIBox2i finalRect)
|
||||
{
|
||||
var topLeft = finalRect.TopLeft / UIScale;
|
||||
var bottomRight = finalRect.BottomRight / UIScale;
|
||||
|
||||
Arrange(new UIBox2(topLeft, bottomRight));
|
||||
}
|
||||
|
||||
public void Arrange(UIBox2 finalRect)
|
||||
{
|
||||
if (!IsMeasureValid)
|
||||
Measure(PreviousMeasure ?? finalRect.Size);
|
||||
|
||||
if (!IsArrangeValid || PreviousArrange != finalRect)
|
||||
{
|
||||
IsArrangeValid = true;
|
||||
ArrangeCore(finalRect);
|
||||
PreviousArrange = finalRect;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual void ArrangeCore(UIBox2 finalRect)
|
||||
{
|
||||
if (!Visible)
|
||||
return;
|
||||
|
||||
var withoutMargins = _margin.Deflate(finalRect);
|
||||
var availWithoutMargins = withoutMargins.Size;
|
||||
var size = availWithoutMargins;
|
||||
var origin = withoutMargins.TopLeft;
|
||||
|
||||
if (_horizontalAlignment != HAlignment.Stretch)
|
||||
size.X = Math.Min(size.X, DesiredSize.X - _margin.SumHorizontal);
|
||||
|
||||
if (_verticalAlignment != VAlignment.Stretch)
|
||||
size.Y = Math.Min(size.Y, DesiredSize.Y - _margin.SumVertical);
|
||||
|
||||
|
||||
size = ApplySizeConstraints(this, size);
|
||||
|
||||
Size = size;
|
||||
_isLayoutUpdateOverrideUsed = true;
|
||||
#pragma warning disable 618
|
||||
LayoutUpdateOverride();
|
||||
_layoutDirty = false;
|
||||
#pragma warning restore 618
|
||||
if (!_isLayoutUpdateOverrideUsed)
|
||||
{
|
||||
var arranged = ArrangeOverride(size);
|
||||
|
||||
size = Vector2.ComponentMin(arranged, size);
|
||||
}
|
||||
|
||||
switch (HorizontalAlignment)
|
||||
{
|
||||
case HAlignment.Stretch:
|
||||
case HAlignment.Center:
|
||||
origin.X += (availWithoutMargins.X - size.X) / 2;
|
||||
break;
|
||||
case HAlignment.Right:
|
||||
origin.X += availWithoutMargins.X - size.X;
|
||||
break;
|
||||
}
|
||||
|
||||
switch (VerticalAlignment)
|
||||
{
|
||||
case VAlignment.Stretch:
|
||||
case VAlignment.Center:
|
||||
origin.Y += (availWithoutMargins.Y - size.Y) / 2;
|
||||
break;
|
||||
case VAlignment.Bottom:
|
||||
origin.Y += availWithoutMargins.Y - size.Y;
|
||||
break;
|
||||
}
|
||||
|
||||
Position = origin;
|
||||
Size = size;
|
||||
}
|
||||
|
||||
protected virtual void LayoutUpdateOverride()
|
||||
protected virtual Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
foreach (var child in Children)
|
||||
{
|
||||
FitChildInPixelBox(child, PixelSizeBox);
|
||||
child.Arrange(UIBox2.FromDimensions(Vector2.Zero, finalSize));
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
[Obsolete("Use Control.ArrangePixel")]
|
||||
protected void FitChildInPixelBox(Control child, UIBox2i pixelBox)
|
||||
{
|
||||
child.ArrangePixel(pixelBox);
|
||||
}
|
||||
|
||||
[Obsolete("Use Control.Arrange")]
|
||||
protected void FitChildInBox(Control child, UIBox2 box)
|
||||
{
|
||||
child.Arrange(box);
|
||||
}
|
||||
|
||||
[Obsolete("Implement ArrangeOverride instead.")]
|
||||
protected virtual void LayoutUpdateOverride()
|
||||
{
|
||||
_isLayoutUpdateOverrideUsed = false;
|
||||
}
|
||||
|
||||
private static Vector2 ApplySizeConstraints(Control control, Vector2 avail)
|
||||
{
|
||||
var minW = control._minWidth;
|
||||
var setW = control._setWidth;
|
||||
var maxW = control._maxWidth;
|
||||
|
||||
var maxConstraint = float.IsNaN(setW) ? float.PositiveInfinity : setW;
|
||||
maxW = MathHelper.Clamp(maxConstraint, minW, maxW);
|
||||
|
||||
var minConstraint = float.IsNaN(setW) ? 0 : setW;
|
||||
minW = MathHelper.Clamp(maxW, minConstraint, minW);
|
||||
|
||||
var minH = control._minHeight;
|
||||
var setH = control._setHeight;
|
||||
var maxH = control._maxHeight;
|
||||
|
||||
maxConstraint = float.IsNaN(setH) ? float.PositiveInfinity : setH;
|
||||
maxH = MathHelper.Clamp(maxConstraint, minH, maxH);
|
||||
|
||||
minConstraint = float.IsNaN(setH) ? 0 : setH;
|
||||
minH = MathHelper.Clamp(minW, minConstraint, minH);
|
||||
|
||||
return (
|
||||
Math.Clamp(avail.X, minW, maxW),
|
||||
Math.Clamp(avail.Y, minH, maxH));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -443,5 +775,21 @@ namespace Robust.Client.UserInterface
|
||||
/// </summary>
|
||||
ShrinkEnd = 8,
|
||||
}
|
||||
|
||||
public enum HAlignment
|
||||
{
|
||||
Stretch,
|
||||
Left,
|
||||
Center,
|
||||
Right
|
||||
}
|
||||
|
||||
public enum VAlignment
|
||||
{
|
||||
Stretch,
|
||||
Top,
|
||||
Center,
|
||||
Bottom
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -233,7 +233,7 @@ namespace Robust.Client.UserInterface
|
||||
|
||||
protected virtual void StylePropertiesChanged()
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
public void ForceRunStyleUpdate()
|
||||
|
||||
@@ -154,7 +154,8 @@ namespace Robust.Client.UserInterface
|
||||
_propagateVisibilityChanged(value);
|
||||
// TODO: unhardcode this.
|
||||
// Many containers ignore children if they're invisible, so that's why we're replicating that ehre.
|
||||
Parent?.MinimumSizeChanged();
|
||||
Parent?.InvalidateMeasure();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -594,7 +595,7 @@ namespace Robust.Client.UserInterface
|
||||
/// <param name="newChild">The new child.</param>
|
||||
protected virtual void ChildAdded(Control newChild)
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -604,7 +605,7 @@ namespace Robust.Client.UserInterface
|
||||
protected virtual void Parented(Control newParent)
|
||||
{
|
||||
StylesheetUpdateRecursive();
|
||||
UpdateLayout();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -642,7 +643,7 @@ namespace Robust.Client.UserInterface
|
||||
/// <param name="child">The former child.</param>
|
||||
protected virtual void ChildRemoved(Control child)
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -35,8 +35,60 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
public int? SeparationOverride { get; set; }
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var separation = ActualSeparation;
|
||||
|
||||
var minSize = Vector2.Zero;
|
||||
var first = true;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
if (!child.Visible)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
child.Measure(availableSize);
|
||||
|
||||
var childSize = child.DesiredSize;
|
||||
if (Vertical)
|
||||
{
|
||||
var taken = childSize.Y;
|
||||
if (!first)
|
||||
{
|
||||
taken += separation;
|
||||
}
|
||||
|
||||
minSize.Y += taken;
|
||||
availableSize.Y = Math.Max(0, availableSize.Y - taken);
|
||||
|
||||
first = false;
|
||||
minSize.X = Math.Max(minSize.X, childSize.X);
|
||||
}
|
||||
else
|
||||
{
|
||||
var taken = childSize.X;
|
||||
if (!first)
|
||||
{
|
||||
taken += separation;
|
||||
}
|
||||
|
||||
minSize.X += taken;
|
||||
availableSize.X = Math.Max(0, availableSize.X - taken);
|
||||
|
||||
first = false;
|
||||
|
||||
minSize.Y = Math.Max(minSize.Y, childSize.Y);
|
||||
}
|
||||
}
|
||||
|
||||
return minSize;
|
||||
}
|
||||
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var finalPixel = (Vector2i) (finalSize * UIScale);
|
||||
var separation = (int) (ActualSeparation * UIScale);
|
||||
|
||||
// Step one: figure out the sizes of all our children and whether they want to stretch.
|
||||
@@ -51,19 +103,20 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
continue;
|
||||
}
|
||||
var (minX, minY) = child.CombinedPixelMinimumSize;
|
||||
|
||||
var (minX, minY) = child.DesiredPixelSize;
|
||||
int minSize;
|
||||
bool stretch;
|
||||
|
||||
if (Vertical)
|
||||
{
|
||||
minSize = minY;
|
||||
stretch = (child.SizeFlagsVertical & SizeFlags.Expand) == SizeFlags.Expand;
|
||||
stretch = child.VerticalExpand;
|
||||
}
|
||||
else
|
||||
{
|
||||
minSize = minX;
|
||||
stretch = (child.SizeFlagsHorizontal & SizeFlags.Expand) == SizeFlags.Expand;
|
||||
stretch = child.HorizontalExpand;
|
||||
}
|
||||
|
||||
if (!stretch)
|
||||
@@ -78,7 +131,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
sizeList.Add((child, minSize, minSize, stretch));
|
||||
}
|
||||
|
||||
var stretchMax = Vertical ? PixelHeight : PixelWidth;
|
||||
var stretchMax = Vertical ? finalPixel.Y : finalPixel.X;
|
||||
|
||||
stretchMax -= separation * (ChildCount - 1);
|
||||
// This is the amount of space allocated for stretchable children.
|
||||
@@ -152,62 +205,19 @@ namespace Robust.Client.UserInterface.Controls
|
||||
UIBox2i targetBox;
|
||||
if (Vertical)
|
||||
{
|
||||
targetBox = new UIBox2i(0, offset, PixelWidth, offset+size);
|
||||
targetBox = new UIBox2i(0, offset, finalPixel.X, offset + size);
|
||||
}
|
||||
else
|
||||
{
|
||||
targetBox = new UIBox2i(offset, 0, offset+size, PixelHeight);
|
||||
targetBox = new UIBox2i(offset, 0, offset + size, finalPixel.Y);
|
||||
}
|
||||
|
||||
FitChildInPixelBox(control, targetBox);
|
||||
control.ArrangePixel(targetBox);
|
||||
|
||||
offset += size;
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
var separation = ActualSeparation;
|
||||
|
||||
var minWidth = 0f;
|
||||
var minHeight = 0f;
|
||||
var first = true;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
if (!child.Visible)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
var (childWidth, childHeight) = child.CombinedMinimumSize;
|
||||
if (Vertical)
|
||||
{
|
||||
minHeight += childHeight;
|
||||
if (!first)
|
||||
{
|
||||
minHeight += separation;
|
||||
}
|
||||
|
||||
first = false;
|
||||
|
||||
minWidth = MathF.Max(minWidth, childWidth);
|
||||
}
|
||||
else
|
||||
{
|
||||
minWidth += childWidth;
|
||||
if (!first)
|
||||
{
|
||||
minWidth += separation;
|
||||
}
|
||||
|
||||
first = false;
|
||||
|
||||
minHeight = MathF.Max(minHeight, childHeight);
|
||||
}
|
||||
}
|
||||
|
||||
return new Vector2(minWidth, minHeight);
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
public enum AlignMode : byte
|
||||
|
||||
@@ -7,15 +7,19 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// </summary>
|
||||
public class CenterContainer : Container
|
||||
{
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var max = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
var childSize = child.CombinedMinimumSize;
|
||||
var childPos = (Size - childSize) / 2;
|
||||
var childSize = child.DesiredSize;
|
||||
var childPos = (finalSize - childSize) / 2;
|
||||
|
||||
FitChildInBox(child, UIBox2.FromDimensions(childPos, childSize));
|
||||
child.Arrange(UIBox2.FromDimensions(childPos, childSize));
|
||||
|
||||
max = Vector2.ComponentMax(max, childSize);
|
||||
}
|
||||
return max;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,13 +31,30 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var contentBox = ActualStyleBox.GetContentBox(PixelSizeBox);
|
||||
var boxSize = ActualStyleBox.MinimumSize / UIScale;
|
||||
var childBox = Vector2.ComponentMax(availableSize - boxSize, Vector2.Zero);
|
||||
var min = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
FitChildInPixelBox(child, (UIBox2i) contentBox);
|
||||
child.Measure(childBox);
|
||||
min = Vector2.ComponentMax(min, child.DesiredSize);
|
||||
}
|
||||
|
||||
return min + boxSize;
|
||||
}
|
||||
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var contentBox = ActualStyleBox.GetContentBox(UIBox2.FromDimensions(Vector2.Zero, finalSize * UIScale));
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.ArrangePixel((UIBox2i) contentBox);
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected internal override void Draw(DrawingHandleScreen handle)
|
||||
@@ -49,17 +66,6 @@ namespace Robust.Client.UserInterface.Controls
|
||||
style.Draw(handle, drawBox);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
var min = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
min = Vector2.ComponentMax(min, child.CombinedMinimumSize);
|
||||
}
|
||||
|
||||
return min + ActualStyleBox.MinimumSize / UIScale;
|
||||
}
|
||||
|
||||
protected override void DrawModeChanged()
|
||||
{
|
||||
switch (DrawMode)
|
||||
|
||||
@@ -49,8 +49,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
_lineEdit = new LineEdit
|
||||
{
|
||||
CustomMinimumSize = new Vector2(40, 0),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
MinSize = new Vector2(40, 0),
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
AddChild(_lineEdit);
|
||||
|
||||
|
||||
@@ -48,7 +48,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_expandBackwards = value;
|
||||
UpdateLayout();
|
||||
InvalidateArrange();
|
||||
}
|
||||
}
|
||||
private bool _expandBackwards;
|
||||
@@ -100,10 +100,17 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// <exception cref="ArgumentOutOfRangeException">
|
||||
/// Thrown if the value assigned is less than or equal to 0.
|
||||
/// </exception>
|
||||
public float MaxWidth
|
||||
[Obsolete("Use MaxGridWidth")]
|
||||
public new float MaxWidth
|
||||
{
|
||||
set => MaxGridWidth = value;
|
||||
}
|
||||
|
||||
public float MaxGridWidth
|
||||
{
|
||||
set => SetMaxSize(Dimension.Column, value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The max height (in virtual pixels) the grid of elements can have. This dynamically determines
|
||||
/// the number of rows based on the size of the elements. Setting this puts this grid
|
||||
@@ -120,12 +127,17 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// <exception cref="ArgumentOutOfRangeException">
|
||||
/// Thrown if the value assigned is less than or equal to 0.
|
||||
/// </exception>
|
||||
public float MaxHeight
|
||||
[Obsolete("Use MaxGridHeight")]
|
||||
public new float MaxHeight
|
||||
{
|
||||
set => MaxGridHeight = value;
|
||||
}
|
||||
|
||||
public float MaxGridHeight
|
||||
{
|
||||
set => SetMaxSize(Dimension.Row, value);
|
||||
}
|
||||
|
||||
|
||||
private int? _vSeparationOverride;
|
||||
|
||||
[SuppressMessage("ReSharper", "StringLiteralTypo")]
|
||||
@@ -199,8 +211,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_limitType = LimitType.Count;
|
||||
|
||||
_limitedDimensionCount = value;
|
||||
MinimumSizeChanged();
|
||||
UpdateLayout();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
private void SetMaxSize(Dimension forDimension, float value)
|
||||
@@ -214,8 +225,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_limitType = LimitType.Size;
|
||||
|
||||
_limitSize = value;
|
||||
MinimumSizeChanged();
|
||||
UpdateLayout();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -263,7 +273,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
int maxMinHeight = -1;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
var (minSizeX, minSizeY) = child.CombinedPixelMinimumSize;
|
||||
var (minSizeX, minSizeY) = child.DesiredPixelSize;
|
||||
maxMinWidth = Math.Max(maxMinWidth, minSizeX);
|
||||
maxMinHeight = Math.Max(maxMinHeight, minSizeY);
|
||||
}
|
||||
@@ -271,7 +281,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
return new Vector2i(maxMinWidth, maxMinHeight);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
// to make it easier to read and visualize, we're just going to use the terms "x" and "y", width, and height,
|
||||
// rows and cols,
|
||||
@@ -280,6 +290,12 @@ namespace Robust.Client.UserInterface.Controls
|
||||
// For the below convention, we pretend that columns have a limit defined, thus
|
||||
// the amount of rows is not limited (unlimited).
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
// TODO: This is not really correct in any fucking way but I CBA to fix this properly.
|
||||
child.Measure(availableSize);
|
||||
}
|
||||
|
||||
var rows = GetCount(UnlimitedDimension);
|
||||
var cols = GetCount(LimitedDimension);
|
||||
var cellSize = CellSize();
|
||||
@@ -304,7 +320,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
// also converting here to our "pretend" scenario where columns have a limit defined.
|
||||
// note if we are limiting by size rather than count, the size of each child is constant (cell size)
|
||||
var (minSizeXActual, minSizeYActual) = _limitType == LimitType.Count ? child.CombinedPixelMinimumSize : cellSize;
|
||||
var (minSizeXActual, minSizeYActual) = _limitType == LimitType.Count ? child.DesiredPixelSize : cellSize;
|
||||
var minSizeX = _limitDimension == Dimension.Column ? minSizeXActual : minSizeYActual;
|
||||
var minSizeY = _limitDimension == Dimension.Column ? minSizeYActual : minSizeXActual;
|
||||
minColWidth[column] = Math.Max(minSizeX, minColWidth[column]);
|
||||
@@ -348,9 +364,9 @@ namespace Robust.Client.UserInterface.Controls
|
||||
return totalSize;
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
// to make it easier to read and visualize, we're just going to use the terms "x" and "y", width, and height,
|
||||
// to make it easier to read and visualize, we're just going to use the terms "x" and "y", width, and height,
|
||||
// rows and cols,
|
||||
// but at the start of the method here we'll set those to what they actually are based
|
||||
// on the limited dimension, which might involve swapping them.
|
||||
@@ -390,19 +406,19 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
// converting here to our "pretend" scenario where columns have a limit defined
|
||||
// note if we are limiting by size rather than count, the size of each child is constant (cell size)
|
||||
var (minSizeXActual, minSizeYActual) = _limitType == LimitType.Count ? child.CombinedPixelMinimumSize : cellSize;
|
||||
var (minSizeXActual, minSizeYActual) = _limitType == LimitType.Count ? child.DesiredPixelSize : cellSize;
|
||||
var minSizeX = _limitDimension == Dimension.Column ? minSizeXActual : minSizeYActual;
|
||||
var minSizeY = _limitDimension == Dimension.Column ? minSizeYActual : minSizeXActual;
|
||||
minColWidth[column] = Math.Max(minSizeX, minColWidth[column]);
|
||||
minRowHeight[row] = Math.Max(minSizeY, minRowHeight[row]);
|
||||
var colSizeFlag = _limitDimension == Dimension.Column
|
||||
? child.SizeFlagsHorizontal
|
||||
: child.SizeFlagsVertical;
|
||||
var rowSizeFlag = UnlimitedDimension == Dimension.Column
|
||||
? child.SizeFlagsHorizontal
|
||||
: child.SizeFlagsVertical;
|
||||
colExpand[column] = colExpand[column] || (colSizeFlag & SizeFlags.Expand) != 0;
|
||||
rowExpand[row] = rowExpand[row] || (rowSizeFlag & SizeFlags.Expand) != 0;
|
||||
var colExpandFlag = _limitDimension == Dimension.Column
|
||||
? child.HorizontalExpand
|
||||
: child.VerticalExpand;
|
||||
var rowExpandFlag = UnlimitedDimension == Dimension.Column
|
||||
? child.HorizontalExpand
|
||||
: child.VerticalExpand;
|
||||
colExpand[column] = colExpand[column] || colExpandFlag;
|
||||
rowExpand[row] = rowExpand[row] || rowExpandFlag;
|
||||
|
||||
index += 1;
|
||||
}
|
||||
@@ -550,10 +566,12 @@ namespace Robust.Client.UserInterface.Controls
|
||||
var boxHeight = _limitDimension == Dimension.Column ? minRowHeight[row] : minColWidth[column];
|
||||
|
||||
var box = UIBox2i.FromDimensions(left, top, boxWidth, boxHeight);
|
||||
FitChildInPixelBox(child, box);
|
||||
child.ArrangePixel(box);
|
||||
|
||||
hOffset += minColWidth[column] + hSep;
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -43,9 +43,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
Name = "_v_scroll",
|
||||
|
||||
SizeFlagsVertical = SizeFlags.Fill,
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
AddChild(_scrollBar);
|
||||
_scrollBar.OnValueChanged += _ => _isAtBottom = _scrollBar.IsAtEnd;
|
||||
@@ -403,7 +401,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var size = Vector2.Zero;
|
||||
if (ActualBackground != null)
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
public Label()
|
||||
{
|
||||
SizeFlagsVertical = SizeFlags.ShrinkCenter;
|
||||
VerticalAlignment = VAlignment.Center;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -40,7 +40,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
_text = value;
|
||||
_textDimensionCacheValid = false;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,7 +52,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
_clipText = value;
|
||||
RectClipContent = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -209,7 +209,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
Fill = 3
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (!_textDimensionCacheValid)
|
||||
{
|
||||
@@ -267,7 +267,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
continue;
|
||||
}
|
||||
|
||||
_cachedTextWidths[_cachedTextWidths.Count-1] += metrics.Value.Advance;
|
||||
_cachedTextWidths[^1] += metrics.Value.Advance;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -27,7 +27,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_textures = value;
|
||||
CalculateMinimumSize();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -43,7 +43,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_textureScale = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -60,7 +60,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_canShrink = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -148,7 +148,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (_textures.Count == 0 || CanShrink)
|
||||
{
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
using System;
|
||||
using JetBrains.Annotations;
|
||||
using Robust.Client.Graphics;
|
||||
using Robust.Shared.Maths;
|
||||
using Robust.Shared.ViewVariables;
|
||||
|
||||
namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
@@ -17,6 +19,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// </summary>
|
||||
public const float AnchorEnd = 1;
|
||||
|
||||
[ViewVariables(VVAccess.ReadWrite)] public bool Debug { get; set; }
|
||||
|
||||
public static readonly AttachedProperty MarginLeftProperty = AttachedProperty.Create("MarginLeft",
|
||||
typeof(LayoutContainer), typeof(float), changed: LayoutPropertyChangedCallback);
|
||||
|
||||
@@ -47,6 +51,9 @@ namespace Robust.Client.UserInterface.Controls
|
||||
public static readonly AttachedProperty GrowVerticalProperty = AttachedProperty.Create("GrowVertical",
|
||||
typeof(LayoutContainer), typeof(GrowDirection), changed: LayoutPropertyChangedCallback);
|
||||
|
||||
public static readonly AttachedProperty<bool> DebugProperty = AttachedProperty<bool>.Create("Debug",
|
||||
typeof(LayoutContainer));
|
||||
|
||||
|
||||
public static void SetMarginLeft(Control control, float value)
|
||||
{
|
||||
@@ -112,16 +119,10 @@ namespace Robust.Client.UserInterface.Controls
|
||||
SetMarginBottom(control, diffY + control.GetValue<float>(MarginBottomProperty));
|
||||
}
|
||||
|
||||
public static void SetSize(Control control, Vector2 size)
|
||||
[Obsolete("Change SetSize on the control instead.")]
|
||||
public new static void SetSize(Control control, Vector2 size)
|
||||
{
|
||||
var (diffX, diffY) = size - control.Size;
|
||||
|
||||
// This is just to make subsequent set calls work correctly.
|
||||
// It should get reset to this exact value next update either way.
|
||||
control.Size = size;
|
||||
|
||||
SetMarginRight(control, diffX + control.GetValue<float>(MarginRightProperty));
|
||||
SetMarginBottom(control, diffY + control.GetValue<float>(MarginBottomProperty));
|
||||
control.SetSize = size;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -297,8 +298,9 @@ namespace Robust.Client.UserInterface.Controls
|
||||
LayoutPresetMode resizeMode = LayoutPresetMode.MinSize,
|
||||
int margin = 0)
|
||||
{
|
||||
control.Measure(Vector2.Infinity);
|
||||
var newSize = control.Size;
|
||||
var minSize = control.CombinedMinimumSize;
|
||||
var minSize = control.DesiredSize;
|
||||
if ((resizeMode & LayoutPresetMode.KeepWidth) == 0)
|
||||
{
|
||||
newSize = new Vector2(minSize.X, newSize.Y);
|
||||
@@ -445,39 +447,131 @@ namespace Robust.Client.UserInterface.Controls
|
||||
control.SetValue(MarginBottomProperty, marginBottom);
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var min = Vector2.Zero;
|
||||
var uiScale = UIScale;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
var growH = child.GetValue<GrowDirection>(GrowHorizontalProperty);
|
||||
var growV = child.GetValue<GrowDirection>(GrowVerticalProperty);
|
||||
|
||||
var anchorMargins = CalcAnchorMargins(availableSize, uiScale, child);
|
||||
var size = availableSize;
|
||||
if (growH == GrowDirection.Constrain)
|
||||
size.X = anchorMargins.Width / uiScale;
|
||||
|
||||
if (growV == GrowDirection.Constrain)
|
||||
size.Y = anchorMargins.Height / uiScale;
|
||||
|
||||
child.Measure(size);
|
||||
min = Vector2.ComponentMax(min, child.DesiredSize);
|
||||
}
|
||||
|
||||
return min;
|
||||
}
|
||||
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.Arrange(CalcChildRect(finalSize, UIScale, child, out _));
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected internal override void Draw(DrawingHandleScreen handle)
|
||||
{
|
||||
base.Draw(handle);
|
||||
|
||||
if (!Debug)
|
||||
return;
|
||||
|
||||
var (pSizeX, pSizeY) = PixelSize;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
var anchorLeft = child.GetValue<float>(AnchorLeftProperty);
|
||||
var anchorTop = child.GetValue<float>(AnchorTopProperty);
|
||||
var anchorRight = child.GetValue<float>(AnchorRightProperty);
|
||||
var anchorBottom = child.GetValue<float>(AnchorBottomProperty);
|
||||
if (!child.GetValue(DebugProperty))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
var marginLeft = child.GetValue<float>(MarginLeftProperty) * UIScale;
|
||||
var marginTop = child.GetValue<float>(MarginTopProperty) * UIScale;
|
||||
var marginRight = child.GetValue<float>(MarginRightProperty) * UIScale;
|
||||
var marginBottom = child.GetValue<float>(MarginBottomProperty) * UIScale;
|
||||
var rect = CalcChildRect(Size, UIScale, child, out var anchorSize);
|
||||
|
||||
var growHorizontal = child.GetValue<GrowDirection>(GrowHorizontalProperty);
|
||||
var growVertical = child.GetValue<GrowDirection>(GrowVerticalProperty);
|
||||
var left = rect.Left * UIScale;
|
||||
var right = rect.Right * UIScale;
|
||||
var top = rect.Top * UIScale;
|
||||
var bottom = rect.Bottom * UIScale;
|
||||
|
||||
// Calculate where the control "wants" to be by its anchors/margins.
|
||||
var left = anchorLeft * pSizeX + marginLeft;
|
||||
var top = anchorTop * pSizeY + marginTop;
|
||||
var right = anchorRight * pSizeX + marginRight;
|
||||
var bottom = anchorBottom * pSizeY + marginBottom;
|
||||
DrawVLine(anchorSize.Left, Color.Pink);
|
||||
DrawVLine(anchorSize.Right, Color.Green);
|
||||
DrawHLine(anchorSize.Top, Color.Pink);
|
||||
DrawHLine(anchorSize.Bottom, Color.Green);
|
||||
|
||||
var (wSizeX, wSizeY) = (right - left, bottom - top);
|
||||
var (minSizeX, minSizeY) = child.CombinedPixelMinimumSize;
|
||||
/*
|
||||
DrawVLine(left, Color.Orange);
|
||||
DrawVLine(right, Color.Blue);
|
||||
DrawHLine(top, Color.Orange);
|
||||
DrawHLine(bottom, Color.Blue);
|
||||
*/
|
||||
|
||||
HandleLayoutOverflow(growHorizontal, minSizeX, left, wSizeX, out var posX, out var sizeX);
|
||||
HandleLayoutOverflow(growVertical, minSizeY, top, wSizeY, out var posY, out var sizeY);
|
||||
|
||||
child.Position = new Vector2(posX, posY) / UserInterfaceManager.UIScale;
|
||||
child.Size = new Vector2(sizeX, sizeY) / UserInterfaceManager.UIScale;
|
||||
handle.DrawRect(new UIBox2(left, top, right, bottom), Color.Red, false);
|
||||
}
|
||||
|
||||
void DrawVLine(float x, Color color)
|
||||
{
|
||||
handle.DrawLine((x, 0), (x, pSizeY), color);
|
||||
}
|
||||
|
||||
void DrawHLine(float y, Color color)
|
||||
{
|
||||
handle.DrawLine((0, y), (pSizeX, y), color);
|
||||
}
|
||||
}
|
||||
|
||||
private static UIBox2 CalcAnchorMargins(Vector2 ourSize, float uiScale, Control child)
|
||||
{
|
||||
var (pSizeX, pSizeY) = ourSize * uiScale;
|
||||
|
||||
var anchorLeft = child.GetValue<float>(AnchorLeftProperty);
|
||||
var anchorTop = child.GetValue<float>(AnchorTopProperty);
|
||||
var anchorRight = child.GetValue<float>(AnchorRightProperty);
|
||||
var anchorBottom = child.GetValue<float>(AnchorBottomProperty);
|
||||
|
||||
var marginLeft = child.GetValue<float>(MarginLeftProperty) * uiScale;
|
||||
var marginTop = child.GetValue<float>(MarginTopProperty) * uiScale;
|
||||
var marginRight = child.GetValue<float>(MarginRightProperty) * uiScale;
|
||||
var marginBottom = child.GetValue<float>(MarginBottomProperty) * uiScale;
|
||||
|
||||
var left = anchorLeft * pSizeX + marginLeft;
|
||||
var top = anchorTop * pSizeY + marginTop;
|
||||
var right = anchorRight * pSizeX + marginRight;
|
||||
var bottom = anchorBottom * pSizeY + marginBottom;
|
||||
|
||||
// Yes, this can return boxes with left > right (and top > bottom).
|
||||
// This is "intentional", see comment in CalcChildRect.
|
||||
|
||||
return new UIBox2(left, top, right, bottom);
|
||||
}
|
||||
|
||||
private static UIBox2 CalcChildRect(Vector2 ourSize, float uiScale, Control child, out UIBox2 anchorSize)
|
||||
{
|
||||
// Calculate where the control "wants" to be by its anchors/margins.
|
||||
var growHorizontal = child.GetValue<GrowDirection>(GrowHorizontalProperty);
|
||||
var growVertical = child.GetValue<GrowDirection>(GrowVerticalProperty);
|
||||
|
||||
anchorSize = CalcAnchorMargins(ourSize, uiScale, child);
|
||||
|
||||
// This intentionally results in negatives if the right bound is < the left bound.
|
||||
// Which then causes HandleLayoutOverflow to CORRECTLY work from the right bound instead.
|
||||
var (wSizeX, wSizeY) = (anchorSize.Right - anchorSize.Left, anchorSize.Bottom - anchorSize.Top);
|
||||
var (minSizeX, minSizeY) = child.DesiredPixelSize;
|
||||
|
||||
HandleLayoutOverflow(growHorizontal, minSizeX, anchorSize.Left, wSizeX, out var posX, out var sizeX);
|
||||
HandleLayoutOverflow(growVertical, minSizeY, anchorSize.Top, wSizeY, out var posY, out var sizeY);
|
||||
|
||||
return UIBox2.FromDimensions(posX / uiScale, posY / uiScale, sizeX / uiScale, sizeY / uiScale);
|
||||
}
|
||||
|
||||
private static void HandleLayoutOverflow(GrowDirection direction, float minSize, float wPos, float wSize,
|
||||
@@ -485,7 +579,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
out float size)
|
||||
{
|
||||
var overflow = minSize - wSize;
|
||||
if (overflow <= 0)
|
||||
if (overflow <= 0 || direction == GrowDirection.Constrain)
|
||||
{
|
||||
pos = wPos;
|
||||
size = wSize;
|
||||
@@ -514,7 +608,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
if (owner.Parent is LayoutContainer container)
|
||||
{
|
||||
container.UpdateLayout();
|
||||
container.InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -537,7 +631,12 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// <summary>
|
||||
/// The control will expand on all axes equally to reach its minimum size.
|
||||
/// </summary>
|
||||
Both
|
||||
Both,
|
||||
|
||||
/// <summary>
|
||||
/// The control will not be allowed to grow on this axis.
|
||||
/// </summary>
|
||||
Constrain,
|
||||
}
|
||||
|
||||
/// <seealso cref="Control.SetMarginsPreset" />
|
||||
|
||||
@@ -242,18 +242,22 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var font = _getFont();
|
||||
var style = _getStyleBox();
|
||||
return new Vector2(0, font.GetHeight(UIScale) / UIScale) + style.MinimumSize / UIScale;
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var style = _getStyleBox();
|
||||
|
||||
FitChildInPixelBox(_renderBox, (UIBox2i) style.GetContentBox(PixelSizeBox));
|
||||
_renderBox.ArrangePixel(
|
||||
(UIBox2i) style.GetContentBox(
|
||||
UIBox2.FromDimensions(Vector2.Zero, finalSize * UIScale)));
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected internal override void TextEntered(GUITextEventArgs args)
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
using System;
|
||||
using Robust.Shared.Maths;
|
||||
|
||||
namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
[Obsolete("Set Margin directly")]
|
||||
public class MarginContainer : Container
|
||||
{
|
||||
public int? MarginBottomOverride { get; set; }
|
||||
@@ -9,36 +11,41 @@ namespace Robust.Client.UserInterface.Controls
|
||||
public int? MarginRightOverride { get; set; }
|
||||
public int? MarginLeftOverride { get; set; }
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var top = MarginTopOverride ?? 0;
|
||||
var bottom = MarginBottomOverride ?? 0;
|
||||
var left = MarginLeftOverride ?? 0;
|
||||
var right = MarginRightOverride ?? 0;
|
||||
|
||||
var box = UIBox2.FromDimensions(left, top, Width - right - left, Height - bottom - top);
|
||||
var margin = GetMargin();
|
||||
var availWithoutMargin = margin.Deflate(availableSize);
|
||||
|
||||
var max = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
FitChildInBox(child, box);
|
||||
child.Measure(availWithoutMargin);
|
||||
max = Vector2.ComponentMax(max, child.DesiredSize);
|
||||
}
|
||||
|
||||
return margin.Inflate(max);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var box = GetMargin().Deflate(UIBox2.FromDimensions(Vector2.Zero, finalSize));
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.Arrange(box);
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
private Thickness GetMargin()
|
||||
{
|
||||
var top = MarginTopOverride ?? 0;
|
||||
var bottom = MarginBottomOverride ?? 0;
|
||||
var left = MarginLeftOverride ?? 0;
|
||||
var right = MarginRightOverride ?? 0;
|
||||
|
||||
var childMinSize = Vector2.Zero;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
childMinSize = Vector2.ComponentMax(child.CombinedMinimumSize, childMinSize);
|
||||
}
|
||||
|
||||
return childMinSize + (left + right, top + bottom);
|
||||
var margin = new Thickness(left, top, right, bottom);
|
||||
return margin;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
Children =
|
||||
{
|
||||
(_popupVBox = new VBoxContainer {CustomMinimumSize = (300, 0)})
|
||||
(_popupVBox = new VBoxContainer {MinSize = (300, 0)})
|
||||
}
|
||||
};
|
||||
_popup.OnPopupHide += PopupHidden;
|
||||
@@ -113,7 +113,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
break;
|
||||
|
||||
case MenuSeparator _:
|
||||
var control = new Control {CustomMinimumSize = (0, 6)};
|
||||
var control = new Control {MinSize = (0, 6)};
|
||||
container.AddChild(control);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -71,14 +71,14 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_label = new Label
|
||||
{
|
||||
StyleClasses = { StyleClassOptionButton },
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
hBox.AddChild(_label);
|
||||
|
||||
var textureRect = new TextureRect
|
||||
{
|
||||
StyleClasses = { StyleClassOptionTriangle },
|
||||
SizeFlagsVertical = SizeFlags.ShrinkCenter,
|
||||
VerticalAlignment = VAlignment.Center,
|
||||
};
|
||||
hBox.AddChild(textureRect);
|
||||
}
|
||||
@@ -112,7 +112,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
if (show)
|
||||
{
|
||||
var globalPos = GlobalPosition;
|
||||
var (minX, minY) = _popupVBox.CombinedMinimumSize;
|
||||
_popupVBox.Measure(Vector2.Infinity);
|
||||
var (minX, minY) = _popupVBox.DesiredSize;
|
||||
var box = UIBox2.FromDimensions(globalPos, (Math.Max(minX, Width), minY));
|
||||
UserInterfaceManager.ModalRoot.AddChild(_popup);
|
||||
_popup.Open(box);
|
||||
|
||||
@@ -60,14 +60,14 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_label = new Label
|
||||
{
|
||||
StyleClasses = { StyleClassOptionButton },
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
hBox.AddChild(_label);
|
||||
|
||||
_triangle = new TextureRect
|
||||
{
|
||||
StyleClasses = { StyleClassOptionTriangle },
|
||||
SizeFlagsVertical = SizeFlags.ShrinkCenter,
|
||||
VerticalAlignment = VAlignment.Center,
|
||||
Visible = !HideTriangle
|
||||
};
|
||||
hBox.AddChild(_triangle);
|
||||
@@ -118,7 +118,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
if (show)
|
||||
{
|
||||
var globalPos = GlobalPosition;
|
||||
var (minX, minY) = _popupVBox.CombinedMinimumSize;
|
||||
_popupVBox.Measure(Vector2.Infinity);
|
||||
var (minX, minY) = _popupVBox.DesiredSize;
|
||||
var box = UIBox2.FromDimensions(globalPos, (Math.Max(minX, Width), minY));
|
||||
UserInterfaceManager.ModalRoot.AddChild(_popup);
|
||||
_popup.Open(box);
|
||||
|
||||
@@ -31,8 +31,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_scrollBar = new VScrollBar
|
||||
{
|
||||
Name = "_v_scroll",
|
||||
SizeFlagsVertical = SizeFlags.Fill,
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
AddChild(_scrollBar);
|
||||
_scrollBar.OnValueChanged += _ => _isAtBottom = _scrollBar.IsAtEnd;
|
||||
@@ -44,7 +43,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_styleBoxOverride = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
_invalidateEntries();
|
||||
}
|
||||
}
|
||||
@@ -168,7 +167,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_invalidateEntries();
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return _getStyleBox()?.MinimumSize ?? Vector2.Zero;
|
||||
}
|
||||
|
||||
@@ -17,26 +17,32 @@ namespace Robust.Client.UserInterface.Controls
|
||||
style?.Draw(handle, PixelSizeBox);
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var contentBox = _getStyleBox()?.GetContentBox(PixelSizeBox) ?? PixelSizeBox;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
FitChildInPixelBox(child, (UIBox2i) contentBox);
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
var styleSize = _getStyleBox()?.MinimumSize ?? Vector2.Zero;
|
||||
var styleSize = (_getStyleBox()?.MinimumSize ?? Vector2.Zero) / UIScale;
|
||||
var measureSize = Vector2.ComponentMax(availableSize - styleSize, Vector2.Zero);
|
||||
var childSize = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
childSize = Vector2.ComponentMax(childSize, child.CombinedMinimumSize);
|
||||
child.Measure(measureSize);
|
||||
childSize = Vector2.ComponentMax(childSize, child.DesiredSize);
|
||||
}
|
||||
|
||||
return styleSize / UIScale + childSize;
|
||||
return styleSize + childSize;
|
||||
}
|
||||
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
var pixelSize = finalSize * UIScale;
|
||||
var ourSize = UIBox2.FromDimensions(Vector2.Zero, pixelSize);
|
||||
var contentBox = _getStyleBox()?.GetContentBox(ourSize) ?? ourSize;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.ArrangePixel((UIBox2i) contentBox);
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
[System.Diagnostics.Contracts.Pure]
|
||||
|
||||
@@ -30,7 +30,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
PopupContainer.SetAltOrigin(this, altPos);
|
||||
|
||||
_desiredSize = box.Value.Size;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
Visible = true;
|
||||
@@ -52,9 +52,11 @@ namespace Robust.Client.UserInterface.Controls
|
||||
OnPopupHide?.Invoke();
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return Vector2.ComponentMax(_desiredSize, base.CalculateMinimumSize());
|
||||
return Vector2.ComponentMax(
|
||||
_desiredSize,
|
||||
base.MeasureOverride(Vector2.ComponentMax(availableSize, _desiredSize)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -54,15 +54,15 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
if (owner.Parent is PopupContainer container)
|
||||
{
|
||||
container.UpdateLayout();
|
||||
container.InvalidateArrange();
|
||||
}
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
foreach (var child in Children)
|
||||
{
|
||||
var size = child.CombinedMinimumSize;
|
||||
var size = child.DesiredSize;
|
||||
var offset = child.GetValue<Vector2>(PopupOriginProperty);
|
||||
var altPos = child.GetValue<Vector2?>(AltOriginProperty);
|
||||
|
||||
@@ -105,22 +105,25 @@ namespace Robust.Client.UserInterface.Controls
|
||||
offset -= (0, offset.Y);
|
||||
}
|
||||
|
||||
FitChildInBox(child, UIBox2.FromDimensions(offset, size));
|
||||
child.Arrange(UIBox2.FromDimensions(offset, size));
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
// Do NOT inherit minimum size from contents!
|
||||
// Just clip 'em.
|
||||
return (0, 0);
|
||||
// Measure to availableSize so that child controls never get too large to fit the whole screen.
|
||||
base.MeasureOverride(availableSize);
|
||||
|
||||
return availableSize;
|
||||
}
|
||||
|
||||
protected override void Resized()
|
||||
{
|
||||
base.Resized();
|
||||
|
||||
UpdateLayout();
|
||||
InvalidateArrange();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,7 +18,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_backgroundStyleBoxOverride = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,7 +28,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_foregroundStyleBoxOverride = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -76,7 +76,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var bgSize = _getBackground()?.MinimumSize ?? Vector2.Zero;
|
||||
var fgSize = _getForeground()?.MinimumSize ?? Vector2.Zero;
|
||||
|
||||
@@ -11,13 +11,11 @@ namespace Robust.Client.UserInterface.Controls
|
||||
private FormattedMessage? _message;
|
||||
private RichTextEntry _entry;
|
||||
|
||||
public float? MaxWidth { get; set; }
|
||||
|
||||
public void SetMessage(FormattedMessage message)
|
||||
{
|
||||
_message = message;
|
||||
_entry = new RichTextEntry(_message);
|
||||
_updateEntry();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
|
||||
public void SetMessage(string message)
|
||||
@@ -27,42 +25,17 @@ namespace Robust.Client.UserInterface.Controls
|
||||
SetMessage(msg);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (_message == null)
|
||||
{
|
||||
return Vector2.Zero;
|
||||
}
|
||||
|
||||
var width = 0f;
|
||||
if (MaxWidth.HasValue)
|
||||
{
|
||||
width = _entry.Width / UIScale;
|
||||
}
|
||||
return (width, _entry.Height / UIScale);
|
||||
}
|
||||
|
||||
private void _updateEntry()
|
||||
{
|
||||
var font = _getFont();
|
||||
_entry.Update(font, availableSize.X * UIScale, UIScale);
|
||||
|
||||
if (_message != null)
|
||||
{
|
||||
var oldHeight = _entry.Height;
|
||||
var oldWidth = _entry.Width;
|
||||
_entry.Update(font, (MaxWidth ?? Width) * UIScale, UIScale);
|
||||
if (oldHeight != _entry.Height || MaxWidth != null && _entry.Width != oldWidth)
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected override void StylePropertiesChanged()
|
||||
{
|
||||
base.StylePropertiesChanged();
|
||||
|
||||
_updateEntry();
|
||||
return (_entry.Width / UIScale, _entry.Height / UIScale);
|
||||
}
|
||||
|
||||
protected internal override void Draw(DrawingHandleScreen handle)
|
||||
@@ -77,13 +50,6 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_entry.Draw(handle, _getFont(), SizeBox, 0, new Stack<FormattedMessage.Tag>(), UIScale);
|
||||
}
|
||||
|
||||
protected override void Resized()
|
||||
{
|
||||
base.Resized();
|
||||
|
||||
_updateEntry();
|
||||
}
|
||||
|
||||
[Pure]
|
||||
private Font _getFont()
|
||||
{
|
||||
|
||||
@@ -129,13 +129,13 @@ namespace Robust.Client.UserInterface.Controls
|
||||
if (_grabData == null)
|
||||
{
|
||||
var box = _getGrabberBox();
|
||||
_isHovered = box.Contains(args.RelativePosition);
|
||||
_isHovered = box.Contains(args.RelativePixelPosition);
|
||||
_updatePseudoClass();
|
||||
return;
|
||||
}
|
||||
|
||||
var (grabPos, grabValue) = _grabData.Value;
|
||||
var (grabRelX, grabRelY) = args.RelativePosition - grabPos;
|
||||
var (grabRelX, grabRelY) = args.RelativePixelPosition - grabPos;
|
||||
float moved;
|
||||
|
||||
if (_orientation == OrientationMode.Horizontal)
|
||||
@@ -219,7 +219,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return _getGrabberStyleBox()?.MinimumSize ?? Vector2.Zero;
|
||||
}
|
||||
|
||||
@@ -26,14 +26,14 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_hScrollBar = new HScrollBar
|
||||
{
|
||||
Visible = false,
|
||||
SizeFlagsVertical = SizeFlags.ShrinkEnd,
|
||||
SizeFlagsHorizontal = SizeFlags.Fill
|
||||
VerticalAlignment = VAlignment.Bottom,
|
||||
HorizontalAlignment = HAlignment.Stretch
|
||||
};
|
||||
_vScrollBar = new VScrollBar
|
||||
{
|
||||
Visible = false,
|
||||
SizeFlagsVertical = SizeFlags.Fill,
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
VerticalAlignment = VAlignment.Stretch,
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
AddChild(_hScrollBar);
|
||||
AddChild(_vScrollBar);
|
||||
@@ -47,7 +47,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_vScrollEnabled = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -57,17 +57,50 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_hScrollEnabled = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (_vScrollEnabled)
|
||||
{
|
||||
_vScrollBar.Measure(availableSize);
|
||||
availableSize.X -= _vScrollBar.DesiredSize.X;
|
||||
}
|
||||
|
||||
if (_hScrollEnabled)
|
||||
{
|
||||
_hScrollBar.Measure(availableSize);
|
||||
availableSize.Y -= _hScrollBar.DesiredSize.Y;
|
||||
}
|
||||
|
||||
var constraint = new Vector2(
|
||||
_hScrollEnabled ? float.PositiveInfinity : availableSize.X,
|
||||
_vScrollEnabled ? float.PositiveInfinity : availableSize.Y);
|
||||
|
||||
var size = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
child.Measure(constraint);
|
||||
size = Vector2.ComponentMax(size, child.DesiredSize);
|
||||
}
|
||||
|
||||
// Unlike WPF/Avalonia we report ZERO here instead of available size.
|
||||
// This is to fix a bunch of jank with e.g. BoxContainer.
|
||||
// Tbh this might be a mistake.
|
||||
// DockPanel when.
|
||||
return Vector2.Zero;
|
||||
}
|
||||
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
if (_vScrollBar?.Parent == null || _hScrollBar?.Parent == null)
|
||||
{
|
||||
// Just don't run this before we're properly initialized.
|
||||
return;
|
||||
return Vector2.Zero;
|
||||
}
|
||||
|
||||
var maxChildMinSize = Vector2.Zero;
|
||||
|
||||
foreach (var child in Children)
|
||||
@@ -77,31 +110,31 @@ namespace Robust.Client.UserInterface.Controls
|
||||
continue;
|
||||
}
|
||||
|
||||
maxChildMinSize = Vector2.ComponentMax(child.CombinedMinimumSize, maxChildMinSize);
|
||||
maxChildMinSize = Vector2.ComponentMax(child.DesiredSize, maxChildMinSize);
|
||||
}
|
||||
|
||||
var (cWidth, cHeight) = maxChildMinSize;
|
||||
var hBarSize = _hScrollBar.CombinedMinimumSize.Y;
|
||||
var vBarSize = _vScrollBar.CombinedMinimumSize.X;
|
||||
var hBarSize = _hScrollBar.DesiredSize.Y;
|
||||
var vBarSize = _vScrollBar.DesiredSize.X;
|
||||
|
||||
var (sWidth, sHeight) = Size;
|
||||
var (sWidth, sHeight) = finalSize;
|
||||
|
||||
try
|
||||
{
|
||||
// Suppress events to avoid weird recursion.
|
||||
_suppressScrollValueChanged = true;
|
||||
|
||||
if (Width < cWidth)
|
||||
if (sWidth < cWidth && _hScrollEnabled)
|
||||
{
|
||||
sHeight -= hBarSize;
|
||||
}
|
||||
|
||||
if (Height < cHeight)
|
||||
if (sHeight < cHeight && _vScrollEnabled)
|
||||
{
|
||||
sWidth -= vBarSize;
|
||||
}
|
||||
|
||||
if (sWidth < cWidth)
|
||||
if (sWidth < cWidth && _hScrollEnabled)
|
||||
{
|
||||
_hScrollBar.Visible = _hScrollVisible = true;
|
||||
_hScrollBar.Page = sWidth;
|
||||
@@ -112,7 +145,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_hScrollBar.Visible = _hScrollVisible = false;
|
||||
}
|
||||
|
||||
if (sHeight < cHeight)
|
||||
if (sHeight < cHeight && _vScrollEnabled)
|
||||
{
|
||||
_vScrollBar.Visible = _vScrollVisible = true;
|
||||
_vScrollBar.Page = sHeight;
|
||||
@@ -129,10 +162,19 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_suppressScrollValueChanged = false;
|
||||
}
|
||||
|
||||
var sSize = (sWidth, sHeight);
|
||||
if (_vScrollVisible)
|
||||
{
|
||||
_vScrollBar.Arrange(UIBox2.FromDimensions(Vector2.Zero, finalSize));
|
||||
}
|
||||
|
||||
FitChildInPixelBox(_vScrollBar, PixelSizeBox);
|
||||
FitChildInPixelBox(_hScrollBar, PixelSizeBox);
|
||||
if (_hScrollVisible)
|
||||
{
|
||||
_hScrollBar.Arrange(UIBox2.FromDimensions(Vector2.Zero, finalSize));
|
||||
}
|
||||
|
||||
var realFinalSize = (
|
||||
_hScrollEnabled ? Math.Max(cWidth, sWidth) : sWidth,
|
||||
_vScrollEnabled ? Math.Max(cHeight, sHeight) : sHeight);
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
@@ -142,47 +184,11 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
|
||||
var position = -_getScrollValue();
|
||||
var rect = UIBox2.FromDimensions(position, Vector2.ComponentMax(child.CombinedMinimumSize, sSize));
|
||||
FitChildInBox(child, rect);
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
var totalX = 0f;
|
||||
var totalY = 0f;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
if (child == _hScrollBar || child == _vScrollBar)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!_vScrollEnabled)
|
||||
{
|
||||
totalY = Math.Max(totalY, child.CombinedMinimumSize.Y);
|
||||
}
|
||||
|
||||
if (!_hScrollEnabled)
|
||||
{
|
||||
totalX = Math.Max(totalX, child.CombinedMinimumSize.X);
|
||||
}
|
||||
var rect = UIBox2.FromDimensions(position, realFinalSize);
|
||||
child.Arrange(rect);
|
||||
}
|
||||
|
||||
if (_vScrollEnabled)
|
||||
{
|
||||
totalX += _vScrollBar.CombinedMinimumSize.X;
|
||||
totalY = Math.Max(_vScrollBar.CombinedMinimumSize.Y, totalY);
|
||||
}
|
||||
|
||||
if (_hScrollEnabled)
|
||||
{
|
||||
totalY += _hScrollBar.CombinedMinimumSize.Y;
|
||||
totalX = Math.Max(_vScrollBar.CombinedMinimumSize.X, totalX);
|
||||
}
|
||||
|
||||
return new Vector2(totalX, totalY);
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected internal override void MouseWheel(GUIMouseWheelEventArgs args)
|
||||
@@ -223,10 +229,12 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
h = 0;
|
||||
}
|
||||
|
||||
if (!_vScrollVisible)
|
||||
{
|
||||
v = 0;
|
||||
}
|
||||
|
||||
return new Vector2(h, v);
|
||||
}
|
||||
|
||||
@@ -237,7 +245,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
return;
|
||||
}
|
||||
|
||||
UpdateLayout();
|
||||
InvalidateArrange();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -109,7 +109,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
var ratio = GetAsRatio();
|
||||
|
||||
var margin = (Width - _grabber.CombinedMinimumSize.X) * ratio + _grabber.CombinedMinimumSize.X / 2;
|
||||
var margin = (Width - _grabber.DesiredSize.X) * ratio + _grabber.DesiredSize.X / 2;
|
||||
SetMarginRight(_fillPanel, margin);
|
||||
SetMarginLeft(_grabber, margin);
|
||||
SetMarginRight(_grabber, margin);
|
||||
@@ -156,7 +156,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
private void HandlePositionChange(Vector2 position)
|
||||
{
|
||||
var grabberWidth = _grabber.CombinedMinimumSize.X;
|
||||
var grabberWidth = _grabber.DesiredSize.X;
|
||||
var ratio = (position.X - grabberWidth / 2) / (Width - grabberWidth);
|
||||
SetAsRatio(ratio);
|
||||
}
|
||||
|
||||
@@ -58,8 +58,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
_lineEdit = new LineEdit
|
||||
{
|
||||
CustomMinimumSize = new Vector2(40, 0),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
MinSize = new Vector2(40, 0),
|
||||
HorizontalExpand = true
|
||||
};
|
||||
AddChild(_lineEdit);
|
||||
|
||||
|
||||
@@ -31,8 +31,9 @@ namespace Robust.Client.UserInterface.Controls
|
||||
// min / max x and y extents in relative virtual pixels of where the split can go regardless
|
||||
// of anything else.
|
||||
private float SplitMin => SplitWidth + SplitEdgeSeparation;
|
||||
private float SplitMax => Vertical ? Height - (SplitWidth + SplitEdgeSeparation) :
|
||||
Width - (SplitWidth + SplitEdgeSeparation);
|
||||
|
||||
private float SplitMax =>
|
||||
Vertical ? Height - (SplitWidth + SplitEdgeSeparation) : Width - (SplitWidth + SplitEdgeSeparation);
|
||||
|
||||
public SplitContainer()
|
||||
{
|
||||
@@ -56,11 +57,10 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
_splitCenter = ClampSplitCenter(newOffset);
|
||||
DefaultCursorShape = Vertical ? CursorShape.VResize : CursorShape.HResize;
|
||||
ForceRunLayoutUpdate();
|
||||
InvalidateArrange();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
// on mouseover, check if they are over the split and change the cursor accordingly
|
||||
var cursor = CursorShape.Arrow;
|
||||
if (CanDragAt(args.RelativePosition))
|
||||
@@ -124,37 +124,32 @@ namespace Robust.Client.UserInterface.Controls
|
||||
var first = GetChild(0);
|
||||
var second = GetChild(1);
|
||||
|
||||
firstMinSize ??= (Vertical ? first.CombinedMinimumSize.Y : first.CombinedMinimumSize.X);
|
||||
secondMinSize ??= (Vertical ? second.CombinedMinimumSize.Y : second.CombinedMinimumSize.X);
|
||||
firstMinSize ??= (Vertical ? first.DesiredSize.Y : first.DesiredSize.X);
|
||||
secondMinSize ??= (Vertical ? second.DesiredSize.Y : second.DesiredSize.X);
|
||||
var size = Vertical ? Height : Width;
|
||||
|
||||
splitCenter = MathHelper.Clamp(splitCenter, firstMinSize.Value, size - (secondMinSize.Value + SplitWidth));
|
||||
splitCenter = MathHelper.Clamp(splitCenter, firstMinSize.Value,
|
||||
size - (secondMinSize.Value + SplitWidth));
|
||||
}
|
||||
|
||||
return splitCenter;
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
base.LayoutUpdateOverride();
|
||||
|
||||
if (ChildCount != 2)
|
||||
{
|
||||
return;
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
var first = GetChild(0);
|
||||
var second = GetChild(1);
|
||||
|
||||
var firstExpand = Vertical
|
||||
? (first.SizeFlagsVertical & SizeFlags.Expand) != 0
|
||||
: (first.SizeFlagsHorizontal & SizeFlags.Expand) != 0;
|
||||
var secondExpand = Vertical
|
||||
? (second.SizeFlagsVertical & SizeFlags.Expand) != 0
|
||||
: (second.SizeFlagsHorizontal & SizeFlags.Expand) != 0;
|
||||
var firstExpand = Vertical ? first.VerticalExpand : first.HorizontalExpand;
|
||||
var secondExpand = Vertical ? second.VerticalExpand : second.HorizontalExpand;
|
||||
|
||||
var firstMinSize = Vertical ? first.CombinedMinimumSize.Y : first.CombinedMinimumSize.X;
|
||||
var secondMinSize = Vertical ? second.CombinedMinimumSize.Y : second.CombinedMinimumSize.X;
|
||||
var firstMinSize = Vertical ? first.DesiredSize.Y : first.DesiredSize.X;
|
||||
var secondMinSize = Vertical ? second.DesiredSize.Y : second.DesiredSize.X;
|
||||
|
||||
var size = Vertical ? Height : Width;
|
||||
|
||||
@@ -181,24 +176,27 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_splitCenter = firstMinSize;
|
||||
}
|
||||
|
||||
_splitCenter += MathHelper.Clamp(0f, firstMinSize - _splitCenter, size - secondMinSize - SplitWidth - _splitCenter);
|
||||
_splitCenter += MathHelper.Clamp(0f, firstMinSize - _splitCenter,
|
||||
size - secondMinSize - SplitWidth - _splitCenter);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (Vertical)
|
||||
{
|
||||
FitChildInBox(first, new UIBox2(0, 0, Width, _splitCenter));
|
||||
FitChildInBox(second, new UIBox2(0, _splitCenter + SplitWidth, Width, Height));
|
||||
first.Arrange(new UIBox2(0, 0, Width, _splitCenter));
|
||||
second.Arrange(new UIBox2(0, _splitCenter + SplitWidth, Width, Height));
|
||||
}
|
||||
else
|
||||
{
|
||||
FitChildInBox(first, new UIBox2(0, 0, _splitCenter, Height));
|
||||
FitChildInBox(second, new UIBox2(_splitCenter + SplitWidth, 0, Width, Height));
|
||||
first.Arrange(new UIBox2(0, 0, _splitCenter, Height));
|
||||
second.Arrange(new UIBox2(_splitCenter + SplitWidth, 0, Width, Height));
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (ChildCount != 2)
|
||||
{
|
||||
@@ -208,8 +206,12 @@ namespace Robust.Client.UserInterface.Controls
|
||||
var first = GetChild(0);
|
||||
var second = GetChild(1);
|
||||
|
||||
var (firstSizeX, firstSizeY) = first.CombinedMinimumSize;
|
||||
var (secondSizeX, secondSizeY) = second.CombinedMinimumSize;
|
||||
// TODO: Probably bad implementation with the new WPF layout.
|
||||
first.Measure(availableSize);
|
||||
second.Measure(availableSize);
|
||||
|
||||
var (firstSizeX, firstSizeY) = first.DesiredSize;
|
||||
var (secondSizeX, secondSizeY) = second.DesiredSize;
|
||||
|
||||
if (Vertical)
|
||||
{
|
||||
@@ -236,6 +238,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// Don't allow user to move the split.
|
||||
/// </summary>
|
||||
NotResizable = -1,
|
||||
|
||||
/// <summary>
|
||||
/// User can resize the split but can't shrink either child
|
||||
/// beyond its minimum size.
|
||||
@@ -255,6 +258,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
/// Automatically adjust the split based on the width of the children
|
||||
/// </summary>
|
||||
Auto = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Manually adjust the split by dragging it
|
||||
/// </summary>
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_scale = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
RectClipContent = true;
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
// TODO: make this not hardcoded.
|
||||
// It'll break on larger things.
|
||||
|
||||
@@ -47,7 +47,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
GetChild(old).Visible = false;
|
||||
var newSelected = GetChild(value);
|
||||
newSelected.Visible = true;
|
||||
_fixChildMargins(newSelected);
|
||||
InvalidateMeasure();
|
||||
|
||||
OnTabChanged?.Invoke(value);
|
||||
}
|
||||
@@ -59,7 +59,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_tabsVisible = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -124,7 +124,6 @@ namespace Robust.Client.UserInterface.Controls
|
||||
{
|
||||
// This is our first child so it must always be visible.
|
||||
newChild.Visible = true;
|
||||
_fixChildMargins(newChild);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -212,44 +211,52 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var total = Vector2i.Zero;
|
||||
var headerSize = Vector2.Zero;
|
||||
|
||||
if (TabsVisible)
|
||||
{
|
||||
headerSize = (0, _getHeaderSize() / UIScale);
|
||||
}
|
||||
|
||||
var panel = _getPanel();
|
||||
var panelSize = (panel?.MinimumSize ?? Vector2.Zero) / UIScale;
|
||||
|
||||
var contentsSize = availableSize - headerSize - panelSize;
|
||||
|
||||
var total = Vector2.Zero;
|
||||
foreach (var child in Children)
|
||||
{
|
||||
if (child.Visible)
|
||||
{
|
||||
total = Vector2i.ComponentMax(child.CombinedPixelMinimumSize, total);
|
||||
child.Measure(contentsSize);
|
||||
total = Vector2.ComponentMax(child.DesiredSize, total);
|
||||
}
|
||||
}
|
||||
|
||||
if (TabsVisible)
|
||||
{
|
||||
total += (0, _getHeaderSize());
|
||||
}
|
||||
|
||||
var panel = _getPanel();
|
||||
total += (Vector2i)(panel?.MinimumSize ?? Vector2.Zero);
|
||||
|
||||
return total / UIScale;
|
||||
return total + headerSize + panelSize;
|
||||
}
|
||||
|
||||
private void _fixChildMargins(Control child)
|
||||
{
|
||||
FitChildInPixelBox(child, _getContentBox());
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
if (ChildCount == 0 || _currentTab >= ChildCount)
|
||||
{
|
||||
return;
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
var headerSize = _getHeaderSize();
|
||||
var panel = _getPanel();
|
||||
var contentBox = new UIBox2i(0, headerSize, (int) (finalSize.X * UIScale), (int) (finalSize.Y * UIScale));
|
||||
if (panel != null)
|
||||
{
|
||||
contentBox = (UIBox2i) panel.GetContentBox(contentBox);
|
||||
}
|
||||
|
||||
var control = GetChild(_currentTab);
|
||||
control.Visible = true;
|
||||
_fixChildMargins(control);
|
||||
control.ArrangePixel(contentBox);
|
||||
return finalSize;
|
||||
}
|
||||
|
||||
protected internal override void KeyBindDown(GUIBoundKeyEventArgs args)
|
||||
@@ -313,19 +320,6 @@ namespace Robust.Client.UserInterface.Controls
|
||||
}
|
||||
}
|
||||
|
||||
[System.Diagnostics.Contracts.Pure]
|
||||
private UIBox2i _getContentBox()
|
||||
{
|
||||
var headerSize = _getHeaderSize();
|
||||
var panel = _getPanel();
|
||||
var panelBox = new UIBox2i(0, headerSize, PixelWidth, PixelHeight);
|
||||
if (panel != null)
|
||||
{
|
||||
return (UIBox2i) panel.GetContentBox(panelBox);
|
||||
}
|
||||
return panelBox;
|
||||
}
|
||||
|
||||
[System.Diagnostics.Contracts.Pure]
|
||||
private int _getHeaderSize()
|
||||
{
|
||||
|
||||
@@ -27,7 +27,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_textureNormal = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -37,7 +37,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_scale = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -78,7 +78,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
handle.DrawTextureRectRegion(texture, PixelSizeBox);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var texture = TextureNormal;
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
|
||||
if (value?.Size != oldSize)
|
||||
{
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -49,7 +49,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_textureScale = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -66,7 +66,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
set
|
||||
{
|
||||
_canShrink = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -223,7 +223,7 @@ namespace Robust.Client.UserInterface.Controls
|
||||
KeepAspectCovered = 8
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
var texture = _texture;
|
||||
|
||||
|
||||
@@ -34,8 +34,8 @@ namespace Robust.Client.UserInterface.Controls
|
||||
_scrollBar = new VScrollBar
|
||||
{
|
||||
Name = "_v_scroll",
|
||||
SizeFlagsVertical = SizeFlags.Fill,
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
VerticalAlignment = VAlignment.Stretch,
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
AddChild(_scrollBar);
|
||||
}
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
using System;
|
||||
using Robust.Client.UserInterface.Controls;
|
||||
using Robust.Shared.Input;
|
||||
using Robust.Shared.IoC;
|
||||
using Robust.Shared.Log;
|
||||
using Robust.Shared.Maths;
|
||||
using Robust.Shared.Timing;
|
||||
|
||||
namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
@@ -125,34 +127,39 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
}
|
||||
else
|
||||
{
|
||||
var top = Rect.Top;
|
||||
var bottom = Rect.Bottom;
|
||||
var left = Rect.Left;
|
||||
var right = Rect.Right;
|
||||
var (minSizeX, minSizeY) = CombinedMinimumSize;
|
||||
var (left, top) = Position;
|
||||
var (right, bottom) = Position + SetSize;
|
||||
|
||||
if ((CurrentDrag & DragMode.Top) == DragMode.Top)
|
||||
{
|
||||
var maxY = bottom - minSizeY;
|
||||
top = Math.Min(args.GlobalPosition.Y - DragOffsetTopLeft.Y, maxY);
|
||||
top = Math.Min(args.GlobalPosition.Y - DragOffsetTopLeft.Y, bottom);
|
||||
}
|
||||
else if ((CurrentDrag & DragMode.Bottom) == DragMode.Bottom)
|
||||
{
|
||||
bottom = Math.Max(args.GlobalPosition.Y + DragOffsetBottomRight.Y, top + minSizeY);
|
||||
bottom = Math.Max(args.GlobalPosition.Y + DragOffsetBottomRight.Y, top);
|
||||
}
|
||||
|
||||
if ((CurrentDrag & DragMode.Left) == DragMode.Left)
|
||||
{
|
||||
var maxX = right - minSizeX;
|
||||
left = Math.Min(args.GlobalPosition.X - DragOffsetTopLeft.X, maxX);
|
||||
left = Math.Min(args.GlobalPosition.X - DragOffsetTopLeft.X, right);
|
||||
}
|
||||
else if ((CurrentDrag & DragMode.Right) == DragMode.Right)
|
||||
{
|
||||
right = Math.Max(args.GlobalPosition.X + DragOffsetBottomRight.X, left + minSizeX);
|
||||
right = Math.Max(args.GlobalPosition.X + DragOffsetBottomRight.X, left);
|
||||
}
|
||||
|
||||
var rect = new UIBox2(left, top, right, bottom);
|
||||
LayoutContainer.SetPosition(this, rect.TopLeft);
|
||||
LayoutContainer.SetSize(this, rect.Size);
|
||||
SetSize = rect.Size;
|
||||
|
||||
/*
|
||||
var timing = IoCManager.Resolve<IGameTiming>();
|
||||
|
||||
var l = GetValue<float>(LayoutContainer.MarginLeftProperty);
|
||||
var t = GetValue<float>(LayoutContainer.MarginTopProperty);
|
||||
|
||||
Logger.Debug($"{timing.CurFrame}: {rect.TopLeft}/({l}, {t}), {rect.Size}/{SetSize}");
|
||||
*/
|
||||
}
|
||||
}
|
||||
|
||||
@@ -215,7 +222,8 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
if (_firstTimeOpened)
|
||||
{
|
||||
LayoutContainer.SetSize(this, CombinedMinimumSize);
|
||||
Measure(Vector2.Infinity);
|
||||
SetSize = DesiredSize;
|
||||
Open();
|
||||
// An explaination: The BadOpenGLVersionWindow was showing up off the top-left corner of the screen.
|
||||
// Basically, if OpenCentered happens super-early, RootControl doesn't get time to layout children.
|
||||
@@ -233,7 +241,8 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
if (_firstTimeOpened)
|
||||
{
|
||||
LayoutContainer.SetSize(this, CombinedMinimumSize);
|
||||
Measure(Vector2.Infinity);
|
||||
SetSize = DesiredSize;
|
||||
Open();
|
||||
LayoutContainer.SetPosition(this, (0, (Parent!.Size.Y - Size.Y) / 2));
|
||||
_firstTimeOpened = false;
|
||||
|
||||
@@ -77,7 +77,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
(Output = new OutputPanel
|
||||
{
|
||||
SizeFlagsVertical = SizeFlags.FillExpand,
|
||||
VerticalExpand = true,
|
||||
StyleBoxOverride = styleBox
|
||||
}),
|
||||
(CommandBar = new HistoryLineEdit {PlaceHolder = "Command Here"})
|
||||
|
||||
@@ -27,11 +27,11 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
IoCManager.InjectDependencies(this);
|
||||
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
|
||||
_contents = new Label
|
||||
{
|
||||
FontColorShadowOverride = Color.Black,
|
||||
FontColorShadowOverride = Color.Black
|
||||
};
|
||||
AddChild(_contents);
|
||||
|
||||
@@ -43,6 +43,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
};
|
||||
|
||||
MouseFilter = _contents.MouseFilter = MouseFilterMode.Ignore;
|
||||
MinWidth = 175;
|
||||
}
|
||||
|
||||
protected override void FrameUpdate(FrameEventArgs args)
|
||||
@@ -70,8 +71,10 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
}
|
||||
else
|
||||
{
|
||||
mouseGridPos = new EntityCoordinates(_mapManager.GetMapEntityId(mouseWorldMap.MapId), mouseWorldMap.Position);
|
||||
tile = new TileRef(mouseWorldMap.MapId, GridId.Invalid, mouseGridPos.ToVector2i(_entityManager, _mapManager), Tile.Empty);
|
||||
mouseGridPos = new EntityCoordinates(_mapManager.GetMapEntityId(mouseWorldMap.MapId),
|
||||
mouseWorldMap.Position);
|
||||
tile = new TileRef(mouseWorldMap.MapId, GridId.Invalid,
|
||||
mouseGridPos.ToVector2i(_entityManager, _mapManager), Tile.Empty);
|
||||
}
|
||||
|
||||
var controlHovered = UserInterfaceManager.CurrentlyHovered;
|
||||
@@ -103,7 +106,8 @@ Mouse Pos:
|
||||
{1}
|
||||
{2}
|
||||
EntId: {3}
|
||||
GridID: {4}", playerScreen, playerWorldOffset, playerCoordinates, entityTransform.Owner.Uid, entityTransform.GridID);
|
||||
GridID: {4}", playerScreen, playerWorldOffset, playerCoordinates, entityTransform.Owner.Uid,
|
||||
entityTransform.GridID);
|
||||
}
|
||||
|
||||
if (controlHovered != null)
|
||||
@@ -112,7 +116,7 @@ Mouse Pos:
|
||||
}
|
||||
|
||||
_contents.Text = stringBuilder.ToString();
|
||||
MinimumSizeChanged();
|
||||
// MinimumSizeChanged();
|
||||
}
|
||||
|
||||
protected internal override void Draw(DrawingHandleScreen handle)
|
||||
@@ -133,10 +137,5 @@ Mouse Pos:
|
||||
|
||||
handle.DrawRect(renderBox, Color.Red, false);
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
return new(175, _contents.CombinedMinimumSize.Y + 10);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,7 +17,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
public DebugMemoryPanel()
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
|
||||
AddChild(_label = new Label());
|
||||
|
||||
|
||||
@@ -69,12 +69,12 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
AddChild(_debugClydePanel = new DebugClydePanel
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.None
|
||||
HorizontalAlignment = HAlignment.Left
|
||||
});
|
||||
|
||||
AddChild(_debugInputPanel = new DebugInputPanel
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.None
|
||||
HorizontalAlignment = HAlignment.Left
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
_contents = new Label();
|
||||
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
|
||||
_contents = new Label
|
||||
{
|
||||
@@ -62,12 +62,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
_contents.Text = string.Join('\n', bandwidth);
|
||||
|
||||
MinimumSizeChanged();
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
return new(_contents.CombinedMinimumSize.X + 10, _contents.CombinedMinimumSize.Y + 10);
|
||||
// MinimumSizeChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,7 +33,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
contents = new Label();
|
||||
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
|
||||
contents = new Label
|
||||
{
|
||||
@@ -68,7 +68,6 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
if (!NetManager.IsConnected)
|
||||
{
|
||||
contents.Text = "Not connected to server.";
|
||||
MinimumSizeChanged();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -89,12 +88,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
DOWN: {receivedBytes / ONE_KIBIBYTE:N} KiB/s, {receivedPackets} pckt/s, {LastReceivedBytes / ONE_KIBIBYTE:N} KiB, {LastReceivedPackets} pckt
|
||||
PING: {NetManager.ServerChannel?.Ping ?? -1} ms";
|
||||
|
||||
MinimumSizeChanged();
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
return new(contents.CombinedMinimumSize.X + 10, contents.CombinedMinimumSize.Y + 10);
|
||||
// MinimumSizeChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,7 +33,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
MouseFilter = _contents.MouseFilter = MouseFilterMode.Ignore;
|
||||
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
}
|
||||
|
||||
protected override void Update(FrameEventArgs args)
|
||||
@@ -52,13 +52,6 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
_contents.Text = $@"Paused: {_gameTiming.Paused}, CurTick: {_gameTiming.CurTick}/{_gameTiming.CurTick-1}, CurServerTick: {_gameState.CurServerTick}, Pred: {_gameTiming.CurTick.Value - _gameState.CurServerTick.Value-1}
|
||||
CurTime: {_gameTiming.CurTime:hh\:mm\:ss\.ff}, RealTime: {_gameTiming.RealTime:hh\:mm\:ss\.ff}, CurFrame: {_gameTiming.CurFrame}
|
||||
ServerTime: {_gameTiming.ServerTime}, TickTimingAdjustment: {_gameTiming.TickTimingAdjustment}";
|
||||
|
||||
MinimumSizeChanged();
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
{
|
||||
return new(_contents.CombinedMinimumSize.X + 10, _contents.CombinedMinimumSize.Y + 10);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -27,11 +27,13 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
private OptionButton OverrideMenu;
|
||||
private Button ClearButton;
|
||||
private Button EraseButton;
|
||||
|
||||
private EntitySpawnButton MeasureButton;
|
||||
protected override Vector2 ContentsMinimumSize => MainVBox?.CombinedMinimumSize ?? Vector2.Zero;
|
||||
//protected override Vector2 ContentsMinimumSize => MainVBox?.CombinedMinimumSize ?? Vector2.Zero;
|
||||
|
||||
// List of prototypes that are visible based on current filter criteria.
|
||||
private readonly List<EntityPrototype> _filteredPrototypes = new();
|
||||
|
||||
// The indices of the visible prototypes last time UpdateVisiblePrototypes was ran.
|
||||
// This is inclusive, so end is the index of the last prototype, not right after it.
|
||||
private (int start, int end) _lastPrototypeIndices;
|
||||
@@ -55,8 +57,6 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
private EntitySpawnButton? SelectedButton;
|
||||
private EntityPrototype? SelectedPrototype;
|
||||
|
||||
protected override Vector2? CustomSize => (250, 300);
|
||||
|
||||
public EntitySpawnWindow(IPlacementManager placementManager,
|
||||
IPrototypeManager prototypeManager,
|
||||
IResourceCache resourceCache)
|
||||
@@ -67,8 +67,12 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
Title = Loc.GetString("Entity Spawn Panel");
|
||||
|
||||
SetSize = (250, 300);
|
||||
MinSize = (250, 200);
|
||||
|
||||
Contents.AddChild(MainVBox = new VBoxContainer
|
||||
{
|
||||
Name = "AAAAAA",
|
||||
Children =
|
||||
{
|
||||
new HBoxContainer
|
||||
@@ -77,7 +81,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
(SearchBar = new LineEdit
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = Loc.GetString("Search")
|
||||
}),
|
||||
|
||||
@@ -90,8 +94,8 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
},
|
||||
new ScrollContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(200.0f, 0.0f),
|
||||
SizeFlagsVertical = SizeFlags.FillExpand,
|
||||
MinSize = new Vector2(200.0f, 0.0f),
|
||||
VerticalExpand = true,
|
||||
Children =
|
||||
{
|
||||
(PrototypeList = new PrototypeListContainer())
|
||||
@@ -109,15 +113,24 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
(OverrideMenu = new OptionButton
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
ToolTip = Loc.GetString("Override placement")
|
||||
})
|
||||
}
|
||||
},
|
||||
(MeasureButton = new EntitySpawnButton {Visible = false})
|
||||
new DoNotMeasure
|
||||
{
|
||||
Visible = false,
|
||||
Children =
|
||||
{
|
||||
(MeasureButton = new EntitySpawnButton())
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
MeasureButton.Measure(Vector2.Infinity);
|
||||
|
||||
for (var i = 0; i < initOpts.Length; i++)
|
||||
{
|
||||
OverrideMenu.AddItem(initOpts[i], i);
|
||||
@@ -225,7 +238,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
// Update visible buttons in the prototype list.
|
||||
|
||||
// Calculate index of first prototype to render based on current scroll.
|
||||
var height = MeasureButton.CombinedMinimumSize.Y + PrototypeListContainer.Separation;
|
||||
var height = MeasureButton.DesiredSize.Y + PrototypeListContainer.Separation;
|
||||
var offset = -PrototypeList.Position.Y;
|
||||
var startIndex = (int) Math.Floor(offset / height);
|
||||
PrototypeList.ItemOffset = startIndex;
|
||||
@@ -394,7 +407,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
set
|
||||
{
|
||||
_totalItemCount = value;
|
||||
MinimumSizeChanged();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -404,13 +417,13 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
set
|
||||
{
|
||||
_itemOffset = value;
|
||||
UpdateLayout();
|
||||
InvalidateMeasure();
|
||||
}
|
||||
}
|
||||
|
||||
public const float Separation = 2;
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
if (ChildCount == 0)
|
||||
{
|
||||
@@ -419,28 +432,31 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
var first = GetChild(0);
|
||||
|
||||
var (minX, minY) = first.CombinedMinimumSize;
|
||||
first.Measure(availableSize);
|
||||
var (minX, minY) = first.DesiredSize;
|
||||
|
||||
return (minX, minY * TotalItemCount + (TotalItemCount - 1) * Separation);
|
||||
}
|
||||
|
||||
protected override void LayoutUpdateOverride()
|
||||
protected override Vector2 ArrangeOverride(Vector2 finalSize)
|
||||
{
|
||||
if (ChildCount == 0)
|
||||
{
|
||||
return;
|
||||
return Vector2.Zero;
|
||||
}
|
||||
|
||||
var first = GetChild(0);
|
||||
|
||||
var height = first.CombinedMinimumSize.Y;
|
||||
var height = first.DesiredSize.Y;
|
||||
var offset = ItemOffset * height + (ItemOffset - 1) * Separation;
|
||||
|
||||
foreach (var child in Children)
|
||||
{
|
||||
FitChildInBox(child, UIBox2.FromDimensions(0, offset, Width, height));
|
||||
child.Arrange(UIBox2.FromDimensions(0, offset, Width, height));
|
||||
offset += Separation + height;
|
||||
}
|
||||
|
||||
return finalSize;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -458,8 +474,6 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
AddChild(ActualButton = new Button
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
SizeFlagsVertical = SizeFlags.FillExpand,
|
||||
ToggleMode = true,
|
||||
});
|
||||
|
||||
@@ -469,16 +483,16 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
(EntityTextureRects = new LayeredTextureRect
|
||||
{
|
||||
CustomMinimumSize = (32, 32),
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkCenter,
|
||||
SizeFlagsVertical = SizeFlags.ShrinkCenter,
|
||||
MinSize = (32, 32),
|
||||
HorizontalAlignment = HAlignment.Center,
|
||||
VerticalAlignment = VAlignment.Center,
|
||||
Stretch = TextureRect.StretchMode.KeepAspectCentered,
|
||||
CanShrink = true
|
||||
}),
|
||||
(EntityLabel = new Label
|
||||
{
|
||||
SizeFlagsVertical = SizeFlags.ShrinkCenter,
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
VerticalAlignment = VAlignment.Center,
|
||||
HorizontalExpand = true,
|
||||
Text = "Backpack",
|
||||
ClipText = true
|
||||
})
|
||||
@@ -497,5 +511,13 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
EraseButton.Pressed = false;
|
||||
}
|
||||
|
||||
private class DoNotMeasure : Control
|
||||
{
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return Vector2.Zero;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -39,10 +39,10 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
_gameTiming = gameTiming;
|
||||
|
||||
SizeFlagsHorizontal = SizeFlags.None;
|
||||
HorizontalAlignment = HAlignment.Left;
|
||||
}
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return (TrackedFrames * FrameWidth, FrameHeight * 2);
|
||||
}
|
||||
|
||||
@@ -1,17 +1,13 @@
|
||||
<SS14Window xmlns="https://spacestation14.io">
|
||||
<SS14Window xmlns="https://spacestation14.io" MinWidth="100" MinHeight="50">
|
||||
<PanelContainer StyleClasses="windowPanel" />
|
||||
<VBoxContainer SeparationOverride="0">
|
||||
<PanelContainer Name="WindowHeader" StyleClasses="windowHeader">
|
||||
<HBoxContainer>
|
||||
<MarginContainer MarginLeftOverride="5" SizeFlagsHorizontal="FillExpand">
|
||||
<Label Name="TitleLabel" StyleIdentifier="foo" ClipText="True"
|
||||
Text="{Loc Exemplary Window Title Here}" VAlign="Center" StyleClasses="windowTitle" />
|
||||
</MarginContainer>
|
||||
<TextureButton Name="CloseButton" StyleClasses="windowCloseButton" SizeFlagsVertical="ShrinkCenter" />
|
||||
<Label Margin="5 0 0 0" HorizontalExpand="true" Name="TitleLabel" StyleIdentifier="foo" ClipText="True"
|
||||
Text="{Loc Exemplary Window Title Here}" VAlign="Center" StyleClasses="windowTitle" />
|
||||
<TextureButton Name="CloseButton" StyleClasses="windowCloseButton" VerticalAlignment="Center" />
|
||||
</HBoxContainer>
|
||||
</PanelContainer>
|
||||
<MarginContainer Name="ContentsContainer" MarginBottomOverride="10" MarginLeftOverride="10"
|
||||
MarginRightOverride="10" MarginTopOverride="10" RectClipContent="True"
|
||||
SizeFlagsVertical="FillExpand" />
|
||||
<Control Name="ContentsContainer" Margin="10" RectClipContent="True" VerticalExpand="true" />
|
||||
</VBoxContainer>
|
||||
</SS14Window>
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using Robust.Client.AutoGenerated;
|
||||
@@ -18,6 +19,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
public const string StyleClassWindowHeader = "windowHeader";
|
||||
public const string StyleClassWindowCloseButton = "windowCloseButton";
|
||||
|
||||
[Obsolete("Set SetSize instead.")]
|
||||
protected virtual Vector2? CustomSize => null;
|
||||
|
||||
public SS14Window()
|
||||
@@ -25,7 +27,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
RobustXamlLoader.Load(this);
|
||||
MouseFilter = MouseFilterMode.Stop;
|
||||
|
||||
WindowHeader.CustomMinimumSize = (0, HEADER_SIZE_Y);
|
||||
WindowHeader.MinSize = (0, HEADER_SIZE_Y);
|
||||
|
||||
Contents = ContentsContainer;
|
||||
|
||||
@@ -33,7 +35,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
XamlChildren = new SS14ContentCollection(this);
|
||||
}
|
||||
|
||||
public MarginContainer Contents { get; private set; }
|
||||
public Control Contents { get; private set; }
|
||||
//private TextureButton CloseButton;
|
||||
|
||||
private const int DRAG_MARGIN_SIZE = 7;
|
||||
@@ -42,19 +44,24 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
private const float HEADER_SIZE_Y = 25;
|
||||
protected virtual Vector2 ContentsMinimumSize => (50, 50);
|
||||
|
||||
protected override Vector2 CalculateMinimumSize()
|
||||
protected override Vector2 MeasureOverride(Vector2 availableSize)
|
||||
{
|
||||
return Vector2.ComponentMax(ContentsMinimumSize, base.CalculateMinimumSize());
|
||||
|
||||
return Vector2.ComponentMax(
|
||||
ContentsMinimumSize,
|
||||
base.MeasureOverride(Vector2.ComponentMax(availableSize, ContentsMinimumSize)));
|
||||
}
|
||||
|
||||
protected override void Opened()
|
||||
{
|
||||
base.Opened();
|
||||
|
||||
#pragma warning disable 618
|
||||
if (_firstTimeOpened && CustomSize != null)
|
||||
{
|
||||
LayoutContainer.SetSize(this, CustomSize.Value);
|
||||
SetSize = CustomSize.Value;
|
||||
}
|
||||
#pragma warning restore 618
|
||||
}
|
||||
|
||||
//private Label TitleLabel;
|
||||
|
||||
@@ -26,12 +26,9 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
},
|
||||
Children =
|
||||
{
|
||||
(OutputPanel = new OutputPanel
|
||||
{
|
||||
SizeFlagsVertical = SizeFlags.FillExpand,
|
||||
})
|
||||
(OutputPanel = new OutputPanel())
|
||||
},
|
||||
SizeFlagsVertical = SizeFlags.FillExpand
|
||||
VerticalExpand = true,
|
||||
},
|
||||
new HBoxContainer
|
||||
{
|
||||
@@ -39,7 +36,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
{
|
||||
(InputBar = new HistoryLineEdit
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = Loc.GetString("Your C# code here.")
|
||||
}),
|
||||
(RunButton = new Button {Text = Loc.GetString("Run")})
|
||||
@@ -50,7 +47,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
InputBar.OnTextEntered += _ => Run();
|
||||
RunButton.OnPressed += _ => Run();
|
||||
CustomMinimumSize = (550, 300);
|
||||
MinSize = (550, 300);
|
||||
}
|
||||
|
||||
protected abstract void Run();
|
||||
|
||||
@@ -25,8 +25,6 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
private bool _clearingSelections;
|
||||
|
||||
protected override Vector2? CustomSize => (300, 300);
|
||||
|
||||
public TileSpawnWindow(ITileDefinitionManager tileDefinitionManager, IPlacementManager placementManager,
|
||||
IResourceCache resourceCache)
|
||||
{
|
||||
@@ -38,7 +36,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
Contents.AddChild(vBox);
|
||||
var hBox = new HBoxContainer();
|
||||
vBox.AddChild(hBox);
|
||||
SearchBar = new LineEdit {PlaceHolder = "Search", SizeFlagsHorizontal = SizeFlags.FillExpand};
|
||||
SearchBar = new LineEdit {PlaceHolder = "Search", HorizontalExpand = true};
|
||||
SearchBar.OnTextChanged += OnSearchBarTextChanged;
|
||||
hBox.AddChild(SearchBar);
|
||||
|
||||
@@ -46,7 +44,7 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
ClearButton.OnPressed += OnClearButtonPressed;
|
||||
hBox.AddChild(ClearButton);
|
||||
|
||||
TileList = new ItemList {SizeFlagsVertical = SizeFlags.FillExpand};
|
||||
TileList = new ItemList {VerticalExpand = true};
|
||||
TileList.OnItemSelected += TileListOnOnItemSelected;
|
||||
TileList.OnItemDeselected += TileListOnOnItemDeselected;
|
||||
vBox.AddChild(TileList);
|
||||
@@ -57,6 +55,8 @@ namespace Robust.Client.UserInterface.CustomControls
|
||||
|
||||
Title = "Place Tiles";
|
||||
SearchBar.GrabKeyboardFocus();
|
||||
|
||||
SetSize = (300, 300);
|
||||
}
|
||||
|
||||
protected override void Dispose(bool disposing)
|
||||
|
||||
@@ -45,7 +45,8 @@ namespace Robust.Client.UserInterface
|
||||
void Render(IRenderHandle renderHandle);
|
||||
|
||||
void QueueStyleUpdate(Control control);
|
||||
void QueueLayoutUpdate(Control control);
|
||||
void QueueMeasureUpdate(Control control);
|
||||
void QueueArrangeUpdate(Control control);
|
||||
void CursorChanged(Control control);
|
||||
/// <summary>
|
||||
/// Hides the tooltip for the indicated control, if tooltip for that control is currently showing.
|
||||
|
||||
@@ -39,7 +39,8 @@ namespace Robust.Client.UserInterface
|
||||
{
|
||||
LayoutContainer.SetPosition(tooltip, screenPosition);
|
||||
|
||||
var combinedMinSize = tooltip.CombinedMinimumSize;
|
||||
tooltip.Measure(Vector2.Infinity);
|
||||
var combinedMinSize = tooltip.DesiredSize;
|
||||
var (right, bottom) = tooltip.Position + combinedMinSize;
|
||||
|
||||
if (right > screenBounds.X)
|
||||
|
||||
@@ -17,6 +17,7 @@ using Robust.Shared.Map;
|
||||
using Robust.Shared.Maths;
|
||||
using Robust.Shared.Network;
|
||||
using Robust.Shared.Timing;
|
||||
using Robust.Shared.ViewVariables;
|
||||
|
||||
namespace Robust.Client.UserInterface
|
||||
{
|
||||
@@ -34,9 +35,9 @@ namespace Robust.Client.UserInterface
|
||||
[Dependency] private readonly IMapManager _mapManager = default!;
|
||||
[Dependency] private readonly IConfigurationManager _configurationManager = default!;
|
||||
|
||||
public UITheme ThemeDefaults { get; private set; } = default!;
|
||||
[ViewVariables] public UITheme ThemeDefaults { get; private set; } = default!;
|
||||
|
||||
public Stylesheet? Stylesheet
|
||||
[ViewVariables] public Stylesheet? Stylesheet
|
||||
{
|
||||
get => _stylesheet;
|
||||
set
|
||||
@@ -50,26 +51,28 @@ namespace Robust.Client.UserInterface
|
||||
}
|
||||
}
|
||||
|
||||
public Control? KeyboardFocused { get; private set; }
|
||||
[ViewVariables] public Control? KeyboardFocused { get; private set; }
|
||||
|
||||
public Control? ControlFocused { get; private set; }
|
||||
[ViewVariables] public Control? ControlFocused { get; private set; }
|
||||
|
||||
public LayoutContainer StateRoot { get; private set; } = default!;
|
||||
public PopupContainer ModalRoot { get; private set; } = default!;
|
||||
public Control? CurrentlyHovered { get; private set; } = default!;
|
||||
public float UIScale { get; private set; } = 1;
|
||||
public float DefaultUIScale => _displayManager.DefaultWindowScale.X;
|
||||
public Control RootControl { get; private set; } = default!;
|
||||
public LayoutContainer WindowRoot { get; private set; } = default!;
|
||||
public LayoutContainer PopupRoot { get; private set; } = default!;
|
||||
public DebugConsole DebugConsole { get; private set; } = default!;
|
||||
public IDebugMonitors DebugMonitors => _debugMonitors;
|
||||
[ViewVariables] public LayoutContainer StateRoot { get; private set; } = default!;
|
||||
[ViewVariables] public PopupContainer ModalRoot { get; private set; } = default!;
|
||||
[ViewVariables] public Control? CurrentlyHovered { get; private set; } = default!;
|
||||
[ViewVariables] public float UIScale { get; private set; } = 1;
|
||||
[ViewVariables] public float DefaultUIScale => _displayManager.DefaultWindowScale.X;
|
||||
[ViewVariables] public Control RootControl { get; private set; } = default!;
|
||||
[ViewVariables] public LayoutContainer WindowRoot { get; private set; } = default!;
|
||||
[ViewVariables] public LayoutContainer PopupRoot { get; private set; } = default!;
|
||||
[ViewVariables] public DebugConsole DebugConsole { get; private set; } = default!;
|
||||
[ViewVariables] public IDebugMonitors DebugMonitors => _debugMonitors;
|
||||
private DebugMonitors _debugMonitors = default!;
|
||||
|
||||
private readonly List<Control> _modalStack = new();
|
||||
|
||||
private bool _rendering = true;
|
||||
|
||||
private float _tooltipTimer;
|
||||
|
||||
// set to null when not counting down
|
||||
private float? _tooltipDelay;
|
||||
private Tooltip _tooltip = default!;
|
||||
@@ -78,7 +81,8 @@ namespace Robust.Client.UserInterface
|
||||
private const float TooltipDelay = 1;
|
||||
|
||||
private readonly Queue<Control> _styleUpdateQueue = new();
|
||||
private readonly Queue<Control> _layoutUpdateQueue = new();
|
||||
private readonly Queue<Control> _measureUpdateQueue = new();
|
||||
private readonly Queue<Control> _arrangeUpdateQueue = new();
|
||||
private Stylesheet? _stylesheet;
|
||||
private ICursor? _worldCursor;
|
||||
private bool _needUpdateActiveCursor;
|
||||
@@ -120,9 +124,14 @@ namespace Robust.Client.UserInterface
|
||||
{
|
||||
Name = "UIRoot",
|
||||
MouseFilter = Control.MouseFilterMode.Ignore,
|
||||
HorizontalAlignment = Control.HAlignment.Stretch,
|
||||
VerticalAlignment = Control.VAlignment.Stretch,
|
||||
IsInsideTree = true
|
||||
};
|
||||
RootControl.Size = _displayManager.ScreenSize / UIScale;
|
||||
|
||||
RootControl.InvalidateMeasure();
|
||||
QueueMeasureUpdate(RootControl);
|
||||
|
||||
_displayManager.OnWindowResized += args => _updateRootSize();
|
||||
|
||||
StateRoot = new LayoutContainer
|
||||
@@ -192,16 +201,28 @@ namespace Robust.Client.UserInterface
|
||||
control.DoStyleUpdate();
|
||||
}
|
||||
|
||||
while (_layoutUpdateQueue.Count != 0)
|
||||
while (_measureUpdateQueue.Count != 0)
|
||||
{
|
||||
var control = _layoutUpdateQueue.Dequeue();
|
||||
var control = _measureUpdateQueue.Dequeue();
|
||||
|
||||
if (control.Disposed)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
control.DoLayoutUpdate();
|
||||
RunMeasure(control);
|
||||
}
|
||||
|
||||
while (_arrangeUpdateQueue.Count != 0)
|
||||
{
|
||||
var control = _arrangeUpdateQueue.Dequeue();
|
||||
|
||||
if (control.Disposed)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
RunArrange(control);
|
||||
}
|
||||
|
||||
// count down tooltip delay if we're not showing one yet and
|
||||
@@ -222,6 +243,46 @@ namespace Robust.Client.UserInterface
|
||||
}
|
||||
}
|
||||
|
||||
private void RunMeasure(Control control)
|
||||
{
|
||||
if (control.IsMeasureValid || !control.IsInsideTree)
|
||||
return;
|
||||
|
||||
if (control.Parent != null)
|
||||
{
|
||||
RunMeasure(control.Parent);
|
||||
}
|
||||
|
||||
if (control == RootControl)
|
||||
{
|
||||
control.Measure(_displayManager.ScreenSize / UIScale);
|
||||
}
|
||||
else if (control.PreviousMeasure.HasValue)
|
||||
{
|
||||
control.Measure(control.PreviousMeasure.Value);
|
||||
}
|
||||
}
|
||||
|
||||
private void RunArrange(Control control)
|
||||
{
|
||||
if (control.IsArrangeValid || !control.IsInsideTree)
|
||||
return;
|
||||
|
||||
if (control.Parent != null)
|
||||
{
|
||||
RunArrange(control.Parent);
|
||||
}
|
||||
|
||||
if (control == RootControl)
|
||||
{
|
||||
control.Arrange(UIBox2.FromDimensions(Vector2.Zero, _displayManager.ScreenSize / UIScale));
|
||||
}
|
||||
else if (control.PreviousArrange.HasValue)
|
||||
{
|
||||
control.Arrange(control.PreviousArrange.Value);
|
||||
}
|
||||
}
|
||||
|
||||
public bool HandleCanFocusDown(Vector2 pointerPosition)
|
||||
{
|
||||
var control = MouseGetControl(pointerPosition);
|
||||
@@ -254,6 +315,7 @@ namespace Robust.Client.UserInterface
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
ControlFocused?.ControlFocusExited();
|
||||
ControlFocused = control;
|
||||
|
||||
@@ -441,6 +503,7 @@ namespace Robust.Client.UserInterface
|
||||
}
|
||||
|
||||
public Vector2 MousePositionScaled => ScreenToUIPosition(_inputManager.MouseScreenPosition);
|
||||
|
||||
public Vector2 ScreenToUIPosition(Vector2 position)
|
||||
{
|
||||
return position / UIScale;
|
||||
@@ -556,9 +619,15 @@ namespace Robust.Client.UserInterface
|
||||
_styleUpdateQueue.Enqueue(control);
|
||||
}
|
||||
|
||||
public void QueueLayoutUpdate(Control control)
|
||||
public void QueueMeasureUpdate(Control control)
|
||||
{
|
||||
_layoutUpdateQueue.Enqueue(control);
|
||||
_measureUpdateQueue.Enqueue(control);
|
||||
_arrangeUpdateQueue.Enqueue(control);
|
||||
}
|
||||
|
||||
public void QueueArrangeUpdate(Control control)
|
||||
{
|
||||
_arrangeUpdateQueue.Enqueue(control);
|
||||
}
|
||||
|
||||
public void CursorChanged(Control control)
|
||||
@@ -711,6 +780,7 @@ namespace Robust.Client.UserInterface
|
||||
PopupRoot.RemoveChild(_suppliedTooltip);
|
||||
_suppliedTooltip = null;
|
||||
}
|
||||
|
||||
CurrentlyHovered?.PerformHideTooltip();
|
||||
_resetTooltipTimer();
|
||||
showingTooltip = false;
|
||||
@@ -760,7 +830,7 @@ namespace Robust.Client.UserInterface
|
||||
// show simple tooltip if there is one
|
||||
_tooltip.Visible = true;
|
||||
_tooltip.Text = hovered.ToolTip;
|
||||
Tooltips.PositionTooltip(_tooltip);
|
||||
Tooltips.PositionTooltip(_tooltip);
|
||||
}
|
||||
|
||||
hovered.PerformShowTooltip();
|
||||
@@ -791,7 +861,7 @@ namespace Robust.Client.UserInterface
|
||||
|
||||
private void _updateRootSize()
|
||||
{
|
||||
RootControl.Size = _displayManager.ScreenSize / UIScale;
|
||||
RootControl.InvalidateMeasure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -813,6 +883,7 @@ namespace Robust.Client.UserInterface
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -11,14 +11,14 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
var hBox = new HBoxContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(200, 0)
|
||||
MinSize = new Vector2(200, 0)
|
||||
};
|
||||
var angle = (Angle) value!;
|
||||
var lineEdit = new LineEdit
|
||||
{
|
||||
Text = angle.Degrees.ToString(CultureInfo.InvariantCulture),
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand
|
||||
HorizontalExpand = true
|
||||
};
|
||||
if (!ReadOnly)
|
||||
{
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
Pressed = (bool)value!,
|
||||
Disabled = ReadOnly,
|
||||
Text = value!.ToString()!,
|
||||
CustomMinimumSize = new Vector2(70, 0)
|
||||
MinSize = new Vector2(70, 0)
|
||||
};
|
||||
if (!ReadOnly)
|
||||
{
|
||||
|
||||
@@ -12,7 +12,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = ((Color)value!).ToHex(),
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
ToolTip = "Hex color here",
|
||||
PlaceHolder = "Hex color here"
|
||||
};
|
||||
|
||||
@@ -20,7 +20,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = value == null ? "null" : value.ToString() ?? "<null ToString()>",
|
||||
Align = Label.AlignMode.Right,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,17 +15,17 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var coords = (EntityCoordinates) value!;
|
||||
var hBoxContainer = new HBoxContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(240, 0),
|
||||
MinSize = new Vector2(240, 0),
|
||||
};
|
||||
|
||||
hBoxContainer.AddChild(new Label {Text = "grid: "});
|
||||
|
||||
var entityManager = IoCManager.Resolve<IEntityManager>();
|
||||
|
||||
|
||||
var gridId = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Grid ID",
|
||||
ToolTip = "Grid ID",
|
||||
Text = coords.GetGridId(entityManager).ToString()
|
||||
@@ -38,7 +38,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var x = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "X",
|
||||
ToolTip = "X",
|
||||
Text = coords.X.ToString(CultureInfo.InvariantCulture)
|
||||
@@ -49,7 +49,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var y = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Y",
|
||||
ToolTip = "Y",
|
||||
Text = coords.Y.ToString(CultureInfo.InvariantCulture)
|
||||
@@ -63,7 +63,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var mapManager = IoCManager.Resolve<IMapManager>();
|
||||
var xVal = float.Parse(x.Text, CultureInfo.InvariantCulture);
|
||||
var yVal = float.Parse(y.Text, CultureInfo.InvariantCulture);
|
||||
|
||||
|
||||
if (!mapManager.TryGetGrid(new GridId(gridVal), out var grid))
|
||||
{
|
||||
ValueChanged(new EntityCoordinates(EntityUid.Invalid, (xVal, yVal)));
|
||||
|
||||
@@ -11,7 +11,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
var hBox = new HBoxContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(200, 0)
|
||||
MinSize = new Vector2(200, 0)
|
||||
};
|
||||
|
||||
var uid = (EntityUid)value!;
|
||||
@@ -19,7 +19,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = uid.ToString(),
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
if (!ReadOnly)
|
||||
{
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = ((ISelfSerialize)value!).Serialize(),
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
|
||||
if (!ReadOnly)
|
||||
|
||||
@@ -22,7 +22,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = NumberToText(value!),
|
||||
Editable = !ReadOnly,
|
||||
CustomMinimumSize = new Vector2(240, 0)
|
||||
MinSize = new Vector2(240, 0)
|
||||
};
|
||||
lineEdit.OnTextEntered += e =>
|
||||
{
|
||||
|
||||
@@ -28,7 +28,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = $"Ref: {toString}",
|
||||
ClipText = true,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
button.OnPressed += ButtonOnOnPressed;
|
||||
return button;
|
||||
|
||||
@@ -11,7 +11,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = (string) value!,
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
};
|
||||
|
||||
if (!ReadOnly)
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
Text = ts.ToString(),
|
||||
Editable = !ReadOnly,
|
||||
CustomMinimumSize = (240, 0)
|
||||
MinSize = (240, 0)
|
||||
};
|
||||
|
||||
lineEdit.OnTextEntered += e =>
|
||||
|
||||
@@ -19,13 +19,13 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
var hBoxContainer = new HBoxContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(200, 0),
|
||||
MinSize = new Vector2(200, 0),
|
||||
};
|
||||
|
||||
var left = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Left",
|
||||
ToolTip = "Left"
|
||||
};
|
||||
@@ -33,7 +33,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var top = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Top",
|
||||
ToolTip = "Top"
|
||||
};
|
||||
@@ -41,7 +41,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var right = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Right",
|
||||
ToolTip = "Right"
|
||||
};
|
||||
@@ -49,7 +49,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var bottom = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Bottom",
|
||||
ToolTip = "Bottom"
|
||||
};
|
||||
|
||||
@@ -18,13 +18,13 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
{
|
||||
var hBoxContainer = new HBoxContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(240, 0),
|
||||
MinSize = new Vector2(240, 0),
|
||||
};
|
||||
|
||||
var x = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "X",
|
||||
ToolTip = "X"
|
||||
};
|
||||
@@ -34,7 +34,7 @@ namespace Robust.Client.ViewVariables.Editors
|
||||
var y = new LineEdit
|
||||
{
|
||||
Editable = !ReadOnly,
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
PlaceHolder = "Y",
|
||||
ToolTip = "Y"
|
||||
};
|
||||
|
||||
@@ -73,11 +73,7 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
var scrollContainer = new ScrollContainer();
|
||||
//scrollContainer.SetAnchorPreset(Control.LayoutPreset.Wide, true);
|
||||
window.Contents.AddChild(scrollContainer);
|
||||
var vBoxContainer = new VBoxContainer
|
||||
{
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand,
|
||||
SizeFlagsVertical = SizeFlags.FillExpand,
|
||||
};
|
||||
var vBoxContainer = new VBoxContainer();
|
||||
scrollContainer.AddChild(vBoxContainer);
|
||||
|
||||
// Handle top bar displaying type and ToString().
|
||||
@@ -107,7 +103,7 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
if (_entity.TryGetComponent(out ISpriteComponent? sprite))
|
||||
{
|
||||
var hBox = new HBoxContainer();
|
||||
top.SizeFlagsHorizontal = SizeFlags.FillExpand;
|
||||
top.HorizontalExpand = true;
|
||||
hBox.AddChild(top);
|
||||
hBox.AddChild(new SpriteView {Sprite = sprite});
|
||||
vBoxContainer.AddChild(hBox);
|
||||
@@ -167,13 +163,13 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
_clientComponents.AddChild(_clientComponentsSearchBar = new LineEdit
|
||||
{
|
||||
PlaceHolder = Loc.GetString("Search"),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
});
|
||||
|
||||
_clientComponents.AddChild(_clientComponentsAddButton = new Button()
|
||||
{
|
||||
Text = Loc.GetString("Add Component"),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
});
|
||||
|
||||
_clientComponentsAddButton.OnPressed += OnClientComponentsAddButtonPressed;
|
||||
@@ -187,7 +183,7 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
var removeButton = new TextureButton()
|
||||
{
|
||||
StyleClasses = { SS14Window.StyleClassWindowCloseButton },
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
button.OnPressed += _ => ViewVariablesManager.OpenVV(component);
|
||||
removeButton.OnPressed += _ => RemoveClientComponent(component);
|
||||
@@ -203,13 +199,13 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
_serverComponents.AddChild(_serverComponentsSearchBar = new LineEdit
|
||||
{
|
||||
PlaceHolder = Loc.GetString("Search"),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
});
|
||||
|
||||
_serverComponents.AddChild(_serverComponentsAddButton = new Button()
|
||||
{
|
||||
Text = Loc.GetString("Add Component"),
|
||||
SizeFlagsHorizontal = SizeFlags.FillExpand
|
||||
HorizontalExpand = true,
|
||||
});
|
||||
|
||||
_serverComponentsSearchBar.OnTextChanged += OnServerComponentsSearchBarChanged;
|
||||
@@ -238,7 +234,7 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
var removeButton = new TextureButton()
|
||||
{
|
||||
StyleClasses = { SS14Window.StyleClassWindowCloseButton },
|
||||
SizeFlagsHorizontal = SizeFlags.ShrinkEnd
|
||||
HorizontalAlignment = HAlignment.Right
|
||||
};
|
||||
button.OnPressed += _ =>
|
||||
{
|
||||
|
||||
@@ -66,8 +66,8 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
window.Contents.AddChild(scrollContainer);
|
||||
var vBoxContainer = new VBoxContainer
|
||||
{
|
||||
SizeFlagsHorizontal = Control.SizeFlags.FillExpand,
|
||||
SizeFlagsVertical = Control.SizeFlags.FillExpand,
|
||||
HorizontalExpand = true,
|
||||
VerticalExpand = true,
|
||||
};
|
||||
scrollContainer.AddChild(vBoxContainer);
|
||||
|
||||
@@ -75,7 +75,7 @@ namespace Robust.Client.ViewVariables.Instances
|
||||
{
|
||||
var headBox = new HBoxContainer();
|
||||
var name = MakeTopBar(top, bottom);
|
||||
name.SizeFlagsHorizontal = Control.SizeFlags.FillExpand;
|
||||
name.HorizontalExpand = true;
|
||||
headBox.AddChild(name);
|
||||
|
||||
_refreshButton = new Button {Text = "Refresh", ToolTip = "RMB to toggle auto-refresh."};
|
||||
|
||||
@@ -50,13 +50,13 @@ namespace Robust.Client.ViewVariables.Traits
|
||||
var outerVBox = new VBoxContainer();
|
||||
_controlsHBox = new HBoxContainer
|
||||
{
|
||||
SizeFlagsHorizontal = Control.SizeFlags.ShrinkCenter
|
||||
HorizontalAlignment = Control.HAlignment.Center
|
||||
};
|
||||
|
||||
{
|
||||
// Page navigational controls.
|
||||
_leftButton = new Button {Text = "<<", Disabled = true};
|
||||
_pageLabel = new LineEdit {Text = "0", CustomMinimumSize = (60, 0)};
|
||||
_pageLabel = new LineEdit {Text = "0", MinSize = (60, 0)};
|
||||
_rightButton = new Button {Text = ">>"};
|
||||
|
||||
_leftButton.OnPressed += _leftButtonPressed;
|
||||
|
||||
@@ -86,7 +86,7 @@ namespace Robust.Client.ViewVariables.Traits
|
||||
{
|
||||
if (!first)
|
||||
{
|
||||
container.AddChild(new Control {CustomMinimumSize = (0, 16)});
|
||||
container.AddChild(new Control {MinSize = (0, 16)});
|
||||
}
|
||||
|
||||
first = false;
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<cc:SS14Window xmlns:cc="clr-namespace:Robust.Client.UserInterface.CustomControls"
|
||||
xmlns:c="clr-namespace:Robust.Client.UserInterface.Controls">
|
||||
<c:VBoxContainer SizeFlagsVertical="FillExpand">
|
||||
<c:LineEdit Name="SearchLineEdit" PlaceHolder="Search component..." SizeFlagsHorizontal="FillExpand" />
|
||||
<c:ItemList Name="ComponentItemList" SizeFlagsVertical="FillExpand" SizeFlagsHorizontal="FillExpand" SelectMode="Single" />
|
||||
<c:Button Name="AddButton" Text="Add Component" TextAlign="Center" SizeFlagsHorizontal="FillExpand"/>
|
||||
<c:VBoxContainer VerticalExpand="True">
|
||||
<c:LineEdit Name="SearchLineEdit" PlaceHolder="Search component..." HorizontalExpand="True" />
|
||||
<c:ItemList Name="ComponentItemList" VerticalExpand="True" HorizontalExpand="True" SelectMode="Single" />
|
||||
<c:Button Name="AddButton" Text="Add Component" TextAlign="Center" HorizontalExpand="True"/>
|
||||
</c:VBoxContainer>
|
||||
</cc:SS14Window>
|
||||
|
||||
@@ -13,8 +13,6 @@ namespace Robust.Client.ViewVariables
|
||||
[GenerateTypedNameReferences]
|
||||
public partial class ViewVariablesAddComponentWindow : SS14Window
|
||||
{
|
||||
protected override Vector2? CustomSize => (200f, 300f);
|
||||
|
||||
private string? _lastSearch;
|
||||
private string[] _components = Array.Empty<string>();
|
||||
|
||||
@@ -32,6 +30,8 @@ namespace Robust.Client.ViewVariables
|
||||
AddButton.OnPressed += OnAddButtonPressed;
|
||||
|
||||
Populate(components);
|
||||
|
||||
SetSize = (200, 300);
|
||||
}
|
||||
|
||||
private void RefreshAddButton()
|
||||
|
||||
@@ -223,8 +223,8 @@ namespace Robust.Client.ViewVariables
|
||||
instance.Initialize(window, obj);
|
||||
window.OnClose += () => _closeInstance(instance, false);
|
||||
_windows.Add(instance, window);
|
||||
window.SetSize = _defaultWindowSize;
|
||||
window.Open();
|
||||
LayoutContainer.SetSize(window, _defaultWindowSize);
|
||||
}
|
||||
|
||||
public async void OpenVV(ViewVariablesObjectSelector selector)
|
||||
@@ -264,8 +264,8 @@ namespace Robust.Client.ViewVariables
|
||||
instance.Initialize(window, blob, session);
|
||||
window.OnClose += () => _closeInstance(instance, false);
|
||||
_windows.Add(instance, window);
|
||||
window.Size = _defaultWindowSize;
|
||||
window.Open();
|
||||
LayoutContainer.SetSize(window, _defaultWindowSize);
|
||||
}
|
||||
|
||||
public Task<ViewVariablesRemoteSession> RequestSession(ViewVariablesObjectSelector selector)
|
||||
|
||||
@@ -32,12 +32,12 @@ namespace Robust.Client.ViewVariables
|
||||
|
||||
MouseFilter = MouseFilterMode.Pass;
|
||||
ToolTip = "Click to expand";
|
||||
CustomMinimumSize = new Vector2(0, 25);
|
||||
MinHeight = 25;
|
||||
|
||||
VBox = new VBoxContainer {SeparationOverride = 0};
|
||||
AddChild(VBox);
|
||||
|
||||
TopContainer = new HBoxContainer {SizeFlagsVertical = SizeFlags.FillExpand};
|
||||
TopContainer = new HBoxContainer {VerticalExpand = true};
|
||||
VBox.AddChild(TopContainer);
|
||||
|
||||
BottomContainer = new HBoxContainer
|
||||
@@ -88,12 +88,12 @@ namespace Robust.Client.ViewVariables
|
||||
}
|
||||
|
||||
var view = editor.Initialize(member.Value, !member.Editable);
|
||||
if (view.SizeFlagsHorizontal != SizeFlags.FillExpand)
|
||||
if (!view.HorizontalExpand)
|
||||
{
|
||||
NameLabel.SizeFlagsHorizontal = SizeFlags.FillExpand;
|
||||
NameLabel.HorizontalExpand = true;
|
||||
}
|
||||
|
||||
NameLabel.CustomMinimumSize = new Vector2(150, 0);
|
||||
NameLabel.MinSize = new Vector2(150, 0);
|
||||
TopContainer.AddChild(view);
|
||||
/*
|
||||
_beingEdited = obj;
|
||||
@@ -113,9 +113,9 @@ namespace Robust.Client.ViewVariables
|
||||
var view = editor.Initialize(value, attr.Access != VVAccess.ReadWrite);
|
||||
if (view.SizeFlagsHorizontal != SizeFlags.FillExpand)
|
||||
{
|
||||
NameLabel.SizeFlagsHorizontal = SizeFlags.FillExpand;
|
||||
NameLabel.HorizontalExpand = true;
|
||||
}
|
||||
NameLabel.CustomMinimumSize = new Vector2(150, 0);
|
||||
NameLabel.MinSize = new Vector2(150, 0);
|
||||
TopContainer.AddChild(view);
|
||||
editor.OnValueChanged += v => { propertyInfo.SetValue(obj, v); };
|
||||
*/
|
||||
|
||||
@@ -28,6 +28,7 @@ using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Xml.Linq;
|
||||
using JetBrains.Annotations;
|
||||
using SysVector3 = System.Numerics.Vector3;
|
||||
using SysVector4 = System.Numerics.Vector4;
|
||||
@@ -882,6 +883,18 @@ namespace Robust.Shared.Maths
|
||||
throw new ArgumentException("Invalid color code and no fallback provided.", nameof(hexColor));
|
||||
}
|
||||
|
||||
public static Color FromXaml(string name)
|
||||
{
|
||||
var color = TryFromHex(name);
|
||||
if (color != null)
|
||||
return color.Value;
|
||||
|
||||
if (TryFromName(name, out var namedColor))
|
||||
return namedColor;
|
||||
|
||||
throw new ArgumentException($"Invalid XAML color name: '{name}'");
|
||||
}
|
||||
|
||||
public static Color Blend(Color dstColor, Color srcColor, BlendFactor dstFactor, BlendFactor srcFactor)
|
||||
{
|
||||
var dst = new SysVector3(dstColor.R, dstColor.G, dstColor.B);
|
||||
|
||||
124
Robust.Shared.Maths/Thickness.cs
Normal file
124
Robust.Shared.Maths/Thickness.cs
Normal file
@@ -0,0 +1,124 @@
|
||||
using System;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using JetBrains.Annotations;
|
||||
|
||||
namespace Robust.Shared.Maths
|
||||
{
|
||||
[PublicAPI]
|
||||
public struct Thickness : IEquatable<Thickness>
|
||||
{
|
||||
public float Left;
|
||||
public float Top;
|
||||
public float Right;
|
||||
public float Bottom;
|
||||
|
||||
public readonly float SumHorizontal => Left + Right;
|
||||
public readonly float SumVertical => Top + Bottom;
|
||||
|
||||
public Thickness(float uniform)
|
||||
{
|
||||
Left = uniform;
|
||||
Top = uniform;
|
||||
Right = uniform;
|
||||
Bottom = uniform;
|
||||
}
|
||||
|
||||
public Thickness(float horizontal, float vertical)
|
||||
{
|
||||
Left = horizontal;
|
||||
Right = horizontal;
|
||||
Top = vertical;
|
||||
Bottom = vertical;
|
||||
}
|
||||
|
||||
public Thickness(float left, float top, float right, float bottom)
|
||||
{
|
||||
Left = left;
|
||||
Top = top;
|
||||
Right = right;
|
||||
Bottom = bottom;
|
||||
}
|
||||
|
||||
[SuppressMessage("ReSharper", "CompareOfFloatsByEqualityOperator")]
|
||||
public readonly bool Equals(Thickness other)
|
||||
{
|
||||
return Equals(in other);
|
||||
}
|
||||
|
||||
public readonly UIBox2 Inflate(in UIBox2 box)
|
||||
{
|
||||
return new(
|
||||
box.Left - Left,
|
||||
box.Top - Top,
|
||||
box.Right + Right,
|
||||
box.Bottom + Bottom);
|
||||
}
|
||||
|
||||
public readonly Vector2 Inflate(in Vector2 size)
|
||||
{
|
||||
return (size.X + SumHorizontal, size.Y + SumVertical);
|
||||
}
|
||||
|
||||
public readonly UIBox2 Deflate(in UIBox2 box)
|
||||
{
|
||||
var left = box.Left + Left;
|
||||
var top = box.Top + Top;
|
||||
return new(
|
||||
left,
|
||||
top,
|
||||
// Avoid inverse boxes if the margins are larger than the box.
|
||||
Math.Max(left, box.Right - Right),
|
||||
Math.Max(top, box.Bottom - Bottom));
|
||||
}
|
||||
|
||||
public readonly Vector2 Deflate(in Vector2 size)
|
||||
{
|
||||
return Vector2.ComponentMax(
|
||||
Vector2.Zero,
|
||||
(size.X - SumHorizontal, size.Y - SumVertical));
|
||||
}
|
||||
|
||||
[SuppressMessage("ReSharper", "CompareOfFloatsByEqualityOperator")]
|
||||
public readonly bool Equals(in Thickness other)
|
||||
{
|
||||
return Left == other.Left &&
|
||||
Top == other.Top &&
|
||||
Right == other.Right &&
|
||||
Bottom == other.Bottom;
|
||||
}
|
||||
|
||||
public override readonly bool Equals(object? obj)
|
||||
{
|
||||
return obj is Thickness other && Equals(other);
|
||||
}
|
||||
|
||||
[SuppressMessage("ReSharper", "NonReadonlyMemberInGetHashCode")]
|
||||
public override readonly int GetHashCode()
|
||||
{
|
||||
return HashCode.Combine(Left, Top, Right, Bottom);
|
||||
}
|
||||
|
||||
public static bool operator ==(in Thickness left, in Thickness right)
|
||||
{
|
||||
return left.Equals(in right);
|
||||
}
|
||||
|
||||
public static bool operator !=(in Thickness left, in Thickness right)
|
||||
{
|
||||
return !left.Equals(in right);
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"{Left},{Top},{Right},{Bottom}";
|
||||
}
|
||||
|
||||
public readonly void Deconstruct(out float left, out float top, out float right, out float bottom)
|
||||
{
|
||||
left = Left;
|
||||
top = Top;
|
||||
right = Right;
|
||||
bottom = Bottom;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -41,6 +41,8 @@ namespace Robust.Shared.Maths
|
||||
/// </summary>
|
||||
public static readonly Vector2 UnitY = new(0, 1);
|
||||
|
||||
public static readonly Vector2 Infinity = new(float.PositiveInfinity, float.PositiveInfinity);
|
||||
|
||||
/// <summary>
|
||||
/// Construct a vector from its coordinates.
|
||||
/// </summary>
|
||||
|
||||
@@ -90,19 +90,19 @@ namespace Robust.Shared.Scripting
|
||||
|
||||
public void setprop(object target, string name, object? value)
|
||||
{
|
||||
target.GetType().GetProperty(name, BindingFlags.Instance | BindingFlags.NonPublic)
|
||||
target.GetType().GetProperty(name, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public)
|
||||
!.SetValue(target, value);
|
||||
}
|
||||
|
||||
public object? fld(object target, string name)
|
||||
{
|
||||
return target.GetType().GetField(name, BindingFlags.Instance | BindingFlags.NonPublic)
|
||||
return target.GetType().GetField(name, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public)
|
||||
!.GetValue(target);
|
||||
}
|
||||
|
||||
public void setfld(object target, string name, object? value)
|
||||
{
|
||||
target.GetType().GetField(name, BindingFlags.Instance | BindingFlags.NonPublic)
|
||||
target.GetType().GetField(name, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public)
|
||||
!.SetValue(target, value);
|
||||
}
|
||||
|
||||
@@ -110,7 +110,7 @@ namespace Robust.Shared.Scripting
|
||||
{
|
||||
var t = target.GetType();
|
||||
// TODO: overloads
|
||||
var m = t.GetMethod(name, BindingFlags.Instance | BindingFlags.NonPublic);
|
||||
var m = t.GetMethod(name, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
|
||||
return m!.Invoke(target, args);
|
||||
}
|
||||
|
||||
|
||||
@@ -15,47 +15,47 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
public void TestLayoutBasic()
|
||||
{
|
||||
var root = new LayoutContainer();
|
||||
var boxContainer = new VBoxContainer {CustomMinimumSize = (50, 60)};
|
||||
var control1 = new Control {CustomMinimumSize = (20, 20)};
|
||||
var control2 = new Control {CustomMinimumSize = (30, 30)};
|
||||
var boxContainer = new VBoxContainer {MinSize = (50, 60)};
|
||||
var control1 = new Control {MinSize = (20, 20)};
|
||||
var control2 = new Control {MinSize = (30, 30)};
|
||||
|
||||
root.AddChild(boxContainer);
|
||||
|
||||
boxContainer.AddChild(control1);
|
||||
boxContainer.AddChild(control2);
|
||||
|
||||
root.ForceRunLayoutUpdate();
|
||||
root.Arrange(new UIBox2(0, 0, 50, 60));
|
||||
|
||||
Assert.That(control1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(control1.Size, Is.EqualTo(new Vector2(50, 20)));
|
||||
Assert.That(control2.Position, Is.EqualTo(new Vector2(0, 20)));
|
||||
Assert.That(control2.Size, Is.EqualTo(new Vector2(50, 30)));
|
||||
Assert.That(boxContainer.CombinedMinimumSize, Is.EqualTo(new Vector2(50, 60)));
|
||||
Assert.That(boxContainer.DesiredSize, Is.EqualTo(new Vector2(50, 60)));
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestLayoutExpand()
|
||||
{
|
||||
var root = new LayoutContainer();
|
||||
var boxContainer = new VBoxContainer {CustomMinimumSize = (50, 60)};
|
||||
var boxContainer = new VBoxContainer {MinSize = (50, 60)};
|
||||
var control1 = new Control
|
||||
{
|
||||
SizeFlagsVertical = Control.SizeFlags.FillExpand
|
||||
VerticalExpand = true
|
||||
};
|
||||
var control2 = new Control {CustomMinimumSize = (30, 30)};
|
||||
var control2 = new Control {MinSize = (30, 30)};
|
||||
|
||||
boxContainer.AddChild(control1);
|
||||
boxContainer.AddChild(control2);
|
||||
|
||||
root.AddChild(boxContainer);
|
||||
|
||||
root.ForceRunLayoutUpdate();
|
||||
root.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(control1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(control1.Size, Is.EqualTo(new Vector2(50, 30)));
|
||||
Assert.That(control2.Position, Is.EqualTo(new Vector2(0, 30)));
|
||||
Assert.That(control2.Size, Is.EqualTo(new Vector2(50, 30)));
|
||||
Assert.That(boxContainer.CombinedMinimumSize, Is.EqualTo(new Vector2(50, 60)));
|
||||
Assert.That(boxContainer.DesiredSize, Is.EqualTo(new Vector2(50, 60)));
|
||||
}
|
||||
|
||||
[Test]
|
||||
@@ -64,30 +64,32 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
var boxContainer = new VBoxContainer();
|
||||
var control1 = new Control
|
||||
{
|
||||
CustomMinimumSize = (50, 30)
|
||||
MinSize = (50, 30)
|
||||
};
|
||||
var control2 = new Control {CustomMinimumSize = (30, 50)};
|
||||
var control2 = new Control {MinSize = (30, 50)};
|
||||
|
||||
boxContainer.AddChild(control1);
|
||||
boxContainer.AddChild(control2);
|
||||
|
||||
Assert.That(boxContainer.CombinedMinimumSize, Is.EqualTo(new Vector2(50, 80)));
|
||||
boxContainer.Measure((100, 100));
|
||||
|
||||
Assert.That(boxContainer.DesiredSize, Is.EqualTo(new Vector2(50, 80)));
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestTwoExpand()
|
||||
{
|
||||
var root = new LayoutContainer();
|
||||
var boxContainer = new VBoxContainer {CustomMinimumSize = (30, 80)};
|
||||
var boxContainer = new VBoxContainer {MinSize = (30, 80)};
|
||||
var control1 = new Control
|
||||
{
|
||||
SizeFlagsVertical = Control.SizeFlags.FillExpand
|
||||
VerticalExpand = true,
|
||||
};
|
||||
var control2 = new Control
|
||||
{
|
||||
SizeFlagsVertical = Control.SizeFlags.FillExpand
|
||||
VerticalExpand = true,
|
||||
};
|
||||
var control3 = new Control {CustomMinimumSize = (0, 50)};
|
||||
var control3 = new Control {MinSize = (0, 50)};
|
||||
|
||||
root.AddChild(boxContainer);
|
||||
|
||||
@@ -95,7 +97,7 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
boxContainer.AddChild(control3);
|
||||
boxContainer.AddChild(control2);
|
||||
|
||||
root.ForceRunLayoutUpdate();
|
||||
root.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(control1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(control1.Size, Is.EqualTo(new Vector2(30, 15)));
|
||||
|
||||
@@ -14,14 +14,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void Test()
|
||||
{
|
||||
var container = new CenterContainer {Size = (100, 100)};
|
||||
var child = new Control {CustomMinimumSize = (50, 50)};
|
||||
var container = new CenterContainer();
|
||||
var child = new Control {MinSize = (50, 50)};
|
||||
|
||||
container.AddChild(child);
|
||||
|
||||
container.ForceRunLayoutUpdate();
|
||||
container.Arrange(UIBox2.FromDimensions(0, 0, 100, 100));
|
||||
|
||||
Assert.That(container.CombinedMinimumSize, Is.EqualTo(new Vector2(50, 50)));
|
||||
Assert.That(container.DesiredSize, Is.EqualTo(new Vector2(50, 50)));
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(25, 25)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
}
|
||||
|
||||
@@ -15,12 +15,12 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestBasic(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Columns = 2} : new GridContainer { MaxWidth = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount ? new GridContainer {Columns = 2} : new GridContainer {MaxGridWidth = 125};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -28,9 +28,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(54, 0)));
|
||||
@@ -43,13 +43,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestBasicRows(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Rows = 2}
|
||||
: new GridContainer {MaxHeight = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Rows = 2}
|
||||
: new GridContainer {MaxGridHeight = 125};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -57,9 +58,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(0, 54)));
|
||||
@@ -75,12 +76,12 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
// max minwidth / minheight among them.
|
||||
// Note that when limiting by count, the behavior is different - rows and columns are individually
|
||||
// expanded based on the max size of their elements
|
||||
var grid = new GridContainer { MaxWidth = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (12, 24)};
|
||||
var child2 = new Control {CustomMinimumSize = (30, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (40, 20)};
|
||||
var child4 = new Control {CustomMinimumSize = (20, 12)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 10)};
|
||||
var grid = new GridContainer {MaxGridWidth = 125};
|
||||
var child1 = new Control {MinSize = (12, 24)};
|
||||
var child2 = new Control {MinSize = (30, 50)};
|
||||
var child3 = new Control {MinSize = (40, 20)};
|
||||
var child4 = new Control {MinSize = (20, 12)};
|
||||
var child5 = new Control {MinSize = (50, 10)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -88,9 +89,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(54, 0)));
|
||||
@@ -102,12 +103,12 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestUnevenLimitSizeRows()
|
||||
{
|
||||
var grid = new GridContainer {MaxHeight = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (12, 2)};
|
||||
var child2 = new Control {CustomMinimumSize = (5, 23)};
|
||||
var child3 = new Control {CustomMinimumSize = (42, 4)};
|
||||
var child4 = new Control {CustomMinimumSize = (2, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 34)};
|
||||
var grid = new GridContainer {MaxGridHeight = 125};
|
||||
var child1 = new Control {MinSize = (12, 2)};
|
||||
var child2 = new Control {MinSize = (5, 23)};
|
||||
var child3 = new Control {MinSize = (42, 4)};
|
||||
var child4 = new Control {MinSize = (2, 50)};
|
||||
var child5 = new Control {MinSize = (50, 34)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -115,9 +116,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(0, 54)));
|
||||
@@ -130,13 +131,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestBasicBackwards(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Columns = 2, ExpandBackwards = true}
|
||||
: new GridContainer { MaxWidth = 125, ExpandBackwards = true};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Columns = 2, ExpandBackwards = true}
|
||||
: new GridContainer {MaxGridWidth = 125, ExpandBackwards = true};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -144,9 +146,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(104, 158)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(new Vector2(0, 108)));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(54, 108)));
|
||||
@@ -159,13 +161,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestBasicRowsBackwards(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Rows = 2, ExpandBackwards = true}
|
||||
: new GridContainer {MaxHeight = 125, ExpandBackwards = true};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Rows = 2, ExpandBackwards = true}
|
||||
: new GridContainer {MaxGridHeight = 125, ExpandBackwards = true};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -173,9 +176,9 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(grid.CombinedMinimumSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
Assert.That(grid.DesiredSize, Is.EqualTo(new Vector2(158, 104)));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(new Vector2(108, 0)));
|
||||
Assert.That(child2.Position, Is.EqualTo(new Vector2(108, 54)));
|
||||
@@ -191,13 +194,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
// in the presence of a MaxWidth with expanding elements, the
|
||||
// pre-expanded size should be used to determine the size of each "cell", and then expansion
|
||||
// happens within the defined control size
|
||||
var grid = limitByCount ? new GridContainer {Columns = 2, Size = (200, 200)}
|
||||
: new GridContainer {MaxWidth = 125, Size = (200, 200)} ;
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50), SizeFlagsHorizontal = Control.SizeFlags.FillExpand};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50), SizeFlagsVertical = Control.SizeFlags.FillExpand};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Columns = 2, SetSize = (200, 200)}
|
||||
: new GridContainer {MaxGridWidth = 125, SetSize = (200, 200)};
|
||||
var child1 = new Control {MinSize = (50, 50), HorizontalExpand = true};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50), VerticalExpand = true};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -205,7 +209,7 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child1.Size, Is.EqualTo(new Vector2(146, 50)));
|
||||
@@ -223,13 +227,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestExpandRows(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Rows = 2, Size = (200, 200)}
|
||||
: new GridContainer {MaxHeight = 125, Size = (200, 200)};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50), SizeFlagsVertical = Control.SizeFlags.FillExpand};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50), SizeFlagsHorizontal = Control.SizeFlags.FillExpand};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Rows = 2, SetSize = (200, 200)}
|
||||
: new GridContainer {MaxGridHeight = 125, SetSize = (200, 200)};
|
||||
var child1 = new Control {MinSize = (50, 50), VerticalExpand = true};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50), HorizontalExpand = true};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -237,7 +242,7 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.ForceRunLayoutUpdate();
|
||||
grid.Arrange(new UIBox2(0, 0, 250, 250));
|
||||
|
||||
Assert.That(child1.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child1.Size, Is.EqualTo(new Vector2(50, 146)));
|
||||
@@ -255,13 +260,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestRowCount(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Columns = 2}
|
||||
: new GridContainer {MaxWidth = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Columns = 2}
|
||||
: new GridContainer {MaxGridWidth = 125};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -269,6 +275,8 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.Measure((250, 250));
|
||||
|
||||
Assert.That(grid.Rows, Is.EqualTo(3));
|
||||
|
||||
grid.RemoveChild(child5);
|
||||
@@ -284,13 +292,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[TestCase(false)]
|
||||
public void TestColumnCountRows(bool limitByCount)
|
||||
{
|
||||
var grid = limitByCount ? new GridContainer {Rows = 2}
|
||||
: new GridContainer{MaxHeight = 125};
|
||||
var child1 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child2 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child3 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child4 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var child5 = new Control {CustomMinimumSize = (50, 50)};
|
||||
var grid = limitByCount
|
||||
? new GridContainer {Rows = 2}
|
||||
: new GridContainer {MaxGridHeight = 125};
|
||||
var child1 = new Control {MinSize = (50, 50)};
|
||||
var child2 = new Control {MinSize = (50, 50)};
|
||||
var child3 = new Control {MinSize = (50, 50)};
|
||||
var child4 = new Control {MinSize = (50, 50)};
|
||||
var child5 = new Control {MinSize = (50, 50)};
|
||||
|
||||
grid.AddChild(child1);
|
||||
grid.AddChild(child2);
|
||||
@@ -298,6 +307,8 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
grid.AddChild(child4);
|
||||
grid.AddChild(child5);
|
||||
|
||||
grid.Measure((250, 250));
|
||||
|
||||
Assert.That(grid.Columns, Is.EqualTo(3));
|
||||
|
||||
grid.RemoveChild(child5);
|
||||
|
||||
@@ -21,7 +21,7 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
LayoutContainer.SetMarginBottom(child, 5);
|
||||
control.AddChild(child);
|
||||
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(5, 5)));
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
@@ -29,7 +29,8 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
LayoutContainer.SetMarginTop(child, 3);
|
||||
LayoutContainer.SetMarginLeft(child, 3);
|
||||
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.InvalidateArrange();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(2, 2)));
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(3, 3)));
|
||||
@@ -44,17 +45,19 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
LayoutContainer.SetAnchorBottom(child, 1);
|
||||
control.AddChild(child);
|
||||
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(100, 100)));
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
|
||||
LayoutContainer.SetAnchorLeft(child, 0.5f);
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.InvalidateArrange();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(50, 0)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(50, 100)));
|
||||
LayoutContainer.SetAnchorTop(child, 0.5f);
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.InvalidateArrange();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(50, 50)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
@@ -66,14 +69,14 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
var control = new LayoutContainer {Size = new Vector2(100, 100)};
|
||||
var child = new Control
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
};
|
||||
|
||||
LayoutContainer.SetMarginRight(child, 20);
|
||||
LayoutContainer.SetMarginBottom(child, 20);
|
||||
|
||||
control.AddChild(child);
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
}
|
||||
@@ -92,7 +95,8 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
LayoutContainer.SetAnchorBottom(child, 1);
|
||||
|
||||
control.AddChild(child);
|
||||
control.ForceRunLayoutUpdate();
|
||||
control.InvalidateArrange();
|
||||
control.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(10, 10)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(80, 80)));
|
||||
@@ -102,18 +106,21 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestGrowEnd()
|
||||
{
|
||||
var parent = new LayoutContainer {Size = (50, 50)};
|
||||
var child = new Control();
|
||||
var parent = new LayoutContainer();
|
||||
var child = new Control {SetSize = (100, 100)};
|
||||
|
||||
LayoutContainer.SetAnchorRight(child, 1);
|
||||
|
||||
parent.AddChild(child);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
// Child should be at 0,0.
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
|
||||
// Making the child have a bigger minimum size should grow it to the bottom size.
|
||||
// i.e. size should change, position should not.
|
||||
child.CustomMinimumSize = (100, 100);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
// Right margin should make the child not have enough space and grow left.
|
||||
LayoutContainer.SetMarginRight(child, -100);
|
||||
parent.InvalidateArrange();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(100, 100)));
|
||||
@@ -123,21 +130,22 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestGrowBegin()
|
||||
{
|
||||
var parent = new LayoutContainer {Size = (50, 50)};
|
||||
var child = new Control();
|
||||
var parent = new LayoutContainer();
|
||||
var child = new Control {SetSize = (100, 100)};
|
||||
|
||||
LayoutContainer.SetGrowHorizontal(child, LayoutContainer.GrowDirection.Begin);
|
||||
LayoutContainer.SetAnchorRight(child, 1);
|
||||
|
||||
parent.AddChild(child);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
// Child should be at 0,0.
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
|
||||
// Making the child have a bigger minimum size should grow it to the bottom right.
|
||||
// i.e. size should change, position should not.
|
||||
child.CustomMinimumSize = (100, 100);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
// Right margin should make the child not have enough space and grow left.
|
||||
LayoutContainer.SetMarginRight(child, -100);
|
||||
parent.InvalidateArrange();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(-100, 0)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(100, 100)));
|
||||
@@ -147,17 +155,22 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestGrowBoth()
|
||||
{
|
||||
var parent = new LayoutContainer {Size = (50, 50)};
|
||||
var child = new Control();
|
||||
var parent = new LayoutContainer {MinSize = (100, 100)};
|
||||
var child = new Control {SetSize = (100, 100)};
|
||||
|
||||
LayoutContainer.SetGrowHorizontal(child, LayoutContainer.GrowDirection.Both);
|
||||
LayoutContainer.SetAnchorRight(child, 1);
|
||||
|
||||
parent.AddChild(child);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
// Child should be at 0,0.
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
|
||||
child.CustomMinimumSize = (100, 100);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
// Right margin should make the child not have enough space and grow left.
|
||||
LayoutContainer.SetMarginRight(child, -100);
|
||||
parent.InvalidateArrange();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(-50, 0)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(100, 100)));
|
||||
@@ -167,22 +180,24 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestGrowDirectionChange()
|
||||
{
|
||||
var parent = new LayoutContainer {Size = (50, 50)};
|
||||
var parent = new LayoutContainer {MinSize = (100, 100)};
|
||||
var child = new Control();
|
||||
parent.AddChild(child);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
// Child should be at 0,0.
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
// Child should be at -100,0.
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(0, 0)));
|
||||
|
||||
child.CustomMinimumSize = (100, 100);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
child.MinSize = (100, 100);
|
||||
parent.InvalidateMeasure();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(Vector2.Zero));
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(0, 0)));
|
||||
Assert.That(child.Size, Is.EqualTo(new Vector2(100, 100)));
|
||||
|
||||
LayoutContainer.SetGrowHorizontal(child, LayoutContainer.GrowDirection.Begin);
|
||||
parent.ForceRunLayoutUpdate();
|
||||
parent.InvalidateArrange();
|
||||
parent.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(child.Position, Is.EqualTo(new Vector2(-100, 0)));
|
||||
}
|
||||
|
||||
@@ -14,20 +14,18 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void Test()
|
||||
{
|
||||
var wrap = new LayoutContainer();
|
||||
var container = new PopupContainer {CustomMinimumSize = (100, 100)};
|
||||
wrap.AddChild(container);
|
||||
var container = new PopupContainer {MinSize = (100, 100)};
|
||||
|
||||
// Need this wrapper so that container has the correct size.
|
||||
wrap.ForceRunLayoutUpdate();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
var popup = new Control {CustomMinimumSize = (50, 50)};
|
||||
var popup = new Control {MinSize = (50, 50)};
|
||||
|
||||
container.AddChild(popup);
|
||||
|
||||
PopupContainer.SetPopupOrigin(popup, (25, 25));
|
||||
|
||||
container.ForceRunLayoutUpdate();
|
||||
container.InvalidateArrange();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(popup.Position, Is.EqualTo(new Vector2(25, 25)));
|
||||
Assert.That(popup.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
@@ -35,15 +33,17 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
// Test that pos gets pushed back to the top left if the size + offset is too large to fit.
|
||||
PopupContainer.SetPopupOrigin(popup, (75, 75));
|
||||
|
||||
container.ForceRunLayoutUpdate();
|
||||
container.InvalidateArrange();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(popup.Position, Is.EqualTo(new Vector2(50, 50)));
|
||||
Assert.That(popup.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
|
||||
// Test that pos = 0 if the popup is too large to fit.
|
||||
popup.CustomMinimumSize = (150, 150);
|
||||
popup.MinSize = (150, 150);
|
||||
|
||||
container.ForceRunLayoutUpdate();
|
||||
container.InvalidateArrange();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(popup.Position, Is.EqualTo(new Vector2(0, 0)));
|
||||
Assert.That(popup.Size, Is.EqualTo(new Vector2(150, 150)));
|
||||
@@ -52,21 +52,19 @@ namespace Robust.UnitTesting.Client.UserInterface.Controls
|
||||
[Test]
|
||||
public void TestAltPos()
|
||||
{
|
||||
var wrap = new LayoutContainer();
|
||||
var container = new PopupContainer {CustomMinimumSize = (100, 100)};
|
||||
wrap.AddChild(container);
|
||||
var container = new PopupContainer {MinSize = (100, 100)};
|
||||
|
||||
// Need this wrapper so that container has the correct size.
|
||||
wrap.ForceRunLayoutUpdate();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
var popup = new Control {CustomMinimumSize = (50, 50)};
|
||||
var popup = new Control {MinSize = (50, 50)};
|
||||
|
||||
container.AddChild(popup);
|
||||
|
||||
PopupContainer.SetPopupOrigin(popup, (75, 75));
|
||||
PopupContainer.SetAltOrigin(popup, (65, 25));
|
||||
|
||||
container.ForceRunLayoutUpdate();
|
||||
container.InvalidateArrange();
|
||||
container.Arrange(new UIBox2(0, 0, 100, 100));
|
||||
|
||||
Assert.That(popup.Position, Is.EqualTo(new Vector2(15, 25)));
|
||||
Assert.That(popup.Size, Is.EqualTo(new Vector2(50, 50)));
|
||||
|
||||
@@ -33,21 +33,21 @@ namespace Robust.UnitTesting.Client.UserInterface
|
||||
// We check that 4 and 1 do not receive events, that 3 receives before 2, and that positions are correct.
|
||||
var control1 = new LayoutContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50)
|
||||
MinSize = new Vector2(50, 50)
|
||||
};
|
||||
var control2 = new LayoutContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
MouseFilter = Control.MouseFilterMode.Stop
|
||||
};
|
||||
var control3 = new LayoutContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
MouseFilter = Control.MouseFilterMode.Pass
|
||||
};
|
||||
var control4 = new LayoutContainer
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
MouseFilter = Control.MouseFilterMode.Ignore
|
||||
};
|
||||
|
||||
@@ -60,7 +60,7 @@ namespace Robust.UnitTesting.Client.UserInterface
|
||||
control3.AddChild(control4);
|
||||
LayoutContainer.SetPosition(control4, (5, 5));
|
||||
|
||||
control1.ForceRunLayoutUpdate();
|
||||
control1.Arrange(new UIBox2(0, 0, 50, 50));
|
||||
|
||||
var mouseEvent = new BoundKeyEventArgs(EngineKeyFunctions.Use, BoundKeyState.Down,
|
||||
new Robust.Shared.Map.ScreenCoordinates(30, 30), true);
|
||||
@@ -208,13 +208,13 @@ namespace Robust.UnitTesting.Client.UserInterface
|
||||
{
|
||||
CanKeyboardFocus = true,
|
||||
KeyboardFocusOnClick = true,
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
MouseFilter = Control.MouseFilterMode.Stop
|
||||
};
|
||||
|
||||
_userInterfaceManager.RootControl.AddChild(control);
|
||||
|
||||
_userInterfaceManager.RootControl.ForceRunLayoutUpdate();
|
||||
_userInterfaceManager.RootControl.Arrange(new UIBox2(0, 0, 50, 50));
|
||||
|
||||
_userInterfaceManager.HandleCanFocusDown((30, 30));
|
||||
|
||||
@@ -233,7 +233,7 @@ namespace Robust.UnitTesting.Client.UserInterface
|
||||
{
|
||||
var control = new Control
|
||||
{
|
||||
CustomMinimumSize = new Vector2(50, 50),
|
||||
MinSize = new Vector2(50, 50),
|
||||
MouseFilter = Control.MouseFilterMode.Stop
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user