How can I increase distance (zfar/gluPerspective) where openGL stops drawing objects? - opengl

I am learning OpenGL and having a problem with gluPerspective. Here is the code I use in Init()
// Calculate The Aspect Ratio Of The Window
// The parameters are:
// (view angle, aspect ration of the width to the height,
// The closest distance to the camera before it clips,
// FOV, Ratio, The farthest distance before it stops drawing)
gluPerspective(45.0f,(GLfloat)width/(GLfloat)height, 0.5f, 3000.0f);
My scene works right.. but as soon as I go a little bit away from my objects they dissapear (As the red balls in image). :
Web where I took graph from
I understand that red balls are outside of view and won't be shown. So what I want is to increase the distance where it stops drawing. I tried increasing 3000.0f but is not working!.
gluPerspective(45.0f,(GLfloat)width/(GLfloat)height, 0.5f, 3000000.0f);
So my question is : How can I increase distance where openGL stops drawing objects?
Some pics about the problem:
Pic1
Pic2

I figured out what was happening so I answer this myself to help other people in the future:
Changing zfar works ok. The problem I had was (not included in the question for simplification) was my skybox. Skybox was small and was hiding the objects with the sky. In pic2 is easy to see!
So if you have a similar problem just double check your skybox. If it were a zfar problem everthing should
be black instead of having a sky texture!

The near and far values define the precision of the depth buffer. The higher the ratio between near and far is the more depth buffer precision errors you will get. Thus your depth buffer might actually allow to draw the objects but if they are small and close to each other they still might not be visible (rejected or be overdrawn).
If you increase from 3000.0f to 10000.0f it might still work. How big are your objects?
Why do you need that big viewing distance in the first place? Maybe there are other approaches that better fit your needs.

Related

Aliased rasterization: why sampling pixel at center?

