public void ShouldDrawRects() { var color = Color.CornflowerBlue; var rect = new Rectangle(0, 0, 6, 4); // Ignoring the bottom line due to rendering inconsistency bug // https://bugzilla.libsdl.org/show_bug.cgi?id=3182 var expected = new [] { 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, }.Select(v => v > 0 ? color : Color.Black) .Select(c => new ColorRGB888(c)) .ToArray(); graphics.Clear(Color.Black); graphics.SetDrawingColor(color); graphics.DrawRects( new Rectangle(0, 0, 3, 5), new Rectangle(3, 0, 3, 5) ); var pixels = new ColorRGB888[graphics.GetPixelBufferSize(rect)]; graphics.ReadPixels(ref pixels, rect); pixels.Should().Equal(expected); }
public void ShouldFillRects() { var color = Color.CornflowerBlue; var rect = new Rectangle(0, 0, 5, 5); var expected = new [] { 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1 }.Select(v => v > 0 ? color : Color.Black) .Select(c => new ColorRGB888(c)) .ToArray(); graphics.Clear(Color.Black); graphics.SetDrawingColor(color); graphics.FillRects( new Rectangle(0, 0, 3, 3), new Rectangle(3, 3, 2, 2) ); var pixels = new ColorRGB888[graphics.GetPixelBufferSize(rect)]; graphics.ReadPixels(ref pixels, rect); pixels.Should().Equal(expected); }
public void ShouldSaveAndLoadTextureFromPng() { var color = new ColorRGB888( Color.FromArgb(unchecked ((int)0xFFC0FFEE)) ); var size = graphics.OutputSize; // Prepare a texture, draw it and save framebuffer contents var texture = graphics.CreateTexture(size.Width, size.Height); var pixels = Enumerable.Repeat(color, texture.PixelCount).ToArray(); texture.SetPixels(ref pixels); graphics.Clear(Color.Black); graphics.Draw(texture); var ms = new MemoryStream(); graphics.SaveAsPng(ms); ms.Seek(0, SeekOrigin.Begin); // Recreate same texture from framebuffer data, draw and compare var sameTexture = TextureFactory.FromStream(graphics, ms, TextureScalingQuality.Nearest, new PngDecoder()); var samePixels = new ColorRGB888[pixels.Length]; graphics.Clear(Color.Black); graphics.Draw(texture); graphics.ReadPixels(ref samePixels); samePixels.Should().Equal(pixels); }
public void ShouldSetBytesInRectangle() { var width = 10; var height = 10; var rectangle = new Rectangle(5, 5, width, height); var format = PixelFormat.Format_RGB888; var texture = graphics.CreateTexture( graphics.OutputSize.Width, graphics.OutputSize.Height, format: format); var pixels = new byte[width * height * format.GetBytesPerPixel()]; for (int i = 0; i < pixels.Length; i++) { pixels[i] = 255; } texture.SetPixels(ref pixels, rectangle); graphics.Draw(texture); var actual = new ColorRGB888[width * height]; graphics.ReadPixels(ref actual, rectangle); actual.Distinct().Should().BeEquivalentTo( new ColorRGB888(Color.White) ); }
/// <summary> /// Saves the graphics using the specified save action. /// </summary> /// <example> /// graphics.Save(image => image.SaveAsJpeg("file.jpg")) /// </example> public static void Save(this Graphics graphics, Action <Image <Rgba32> > onSave) { var targetFormat = PixelFormat.Format_ABGR8888; var size = graphics.OutputSize; var pixelData = new ColorRGB888[graphics.PixelCount]; graphics.ReadPixels(ref pixelData); var pixelHandle = GCHandle.Alloc(pixelData, GCHandleType.Pinned); try { var image = new Image <Rgba32>(size.Width, size.Height); unsafe { fixed(void *target = &MemoryMarshal.GetReference(image.GetPixelSpan())) { Pixels.Convert(size.Width, size.Height, 4 * size.Width, 4 * size.Width, PixelFormat.Format_RGB888, targetFormat, pixelHandle.AddrOfPinnedObject(), (IntPtr)target); } } onSave(image); image.Dispose(); } finally { pixelHandle.Free(); } }
public static void OutputIsCloseTo(this Graphics graphics, string pathToReferenceImage, float tolerance = 0.05f) { if (!File.Exists(pathToReferenceImage)) { graphics.SaveAsPng(pathToReferenceImage); throw new FileNotFoundException("No reference present, generated one"); } var reference = SurfaceFactory.FromFile(pathToReferenceImage); if (reference.Size != graphics.OutputSize) { throw new ArgumentException("Wrong reference image size"); } var refPixels = new ColorRGB888[reference.PixelCount]; reference.ReadPixels(ref refPixels); var ms = new MemoryStream(); graphics.SaveAsPng(ms); ms.Seek(0, SeekOrigin.Begin); var actual = SurfaceFactory.FromStream(ms, new PngDecoder()); var actualPixels = new ColorRGB888[reference.PixelCount]; actual.ReadPixels(ref actualPixels); reference.Dispose(); actual.Dispose(); var difference = 0.0f; for (int i = 0; i < refPixels.Length; i++) { var refColor = refPixels[i]; var actualColor = actualPixels[i]; if (refColor.Equals(actualColor)) { continue; } difference += Math.Abs(refColor.R - actualColor.R) / 255.0f; difference += Math.Abs(refColor.G - actualColor.G) / 255.0f; difference += Math.Abs(refColor.B - actualColor.B) / 255.0f; } difference /= reference.PixelCount; difference.Should().BeLessOrEqualTo(tolerance); }
public void ShouldSetAllTexturePixels() { var color = Color.CornflowerBlue; var size = graphics.OutputSize; var texture = graphics.CreateTexture(size.Width, size.Height); var pixels = Enumerable.Repeat(new ColorRGB888(color), texture.PixelCount) .ToArray(); texture.SetPixels(ref pixels); graphics.Draw(texture); var actual = new ColorRGB888[texture.PixelCount]; graphics.ReadPixels(ref actual); actual.Should().BeEquivalentTo(pixels); }
public void ShouldReadPixelsFromFramebuffer() { var color = Color.CornflowerBlue; var readBuffer = new ColorRGB888[graphics.PixelCount]; graphics.Clear(Color.Black); graphics.ReadPixels(ref readBuffer); readBuffer.Distinct().Should().BeEquivalentTo(new ColorRGB888()); graphics.Clear(color); app.Tick(); graphics.Clear(color); graphics.ReadPixels(ref readBuffer); readBuffer.Distinct().Should().BeEquivalentTo(new ColorRGB888(color)); }
public void ShouldSaveFramebufferData() { var color = Color.CornflowerBlue.WithoutName(); graphics.Clear(color); var ms = new MemoryStream(); graphics.SaveAsPng(ms); ms.Seek(0, SeekOrigin.Begin); var surface = SurfaceFactory.FromStream(ms, new PngDecoder()); var pixels = new ColorRGB888[surface.PixelCount]; surface.ReadPixels(ref pixels); pixels.Distinct().Select(c => c.AsColor()) .Should().BeEquivalentTo(color); }
public void ShouldReadPixelsFromFramebufferInRectangle() { var color = Color.CornflowerBlue; var rectangle = new Rectangle(5, 5, 10, 10); var readBuffer = new ColorRGB888[graphics.GetPixelBufferSize(rectangle)]; graphics.Clear(Color.Black); graphics.ReadPixels(ref readBuffer, rectangle); readBuffer.Distinct().Should().BeEquivalentTo(new ColorRGB888()); var texture = graphics.CreateTexture(rectangle.Width, rectangle.Height); var textureData = Enumerable.Repeat(new ColorRGB888(color), texture.PixelCount).ToArray(); texture.SetPixels(ref textureData); graphics.Draw(texture, dstRect: rectangle); graphics.ReadPixels(ref readBuffer, rectangle); readBuffer.Distinct().Should().BeEquivalentTo(new ColorRGB888(color)); }
public void ShouldSetTexturePixelsInRectangle(PixelFormat format) { var screenSize = graphics.OutputSize; var portion = new Rectangle(5, 10, 15, 20); var texture = graphics.CreateTexture(screenSize.Width, screenSize.Height, format: format); var pixelCount = texture.GetPixelBufferSize <ColorRGB888>(portion); var pixels = new ColorRGB888[pixelCount]; for (int i = 0; i < pixelCount; i++) { pixels[i] = new ColorRGB888( Color.FromArgb(i % 200 + 55, i % 200 + 55, i % 200 + 55)); } texture.SetPixels(ref pixels, portion); graphics.Draw(texture); var actual = new ColorRGB888[pixelCount]; graphics.ReadPixels(ref actual, portion); actual.Should().BeEquivalentTo(pixels); }
public void ShouldDrawInSpecifiedRectangles(Rectangle?src, Rectangle?dst) { var color = new ColorRGB888(Color.CornflowerBlue); var size = graphics.OutputSize; var texture = graphics.CreateTexture( dst?.Width ?? size.Width, dst?.Height ?? size.Height); var pixels = Enumerable.Repeat( color, texture.GetPixelBufferSize <ColorRGB888>(src) ).ToArray(); texture.SetPixels(ref pixels, src); graphics.Clear(Color.Black); graphics.Draw(texture, src, dst); var portion = Project(texture, src, dst); var actual = new ColorRGB888[graphics.GetPixelBufferSize(portion)]; graphics.ReadPixels(ref actual, portion); actual.Distinct().Should().BeEquivalentTo(color); }
public void ShouldRotateAndDraw(Rectangle?src, Rectangle?dst, int angleIn90DegIncrements, Point?center) { var color = new ColorRGB888(Color.CornflowerBlue); var size = graphics.OutputSize; var texture = graphics.CreateTexture( dst?.Width ?? size.Width, dst?.Height ?? size.Height); var pixels = new ColorRGB888[ texture.GetPixelBufferSize <ColorRGB888>(src) ]; for (int i = 0; i < pixels.Length; i++) { pixels[i] = new ColorRGB888(Color.FromArgb( i % 255, i % 255, i % 255 )); } texture.SetPixels(ref pixels, src); for (int i = 0; i < angleIn90DegIncrements; i++) { pixels = RotateArrayClockwise(pixels, i % 2 == 0 ? texture.Width : texture.Height, i % 2 == 0 ? texture.Height : texture.Width); } graphics.Clear(Color.Black); graphics.Draw(texture, src, dst, angleIn90DegIncrements * 90, center); var portion = Project(texture, src, dst, angleIn90DegIncrements, center); var actual = new ColorRGB888[graphics.GetPixelBufferSize(portion)]; graphics.ReadPixels(ref actual, portion); actual.Should().Equal(pixels); }