1
0
mirror of https://github.com/ppy/osu.git synced 2024-09-24 09:27:24 +08:00
osu-lazer/osu.Game/Graphics/UserInterface/DialogButton.cs
Dean Herbert 4f6263ef86 Make many internal classes and methods public
This is important when using dynamic compiling to rapidly iterate. Until we actually split projects out into pieces (like the abstract ruleset project we have talked about) there is no advantage to using internal in the osu! game code.
2017-11-21 12:06:16 +09:00

274 lines
9.6 KiB
C#

// Copyright (c) 2007-2017 ppy Pty Ltd <contact@ppy.sh>.
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
using OpenTK;
using OpenTK.Graphics;
using osu.Framework.Graphics;
using osu.Framework.Graphics.Colour;
using osu.Framework.Graphics.Shapes;
using osu.Framework.Graphics.Sprites;
using osu.Framework.Graphics.Containers;
using osu.Game.Graphics.Backgrounds;
using osu.Game.Graphics.Sprites;
using osu.Framework.Extensions.Color4Extensions;
using osu.Game.Graphics.Containers;
namespace osu.Game.Graphics.UserInterface
{
public class DialogButton : OsuClickableContainer
{
private const float hover_width = 0.9f;
private const float hover_duration = 500;
private const float glow_fade_duration = 250;
private const float click_duration = 200;
private Color4 buttonColour;
public Color4 ButtonColour
{
get
{
return buttonColour;
}
set
{
buttonColour = value;
updateGlow();
colourContainer.Colour = value;
}
}
private Color4 backgroundColour = OsuColour.Gray(34);
public Color4 BackgroundColour
{
get
{
return backgroundColour;
}
set
{
backgroundColour = value;
background.Colour = value;
}
}
private string text;
public string Text
{
get
{
return text;
}
set
{
text = value;
spriteText.Text = Text;
}
}
private float textSize = 28;
public float TextSize
{
get
{
return textSize;
}
set
{
textSize = value;
spriteText.TextSize = value;
}
}
private readonly Container backgroundContainer;
private readonly Container colourContainer;
private readonly Container glowContainer;
private readonly Box leftGlow;
private readonly Box centerGlow;
private readonly Box rightGlow;
private readonly Box background;
private readonly SpriteText spriteText;
private Vector2 hoverSpacing => new Vector2(3f, 0f);
private bool didClick; // Used for making sure that the OnMouseDown animation can call instead of OnHoverLost's when clicking
public override bool ReceiveMouseInputAt(Vector2 screenSpacePos) => backgroundContainer.ReceiveMouseInputAt(screenSpacePos);
protected override bool OnClick(Framework.Input.InputState state)
{
didClick = true;
colourContainer.ResizeTo(new Vector2(1.5f, 1f), click_duration, Easing.In);
flash();
this.Delay(click_duration).Schedule(delegate
{
colourContainer.ResizeTo(new Vector2(0.8f, 1f));
spriteText.Spacing = Vector2.Zero;
glowContainer.FadeOut();
});
return base.OnClick(state);
}
protected override bool OnHover(Framework.Input.InputState state)
{
spriteText.TransformSpacingTo(hoverSpacing, hover_duration, Easing.OutElastic);
colourContainer.ResizeTo(new Vector2(hover_width, 1f), hover_duration, Easing.OutElastic);
glowContainer.FadeIn(glow_fade_duration, Easing.Out);
base.OnHover(state);
return true;
}
protected override void OnHoverLost(Framework.Input.InputState state)
{
if (!didClick)
{
colourContainer.ResizeTo(new Vector2(0.8f, 1f), hover_duration, Easing.OutElastic);
spriteText.TransformSpacingTo(Vector2.Zero, hover_duration, Easing.OutElastic);
glowContainer.FadeOut(glow_fade_duration, Easing.Out);
}
didClick = false;
}
private void flash()
{
var flash = new Box
{
RelativeSizeAxes = Axes.Both
};
colourContainer.Add(flash);
flash.Colour = ButtonColour;
flash.Blending = BlendingMode.Additive;
flash.Alpha = 0.3f;
flash.FadeOutFromOne(click_duration);
flash.Expire();
}
private void updateGlow()
{
leftGlow.Colour = ColourInfo.GradientHorizontal(new Color4(ButtonColour.R, ButtonColour.G, ButtonColour.B, 0f), ButtonColour);
centerGlow.Colour = ButtonColour;
rightGlow.Colour = ColourInfo.GradientHorizontal(ButtonColour, new Color4(ButtonColour.R, ButtonColour.G, ButtonColour.B, 0f));
}
public DialogButton()
{
RelativeSizeAxes = Axes.X;
Children = new Drawable[]
{
backgroundContainer = new Container
{
RelativeSizeAxes = Axes.Both,
Width = 1f,
Children = new Drawable[]
{
background = new Box
{
RelativeSizeAxes = Axes.Both,
Colour = backgroundColour,
},
},
},
glowContainer = new Container
{
RelativeSizeAxes = Axes.Both,
Width = 1f,
Alpha = 0f,
Children = new Drawable[]
{
leftGlow = new Box
{
RelativeSizeAxes = Axes.Both,
Origin = Anchor.TopLeft,
Anchor = Anchor.TopLeft,
Width = 0.125f,
},
centerGlow = new Box
{
RelativeSizeAxes = Axes.Both,
Origin = Anchor.Centre,
Anchor = Anchor.Centre,
Width = 0.75f,
},
rightGlow = new Box
{
RelativeSizeAxes = Axes.Both,
Origin = Anchor.TopRight,
Anchor = Anchor.TopRight,
Width = 0.125f,
},
},
},
new Container
{
RelativeSizeAxes = Axes.Both,
Origin = Anchor.Centre,
Anchor = Anchor.Centre,
Masking = true,
Children = new Drawable[]
{
colourContainer = new Container
{
RelativeSizeAxes = Axes.Both,
Origin = Anchor.Centre,
Anchor = Anchor.Centre,
Width = 0.8f,
Masking = true,
MaskingSmoothness = 2,
EdgeEffect = new EdgeEffectParameters
{
Type = EdgeEffectType.Shadow,
Colour = Color4.Black.Opacity(0.2f),
Radius = 5,
},
Colour = ButtonColour,
Shear = new Vector2(0.2f, 0),
Children = new Drawable[]
{
new Box
{
EdgeSmoothness = new Vector2(2, 0),
RelativeSizeAxes = Axes.Both,
},
new Container
{
RelativeSizeAxes = Axes.Both,
Masking = true,
MaskingSmoothness = 0,
Children = new[]
{
new Triangles
{
RelativeSizeAxes = Axes.Both,
TriangleScale = 4,
ColourDark = OsuColour.Gray(0.88f),
Shear = new Vector2(-0.2f, 0),
},
},
},
},
},
},
},
spriteText = new OsuSpriteText
{
Text = Text,
Anchor = Anchor.Centre,
Origin = Anchor.Centre,
TextSize = 28,
Font = "Exo2.0-Bold",
Shadow = true,
ShadowColour = new Color4(0, 0, 0, 0.1f),
Colour = Color4.White,
},
};
updateGlow();
}
}
}