Jump to content
  • Advertisement
Sign in to follow this  
Endurion

DX11 D3D11 - Bitmap Font Rendering

This topic is 872 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi,

I'm currently working on an D3D11 module for my engine. I've got it to work fine mostly and I can now switch between DX8, DX9 and DX11 (with shaders).

However I have extreme performance problems with text rendering. I'm using bitmap fonts, and the naive approach, that worked fine for DX8 and DX9 used single quads per letter and DrawPrimitiveUP. Obviously that's not available anymore with DX11.

For DX11 my simple implementation creates a vertex buffer, fill it with data, upload it, render it and destroy it. One "optimization" was to reuse the created vertex buffer for every quad, but that didn't help much. It seems DrawPrimitiveUP does some heavy optimization under the hood, but the nature of that is unfortunately not known (to me).

What would be the best approach here? Really create vertex buffers for every string currently displayed and cache them?
I would prefer to stay with bitmap fonts (I'm aware of the downsides of foreign languages, etc..)

Share this post


Link to post
Share on other sites
Advertisement

Do you create a buffer for each quad or are you using a buffer to hold multiple quads? (the text you wrote to me indicates that you create a buffer for each quad so just want to clear that up)

 

You should discard the content of the old buffer when you are filling it again with new data, you could create a quad data that contains all of the transformed vertex data and then just copy that into the vertex buffer for rendering. You would need a new VB if you change font or scaling size offcourse, and even that is fixable with instanced rendering.

Edited by NightCreature83

Share this post


Link to post
Share on other sites

I've has font problem several days ago and i decided to use Direct2D shared surface. It is not perfect but it works well.

Share this post


Link to post
Share on other sites

Your approach should be fast enough, i use it for my entire gui draw which is rebuilt each frame.

Share this post


Link to post
Share on other sites

Please report back if you manage to make it work. Tell me if you are somehow able to predict how much space will rendered text take, I cannot find out how to do it.

Share this post


Link to post
Share on other sites

I just do the naive thing with 2D and it seems quite fast. Even on older hardware I could throw tens of thousands of them around like it was nothing.

 

I pre-fill a static 16 bit index buffer and create a dynamic vertex buffer for my sprites. I create the sprite geometry each frame and do some basic sorting and batching. It's pretty easy to batch large amounts of the sprites into a single draw call. Buffers for it are created once up front and destroyed only at the end.

 

Since the index buffer was 16 bit, I capped the number of sprites at 10922 per draw call.

 

(10922 * 4) * sizeof(Vertex2D)... which was 32. So 1398016 bytes for the vertex buffer. About 1.4mb.

Share this post


Link to post
Share on other sites

I completely did not understand clashie... :) Are you able to change the text during runtime efficiently?

Share this post


Link to post
Share on other sites
I highly recommend that you just grab the DirectXTK and use the helpers it provides for bitmap fonts and sprite rendering. If you need something special that it can't handle, at least look at how it solves the problem.

Note that it also provides a number of other very useful utilities like screen grab (screenshot) helpers, a decent math library, texture loading, simplified effects framework, and so on.

Share this post


Link to post
Share on other sites
A thanks for the recommendations. Looks like I'm off to implement nice batching then. I thought so, I was just befuddled at what a difference it makes, the little bit of text would cause such tremendous slowdowns.

@NightCreature83: I was creating a buffer for every quad. So that's quite a few reuses per frame for a few lines of text :)

Share this post


Link to post
Share on other sites

A thanks for the recommendations. Looks like I'm off to implement nice batching then. I thought so, I was just befuddled at what a difference it makes, the little bit of text would cause such tremendous slowdowns.

@NightCreature83: I was creating a buffer for every quad. So that's quite a few reuses per frame for a few lines of text :)

Its the number of buffers here that are the problem, you are usually better of creating a fewer vertex buffers and having a few large ones than really small ones, the CPU overhead will cost more on the small buffers than on the large ones.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!