Both OpenGL and Direct3D use pixel's center as a sample point during rasterization (without antialiasing).
For example here is the quote from D3D11 rasterization rules:
Any pixel center which falls inside a triangle is drawn
I tried to find out what is the reason to use (0.5, 0.5) instead of, say, (0.0, 0.0) or whatever else in range of 0.0 - 1.0f for both x and y.
The result might be translated a little, but does it really matter? Does it produce some visible artifacts? May be, it makes some algorithms harder to implement? Or it's just a convention?
Again, I don't talk about multisampling here.
So what is the reason?
Maybe this is not the answer to your problem, but I try to answer your question from ray tracing perspective.
In ray tracing, you can get color of every single points in the scene. But since we have a limited amount of pixel, you need to downsample to your image to your screen pixels.
In ray tracing, if you use 1 ray per pixel, we generally choose center point to create our ray which gives the most correct render results. In the image below, I try to show the difference when you choose a corner of pixel or center. The distance will get bigger when your object is far from the rendering screen.
If you use more than one ray for each pixel, lets say 5 rays (4 corners + 1 center) and average the result, you will of course get more realistic image ( Will handle aliasing problems much better) However it will be slower as you guess.
So, it is probably the same idea that opengl and directX take one sample for each pixel instead of multisampling and taking average (Performance issues) and center point is probably giving the best result.
EDIT :
For area rasterization, center of pixel is used because if center of pixel remains inside Area, it is guaranteed that at least 50% of pixel is inside the shape.(Except shape corners) That's why since the proportion is greater than half that pixel is colored.
For other corner selections there is no general rule. Lets look at example image below. The black point (bottom left) is outside of area and should not be drawn (And when you look at it more than half of pixel is outside. However if you look at blue point %80 of pixel is inside area but since bottom left corner is outside area it shouldn't be drawn
This answer mainly focuses on the OP's comment on
Cagkan Toptas answer:
Thanx for the answer, but my question is: why does it give better
results? Does it at all? If yes, what is the explanation?"
It depends on how you define "better" results. From an image qualioty perspective, it does not change much, as long as the primitves are not specifically aligned (after the projection).
Using just one sample at (0,0) instead (0.5, 0.5) will just shift the scene by half a pixel (in both axis, of course). In the general case of aribitrary placed primitves, the average error should be the same.
However, if you want "pixel-exact" drawing (i.e. for text, and UI, and also full-screen post-processing effects), you just would have to take the convention of the underlying implementation into account, and both conventions would work.
One advantage of the "center at half integers" rule is that you can get the integer pixel coordinates (with respect to the sample locations) of the nearest pixel by a simple floor(floating_point_coords) operation, which is simpler than rounding to the nearest integer.

Deferred Lighting | Point Lights Using Circles

I'm implementing a deferred lighting mechanism in my OpenGL graphics engine following this tutorial. It works fine, I don't get into trouble with that.
When it comes to the point lights, it says to render spheres around the lights to only pass those pixels throught the lighting shader, that might be affected by the light. There are some Issues with that method concerning cullface and camera position precisely explained here. To solve those, the tutorial uses the stencil-test.
I doubt the efficiency of that method which leads me to my first Question:
Wouldn't it be much better to draw a circle representing the light-sphere?
A sphere always looks like a circle on the screen, no matter from which perspective you're lokking at it. The task would be to determine the screenposition and -scaling of the circle. This method would have 3 advantages:
No cullface-issue
No camereposition-in-lightsphere-issue
Much more efficient (amount of vertices severely reduced + no stencil test)
Are there any disadvantages using this technique?
My second Question deals with implementing mentioned method. The circles' center position could be easily calculated as always:
vec4 screenpos = modelViewProjectionMatrix * vec4(pos, 1.0);
vec2 centerpoint = vec2(screenpos / screenpos.w);
But now how to calculate the scaling of the resulting circle?
It should be dependent on the distance (camera to light) and somehow the perspective view.
I don't think that would work. The point of using spheres is they are used as light volumes and not just circles. We want to apply lighting to those polygons in the scene that are inside the light volume. As the scene is rendered, the depth buffer is written to. This data is used by the light volume render step to apply lighting correctly. If it were just a circle, you would have no way of knowing whether A and C should be illuminated or not, even if the circle was projected to a correct depth.
I didn't read the whole thing, but i think i understand general idea of this method.
Won't help much. You will still have issues if you move the camera so that the circle will be behind the near plane - in this case none of the fragments will be generated, and the light will "disappear"
Lights described in the article will have a sharp falloff - understandably so, since sphere or circle will have sharp border. I wouldn-t call it point lightning...
For me this looks like premature optimization... I would certainly just be rendering whole screenquad and do the shading almost as usual, with no special cases to worry about. Don't forget that all the manipulations with opengl state and additional draw operations will also introduce overhead, and it is not clear which one will outscale the other here.
You forgot to do perspective division here
The simplest way to calculate scaling - transform a point on the surface of sphere to screen coords, and calculate vector length. It mst be a point on the border in screen space, obviously.

OpenGL projection clipping

For example if we have ortho projection:
left = -aspect, right = aspect, top = 1.0, bottom = -1.0, far = 1.0, near = -1.0
And will draw triangle at -2.0, it will be cut of by near clipping plane. Will it really saves some precious rendering time?
Culling determinate if we need to draw something and discards if out of our view (written by programer in vertex shader/in main program). Clipping == cheap auto culling?
Also just in theme of cheap culling - will be
if(dist(cam.pos, sprite.pos) < MAX_RENDER_DIST)
draw_sprite(sprite);
just enough for simple 2d game?
Default OpenGL clipping space is -1 to +1, for x, y and z.
The conditional test for sprite distance will work. It is kind of not needed, as the far clipping plane will do almost the same thing. Usually it is good enough. There are cases where the test is needed. Objects at the corner inside the clipping planes may come outside the far clipping plane with the camera turns. The reason is that distance from the camera to the corner is longer than the perpendicular distance from the camera to the far clipping plane. This is not a problem if you have a 2D game and do not allow changes of the camera viewing angle.
If you have a simple 2D game, chances are high that you do not need to worry about graphics optimization. If you are drawing sprites outside of the clipping planes, you save time. But how much time you save depends. If a huge amount of the sprites are outside, you may save considerable time. But then, you should probably consider what algorithm you use, and not draw things that are not going to be shown anyway. If only a small percentage of the sprites are outside, then the time saved will be negligible.
The problem with clipping in the GPU is that it happens relatively late in the pipeline, just before rasterization, so a lot of computations could already be done for nothing.
Doing it on the CPU can save these computations from happening and, also very important, reduce the number of actual draw commands (which can also be a bottleneck).
However, you do want to do this fast in the CPU, typically you'll use an octree or similar to represent data so you can discard an entire subtree at once. If you have to go over each polygon or even object separately this can become to expensive.
So in conclusion: the usefulness depends on where your bottleneck lies (cpu, vertex shader, transmission rate, ...).

When loading an OBJ i get this

and this time i have loaded a model successfully! yay!!
but theres a slight problem, one that i had with another obj loader...
heres what it looks like:
http://img132.imageshack.us/i/newglitch2.jpg/
heres another angle if u cant see it right away:
http://img42.imageshack.us/i/newglitch3.jpg/
now this is supposed to look like a cube, but as you can see, the edges of the faces on the cube are being very choppy
is anyone else having this problem, or if anyone knows how to solve this then let me know
also comment if theres any code that needs to be shown, ill be happy to post it.
hey i played around with the code(changed some stuff) and this is what i have come up with
ORIGINAL:
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(50.f,(double)800 / (double)600,0.f,200.f);
glTranslatef(0.f, 0.f, -10.0f);
result: choopy image(look at images)
CURRENT:
glMatrixMode(GL_MODELVIEW);
gluPerspective(50.f,(double)800 / (double)600,0.f,200.f);
glTranslatef(0.f, 0.f, -50.0f);
glLoadIdentity();
result: model is not choppy but cannot move camera(model is right in front of me)
gluPerspective(50.f,(double)800 / (double)600,0.f,200.f);
^^^
|
That's your problem right there ---------------+
The near clip distance must be greater than 0 for perspective projections. Actually you should choose near to be as far away as possible and the far clip plane to be as near as possible.
Say your depth buffer is 16 bits wide, then you slice the scene into 32768 slices. The slice distribution follows a 1/x law. Technically you're dividing by zero.
Well this looks like a projection setting issue. Some parts of your cube, when transformed into clip space, exceed near/far planes.
From what I see you are using orthogonal projection matrix - it's standard for making 2D UI. Please review nearVal and farVal of your glOrtho call. For 2D UI they are usually set as -1 and 1 respectively (or 0 and 1), so may want to either scale down cube or increase view frustum depth by modifying mentioned parameters.

Compute bounding quad of a sphere with vertex shader

I'm trying to implement an algorithm from a graphics paper and part of the algorithm is rendering spheres of known radius to a buffer. They say that they render the spheres by computing the location and size in a vertex shader and then doing appropriate shading in a fragment shader.
Any guesses as to how they actually did this? The position and radius are known in world coordinates and the projection is perspective. Does that mean that the sphere will be projected as a circle?
I found a paper that describes what you need - calculating the bounding quadric. See:
http://web4.cs.ucl.ac.uk/staff/t.weyrich/projects/quadrics/pbg06.pdf
Section 3.2, Bounding Box calculation. The paper also mentions doing it on the vertex shader, so it might be what you're after.
Some personal thought:
You can approximate the bounding box by approximating the size of the sphere by its radius, though. Transform that to screen space and you'll get a slightly larger than correct bounding box, but it won't be that far off. This fails when the camera is too close to the point, or when the sphere it too large, of course. But otherwise should be quite optimal to calculate, as it would be simply a ratio between two similar, right triangles.
If you can figure out the chord length, then the ratio will yield the precise answer, but that's a little beyond me at the moment.
alt text http://xavierho.com/temp/Sphere-Screen-Space.png
Of course, that's just a rough approximation, and has a large error sometimes, but it would get things going quickly, easy.
Otherwise, see paper linked above and use the correct way. =]
The sphere will be projected as an ellipse unless it's at the cameras center as brainjam says.
The article that Xavier Ho links to describes the generalization of sphere projection (That is, quadratic projection). It is a very good read and I recommend it too. However, if you are only interested in sphere projection and more precisely the quadrilateral that bounds the projection then The Mechanics of Robust Stencil Shadows, page 6: Scissor Optimization details how to do it.
A Note on Xavier Ho's Approximation
I would like to add that the approximation that Xavier Ho suggests is, as he notes too, very approximative. I actually used it for a tile-based forward renderer to approximate light bounds in screen space. The following image shows how it neatly enables good performance with 400 omni (spherically bound) lights in a scene: Tile-based Rendering - Far View. However, just like Xavier Ho predicted the inaccuracy of the light bounds causes artifacts up close as seen here when zoomed in: Tile-based Rendering - Close view. The overlapping quadrilaterals fail to bound the lights completely and instead clip the edges revealing the tile grid.
In general, a sphere is seen as an ellipse in perspective:
(source: jrank.org)
The above image is at the bottom of this article.
Section 6 of this article describes how the bounding trapezoid of the sphere's projection is obtained. Before computers, artists and draftsmen has to figure this out by hand.