diff --git a/Demos/UiDemo.cs b/Demos/UiDemo.cs index fffc755..b682498 100644 --- a/Demos/UiDemo.cs +++ b/Demos/UiDemo.cs @@ -134,12 +134,19 @@ namespace Demos { root.AddChild(new Paragraph(Anchor.AutoLeft, 1, paragraph => "Slider is at " + (slider.CurrentValue * 100).Floor() + "%") {PositionOffset = new Vector2(0, 1)}); root.AddChild(slider); + // This button uses a coroutine from my Coroutine NuGet package (which is included with MLEM.Startup) + // but the important thing it does is change its visual scale and offset (check the method below for more info) + root.AddChild(new Button(Anchor.AutoCenter, new Vector2(0.5F, 10), "Wobble", "This button wobbles around visually when clicked, but this doesn't affect its actual size and positioning") { + OnClicked = (element, button) => CoroutineHandler.Start(this.WobbleButton(element)), + PositionOffset = new Vector2(0, 1) + }); + // Below are some querying examples that help you find certain elements easily var children = root.GetChildren(); var totalChildren = root.GetChildren(regardChildrensChildren: true); Console.WriteLine($"The root has {children.Count()} children, but there are {totalChildren.Count()} when regarding children's children"); - + var textFields = root.GetChildren(); Console.WriteLine($"The root has {textFields.Count()} text fields"); @@ -152,6 +159,23 @@ namespace Demos { Console.WriteLine($"The root has {autoWidthChildren.Count()} auto-width children, {autoWidthButtons.Count()} of which are buttons"); } + // This method is used by the wobbling button (see above) + // Note that this particular example makes use of the Coroutine package + private IEnumerator WobbleButton(Element button) { + var counter = 0F; + while (counter < 10) { + // The imporant bit is that it changes its added display scale and offset, allowing the button to still maintain the + // correct position and scaling for both anchoring and interacting purposes, but to show any kind of animation visually + // This could be useful, for example, to create a little feedback effect to clicking it where it changes size for a second + button.AddedDisplayScale = new Vector2((float) Math.Sin(counter)); + button.AddedDisplayOffset = new Vector2((float) Math.Sin(counter / 2) * 4, 0); + counter += 0.1F; + yield return new WaitSeconds(0.01F); + } + button.AddedDisplayScale = Vector2.Zero; + button.AddedDisplayOffset = Vector2.Zero; + } + protected override void DoDraw(GameTime gameTime) { this.GraphicsDevice.Clear(Color.CornflowerBlue); base.DoDraw(gameTime); diff --git a/MLEM.Ui/Elements/Element.cs b/MLEM.Ui/Elements/Element.cs index 2ce05f2..ebe281b 100644 --- a/MLEM.Ui/Elements/Element.cs +++ b/MLEM.Ui/Elements/Element.cs @@ -74,6 +74,10 @@ namespace MLEM.Ui.Elements { } } public Point ScaledChildPadding => this.childPadding.Multiply(this.Scale); + public Vector2 AddedDisplayOffset; + public Point ScaledDisplayOffset => (this.AddedDisplayOffset * this.Scale).ToPoint(); + public Vector2 AddedDisplayScale; + public Point ScaledDisplayScale => (this.AddedDisplayScale * this.Scale).ToPoint(); public MouseClickCallback OnClicked; public GenericCallback OnSelected; @@ -123,7 +127,8 @@ namespace MLEM.Ui.Elements { public Rectangle DisplayArea { get { var padded = this.Area; - padded.Location += this.ScaledPadding; + padded.Inflate(this.ScaledDisplayScale.X, this.ScaledDisplayScale.Y); + padded.Location += this.ScaledPadding + this.ScaledDisplayOffset; padded.Width -= this.ScaledPadding.X * 2; padded.Height -= this.ScaledPadding.Y * 2; return padded; @@ -358,23 +363,23 @@ namespace MLEM.Ui.Elements { public IEnumerable GetChildren(Func condition = null, bool regardChildrensChildren = false) { foreach (var child in this.Children) { - if (condition == null || condition(child)) - yield return child; if (regardChildrensChildren) { foreach (var cc in child.GetChildren(condition, true)) yield return cc; } + if (condition == null || condition(child)) + yield return child; } } public IEnumerable GetChildren(Func condition = null, bool regardChildrensChildren = false) where T : Element { foreach (var child in this.Children) { - if (child is T t && (condition == null || condition(t))) - yield return t; if (regardChildrensChildren) { foreach (var cc in child.GetChildren(condition, true)) yield return cc; } + if (child is T t && (condition == null || condition(t))) + yield return t; } }