8
\$\begingroup\$

I'm using an orthographic camera to render slices of a model (in order to voxelize it). I render each slice both from above and below in order to determine what is inside each slice.

The model I render is a simple 'T' shape constructed from two cubes. The cubes have the same dimensions and have the same Y (height) coordinate. Here's a render of it in Blender:

The T model

I render this model once directly from above and once directly from below. My expectation was that I would get exactly the same image (except for mirroring over the y-axis). However when I render using a very low resolution render target (25x25) the position (in pixels) of the 'T' is different when rendered from above as opposed to rendered from below. See figure 2 and 3. The pink blocks are not part of the original rendering but I've added them so you can easily count/see the differences.

Rendered from above From Above

Rendered from below From Below

This is probably due to what I've read about pixel and texel coordinates which might be biased to the top-left as seen from the camera. Since I'm using the same 'up' vector for both of my camera's my bias only shows on the x-axis. I've tried to change the position of the camera and it's look-at by, what I thought, should be half a pixel. I've tried both shifting a single camera and shifting both cameras and while I see some effect I am not able to get a pixel-by-pixel perfect copy from both camera's.

Here I initialize the camera and compute, what I believe to be, half pixel. boundsDimX and boundsDimZ is a slightly enlarged bounding box around the model which I also use as the width and height of the view volume of the orthographic camera.

Matrix projection = Matrix.CreateOrthographic(boundsDimX, boundsDimZ, 0.5f, sliceHeight + 0.5f);
Vector3 halfPixel = new Vector3(boundsDimX / (float)renderTarget.Width, 0, 
    boundsDimY / (float)renderTarget.Height) * 0.5f;

This is the code where I set the camera position and camera look ats

  // Position camera                      
                if (downwards)
                {
                    float cameraHeight = bounds.Max.Y + 0.501f - (sliceHeight * i);
                    Vector3 cameraPosition = new Vector3
                    (
                        boundsCentre.X, // possibly adjust by half a pixel?
                        cameraHeight,
                        boundsCentre.Z
                    );
                    camera.Position = cameraPosition;
                    camera.LookAt = new Vector3(cameraPosition.X, cameraHeight - 1.0f, cameraPosition.Z);

                }
                else
                {
                    float cameraHeight = bounds.Max.Y - 0.501f - (sliceHeight * i);
                    Vector3 cameraPosition = new Vector3
                    (
                        boundsCentre.X,
                        cameraHeight,
                        boundsCentre.Z
                    );
                    camera.Position = cameraPosition;
                    camera.LookAt = new Vector3(cameraPosition.X, cameraHeight + 1.0f, cameraPosition.Z);
                }

Main Question Now you've seen all the problems and code you can guess it. My main question is. How do I align both camera's so that they each render exactly the same image (mirrored along the Y axis)?

\$\endgroup\$
  • \$\begingroup\$ The solution so far seems to be to move the camera that takes a picture from below exactly one pixel to the left (-x). However I cannot explain why and thus cannot guarantee that it will work for everything I throw at it. Any ideas? \$\endgroup\$ – Roy T. Jun 1 '14 at 9:01
  • \$\begingroup\$ Did you thought about keeping everything in place, but scaling the Y of the model (cubes) by -1 ? Then you would have all the same except for the objects being flipped. P.S. Of course you will need to -1 the normals and polygons faces too. \$\endgroup\$ – Kromster says support Monica Jun 2 '14 at 8:33
  • \$\begingroup\$ Thats actually a pretty cool idea \$\endgroup\$ – Roy T. Jun 3 '14 at 9:28
  • \$\begingroup\$ Since you approve, I've posted it as an answer. Tell me if it works for you! \$\endgroup\$ – Kromster says support Monica Jun 3 '14 at 9:34
2
+75
\$\begingroup\$

This is a different view on the problem presented, which might help to avoid rasterization differences issues altogether

Did you consider keeping everything in place, but scaling the Y of the model (cubes) by '-1' along the section plane? Then you will have everything exactly the same except for the objects being flipped upside-down - meaning you will get their down sides for your goal. Of course you will need to '-1' the normals and polygons facing directions too.

\$\endgroup\$
  • \$\begingroup\$ Though your answer does not explain why my method didn't work. (And that's where the bounty was for) I'll not award the bounty right now. But because its a good suggestion the automatic 50% bounty should be awarded to you in a day, and I think you deserve it :). \$\endgroup\$ – Roy T. Jun 9 '14 at 12:06
  • \$\begingroup\$ @RoyT.: Sounds fair. However you still ought to tell us, if suggested solution did solved your problem - so that others who face the same problem will know how to handle it. \$\endgroup\$ – Kromster says support Monica Jun 9 '14 at 12:09

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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