Rendering to multiple viewports

Jul 12, 2013 at 3:12 AM
Hello,

I am rendering to multiple monitors, each with their own D3D11_VIEWPORT. I am using ID3D11DeviceContext::RSSetViewports( numberOfViewports, viewports ) to set a different viewport for each output.

When I render my sprite batches and primitive batches, they seem to be rendering based on the dimensions of the first viewport. As far as I can tell, I'm missing something, but I'm not sure what just yet. How should I be handling this situation? As far as I know, I may be missing something relating to my configuration that isn't even specific to DXTK...

Thanks for your time and help!
Allen
Coordinator
Jul 12, 2013 at 6:07 AM
SpriteBatch does not support multiple viewports - it will always just output to viewport #0.
Jul 12, 2013 at 1:29 PM
Oh, I see. Thanks for the quick response! I have some more questions on the topic, though...

Should I be expecting this feature sometime in the future? If not, are there any strong technical reasons that the design of the DXTK (spritebatch and primitivebatch specifically) could not support multiple viewports? I'm thinking maybe I could try to hack it in on my own...

Otherwise, maybe I could just use the same viewport to render to each output by making the viewport large enough for all outputs. I might need to overcome some unexpected stretching, but maybe it's possible...

Thanks,
Allen
Coordinator
Jul 12, 2013 at 3:17 PM
I'm not really clear on how you would expect this to work. Multiple viewports are a D3D10 feature, used with geometry shaders (the geometry shader can select which viewport to use when outputting each primitive). This is used for some advanced rendering techniques where different primitives within a single draw call are routed to different output locations.

That functionality doesn't make sense for SpriteBatch for several reasons:
  • Geometry shaders are a 10.0 feature, while DirectXTK supports all the way down to 9.1 feature level
  • SpriteBatch just draws a single sprite to the active rendertarget - there's no mechanism to select which of multiple outputs each sprite should go to
  • Rendering to multiple outputs is more easily accomplished just by drawing to one, then switching rendertarget before drawing to the other
Could you explain more about what you're trying to achieve with these viewports?
Jul 12, 2013 at 4:11 PM
OK, thanks for your thoughts, Shawn -- you've made some good points that I need to look into.

I am making tool for testing input lag on digital displays. This tool is modelled off of SMTT by Thomas Thiemann based on his research at prad.de. DXTK has been great for getting me to an MVP ASAP, especially because I have been primarily writing the software on bus trips to and from work. ;)

This tool requires repeatedly rendering a timer value to each output, one after the other. Each output will typically be set at a different resolution.

My setup includes a different render target for each output, and I am switching between them as you suggested. My assumption to need to create a separate viewport for each output may have been wrong, but I originally thought it would be necessary because each output may have a different resolution.

Again, I'll look into those points and report back soon when I have a better understanding...

Thanks,
Allen
Coordinator
Jul 12, 2013 at 5:57 PM
You need different size viewports for differently sized render targets, but you don't need to set all of these viewports simultaneously. Just change the viewport settings at the same time as you change rendertarget.
Jul 12, 2013 at 11:13 PM
Hahahah! I see my silliness now. That would be ridiculous if you couldn't change your active viewport many times while rendering.

I guess because I always saw the ID3D11DeviceContext::RSSetViewports call in the initialization step of sample code, I assumed that it was an expensive call and should be set once. I see now that it makes sense to call RSSetViewports each time I switch my render target.

Thanks for walking me through this one. Everything's looking great now!

Best,
Allen