14
$\begingroup$

A fairly basic, in some ways, question, but one that many people, myself included, don't really know the answer to. GPU manufacturers often cite extremely high numbers, and the spread between polygon counts that various game engines claim to support often spans multiple orders of magnitude, and then still depends heavily on a lot of variables.

I'm aware that this is a broad, pretty much open-ended question, and I apologize for that, I just thought that it would be a valuable question to have on here nonetheless.

$\endgroup$
9
  • 2
    $\begingroup$ I don't think the question's necessarily too open-ended, but any numeric answer is going to be wrong within 12 months. $\endgroup$
    – Dan Hulme
    Dec 10, 2015 at 9:51
  • $\begingroup$ @DanHulme Yeah, but the approaches used to reach that kind of efficiency stay the same. And when not, I've seen questions that require updating answers periodically on other stackexchange sites, so I think that's fine. $\endgroup$ Dec 10, 2015 at 18:47
  • 9
    $\begingroup$ This is really impossible to answer. First of all, what is "realtime"—60fps? 30? Less? Second, the answer will vary hugely based on what GPU you have and what resolution you're rendering at. Third, the answer will vary hugely depending on the details of how the rendering works. Limits on scene complexity are more complicated than just the number of polygons per se, but involve such things as the number of draw calls, state changes, render passes and so on—which are affected by how the engine works, how the artists constructed the scene, and so on... $\endgroup$ Dec 11, 2015 at 6:39
  • 1
    $\begingroup$ @Llamageddon Considering your comments, I'm not quite sure what you actually ask for. On one hand, your question title is quite clear (max out geometry and how to do so), but as Nathan pointed out, this is kind of impossible to answer. On the other hand, in your comments you say you want to know how to minimize cost per frame. This is an extremely broad question, because you could improve/optimize your shaders, scene graph, models, textures, API usage, simply everything that does some part of your rendering. You could probably write entire books about this (if not done by someone already). $\endgroup$
    – Nero
    Dec 12, 2015 at 0:39
  • 1
    $\begingroup$ this is a bit late, but here you can see a STATIC mesh with 24.000.000 Vertices in Blender. And i can rotate it SMOOTH with 40 FPS. I think it is just amazing what modern graphic cards can do. $\endgroup$
    – user6420
    Apr 9, 2017 at 15:42

2 Answers 2

7
$\begingroup$

I think it is commonly accepted that real time is everything that is above interactive. And interactive is defined as "responds to input but is not smooth in the fact that the animation seems jaggy".
So real time will depend on the speed of the movements one needs to represent. Cinema projects at 24 FPS and is sufficiently real time for many cases.

Then how many polygons a machine can deal with is easily verifiable by checking for yourself. Just create a little VBO patch as a simple test and a FPS counter, many DirectX or OpenGL samples will give you the perfect test bed for this benchmark.

You'll find if you have a high end graphics card that you can display about 1 million polygons in real time. However, as you said, engines will not claim support so easily because real world scene data will cause a number of performance hogs that are unrelated to polygon count.

You have:

  • fill rate
    • texture sampling
    • ROP output
  • draw calls
  • render target switches
  • buffer updates (uniform or other)
  • overdraw
  • shader complexity
  • pipeline complexity (any feedback used? iterative geometry shading? occlusion?)
  • synch points with CPU (pixel readback?)
  • polygon richness

Depending on the weak and strong points of a particular graphic card, one or another of these points is going to be the bottleneck. It's not like you can say for sure "there, that's the one".

EDIT:

I wanted to add that, one cannot use the GFlops spec figure of one specific card and map it linearly to polygon pushing capacity. Because of the fact that polygon treatment has to go through a sequential bottleneck in the graphics pipeline as explained in great detail here: https://fgiesen.wordpress.com/2011/07/03/a-trip-through-the-graphics-pipeline-2011-part-3/
TLDR: the vertices have to fit into a small cache before primitive assembly which is natively a sequential thing (the vertex buffer order matters).

