1
0
Fork 0
mirror of https://github.com/Ellpeck/MLEM.git synced 2024-06-27 06:51:43 +02:00

added ElementHelper and did some textfield changes

This commit is contained in:
Ellpeck 2019-08-24 12:40:20 +02:00
parent 404e95c8f2
commit cb5594bada
4 changed files with 101 additions and 33 deletions

View file

@ -79,7 +79,7 @@ namespace Demos {
image.IsHidden = !image.IsHidden; image.IsHidden = !image.IsHidden;
} }
}); });
root.AddChild(new VerticalSpace(3)); root.AddChild(new VerticalSpace(3));
root.AddChild(new Paragraph(Anchor.AutoLeft, 1, "Note that the default style does not contain any textures or font files and, as such, is quite bland. However, the default style is quite easy to override.")); root.AddChild(new Paragraph(Anchor.AutoLeft, 1, "Note that the default style does not contain any textures or font files and, as such, is quite bland. However, the default style is quite easy to override."));
root.AddChild(new Button(Anchor.AutoCenter, new Vector2(1, 10), "Change Style") { root.AddChild(new Button(Anchor.AutoCenter, new Vector2(1, 10), "Change Style") {
@ -97,7 +97,7 @@ namespace Demos {
root.AddChild(new VerticalSpace(3)); root.AddChild(new VerticalSpace(3));
// a paragraph with formatting codes. To see them all or to add more, check the TextFormatting class // a paragraph with formatting codes. To see them all or to add more, check the TextFormatting class
root.AddChild(new Paragraph(Anchor.AutoLeft, 1,"Paragraphs can also contain [Blue]formatting codes[White], including colors and [Italic]text styles[Regular]. The names of all [Orange]MonoGame Colors[White] can be used, as well as the codes [Italic]Italic[Regular] and [Bold]Bold[Regular]. \n[Italic]Even [CornflowerBlue]Cornflower Blue[White] works!")); root.AddChild(new Paragraph(Anchor.AutoLeft, 1, "Paragraphs can also contain [Blue]formatting codes[White], including colors and [Italic]text styles[Regular]. The names of all [Orange]MonoGame Colors[White] can be used, as well as the codes [Italic]Italic[Regular] and [Bold]Bold[Regular]. \n[Italic]Even [CornflowerBlue]Cornflower Blue[White] works!"));
root.AddChild(new VerticalSpace(3)); root.AddChild(new VerticalSpace(3));
root.AddChild(new Paragraph(Anchor.AutoCenter, 1, "Text input:", true)); root.AddChild(new Paragraph(Anchor.AutoCenter, 1, "Text input:", true));
@ -155,6 +155,10 @@ namespace Demos {
PositionOffset = new Vector2(0, 1) PositionOffset = new Vector2(0, 1)
}); });
root.AddChild(new VerticalSpace(3));
root.AddChild(new Paragraph(Anchor.AutoLeft, 1, "There are also some additional \"components\" which are created as combinations of other components. You can find all of them in the ElementHelper class. Here are some examples:"));
root.AddChild(ElementHelper.NumberField(Anchor.AutoLeft, new Vector2(1, 10))).PositionOffset = new Vector2(0, 1);
// Below are some querying examples that help you find certain elements easily // Below are some querying examples that help you find certain elements easily
var children = root.GetChildren(); var children = root.GetChildren();

View file

@ -85,6 +85,7 @@ namespace MLEM.Ui.Elements {
public MouseCallback OnMouseEnter; public MouseCallback OnMouseEnter;
public MouseCallback OnMouseExit; public MouseCallback OnMouseExit;
public TextInputCallback OnTextInput; public TextInputCallback OnTextInput;
public GenericCallback OnAreaUpdated;
private UiSystem system; private UiSystem system;
public UiSystem System { public UiSystem System {
@ -289,6 +290,8 @@ namespace MLEM.Ui.Elements {
} }
this.area = new Rectangle(pos, actualSize); this.area = new Rectangle(pos, actualSize);
this.OnAreaUpdated?.Invoke(this);
foreach (var child in this.Children) foreach (var child in this.Children)
child.ForceUpdateArea(); child.ForceUpdateArea();

View file

@ -0,0 +1,42 @@
using Microsoft.Xna.Framework;
using MLEM.Input;
namespace MLEM.Ui.Elements {
public static class ElementHelper {
public static Group NumberField(Anchor anchor, Vector2 size, int defaultValue = 0, int stepPerClick = 1, TextField.Rule rule = null, TextField.TextChanged onTextChange = null) {
var group = new Group(anchor, size, false);
var field = new TextField(Anchor.TopLeft, Vector2.One, rule ?? TextField.OnlyNumbers);
field.OnTextChange = onTextChange;
field.AppendText(defaultValue.ToString());
group.AddChild(field);
group.OnAreaUpdated += e => field.Size = new Vector2((e.Area.Width - e.Area.Height / 2) / e.Scale, 1);
var upButton = new Button(Anchor.TopRight, Vector2.One, "+") {
OnClicked = (element, button) => {
if (button == MouseButton.Left) {
var text = field.Text.ToString();
field.SetText(int.Parse(text) + stepPerClick);
}
}
};
group.AddChild(upButton);
group.OnAreaUpdated += e => upButton.Size = new Vector2(e.Area.Height / 2 / e.Scale);
var downButton = new Button(Anchor.BottomRight, Vector2.One, "-") {
OnClicked = (element, button) => {
if (button == MouseButton.Left) {
var text = field.Text.ToString();
field.SetText(int.Parse(text) - stepPerClick);
}
}
};
group.AddChild(downButton);
group.OnAreaUpdated += e => downButton.Size = new Vector2(e.Area.Height / 2 / e.Scale);
return group;
}
}
}

View file

@ -21,10 +21,10 @@ namespace MLEM.Ui.Elements {
public NinePatch HoveredTexture; public NinePatch HoveredTexture;
public Color HoveredColor; public Color HoveredColor;
public float TextScale; public float TextScale;
public readonly StringBuilder Text = new StringBuilder(); private readonly StringBuilder text = new StringBuilder();
public string Text => this.text.ToString();
public string PlaceholderText; public string PlaceholderText;
public TextChanged OnTextChange; public TextChanged OnTextChange;
public int MaxTextLength = int.MaxValue;
public float TextOffsetX = 4; public float TextOffsetX = 4;
private IGenericFont font; private IGenericFont font;
private double caretBlinkTimer; private double caretBlinkTimer;
@ -37,38 +37,37 @@ namespace MLEM.Ui.Elements {
this.OnTextInput += (element, key, character) => { this.OnTextInput += (element, key, character) => {
if (!this.IsSelected) if (!this.IsSelected)
return; return;
var textChanged = false;
if (key == Keys.Back) { if (key == Keys.Back) {
if (this.Text.Length > 0) { if (this.text.Length > 0) {
this.Text.Remove(this.Text.Length - 1, 1); this.RemoveText(this.text.Length - 1, 1);
textChanged = true;
} }
} else if (this.InputRule(this, character.ToString())) { } else {
if (this.Text.Length < this.MaxTextLength) { this.AppendText(character);
this.Text.Append(character);
textChanged = true;
}
}
if (textChanged) {
var length = this.font.MeasureString(this.Text).X * this.TextScale;
var maxWidth = this.DisplayArea.Width / this.Scale - this.TextOffsetX * 2;
if (length > maxWidth) {
for (var i = 0; i < this.Text.Length; i++) {
var substring = this.Text.ToString(i, this.Text.Length - i);
if (this.font.MeasureString(substring).X * this.TextScale <= maxWidth) {
this.textStartIndex = i;
break;
}
}
} else {
this.textStartIndex = 0;
}
this.OnTextChange?.Invoke(this, this.Text.ToString());
} }
}; };
} }
private void HandleTextChange() {
// not initialized yet
if (this.font == null)
return;
var length = this.font.MeasureString(this.text).X * this.TextScale;
var maxWidth = this.DisplayArea.Width / this.Scale - this.TextOffsetX * 2;
if (length > maxWidth) {
for (var i = 0; i < this.text.Length; i++) {
var substring = this.text.ToString(i, this.text.Length - i);
if (this.font.MeasureString(substring).X * this.TextScale <= maxWidth) {
this.textStartIndex = i;
break;
}
}
} else {
this.textStartIndex = 0;
}
this.OnTextChange?.Invoke(this, this.text.ToString());
}
public override void Update(GameTime time) { public override void Update(GameTime time) {
base.Update(time); base.Update(time);
@ -88,16 +87,36 @@ namespace MLEM.Ui.Elements {
batch.Draw(tex, this.DisplayArea.OffsetCopy(offset), color, this.Scale); batch.Draw(tex, this.DisplayArea.OffsetCopy(offset), color, this.Scale);
var textPos = this.DisplayArea.Location.ToVector2() + new Vector2(offset.X + this.TextOffsetX * this.Scale, offset.Y + this.DisplayArea.Height / 2); var textPos = this.DisplayArea.Location.ToVector2() + new Vector2(offset.X + this.TextOffsetX * this.Scale, offset.Y + this.DisplayArea.Height / 2);
if (this.Text.Length > 0 || this.IsSelected) { if (this.text.Length > 0 || this.IsSelected) {
var caret = this.IsSelected && this.caretBlinkTimer >= 0.5F ? "|" : ""; var caret = this.IsSelected && this.caretBlinkTimer >= 0.5F ? "|" : "";
var text = this.Text.ToString(this.textStartIndex, this.Text.Length - this.textStartIndex) + caret; var display = this.text.ToString(this.textStartIndex, this.text.Length - this.textStartIndex) + caret;
this.font.DrawCenteredString(batch, text, textPos, this.TextScale * this.Scale, Color.White * alpha, false, true); this.font.DrawCenteredString(batch, display, textPos, this.TextScale * this.Scale, Color.White * alpha, false, true);
} else if (this.PlaceholderText != null) { } else if (this.PlaceholderText != null) {
this.font.DrawCenteredString(batch, this.PlaceholderText, textPos, this.TextScale * this.Scale, Color.Gray * alpha, false, true); this.font.DrawCenteredString(batch, this.PlaceholderText, textPos, this.TextScale * this.Scale, Color.Gray * alpha, false, true);
} }
base.Draw(time, batch, alpha, offset); base.Draw(time, batch, alpha, offset);
} }
public void SetText(object text) {
if (!this.InputRule(this, text.ToString()))
return;
this.text.Clear();
this.text.Append(text);
this.HandleTextChange();
}
public void AppendText(object text) {
if (!this.InputRule(this, text.ToString()))
return;
this.text.Append(text);
this.HandleTextChange();
}
public void RemoveText(int index, int length) {
this.text.Remove(index, length);
this.HandleTextChange();
}
protected override void InitStyle(UiStyle style) { protected override void InitStyle(UiStyle style) {
base.InitStyle(style); base.InitStyle(style);
this.TextScale = style.TextScale; this.TextScale = style.TextScale;