mirror of
https://github.com/Ellpeck/MLEM.git
synced 2024-11-27 23:08:35 +01:00
Compare commits
3 commits
23103613cd
...
7f4cc773ec
Author | SHA1 | Date | |
---|---|---|---|
7f4cc773ec | |||
5d4f1293c7 | |||
60af21aff4 |
4 changed files with 35 additions and 11 deletions
|
@ -46,10 +46,12 @@ Improvements
|
||||||
- Allow dropdowns to have scrolling panels
|
- Allow dropdowns to have scrolling panels
|
||||||
- Improved Panel performance when adding and removing a lot of children
|
- Improved Panel performance when adding and removing a lot of children
|
||||||
- Don't reset the caret position of a text field when selecting or deselecting it
|
- Don't reset the caret position of a text field when selecting or deselecting it
|
||||||
|
- Improved UiParser.ParseImage with locks and a callback action
|
||||||
|
|
||||||
Fixes
|
Fixes
|
||||||
- Fixed panels updating their relevant children too much when the scroll bar is hidden
|
- Fixed panels updating their relevant children too much when the scroll bar is hidden
|
||||||
- Fixed a stack overflow exception when a panel's scroll bar auto-hiding causes elements to gain height
|
- Fixed a stack overflow exception when a panel's scroll bar auto-hiding causes elements to gain height
|
||||||
|
- Fixed scrolling panels calculating their height incorrectly when their first child is hidden
|
||||||
|
|
||||||
### MLEM.Extended
|
### MLEM.Extended
|
||||||
Improvements
|
Improvements
|
||||||
|
|
|
@ -144,6 +144,12 @@ namespace MLEM.Ui.Elements {
|
||||||
ret.X = ret.Y * this.Texture.Width / this.Texture.Height + this.ScaledAutoSizeAddedAbsolute.X;
|
ret.X = ret.Y * this.Texture.Width / this.Texture.Height + this.ScaledAutoSizeAddedAbsolute.X;
|
||||||
if (this.SetHeightBasedOnAspect)
|
if (this.SetHeightBasedOnAspect)
|
||||||
ret.Y = ret.X * this.Texture.Height / this.Texture.Width + this.ScaledAutoSizeAddedAbsolute.Y;
|
ret.Y = ret.X * this.Texture.Height / this.Texture.Width + this.ScaledAutoSizeAddedAbsolute.Y;
|
||||||
|
} else {
|
||||||
|
// if we don't have a texture and we auto-set width or height, calculate as if we had a texture with a size of 0
|
||||||
|
if (this.SetWidthBasedOnAspect)
|
||||||
|
ret.X = this.ScaledAutoSizeAddedAbsolute.X;
|
||||||
|
if (this.SetHeightBasedOnAspect)
|
||||||
|
ret.Y = this.ScaledAutoSizeAddedAbsolute.Y;
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
@ -223,10 +223,10 @@ namespace MLEM.Ui.Elements {
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="elementY">The y coordinate to scroll to, which should have this element's <see cref="Element.Scale"/> applied.</param>
|
/// <param name="elementY">The y coordinate to scroll to, which should have this element's <see cref="Element.Scale"/> applied.</param>
|
||||||
public void ScrollToElement(float elementY) {
|
public void ScrollToElement(float elementY) {
|
||||||
var firstChild = this.Children.FirstOrDefault(c => c != this.ScrollBar);
|
var highestValidChild = this.Children.FirstOrDefault(c => c != this.ScrollBar && !c.IsHidden);
|
||||||
if (firstChild == null)
|
if (highestValidChild == null)
|
||||||
return;
|
return;
|
||||||
this.ScrollBar.CurrentValue = (elementY - this.Area.Height / 2 - firstChild.Area.Top) / this.Scale + this.ChildPadding.Value.Height / 2;
|
this.ScrollBar.CurrentValue = (elementY - this.Area.Height / 2 - highestValidChild.Area.Top) / this.Scale + this.ChildPadding.Value.Height / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc />
|
/// <inheritdoc />
|
||||||
|
@ -282,9 +282,9 @@ namespace MLEM.Ui.Elements {
|
||||||
|
|
||||||
float childrenHeight;
|
float childrenHeight;
|
||||||
if (this.Children.Count > 1) {
|
if (this.Children.Count > 1) {
|
||||||
var firstChild = this.Children.FirstOrDefault(c => c != this.ScrollBar);
|
var highestValidChild = this.Children.FirstOrDefault(c => c != this.ScrollBar && !c.IsHidden);
|
||||||
var lowestChild = this.GetLowestChild(c => c != this.ScrollBar && !c.IsHidden, true);
|
var lowestChild = this.GetLowestChild(c => c != this.ScrollBar && !c.IsHidden, true);
|
||||||
childrenHeight = lowestChild.GetTotalCoveredArea(false).Bottom - firstChild.Area.Top;
|
childrenHeight = lowestChild.GetTotalCoveredArea(false).Bottom - highestValidChild.Area.Top;
|
||||||
} else {
|
} else {
|
||||||
// if we only have one child (the scroll bar), then the children take up no visual height
|
// if we only have one child (the scroll bar), then the children take up no visual height
|
||||||
childrenHeight = 0;
|
childrenHeight = 0;
|
||||||
|
|
|
@ -10,6 +10,7 @@ using MLEM.Ui.Style;
|
||||||
|
|
||||||
#if NETSTANDARD2_0_OR_GREATER || NET6_0_OR_GREATER
|
#if NETSTANDARD2_0_OR_GREATER || NET6_0_OR_GREATER
|
||||||
using System.Net.Http;
|
using System.Net.Http;
|
||||||
|
|
||||||
#else
|
#else
|
||||||
using System.Net;
|
using System.Net;
|
||||||
#endif
|
#endif
|
||||||
|
@ -138,23 +139,33 @@ namespace MLEM.Ui.Parsers {
|
||||||
/// This method invokes an asynchronouns action, meaning the <see cref="Image"/>'s <see cref="Image.Texture"/> will likely not have loaded in when this method returns.
|
/// This method invokes an asynchronouns action, meaning the <see cref="Image"/>'s <see cref="Image.Texture"/> will likely not have loaded in when this method returns.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="path">The absolute, relative or web path to the image.</param>
|
/// <param name="path">The absolute, relative or web path to the image.</param>
|
||||||
|
/// <param name="onImageFetched">An action that is invoked with the loaded image once it is fetched. Note that this action will be invoked asynchronously.</param>
|
||||||
/// <returns>The loaded image.</returns>
|
/// <returns>The loaded image.</returns>
|
||||||
/// <exception cref="NullReferenceException">Thrown if <see cref="GraphicsDevice"/> is null, or if there is an <see cref="Exception"/> loading the image and <see cref="ImageExceptionHandler"/> is unset.</exception>
|
/// <exception cref="NullReferenceException">Thrown if <see cref="GraphicsDevice"/> is null, or if there is an <see cref="Exception"/> loading the image and <see cref="ImageExceptionHandler"/> is unset.</exception>
|
||||||
protected Image ParseImage(string path) {
|
protected Image ParseImage(string path, Action<TextureRegion> onImageFetched = null) {
|
||||||
if (this.GraphicsDevice == null)
|
if (this.GraphicsDevice == null)
|
||||||
throw new NullReferenceException("A UI parser requires a GraphicsDevice for parsing images");
|
throw new NullReferenceException("A UI parser requires a GraphicsDevice for parsing images");
|
||||||
|
|
||||||
|
var imageLock = new object();
|
||||||
TextureRegion image = null;
|
TextureRegion image = null;
|
||||||
return new Image(Anchor.AutoLeft, Vector2.One, _ => image) {
|
return new Image(Anchor.AutoLeft, Vector2.One, _ => {
|
||||||
|
lock (imageLock)
|
||||||
|
return image;
|
||||||
|
}) {
|
||||||
SetHeightBasedOnAspect = true,
|
SetHeightBasedOnAspect = true,
|
||||||
OnAddedToUi = e => {
|
OnAddedToUi = e => {
|
||||||
if (image == null)
|
bool imageNull;
|
||||||
|
lock (imageLock)
|
||||||
|
imageNull = image == null;
|
||||||
|
if (imageNull)
|
||||||
LoadImageAsync();
|
LoadImageAsync();
|
||||||
},
|
},
|
||||||
OnRemovedFromUi = e => {
|
OnRemovedFromUi = e => {
|
||||||
|
lock (imageLock) {
|
||||||
image?.Texture.Dispose();
|
image?.Texture.Dispose();
|
||||||
image = null;
|
image = null;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
async void LoadImageAsync() {
|
async void LoadImageAsync() {
|
||||||
|
@ -178,7 +189,12 @@ namespace MLEM.Ui.Parsers {
|
||||||
using (var stream = Path.IsPathRooted(path) ? File.OpenRead(path) : TitleContainer.OpenStream(path))
|
using (var stream = Path.IsPathRooted(path) ? File.OpenRead(path) : TitleContainer.OpenStream(path))
|
||||||
tex = Texture2D.FromStream(this.GraphicsDevice, stream);
|
tex = Texture2D.FromStream(this.GraphicsDevice, stream);
|
||||||
}
|
}
|
||||||
|
lock (imageLock) {
|
||||||
|
if (image == null) {
|
||||||
image = new TextureRegion(tex);
|
image = new TextureRegion(tex);
|
||||||
|
onImageFetched?.Invoke(image);
|
||||||
|
}
|
||||||
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
if (this.ImageExceptionHandler != null) {
|
if (this.ImageExceptionHandler != null) {
|
||||||
this.ImageExceptionHandler.Invoke(path, e);
|
this.ImageExceptionHandler.Invoke(path, e);
|
||||||
|
|
Loading…
Reference in a new issue