If you compare the GeForce 7800 (9yr old?) to this year's 980, it seems the number of operations per second it is capable of has increased one thousand fold. But you can bet that it's not going to push polygons a thousand times faster (which would be around 200 billion a second by this simple metric).

EDIT2:

To answer the question "what can one do to optimize an engine", as in "not to lose too much efficiency in state switches and other overheads".
That is a question as old as engines themselves. And is becoming more complex as history progress.

Indeed in real world situation, typical scene data will contain many materials, many textures, many different shaders, many render targets and passes, and many vertex buffers and so on. One engine I worked with worked with the notion of packets:

One packet is what can be rendered with one draw call.
It contains identifiers to:

  • vertex buffer
  • index buffer
  • camera (gives the pass and render target)
  • material id (gives shader, textures and UBO)
  • distance to eye
  • is visible

So the first step of each frame is to run a quick sort on the packet list using a sort function with an operator that gives priority to visibility, then pass, then material, then geometry and finally distance.

Drawing close objects gets prirority to maximize early Z culling.
Passes are fixed steps, so we have no choice but to respect them.
Material is the most expensive thing to state-switch after render targets.

Even in-between different materials IDs, a sub-ordering can been made using a heuristical criterion to diminish the number of shader changes (most expensive within material state-switch operations), and secondly texture binding changes.

After all this ordering, one can apply mega texturing, virtual texturing, and attribute-less rendering (link) if deemed necessary.

About engine API also one common thing is to defer the issuing of the state-setting commands required by the client. If a client requests "set camera 0", it is best to just store this request and if later the client calls "set camera 1" but with no other commands in between, the engine can detect the uselessness of the first command and drop it. This is redundancy elimination, which is possible by using a "fully retained" paradigm. By opposition to "immediate" paradigm, which would be just a wrapper above the native API and issue the commands right as ordered by client code. (example: virtrev)

And finally, with modern hardware, a very expensive (to develop), but potentially highly rewarding step to take is to switch API to metal/mantle/vulkan/DX12-style and preparing the rendering commands by hand.

An engine that prepares rendering commands creates a buffer that holds a "command list" that is overwritten at each frame.

Usually there is a notion of frame "budget", a game can afford. You need to do everything in 16 milliseconds, so you clearly partition GPU time "2 ms for lightpre pass", "4 ms for materials pass", "6 ms for indirect lighting", "4 ms for postprocesses"...

$\endgroup$
5
  • 2
    $\begingroup$ A million seems a bit low to me. $\endgroup$
    – joojaa
    Dec 14, 2015 at 9:00
  • 1
    $\begingroup$ just take how many MPoly/s the card is capable of, and that's the FPS at which it will render 1 million. I just recalled an experiment for a terrain renderer on an ATI4800HD. If you take this list en.wikipedia.org/wiki/List_of_Nvidia_graphics_processing_units they don't give Vertices/s info starting from the era of unified architecture. but 10 year old hardware seems to advertise about 40 FPS for 1 million triangles. + c.f. edit in my answer $\endgroup$
    – v.oddou
    Dec 14, 2015 at 9:30
  • 1
    $\begingroup$ @v.oddou Yeah, but to get near that number you need to do batching of geometry, or instancing, in case of dynamic scenes, and that is what I'm asking about. How to not bottleneck yourself 2% of the way towards what hardware can do. $\endgroup$ Dec 14, 2015 at 13:49
  • $\begingroup$ @Llamageddon aaah, I see, THAT is a question indeed. Let me see what I can say about it. (EDIT2) $\endgroup$
    – v.oddou
    Dec 15, 2015 at 1:47
  • $\begingroup$ Great in depth answer! I've made a few minor edits, as a user rather than a moderator. Feel free to roll back any/all if they don't match your intention. $\endgroup$ Dec 17, 2015 at 12:50
-1
$\begingroup$

In my experience using VBO allows to render model consisting of 500 million triangles in realtime (more then 20 fps) on NVidia RTX 2080 videocard.

Model size is 8GB, there is 11GB available video memory

$\endgroup$

Not the answer you're looking for? Browse other questions tagged or ask your own question.