618 lines
16 KiB
C#
618 lines
16 KiB
C#
|
|
using Godot;
|
|
using Rokojori;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
|
|
namespace Rokojori
|
|
{
|
|
[Tool]
|
|
[GlobalClass,Icon("res://addons/rokojori_action_library/Icons/UIImage.svg")]
|
|
public partial class UIImage:TextureRect, UIStylePropertyContainerNode, UIHolderControl, IAssemblyReload
|
|
{
|
|
UIImageType _imageType;
|
|
[Export]
|
|
public UIImageType imageType
|
|
{
|
|
get => _imageType;
|
|
set
|
|
{
|
|
if ( _imageType != value )
|
|
{
|
|
if ( _imageType != null )
|
|
{
|
|
_imageType.Clear( this );
|
|
}
|
|
}
|
|
|
|
_imageType = value;
|
|
|
|
UpdateImageType();
|
|
}
|
|
}
|
|
|
|
UI ui;
|
|
|
|
public void SetUI( UI ui, bool computeDepth = true )
|
|
{
|
|
this.ui = ui;
|
|
|
|
if ( computeDepth )
|
|
{
|
|
ComputeUIAncestorDepth();
|
|
}
|
|
|
|
}
|
|
|
|
|
|
public UI GetUI( bool computeDepth = true )
|
|
{
|
|
if ( this.ui != null )
|
|
{
|
|
return this.ui;
|
|
}
|
|
|
|
var ui = this.FindParentThatIs<UI>();
|
|
|
|
if ( ui == null )
|
|
{
|
|
|
|
this._uiAncestorDepth = -1;
|
|
this.LogInfo( "No UI in parents >", ui );
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
if ( computeDepth )
|
|
{
|
|
ComputeUIAncestorDepth();
|
|
}
|
|
|
|
|
|
return ui;
|
|
}
|
|
|
|
void UpdateImageType()
|
|
{
|
|
ResetImageType();
|
|
|
|
if ( _imageType != null )
|
|
{
|
|
// this.LogInfo( "Assigning Image Type:", _imageType );
|
|
_imageType.Assign( this );
|
|
}
|
|
}
|
|
|
|
string hoverID = IDGenerator.GenerateID();
|
|
|
|
public override void _Ready()
|
|
{
|
|
MouseEntered += ()=>
|
|
{
|
|
AddUISelectorFlag( UISelectorFlag.Hover, hoverID );
|
|
this.SetDirty();
|
|
|
|
};
|
|
|
|
MouseExited += ()=>
|
|
{
|
|
RemoveUISelectorFlag( UISelectorFlag.Hover, hoverID );
|
|
this.SetDirty();
|
|
};
|
|
|
|
UpdateImageType();
|
|
ComputeUIAncestorDepth();
|
|
}
|
|
|
|
public override void _EnterTree()
|
|
{
|
|
UpdateImageType();
|
|
ComputeUIAncestorDepth();
|
|
}
|
|
|
|
public override void _ExitTree()
|
|
{
|
|
_uiAncestorDepth = -1;
|
|
}
|
|
|
|
public void OnAssemblyReloaded()
|
|
{
|
|
UpdateImageType();
|
|
}
|
|
|
|
int _uiAncestorDepth;
|
|
|
|
public void ComputeUIAncestorDepth()
|
|
{
|
|
SetUIAncestorDepth( NodesWalker.Get().GetAncestorDistance( this, GetUI( false ) ) );
|
|
}
|
|
|
|
public void SetUIAncestorDepth( int depth )
|
|
{
|
|
_uiAncestorDepth = depth;
|
|
}
|
|
|
|
public int GetUIAncestorDepth()
|
|
{
|
|
return _uiAncestorDepth;
|
|
}
|
|
|
|
void ResetImageType()
|
|
{
|
|
ExpandMode = TextureRect.ExpandModeEnum.IgnoreSize;
|
|
StretchMode = TextureRect.StretchModeEnum.Scale;
|
|
Material = null;
|
|
}
|
|
|
|
protected override void Dispose( bool disposing)
|
|
{
|
|
_selectorFlagReferenceCounter.Clear();
|
|
}
|
|
|
|
MapList<UISelectorFlag,string> _selectorFlagReferenceCounter = new MapList<UISelectorFlag, string>();
|
|
|
|
public void AddUISelectorFlag( UISelectorFlag flag, string reference = "" )
|
|
{
|
|
SetSelectorFlagReference( flag, reference, true );
|
|
}
|
|
|
|
public void RemoveUISelectorFlag( UISelectorFlag flag, string reference = "" )
|
|
{
|
|
SetSelectorFlagReference( flag, reference, false );
|
|
}
|
|
|
|
void SetSelectorFlagReference( UISelectorFlag flag, string reference, bool enable )
|
|
{
|
|
if ( enable )
|
|
{
|
|
_selectorFlagReferenceCounter.AddIfNotPresent( flag, reference );
|
|
}
|
|
else
|
|
{
|
|
_selectorFlagReferenceCounter.Remove( flag, reference );
|
|
}
|
|
|
|
var numFlagsBefore = _selectorFlags.Count;
|
|
_selectorFlags = _selectorFlagReferenceCounter.Keys.ToList();
|
|
|
|
var changed = numFlagsBefore != _selectorFlags.Count;
|
|
|
|
UISelector.UpdateParentUISelectorFlags( this );
|
|
|
|
if ( changed )
|
|
{
|
|
// this.LogInfo( "Changed flag:", flag, reference );
|
|
this.SetDirty();
|
|
}
|
|
|
|
|
|
}
|
|
|
|
List<UISelectorFlag> _selectorFlags = [];
|
|
List<UISelectorFlag> _parentSelectorFlags = [];
|
|
|
|
public List<UISelectorFlag> GetUISelectorFlags()
|
|
{
|
|
return _selectorFlags;
|
|
}
|
|
|
|
public List<UISelectorFlag> GetParentUISelectorFlags()
|
|
{
|
|
return _parentSelectorFlags;
|
|
}
|
|
|
|
public void CopyNumberShaderPropertyFrom( CustomMaterialProperty<float> name, UINumber number, TransitionSettings transition )
|
|
{
|
|
SetNumberShaderProperty( name.GetPropertyName<FloatPropertyName>(), number, transition );
|
|
}
|
|
|
|
public void SetNumberShaderProperty( FloatPropertyName name, UINumber number, TransitionSettings transition )
|
|
{
|
|
if ( name == null || name.propertyName == null )
|
|
{
|
|
this.LogInfo( "Name is null" );
|
|
return;
|
|
}
|
|
|
|
|
|
for ( int i = 0; i < numberProperties.Length; i++ )
|
|
{
|
|
if ( numberProperties[ i ] == null || numberProperties[ i ].floatPropertyName == null )
|
|
{
|
|
return;
|
|
}
|
|
}
|
|
|
|
if ( number == null )
|
|
{
|
|
var index = Arrays.FindIndex( numberProperties, p => p.floatPropertyName.propertyName == name.propertyName );
|
|
numberProperties = Arrays.RemoveIndex( numberProperties, index );
|
|
return;
|
|
}
|
|
|
|
var shaderUINumber = Arrays.Find( numberProperties, p => p.floatPropertyName.propertyName == name.propertyName );
|
|
|
|
if ( shaderUINumber == null )
|
|
{
|
|
shaderUINumber = new ShaderUINumber();
|
|
shaderUINumber.floatPropertyName = name;
|
|
numberProperties = Arrays.AddEntry( numberProperties, shaderUINumber );
|
|
}
|
|
|
|
shaderUINumber.number = number;
|
|
}
|
|
|
|
public void CopyColorShaderPropertyFrom( CustomMaterialProperty<Color> name, UIColor color )
|
|
{
|
|
SetColorShaderProperty( name.GetPropertyName<ColorPropertyName>(), color );
|
|
}
|
|
|
|
public void SetColorShaderProperty( ColorPropertyName name, UIColor color )
|
|
{
|
|
if ( name == null || name.propertyName == null )
|
|
{
|
|
this.LogInfo( "Name is null" );
|
|
return;
|
|
}
|
|
|
|
for ( int i = 0; i < colorProperties.Length; i++ )
|
|
{
|
|
if ( colorProperties[ i ] == null || colorProperties[ i ].colorPropertyName == null )
|
|
{
|
|
return;
|
|
}
|
|
}
|
|
|
|
if ( color == null )
|
|
{
|
|
var index = Arrays.FindIndex( colorProperties, p => p != null && p.colorPropertyName.propertyName == name.propertyName );
|
|
colorProperties = Arrays.RemoveIndex( colorProperties, index );
|
|
return;
|
|
}
|
|
|
|
var shaderUIColor = Arrays.Find( colorProperties, p => p != null && p.colorPropertyName.propertyName == name.propertyName );
|
|
|
|
if ( shaderUIColor == null )
|
|
{
|
|
shaderUIColor = new ShaderUIColor();
|
|
shaderUIColor.colorPropertyName = name;
|
|
colorProperties = Arrays.AddEntry( colorProperties, shaderUIColor );
|
|
}
|
|
|
|
shaderUIColor.color = color;
|
|
}
|
|
|
|
[Export]
|
|
public UIStyle parentStyle;
|
|
|
|
[ExportGroup("Size & Margins")]
|
|
[Export]
|
|
public UINumber width;
|
|
|
|
[Export]
|
|
public UINumber height;
|
|
|
|
|
|
[Export]
|
|
public UINumber margin;
|
|
|
|
[Export]
|
|
public UINumber marginLeft;
|
|
[Export]
|
|
public UINumber marginTop;
|
|
[Export]
|
|
public UINumber marginRight;
|
|
[Export]
|
|
public UINumber marginBottom;
|
|
|
|
|
|
[ExportGroup( "Position" )]
|
|
[Export]
|
|
public UIPosition position;
|
|
[Export]
|
|
public UILineWrap lineWrap;
|
|
[Export]
|
|
public UINumber left;
|
|
[Export]
|
|
public UINumber top;
|
|
[Export]
|
|
public UINumber right;
|
|
[Export]
|
|
public UINumber bottom;
|
|
|
|
|
|
[ExportGroup( "Rotation & Scale" )]
|
|
[Export]
|
|
public UINumber pivotX;
|
|
[Export]
|
|
public UINumber pivotY;
|
|
|
|
[Export]
|
|
public UINumber rotation;
|
|
|
|
[Export]
|
|
public UINumber scale;
|
|
|
|
[Export]
|
|
public UINumber scaleX;
|
|
[Export]
|
|
public UINumber scaleY;
|
|
|
|
[ExportGroup( "Shader Properties" )]
|
|
[Export]
|
|
public ShaderUIColor[] colorProperties = new ShaderUIColor[ 0 ];
|
|
// public List<ActiveStyleTransition<UIColor,ColorPropertyName>> activeShaderColorTransitions = new List<ActiveStyleTransition<UIColor,ColorPropertyName>>();
|
|
// public List<ActiveStyleTransition<UIColor,ColorPropertyName>> GetActiveShaderUIColorTransitions()
|
|
// {
|
|
// return activeShaderColorTransitions;
|
|
// }
|
|
|
|
[Export]
|
|
public ShaderUINumber[] numberProperties = new ShaderUINumber[ 0 ];
|
|
// public List<ActiveStyleTransition<UINumber,FloatPropertyName>> activeShaderNumberTransitions = new List<ActiveStyleTransition<UINumber,FloatPropertyName>>();
|
|
// public List<ActiveStyleTransition<UINumber,FloatPropertyName>> GetActiveShaderUINumberTransitions()
|
|
// {
|
|
// return activeShaderNumberTransitions;
|
|
// }
|
|
|
|
[ExportGroup("Transitions")]
|
|
[Export]
|
|
public TransitionSettingsAll transitionSettings;
|
|
public TransitionSettingsAll GetTransitionSettingsAll()
|
|
{
|
|
return transitionSettings;
|
|
}
|
|
|
|
[Export]
|
|
public UINumberTransition[] numberTransitions = new UINumberTransition[0];
|
|
public UINumberTransition[] GetNumberTransitions()
|
|
{
|
|
return numberTransitions;
|
|
}
|
|
|
|
public List<ActiveStyleTransition<UINumber,UIStyleNumberPropertyAndName>> activeNumberTransitions = new List<ActiveStyleTransition<UINumber,UIStyleNumberPropertyAndName>>();
|
|
public List<ActiveStyleTransition<UINumber,UIStyleNumberPropertyAndName>> GetActiveUINumberTransitions()
|
|
{
|
|
return activeNumberTransitions;
|
|
}
|
|
|
|
[Export]
|
|
public UIColorTransition[] colorTransitions = new UIColorTransition[ 0 ];
|
|
public UIColorTransition[] GetColorTransitions()
|
|
{
|
|
return colorTransitions;
|
|
}
|
|
|
|
public List<ActiveStyleTransition<UIColor,UIStyleColorPropertyAndName>> activeColorTransitions = new List<ActiveStyleTransition<UIColor,UIStyleColorPropertyAndName>>();
|
|
public List<ActiveStyleTransition<UIColor,UIStyleColorPropertyAndName>> GetActiveUIColorTransitions()
|
|
{
|
|
return activeColorTransitions;
|
|
}
|
|
|
|
|
|
|
|
public UIStyle GetUIStyleParent()
|
|
{
|
|
return parentStyle;
|
|
}
|
|
|
|
public UIPosition GetUIPosition()
|
|
{
|
|
return position;
|
|
}
|
|
|
|
public UILineWrap GetUILineWrap()
|
|
{
|
|
return lineWrap;
|
|
}
|
|
|
|
public UILayout GetUILayout()
|
|
{
|
|
return UILayout.___;
|
|
}
|
|
|
|
|
|
public ShaderUIColor[] GetShaderUIColors()
|
|
{
|
|
return colorProperties;
|
|
}
|
|
|
|
public ShaderUINumber[] GetShaderUINumbers()
|
|
{
|
|
return numberProperties;
|
|
}
|
|
|
|
public UINumber GetUIStyleNumberProperty( UIStyleNumberProperty property, string shaderPropertyName, UIStylePropertyContainer source )
|
|
{
|
|
|
|
switch ( property )
|
|
{
|
|
case UIStyleNumberProperty.Width: return width;
|
|
case UIStyleNumberProperty.Height: return height;
|
|
|
|
case UIStyleNumberProperty.Margin: return margin;
|
|
|
|
case UIStyleNumberProperty.MarginLeft: return marginLeft;
|
|
case UIStyleNumberProperty.MarginRight: return marginRight;
|
|
case UIStyleNumberProperty.MarginTop: return marginTop;
|
|
case UIStyleNumberProperty.MarginBottom: return marginBottom;
|
|
|
|
|
|
case UIStyleNumberProperty.Left: return left;
|
|
case UIStyleNumberProperty.Right: return right;
|
|
case UIStyleNumberProperty.Top: return top;
|
|
case UIStyleNumberProperty.Bottom: return bottom;
|
|
|
|
case UIStyleNumberProperty.PivotX: return pivotX;
|
|
case UIStyleNumberProperty.PivotY: return pivotY;
|
|
case UIStyleNumberProperty.Rotation: return rotation;
|
|
|
|
case UIStyleNumberProperty.Scale: return scale;
|
|
case UIStyleNumberProperty.ScaleX: return scaleX;
|
|
case UIStyleNumberProperty.ScaleY: return scaleY;
|
|
}
|
|
|
|
if ( UIStyleNumberProperty.FloatShaderProperty == property )
|
|
{
|
|
var numberProperty = numberProperties.Find( n => n.floatPropertyName.propertyName == shaderPropertyName );
|
|
|
|
if ( numberProperty != null )
|
|
{
|
|
return numberProperty.number;
|
|
}
|
|
|
|
}
|
|
|
|
|
|
return null;
|
|
}
|
|
|
|
public void SetUIStyleNumberProperty( UIStyleNumberProperty property, UINumber number )
|
|
{
|
|
switch ( property )
|
|
{
|
|
case UIStyleNumberProperty.Left: { left = number; } break;
|
|
case UIStyleNumberProperty.Right: { right = number; } break;
|
|
case UIStyleNumberProperty.Top: { top = number; } break;
|
|
case UIStyleNumberProperty.Bottom: { bottom = number; } break;
|
|
|
|
case UIStyleNumberProperty.Width: { width = number; } break;
|
|
case UIStyleNumberProperty.Height: { height = number; } break;
|
|
|
|
case UIStyleNumberProperty.Margin: { margin = number; } break;
|
|
|
|
case UIStyleNumberProperty.MarginLeft: { marginLeft = number; } break;
|
|
case UIStyleNumberProperty.MarginRight: { marginRight = number; } break;
|
|
case UIStyleNumberProperty.MarginTop: { marginTop = number; } break;
|
|
case UIStyleNumberProperty.MarginBottom: { marginBottom = number; } break;
|
|
|
|
case UIStyleNumberProperty.PivotX: { pivotX = number; } break;
|
|
case UIStyleNumberProperty.PivotY: { pivotY = number; } break;
|
|
case UIStyleNumberProperty.Rotation: { rotation = number; } break;
|
|
|
|
case UIStyleNumberProperty.Scale: { scale = number; } break;
|
|
case UIStyleNumberProperty.ScaleX: { scaleX = number; } break;
|
|
case UIStyleNumberProperty.ScaleY: { scaleY = number; } break;
|
|
}
|
|
|
|
this.SetLayoutDirtyFlag();
|
|
|
|
}
|
|
|
|
bool _isAnimated = false;
|
|
int _isLayoutDirty = 3;
|
|
|
|
public void ResetDirtyFlags()
|
|
{
|
|
_isAnimated = false;
|
|
_isLayoutDirty = Mathf.Max( 0, _isLayoutDirty - 1 );
|
|
}
|
|
|
|
public void SetAnimatedFlag()
|
|
{
|
|
_isAnimated = true;
|
|
this.SetDirty();
|
|
}
|
|
|
|
public void SetLayoutDirtyFlag()
|
|
{
|
|
_isLayoutDirty = 3;
|
|
this.SetDirty();
|
|
}
|
|
|
|
|
|
public bool IsDirty()
|
|
{
|
|
return _isAnimated || _isLayoutDirty != 0 || this.HasActiveTransitions();
|
|
}
|
|
|
|
|
|
public void Update()
|
|
{
|
|
|
|
if ( Texture == null )
|
|
{
|
|
Size = new Vector2( 0, 0 );
|
|
return;
|
|
}
|
|
|
|
var tw = Texture.GetWidth();
|
|
var th = Texture.GetHeight();
|
|
|
|
|
|
var w = UINumber.Compute( this, UIStyleNumberProperty.Width, tw, tw / 100f );
|
|
var h = UINumber.Compute( this, UIStyleNumberProperty.Height, th, th / 100f );
|
|
|
|
Size = new Vector2( w, h );
|
|
|
|
if ( Material == null )
|
|
{
|
|
return;
|
|
}
|
|
|
|
var ui = GetUI();
|
|
|
|
if ( ui == null || ui.settings == null || ui.settings.sizePropertyName == null )
|
|
{
|
|
return;
|
|
}
|
|
|
|
ui.settings.sizePropertyName.Set( Material, Size );
|
|
|
|
var colorProperties = imageType != null ? imageType.GetColorShaderProperties() : [];
|
|
var colorPropertyName = new ColorPropertyName();
|
|
|
|
foreach ( var c in colorProperties )
|
|
{
|
|
var color = UIColor.Compute( this, UIStyleColorProperty.ColorShaderProperty, c, Colors.White );
|
|
colorPropertyName.propertyName = c;
|
|
colorPropertyName.Set( Material, color );
|
|
}
|
|
|
|
var numberProperties = imageType != null ? imageType.GetNumberShaderProperties() : [];
|
|
var numberPropertyName = new FloatPropertyName();
|
|
|
|
foreach ( var n in numberProperties )
|
|
{
|
|
var value = UINumber.Compute( this, UIStyleNumberProperty.FloatShaderProperty, n );
|
|
numberPropertyName.propertyName = n;
|
|
numberPropertyName.Set( Material, value );
|
|
}
|
|
|
|
}
|
|
|
|
public UIColor GetUIStyleColorProperty( UIStyleColorProperty property, string shaderPropertyName, UIStylePropertyContainer source )
|
|
{
|
|
if ( property != UIStyleColorProperty.ColorShaderProperty )
|
|
{
|
|
return null;
|
|
}
|
|
|
|
if ( imageType != null )
|
|
{
|
|
var uiColor = imageType.GetUIStyleColorProperty( property, shaderPropertyName );
|
|
|
|
if ( uiColor != null )
|
|
{
|
|
return uiColor;
|
|
}
|
|
}
|
|
|
|
var shaderUIColor = colorProperties.Find( c => c.colorPropertyName.propertyName == shaderPropertyName );
|
|
|
|
return shaderUIColor != null ? shaderUIColor.color : null;
|
|
|
|
}
|
|
|
|
public Font GetFont()
|
|
{
|
|
return null;
|
|
}
|
|
|
|
public Vector2 GetUISize()
|
|
{
|
|
return GetSize();
|
|
}
|
|
}
|
|
} |