2

I've been working on a C#/GDI graphical app for a couple years. I've spent a lot of time optimizing the drawing code. I am drawing to the screen by invalidating a PictureBox control about 10 times a second, and by leveraging subsequent OnPaint event that occurs when Windows triggers it. The OnPaint event gives me access to the Graphics object via the PaintEventArgs param.

Per frame: I draw hundreds of lines, hundreds of rectangles, and I call the Graphics.DrawString() method hundreds of times as well.

I started putting together a SharpDX project in hopes I could draw more 2D elements, and draw faster to the screen. I set up 2 test projects that draw the same 2D elements on the screen using GDI and using SharpDX. I used a C# StopWatch object to detect how long it was taking to draw all the 2D elements. So far, I have not noticed any speed improvement when drawing with SharpDX. Both GDI and SharpDX average about 20millis per draw.

How much of a speed improvement should I expect by using SharpDX? And which portion of the rasterization is supposed to make it faster than GDI?

BullsFan23
  • 23
  • 4
  • Have you tried this in full screen mode, using a release build? I'm no DirectX expert but from what I understand, full-screen exclusive drawing is a lot more performant. (Don't quote me on that.) BTW, plain old GDI is much faster than GDI+ - if you use functions like `DrawString`, you're using GDI+. – xxbbcc Jun 02 '15 at 21:17
  • Hi! Thanks for the feedback. This particular project will always run inside a window. Maybe the performance improvements people see with SharpDX over GDI are mostly full-screen applications? Interesting point about GDI vs GDI+.....I tried a few different ways of getting text drawn on the screen and DrawString was much faster than TextRenderer/DrawText in almost every case. Thanks - I'll do a little more digging. – BullsFan23 Jun 02 '15 at 21:47
  • Which part of SharpDX are you using? Direct2D or Direct3D (and in D3D case, which runtime version) – mrvux Jun 03 '15 at 15:12
  • I am only using Direct2D. – BullsFan23 Jun 04 '15 at 13:10

2 Answers2

1

I worked on a Windows Forms app where the "rendering system" was pluggable, and I initially wrote two rendering systems: one in GDI+, and one in Managed DirectX (a .NET wrapper around DirectX, similar to SharpDX). Because I was doing a lot of drawing of images at arbitrary scales, Managed DirectX blew GDI+ out of the water for our use case. Drawing code that used 1-pixel-wide lines was also very fast in Managed DirectX. Thick lines were much slower than single-pixel lines, because they were actually rendered as triangle strips (which can be drawn quickly by the GPU) whose coordinates had to be calculated by the CPU, and the geometry was complicated by segment joints (which were rounded, if I remember right). Fortunately, in our application we didn't need to draw curves, but those would have to be approximated by small line segments (for single-pixel widths) and triangles (for anything thicker).

It's things like CPU-based approximation and triangulation that slow a Direct3D app down. 3D games use pre-calculated meshes and make use of vertex buffers on the GPU to avoid moving data back and forth from the CPU to GPU. I don't have any data comparing speeds between GDI+ and DirectX, but these are some things to consider.

adv12
  • 8,443
  • 2
  • 24
  • 48
  • Hi! Thanks for sharing. Yes, I would like to have something similar, where the technology that actually draws to the screen is abstracted away and the rendering system becomes pluggable. – BullsFan23 Jun 04 '15 at 13:13
  • Hi adv12....I just added some simple rotation to my test case, and SharpDX became the clear winner. It was much, much faster! To me it seems that for untranslated, basic 2D shapes, SharpDX does not offer much of an edge. But as soon as I add some sort of translation, its clear that SharpDX becomes the obvious choice. – BullsFan23 Jun 04 '15 at 14:00
  • I can mark this as the accepted answer, although I would still like someone to confirm whether I should expect a speed boost or not when I'm just drawing non-translated basic 2D shapes and text. So far, it seems like the answer is simply "no" – BullsFan23 Jun 19 '15 at 14:53
  • Yeah, I don't know for sure. I was using Direct3D for 2D drawing because at the time there was no Direct2D, so I don't know details about Direct2D performance. Thanks for the accept, and good luck with your app. – adv12 Jun 19 '15 at 14:58
1

Direct2D takes a bit of getting used to, but once you get it up and running properly I can promise that you will never look back. I used it to migrate a very large project which was based on DirectDraw with GDI+ Interop and saw a huge performance increase as well as better stability and a more satisfying development experience.

It has received a lot of negative press about performance, particularly when it was first introduced but if you hook it up to a DXGI swap chain (which is very easy to do) and keep your code sensible, the benefits will be most clear.

SharpDX is the right choice and it will only get faster in the near future, with SSE/SIMD driven primitives just around the corner.

DirectlyX
  • 31
  • 2
  • Thanks for checking this out DirectlyX! In my software, I draw hundreds of non-scaled, non-rotated GDI rectangles every frame. I did quite a few side-by-side tests against SharpDX and did not notice any improvement. If I added rotation or scaling, SharpDX immediately became the obvious winner. To me it seems like since I'm not rotating or scaling any of my primitives, SharpDX does not currently offer any speed advantage. Can you clarify why you think I should see a large perf advantage in my case? – BullsFan23 Aug 18 '15 at 19:20
  • If you are not doing any transformation on your primitives, using Geometry Realization in Direct2D is the most efficient way to render. The primitives are cached in the GPU. In your case, doing it this way should free up the CPU overhead involved in doing hundreds of GDI calls. – DirectlyX Jan 20 '16 at 15:48
  • Very interesting! Thanks DirecltyX I will need to investigate this. – BullsFan23 Jan 21 '16 at 22:23