mirror of
https://github.com/sourcegit-scm/sourcegit.git
synced 2024-12-24 20:57:19 -08:00
enhance: new image alpha blend implementation
This commit is contained in:
parent
7a5279f717
commit
209f51da9e
2 changed files with 59 additions and 39 deletions
|
@ -21,8 +21,8 @@
|
||||||
<TextBlock Text="SIDE-BY-SIDE" FontSize="11"/>
|
<TextBlock Text="SIDE-BY-SIDE" FontSize="11"/>
|
||||||
</TabItem.Header>
|
</TabItem.Header>
|
||||||
|
|
||||||
<UniformGrid Rows="1" Margin="8,16" HorizontalAlignment="Center" VerticalAlignment="Center">
|
<UniformGrid Rows="1" Margin="0,16" HorizontalAlignment="Center" VerticalAlignment="Center">
|
||||||
<Grid RowDefinitions="Auto,*" IsVisible="{Binding Old, Converter={x:Static ObjectConverters.IsNotNull}}">
|
<Grid RowDefinitions="Auto,*" Margin="16,0" IsVisible="{Binding Old, Converter={x:Static ObjectConverters.IsNotNull}}">
|
||||||
<StackPanel Grid.Row="0" Orientation="Horizontal" HorizontalAlignment="Center">
|
<StackPanel Grid.Row="0" Orientation="Horizontal" HorizontalAlignment="Center">
|
||||||
<Border Height="16" Background="{DynamicResource Brush.Badge}" CornerRadius="8" VerticalAlignment="Center">
|
<Border Height="16" Background="{DynamicResource Brush.Badge}" CornerRadius="8" VerticalAlignment="Center">
|
||||||
<TextBlock Classes="monospace" Text="{DynamicResource Text.Diff.Binary.Old}" Margin="8,0" FontSize="10"/>
|
<TextBlock Classes="monospace" Text="{DynamicResource Text.Diff.Binary.Old}" Margin="8,0" FontSize="10"/>
|
||||||
|
@ -36,15 +36,16 @@
|
||||||
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
||||||
<Border Background="{DynamicResource Brush.Popup}" HorizontalAlignment="Center" Padding="8">
|
<Border Background="{DynamicResource Brush.Popup}" HorizontalAlignment="Center" Padding="8">
|
||||||
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}">
|
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}">
|
||||||
<v:ImageContainer>
|
<Grid>
|
||||||
|
<v:ImageContainer/>
|
||||||
<Image Source="{Binding Old}" Stretch="Uniform" VerticalAlignment="Center"/>
|
<Image Source="{Binding Old}" Stretch="Uniform" VerticalAlignment="Center"/>
|
||||||
</v:ImageContainer>
|
</Grid>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
|
||||||
<Grid RowDefinitions="Auto,*" Margin="32,0,0,0" IsVisible="{Binding New, Converter={x:Static ObjectConverters.IsNotNull}}">
|
<Grid RowDefinitions="Auto,*" Margin="16,0" IsVisible="{Binding New, Converter={x:Static ObjectConverters.IsNotNull}}">
|
||||||
<StackPanel Grid.Row="0" Orientation="Horizontal" HorizontalAlignment="Center">
|
<StackPanel Grid.Row="0" Orientation="Horizontal" HorizontalAlignment="Center">
|
||||||
<Border Height="16" Background="Green" CornerRadius="8" VerticalAlignment="Center">
|
<Border Height="16" Background="Green" CornerRadius="8" VerticalAlignment="Center">
|
||||||
<TextBlock Classes="monospace" Text="{DynamicResource Text.Diff.Binary.New}" Margin="8,0" FontSize="10"/>
|
<TextBlock Classes="monospace" Text="{DynamicResource Text.Diff.Binary.New}" Margin="8,0" FontSize="10"/>
|
||||||
|
@ -58,9 +59,10 @@
|
||||||
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
||||||
<Border Background="{DynamicResource Brush.Popup}" HorizontalAlignment="Center" Padding="8">
|
<Border Background="{DynamicResource Brush.Popup}" HorizontalAlignment="Center" Padding="8">
|
||||||
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}">
|
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}">
|
||||||
<v:ImageContainer>
|
<Grid>
|
||||||
|
<v:ImageContainer/>
|
||||||
<Image Source="{Binding New}" Stretch="Uniform" VerticalAlignment="Center"/>
|
<Image Source="{Binding New}" Stretch="Uniform" VerticalAlignment="Center"/>
|
||||||
</v:ImageContainer>
|
</Grid>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
|
@ -95,11 +97,9 @@
|
||||||
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
||||||
<Border HorizontalAlignment="Center" Background="{DynamicResource Brush.Window}">
|
<Border HorizontalAlignment="Center" Background="{DynamicResource Brush.Window}">
|
||||||
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}" Margin="8">
|
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}" Margin="8">
|
||||||
<v:ImageContainer>
|
|
||||||
<v:ImagesSwipeControl OldImage="{Binding Old}"
|
<v:ImagesSwipeControl OldImage="{Binding Old}"
|
||||||
NewImage="{Binding New}"
|
NewImage="{Binding New}"
|
||||||
RenderOptions.BitmapInterpolationMode="HighQuality"/>
|
RenderOptions.BitmapInterpolationMode="HighQuality"/>
|
||||||
</v:ImageContainer>
|
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
|
@ -133,12 +133,9 @@
|
||||||
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
<Border Grid.Row="1" Margin="0,12,0,0" Effect="drop-shadow(0 0 8 #A0000000)">
|
||||||
<Border HorizontalAlignment="Center" Background="{DynamicResource Brush.Window}">
|
<Border HorizontalAlignment="Center" Background="{DynamicResource Brush.Window}">
|
||||||
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}" Margin="8">
|
<Border BorderThickness="1" BorderBrush="{DynamicResource Brush.Border1}" Margin="8">
|
||||||
<v:ImageContainer>
|
|
||||||
<v:ImageBlendControl Alpha="{Binding #ImageBlendSlider.Value}"
|
<v:ImageBlendControl Alpha="{Binding #ImageBlendSlider.Value}"
|
||||||
OldImage="{Binding Old}"
|
OldImage="{Binding Old}"
|
||||||
NewImage="{Binding New}"
|
NewImage="{Binding New}"/>
|
||||||
RenderOptions.BitmapInterpolationMode="HighQuality"/>
|
|
||||||
</v:ImageContainer>
|
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
</Border>
|
</Border>
|
||||||
|
|
|
@ -9,10 +9,8 @@ using Avalonia.Styling;
|
||||||
|
|
||||||
namespace SourceGit.Views
|
namespace SourceGit.Views
|
||||||
{
|
{
|
||||||
public class ImageContainer : ContentControl
|
public class ImageContainer : Control
|
||||||
{
|
{
|
||||||
protected override Type StyleKeyOverride => typeof(ContentControl);
|
|
||||||
|
|
||||||
public override void Render(DrawingContext context)
|
public override void Render(DrawingContext context)
|
||||||
{
|
{
|
||||||
if (_bgBrush == null)
|
if (_bgBrush == null)
|
||||||
|
@ -54,7 +52,7 @@ namespace SourceGit.Views
|
||||||
private DrawingBrush _bgBrush = null;
|
private DrawingBrush _bgBrush = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public class ImagesSwipeControl : Control
|
public class ImagesSwipeControl : ImageContainer
|
||||||
{
|
{
|
||||||
public static readonly StyledProperty<double> AlphaProperty =
|
public static readonly StyledProperty<double> AlphaProperty =
|
||||||
AvaloniaProperty.Register<ImagesSwipeControl, double>(nameof(Alpha), 0.5);
|
AvaloniaProperty.Register<ImagesSwipeControl, double>(nameof(Alpha), 0.5);
|
||||||
|
@ -91,6 +89,8 @@ namespace SourceGit.Views
|
||||||
|
|
||||||
public override void Render(DrawingContext context)
|
public override void Render(DrawingContext context)
|
||||||
{
|
{
|
||||||
|
base.Render(context);
|
||||||
|
|
||||||
var alpha = Alpha;
|
var alpha = Alpha;
|
||||||
var w = Bounds.Width;
|
var w = Bounds.Width;
|
||||||
var h = Bounds.Height;
|
var h = Bounds.Height;
|
||||||
|
@ -199,7 +199,7 @@ namespace SourceGit.Views
|
||||||
private bool _lastInSlider = false;
|
private bool _lastInSlider = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public class ImageBlendControl : Control
|
public class ImageBlendControl : ImageContainer
|
||||||
{
|
{
|
||||||
public static readonly StyledProperty<double> AlphaProperty =
|
public static readonly StyledProperty<double> AlphaProperty =
|
||||||
AvaloniaProperty.Register<ImageBlendControl, double>(nameof(Alpha), 1.0);
|
AvaloniaProperty.Register<ImageBlendControl, double>(nameof(Alpha), 1.0);
|
||||||
|
@ -236,30 +236,50 @@ namespace SourceGit.Views
|
||||||
|
|
||||||
public override void Render(DrawingContext context)
|
public override void Render(DrawingContext context)
|
||||||
{
|
{
|
||||||
|
base.Render(context);
|
||||||
|
|
||||||
var rect = new Rect(0, 0, Bounds.Width, Bounds.Height);
|
var rect = new Rect(0, 0, Bounds.Width, Bounds.Height);
|
||||||
var alpha = Alpha;
|
var alpha = Alpha;
|
||||||
var left = OldImage;
|
var left = OldImage;
|
||||||
var right = NewImage;
|
var right = NewImage;
|
||||||
|
|
||||||
var drawLeft = left != null && alpha < 1.0;
|
var drawLeft = left != null && alpha < 1.0;
|
||||||
var drawRight = right != null && alpha > 0;
|
var drawRight = right != null && alpha > 0;
|
||||||
|
var psize = left == null ? right.PixelSize : left.PixelSize;
|
||||||
|
var dpi = left == null ? right.Dpi : left.Dpi;
|
||||||
|
|
||||||
|
using (var rt = new RenderTargetBitmap(psize, dpi))
|
||||||
|
{
|
||||||
|
var rtRect = new Rect(rt.Size);
|
||||||
|
using (var dc = rt.CreateDrawingContext())
|
||||||
|
{
|
||||||
if (drawLeft)
|
if (drawLeft)
|
||||||
{
|
{
|
||||||
using (context.PushRenderOptions(new RenderOptions() { BitmapBlendingMode = BitmapBlendingMode.Source }))
|
|
||||||
using (context.PushOpacity(1 - alpha))
|
|
||||||
context.DrawImage(left, rect);
|
|
||||||
|
|
||||||
if (drawRight)
|
if (drawRight)
|
||||||
{
|
{
|
||||||
using (context.PushRenderOptions(new RenderOptions() { BitmapBlendingMode = BitmapBlendingMode.Plus }))
|
using (dc.PushRenderOptions(RO_SRC))
|
||||||
using (context.PushOpacity(alpha))
|
using (dc.PushOpacity(1 - alpha))
|
||||||
context.DrawImage(right, rect);
|
dc.DrawImage(left, rtRect);
|
||||||
|
|
||||||
|
using (dc.PushRenderOptions(RO_DST))
|
||||||
|
using (dc.PushOpacity(alpha))
|
||||||
|
dc.DrawImage(right, rtRect);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
using (dc.PushRenderOptions(RO_SRC))
|
||||||
|
using (dc.PushOpacity(1 - alpha))
|
||||||
|
dc.DrawImage(left, rtRect);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (drawRight)
|
else if (drawRight)
|
||||||
{
|
{
|
||||||
using (context.PushOpacity(alpha))
|
using (dc.PushRenderOptions(RO_SRC))
|
||||||
context.DrawImage(right, rect);
|
using (dc.PushOpacity(alpha))
|
||||||
|
dc.DrawImage(right, rtRect);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
context.DrawImage(rt, rtRect, rect);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -290,6 +310,9 @@ namespace SourceGit.Views
|
||||||
|
|
||||||
return new Size(scale * img.Width, scale * img.Height);
|
return new Size(scale * img.Width, scale * img.Height);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static readonly RenderOptions RO_SRC = new RenderOptions() { BitmapBlendingMode = BitmapBlendingMode.Source, BitmapInterpolationMode = BitmapInterpolationMode.HighQuality };
|
||||||
|
private static readonly RenderOptions RO_DST = new RenderOptions() { BitmapBlendingMode = BitmapBlendingMode.Plus, BitmapInterpolationMode = BitmapInterpolationMode.HighQuality };
|
||||||
}
|
}
|
||||||
|
|
||||||
public partial class ImageDiffView : UserControl
|
public partial class ImageDiffView : UserControl
|
||||||
|
|
Loading…
Reference in a new issue