Reputation: 99
I am saving the rendered image using render target bitmap, and it is saved properly in the given size, but when I set background to the grid in which image is placed, I am getting different output. Can any one explain this behavior?
<Grid x:Name="grid1" Grid.Row="0" Background="Red">
<Image x:Name="image1" Source="Images/butterfly.jpg" >
</Image>
</Grid>
Code behind
RenderTargetBitmap result = GetImage(this.grid1);
Stream imageStream = new MemoryStream();
SaveAsPng(result, imageStream);
public static RenderTargetBitmap GetImage(Grid view)
{
Size size = new Size(1122, 750);
if (size.IsEmpty)
return null;
RenderTargetBitmap result = new RenderTargetBitmap((int)size.Width, (int)size.Height, 96, 96, PixelFormats.Pbgra32);
DrawingVisual drawingvisual = new DrawingVisual();
using (DrawingContext context = drawingvisual.RenderOpen())
{
context.DrawRectangle(new VisualBrush(view), null, new Rect(new Point(), size));
context.Close();
}
result.Render(drawingvisual);
return result;
}
public static void SaveAsPng(RenderTargetBitmap src, Stream outputStream)
{
var saveFileDialog = new SaveFileDialog()
{
Filter = "Image Files (*.bmp, *.png, *.jpg)|*.bmp;*.png;*.jpg"
};
if (saveFileDialog.ShowDialog() == true)
{
var encoder = new PngBitmapEncoder();
encoder.Frames.Add(BitmapFrame.Create(src));
using (FileStream stream = new FileStream(saveFileDialog.FileName, FileMode.Create))
encoder.Save(stream);
}
}
Without Background With Background
Upvotes: 0
Views: 888
Reputation: 128061
In order to retain the original element dimensions in the DrawingVisual, you should set the VisualBrush's Stretch
to None
. If necessary, you can also get precise control of the placement of the visual by setting the VisualBrush's Viewport
, Viewbox
, AlignmentX
and AlignmentY
properties.
Also consider passing the result size as an argument to your GetImage
method, and use the most general type for the view
argument:
public static BitmapSource GetImage(Visual view, Size size)
{
var bitmap = new RenderTargetBitmap(
(int)size.Width, (int)size.Height, 96, 96, PixelFormats.Pbgra32);
var visualBrush = new VisualBrush
{
Visual = view,
Stretch = Stretch.None
};
var drawingvisual = new DrawingVisual();
using (var context = drawingvisual.RenderOpen())
{
context.DrawRectangle(visualBrush, null, new Rect(size));
}
bitmap.Render(drawingvisual);
return bitmap;
}
Also make the SaveAsPng
method more flexible by changing the argument type. The outputStream
argument isn't used at all, so remove it.
public static void SaveAsPng(BitmapSource src)
Then call both methods like this:
var result = GetImage(grid1, new Size(1122, 750));
SaveAsPng(result);
Upvotes: 3