The motivation for this project comes from the SIGGRAPH '96 paper entitled "Modeling and Rendering Architecture from Photographs: A hybrid geometry- and image-based approach" by Debevec, Taylor, and Malik.
My approach was to place the object at the origin of the world-space and then using mouse interaction, move the camera position about the origin. This is not typically how movement is achieved in OpenGL, usually the camera is stationary and the world is translated, etc. around the viewer. Both achieve the same effect, but there is a reason I did it this way.
When I create a "cubish" object, I orient it along the xyz-axis so the definition of its surface normals are easy, (1,0,0) is straight to the right, (0,-1,0) is straight down, etc. When I move the camera using the gluLookAt() method, I must define the xyz position of the camera and the xyz point that it is looking at. Simple math with these two vectors will give me my viewing vector. I always know my camera info because it is the information I change with mouse interaction.
I now have surface normals and my view vector. Using the dot product between the two, I determine if I am looking at a surface straight on (Dot product = 1) or from an angle (0 < Dot Product < 1).
For each surface, I define a texture for "straight on," "looking from the left," and "looking from the right." Using the OpenGL blending operation, I fade from one texture to another. The three textures exist at the same time on 3 duplicate overlapping surfaces. I merely change the alpha value of each layer to fade that texture in or out.
For example, if I am looking straight at a square textured plane, the dot product will be 1.0. This means my "straight on" texture will have an alpha of 1.0 (opaque) and the angle textures will have an alpha of (1 - dot product, which is 0, clear). As you rotate to say 45 degrees, the dot product becomes 0.5 so the "straight on" texture is 0.5 opaque and the angle texture is (1-0.5 = 0.5 also).
Blending two textures sometimes leaves a "ghosting" of the two textures on top of each other. At an angle of 45 degrees, you theoretically are seeing 50% of the color from each texture. For better results, I use (dot product) for the "straight-on" alpha value and (1-dp*dp*dp) for the angle alpha. This achieves a faster transition.
Another problem is inherent to OpenGL and texturing. I found it very difficult to create decent textures for non-cubelike objects or even long rectangle-shaped object such as my truck. I can take a picture of my truck straight on without a large distortion of its square shape, but when I take a picture from an angle, the perspective significantly distorts the image. I tried my best to redistort the image back to a cube shape (since textures in OpenGL must be 2^n by 2^n squares) but this was tricky at best.
Finally, the dot product is not signed. 45 degrees off to the left is the same as 45 degrees of to the right. In retrospect, I believe this could be overcome by using polar coordinates, but for my application I had to use additional information such as the signed direction of the view vector to determine which side I was on.
This shows the "ghosting" effect that occurs as one texture blends into another. The transition is noticeable but acceptable if you keep rotating past this "inflection point," but if you stop at the blending point then it looks pretty bad, as shown on the left.
The next series of pictures shows how the texture changes as we rotate around the truck. I highlighted areas of the texture that exhibit the effect best.
My final results are decent. The view dependent texturing works, but future work could improve its performance. A simpler model would also help a lot, such as a fishtank or computer tower. This won't have as much perspective distortion when photographed. About half the time spent on this assignment was needed to tweak and align these textures on the truck (especially the non-square side-profile surface).
These are some good OpenGL pages with information on multitexturing (which I scrapped halfway through), textures in general, loading textures, dot products info, etc.
Dot Product http://freespace.virgin.net/hugo.elias/routines/r_dot.htm
Multitexturing http://tfpsly.planet-d.net/english/3d/multitexturing.html
LOTS of good tutorials http://nehe.gamedev.net/
Loading textures http://www.nullterminator.net/gltexture.html
Texture info http://www.flipcode.com/articles/article_advgltextures.shtml