Browse Source

Keeping it simple, ColorTransition will now just use sRGB premultiplied space

color interpolation.
pull/1461/head
Jumar Macato 8 years ago
parent
commit
7247d53d6d
  1. 33
      src/Avalonia.Animation/ColorInterpolationMode.cs
  2. 67
      src/Avalonia.Visuals/Animation/Transitions/ColorTransition.cs

33
src/Avalonia.Animation/ColorInterpolationMode.cs

@ -1,33 +0,0 @@
namespace Avalonia.Animation
{
/// <summary>
/// Defines the intermediate color space
/// in which the color interpolation will be done.
/// </summary>
public enum ColorInterpolationMode
{
/// <summary>
/// Premultiply the alpha component and interpolate from RGB color space.
/// </summary>
PremultipliedRGB,
/// <summary>
/// Directly interpolate from RGB color space.
/// Fastest but the least accurate, perception-wise.
/// </summary>
RGB,
/// <summary>
/// Converts RGB into HSV color space and interpolates.
/// Slow but accurate, perception-wise.
/// </summary>
HSV,
/// <summary>
/// Converts RGB into HSV color space and interpolates.
/// Slowest but the most accurate, perception-wise.
/// </summary>
LAB,
}
}

67
src/Avalonia.Visuals/Animation/Transitions/ColorTransition.cs

@ -11,73 +11,30 @@ namespace Avalonia.Animation.Transitions
{
/// <summary>
/// Transition class that handles <see cref="AvaloniaProperty"/> with <see cref="SolidColorBrush"/> types.
/// TODO: Must be refactored to handle object creation.
/// TODO: Must be refactored to handle object creation every frame.
/// </summary>
public class ColorTransition : Transition<SolidColorBrush>
{
/// <summary>
/// Defines the <see cref="AnimationPlayState"/> property.
/// </summary>
public static readonly DirectProperty<ColorTransition, ColorInterpolationMode> InterpolationModeProperty =
AvaloniaProperty.RegisterDirect<ColorTransition, ColorInterpolationMode>(
nameof(InterpolationMode),
o => o.InterpolationMode,
(o, v) => o.InterpolationMode = v);
/// <summary>
/// Gets or sets the state of the animation for this
/// control.
/// </summary>
public ColorInterpolationMode InterpolationMode
{
get { return _interpolationMode; }
set { SetAndRaise(InterpolationModeProperty, ref _interpolationMode, value); }
}
private ColorInterpolationMode _interpolationMode;
public override IObservable<SolidColorBrush> DoTransition(IObservable<double> progress, SolidColorBrush oldValue, SolidColorBrush newValue)
{
var oldColor = new Vector4(oldValue.Color.R, oldValue.Color.G, oldValue.Color.B, oldValue.Color.A);
var newColor = new Vector4(newValue.Color.R, newValue.Color.G, newValue.Color.B, oldValue.Color.A);
oldColor = oldColor / 255f;
newColor = newColor / 255f;
var deltaColor = newColor - oldColor;
var premultOV = new Vector4(oldColor.W, oldColor.W, oldColor.W, 1);
var premultNV = new Vector4(newColor.W, newColor.W, newColor.W, 1);
switch (InterpolationMode)
{
case ColorInterpolationMode.PremultipliedRGB:
var premultOV = new Vector4(oldColor.W, oldColor.W, oldColor.W, 1);
var premultNV = new Vector4(newColor.W, newColor.W, newColor.W, 1);
oldColor *= premultOV;
newColor *= premultNV;
return progress
.Select(p =>
{
var time = (float)Easing.Ease(p);
var interpolatedColor = (deltaColor * time) + oldColor;
return new SolidColorBrush(Color.FromVector4(interpolatedColor, true));
});
case ColorInterpolationMode.RGB:
return progress
.Select(p =>
{
var time = (float)Easing.Ease(p);
var interpolatedColor = (deltaColor * time) + oldColor;
return new SolidColorBrush(Color.FromVector4(interpolatedColor, true));
});
default:
throw new NotImplementedException($"'{Enum.GetName(typeof(ColorInterpolationMode), InterpolationMode)}' color interpolation is not supported.");
}
oldColor *= premultOV;
newColor *= premultNV;
return progress
.Select(p =>
{
var time = (float)Easing.Ease(p);
var interpolatedColor = (deltaColor * time) + oldColor;
return new SolidColorBrush(Color.FromVector4(interpolatedColor, true));
});
}
}
}

Loading…
Cancel
Save