tags:

views:

68

answers:

1

What is the best approach to render charts and then save them on a hard drive for further distribution using WPF? I found a number of ways to accomplish this by using the following types:

  1. DrawingVisual - creating a object of this type and then rendering graphics on its context;
  2. Shape - deriving from the Shape class and then overriding its DefiningGeometry property where the actual rendering is happening;
  3. PathFigure - adding LineSegment-s to an instance of this class and then adding this instance to a Canvas;
  4. Adorner - deriving from it and then overriding its OnRender method;
  5. WritableBitmap - rendering on it and then adding the bitmap to a Canvas.

Of course I'm going to write an app to test how fast each of these will be. But can anybody tell me:

  • whether am I on the right track?
  • are there any other means to do such rendering?
  • which one of them is the best in terms of performance?
+1  A: 

It all depends on your actual usage, in your case you mention saving on the hard drive for "further distribution" - I'm going to assume you are saving them as an image (jpg or png) and not as wpf objects (xaml).

  1. You should consider if WPF is the right tool for the job, WPF is a UI framework and not a generic image processing library, it may be best to use something else entirely for generating images.

  2. For a reasonable number of points your performance bottleneck will be encoding the image and saving it to disk - not actually rendering it - so you should choose the method that is easier for you to code.

  3. All the articles about high performance WPF charts are a: about charts with 10,000 points and more (because that is where the performance problems are), b: about charts you display in your GUI (because otherwise you can use an image processing library to create the bitmap) and c: charts that change all the time (so they work nicely with data binding) - there's a reason why they don't talk about saving charts to disk.

  4. For a very large number of points:

    • The fastest way to draw in WPF is to inherit from FrameworkElement (not Adorner) and override OnRender.
    • When the data changes often it is recommended to use multiple DrawingVisual objects because then you don't have to re-render everything when one value change - but this is not relevant for you since the image won't change after you save it anyway.
    • WritableBitmap is used for raw bitmap access, you use it when you decide to give up on all the nice layout and drawing WPF gives you because you can't take the overhead, if this is the case you should re-read my first point above.

So, to summarize, you are asking the wrong question :-) if you need to save images to disk than either the WPF rendering speed is not your bottleneck or you shouldn't be using WPF to begin with. If you do use WPF just pick whatever is easiest for you to code.

BTW: Adorners are used to display "floating" elements above the normal UI, you can use them for tooltip-like features but not for the main chart rendering (and you probably don't want them at all since your main usage is saving the image to disk), FrameworkElement is the base class you are looking for.

Nir
Thanks, Nir, for your answer. Having read it, I realize that I asked the wrong question )
Serge