3

I am creating a WPF application with a Viewport3D and inside the viewport I have meshes with text on them. The text is different for each of the mesh. (This means that I can have a single reference for a material for the regular meshes, but for the text I need to create different materials every time.) I have also froze all the regular meshes since they are static.

However I can create any number of meshes, with a SolidColorBrush, that I want and the performance stays stable. (I have tried up to about 700 - 800 meshes)

However if I implement the text meshes the performance drops drastically. For example when I have around 200 regular Meshes and 200 text Meshes, the performance is very bad.

I have tried two different ways to render text; - I have tried rendering text as a Viewport2DVisual3D. (However I presume this is a terrible way, since it means in my prior example there are 200 viewports additional to the Viewport3D itself.) - I have tried rendering text as a GeometryModel3D, so the creation is the same as the regular brushes. However the material consists of a VisualBrush instead of a SolidColorBrush. (This does enhance the performance quite a bit, but still not perfect)

Does anyone have solutions to further enhance my performance with rendering text, so that I can render many more?

(I already followed most of the performance guidelines on the following site: https://msdn.microsoft.com/en-us/library/bb613553%28v=vs.110%29.aspx)

@edit: I have found that if I do the following with a visualbrush:

VisualBrush v = new VisualBrush(Text.createCubeStackText(text1));
RenderOptions.SetCachingHint(v, CachingHint.Cache);
viewport.Material = new DiffuseMaterial(v);

It improves the performance really much. I have tried, and can now render 700 regular meshes and 300 text meshes without any performance problems. Performance starts to drop with 550 text meshes and 550 regular meshes.

(I would still like any other suggestion though.)

Revils
  • 1,478
  • 1
  • 14
  • 31
  • 1
    Have you tried to freeze your Brushes? – Tomtom Mar 12 '15 at 09:45
  • Yes that was the first thing that I have tried – Revils Mar 12 '15 at 09:50
  • Side note: do not compare numbers of meshes, compare number of triangles. 3D text consists of many, many triangles. – Emond Mar 12 '15 at 14:44
  • Ah yeah, that is a good point. My application consists of cubes hence 12 triangles. My text is a Visualbrush printed on a geometrymodel3d so this is only two triangles. per text – Revils Mar 12 '15 at 17:08

1 Answers1

1

Text in 3D can be very slow due to the tessellation that is needed to render the text. You might want to consider:

  1. Remove the 3D rendering of text by overlaying the 3DViewport with a canvas and calculate the proper location of the text and render the text as a 2D overlay. You could even change the font size dependent on the Z value of the text's position

  2. Render the text to a (transparent) bitmap and add the text as a texture to a billboard in the 3D scene

Use IsHitTestVisible=false to click-through the overlay and project the 3D position of the text to the canvas by using this: Projecting a 3D point to a 2D screen coordinate

Community
  • 1
  • 1
Emond
  • 50,210
  • 11
  • 84
  • 115
  • I thought about your first suggestion before I implemented the text as a mesh. But how can I calculate the movement relative to the 3D position inside the Viewport? (If I scroll the viewport, the mesh in 3d has to move the same relative amount of the label in 2d) Furthermore, what about hit testing, when I want to click or scroll on a mesh and the 2D text is in front of that. Will it work? – Revils Mar 12 '15 at 10:17
  • You could switch off hittesting for the overlay so you would click-through. To keep the overlay in sync with the 3D projection you would need to project the 3D position to the overlay (which is just applying the projection transformation based on the camera) – Emond Mar 12 '15 at 10:43
  • The problem is that I need hittesting for the functions of my application. – Revils Mar 12 '15 at 14:08
  • @Sliver2009 - I added to my answer some details about your comments – Emond Mar 12 '15 at 14:08
  • @Sliver2009 - You can disable the hit testing for just the labels – Emond Mar 12 '15 at 14:09