Skip to main content
gamedev.net
🔒 Locked

Scale

Started by Zakwayda May 10, 2004 at 4:29 PM 17 replies 2.4k views
Original Post
Zakwayda
Zakwayda
Hi, I''m trying to choose a consistent scale for my game engine, and I''m not sure what the best way to go is. I know it''s somewhat arbitrary, but I also know that there can be precision issues if the scale is too large or small. My world is average size, comparable to your average Q3 level. 1 unit per meter would be nice, but would that introduce precision problems on the low end? So my question is, what would be a good scale, in units per meter, to use for my engine? Thanks.
Drilian
Drilian
I use one unit per decimeter (.1 meters). I chose it arbitrarily, but it worked well for me. And it's easy to think about in terms of real-world space.

EDIT: I should say, for indoor and small outdoor environments. For large-scale outdoors (different project), I use 1 unit = 1 meter. With a far plane of 2000 meters, using the decimeter scale was just crazy, given a near plane of z = 1 unit. Not enough z resolution to go around.

[edited by - Drilian on May 10, 2004 5:34:00 PM]
Etnu
Etnu
It really depends on how detailed the geometry is going to be.

For the project I''m working on right now, for example, I use a grid that''s aligned to the unit space I''m working with. Each unit is about 100cm or so. That gives me plenty of detail, since it''s mostly an outdoor-type of deal, but obviously it wouldn''t be nearly precise enough for, say, a human face.



He that is not busy born is busy dying.
---------------------------Hello, and Welcome to some arbitrary temporal location in the space-time continuum.
Max_Payne
Max_Payne
In our old engine we used to have one unit = 0.1 meter... It makes no sense, and introduces useless factors everywhere (you have to have your velocity in decimeters per seconds to be consistant... forces arent in newton anymore). We eventually switched everything to be perfectly metric.

The near and far plane should be set for your needs... If you work in metric, you can set the near plane at 0.01 if you want... The metric system is just more convenient, more natural and easier to scale things with



Looking for a serious game project?
www.xgameproject.com

Looking for a serious game project?
www.xgameproject.com
JohnBolton
JohnBolton
If you are using floating point, your choice of scale has no effect on precision. What will cause a precision problem is a high value for the ratio between the largest values and the smallest values, and that is the same regardless of your choice of scale.

If you are using fixed point, then your precision and scale are determined by the size of the world and the number of bits in the fixed point value.
John BoltonLocomotive Games (THQ)Current Project: Destroy All Humans (Wii). IN STORES NOW!
Drilian
Drilian
Yes, you''re correct. The float precision is going to be same whether you use 1 unit = 1 meter vs 1 unit = .1 meter. Just make sure to set the front/near plane accordingly (i.e. if at 1u = .1m, you were going to set the near plane at 1 and far at 2000, instead set the near plane at .1 and far at 200 for 1u = 1m. The result should be the same). Also it would make calculations line up with textbook equations, as per Max_Payne''s answer.

Good call. I should have known that.
sBibi
sBibi
"The near and far plane should be set for your needs... If you work in metric, you can set the near plane at 0.01 if you want... The metric system is just more convenient, more natural and easier to scale things with"

I have to disagree with that...
if you care a little bit about Z-buffer precision, resolution, Z-fighting/flickering, whatever, the near plane shouldn''t be set to fit your needs. I personally prefer to set my units according to the near plane value, witch I try to keep between 2 and 2.5.
there is something called Z-buffer mapping you know... and that nice thing is all but linear. if you scale everything down by a 100 and have your near plane at, say, 0.01, you won''t have the same Z-buffer precision _at_all_, it''s completely non linear...
if you need to see stuff 1 cm away from your camera, you shouldn''t touch the near plane if you don''t want Z-fighting to occur everywhere... keep it over 1, and instead, scale your units, and make 1 unit equal 1 or 0.5 centimeter.
if you don''t want Z-buffer problems, the near plane value is a constraint, not something that you should touch the way you like.

and that thing of having constants in the metric system only maybe makes your life easier when coding, but in the end, you''ll have other problems...

"and introduces useless factors everywhere"

it''s like working in inches instead of meters, or in bananas instead of decimeters, you don''t care...

"It makes no sense, and introduces useless factors everywhere"

#define BANANAS_TO_METERS(v) (v * 8.36752)

"If you are using floating point, your choice of scale has no effect on precision"

yes, I totally agree, except for Z-buffer depth values mapping
technobot
technobot
IIRC, the imprtant thing as far the z-buffer is concerened, is the ratio between far and near planes, not the near plane alone. So if you set 0.1 and 500 (meters) or 1 and 5000 (decimeteres), you should get the same precision.

Michael K.,
Co-designer and Graphics Programmer of "The Keepers"



We come in peace... surrender or die!
Michael K.
Coincoin
Coincoin
quote:
Original post by sBibi
"The near and far plane should be set for your needs... If you work in metric, you can set the near plane at 0.01 if you want... The metric system is just more convenient, more natural and easier to scale things with"

I have to disagree with that...
if you care a little bit about Z-buffer precision, resolution, Z-fighting/flickering, whatever, the near plane shouldn't be set to fit your needs. I personally prefer to set my units according to the near plane value, witch I try to keep between 2 and 2.5.
there is something called Z-buffer mapping you know... and that nice thing is all but linear. if you scale everything down by a 100 and have your near plane at, say, 0.01, you won't have the same Z-buffer precision _at_all_, it's completely non linear...
if you need to see stuff 1 cm away from your camera, you shouldn't touch the near plane if you don't want Z-fighting to occur everywhere... keep it over 1, and instead, scale your units, and make 1 unit equal 1 or 0.5 centimeter.
if you don't want Z-buffer problems, the near plane value is a constraint, not something that you should touch the way you like.

and that thing of having constants in the metric system only maybe makes your life easier when coding, but in the end, you'll have other problems...

"and introduces useless factors everywhere"

it's like working in inches instead of meters, or in bananas instead of decimeters, you don't care...

"It makes no sense, and introduces useless factors everywhere"

#define BANANAS_TO_METERS(v) (v * 8.36752)

"If you are using floating point, your choice of scale has no effect on precision"

yes, I totally agree, except for Z-buffer depth values mapping


This is wrong. When you project your vertex to screen space, the Z is scaled to values between 0.0 and 1.0, 0 being at the near clip, and 1 at the far clip. This normalized value is converted to integer and written to the zbuffer. The video card rasterizer has absolutly no idea what your scaling is, it has absolutly no idea what your near clip and far clip values are. All it knows is there is a matrix transform that outputs z values between 0.0 and 1.0, and this is what gets written in the zbuffer.


[edited by - Coincoin on May 11, 2004 4:15:32 PM]
Etnu
Etnu
quote:

If you are using floating point, your choice of scale has no effect on precision.



That''s true if you *ALSO* scale the number of vertices you use per unit. Things are a little easier to visualize when you make them 1 unit = 1 vertice.

Granted, that''s not necessarily a "requirement", but it does make things quite a bit simpler.
---------------------------Hello, and Welcome to some arbitrary temporal location in the space-time continuum.
Zakwayda
Zakwayda
Thanks for all the feedback! Sounds like there''s not really a concensus on the subject, and I admit I didn''t quite follow all the arguments presented here.

I gather, though, that it''s important to pick a good ratio between your far and near planes, but that the actual values aren''t that important? So what (in meters) would be good far and near plane values for say, your average-sized Q3 level?

Once you''ve established that, I suppose you could use just about any value for units per meter. It could even be made a global constant or variable, and physics calculations could be scaled appropriately.

Let me know if I''m interpreting things correctly, or if I''m off base.
Coincoin
Coincoin
Choosing good values for near and far planes depends a lot on what you need to display.

Near clip:
Always get a near clip as far as you can. You should at least make it smaller than your main character collision cylinder, but try to push it forward as much as you can.

Far clip:
What you first need to know is what's the max range you want to display. That's not quite the far clip yet.

Then, analyse your needs.

- If you need high precision only on things near you, use a far clip that's slightly higher than the max displaying range you need. Be aware that doing that WILL create z-fighting artifact on things far from you.

- However, if you need overall precision on all depths, you should raise your far clip value up to 15 times your needed max range. This will have the effect of stretching 80% of the efficient z values accross your display range, but will reduce overall z buffer precision, which is usually a good trade.

Nothing prevents you from finding a value in-between. You could also change these values each frame depending on what you are doing (sniping or not).

[edited by - Coincoin on May 11, 2004 5:19:48 PM]
sBibi
sBibi
quote:
This is wrong. When you project your vertex to screen space, the Z is scaled to values between 0.0 and 1.0, 0 being at the near clip, and 1 at the far clip. This normalized value is converted to integer and written to the zbuffer. The video card rasterizer has absolutly no idea what your scaling is, it has absolutly no idea what your near clip and far clip values are. All it knows is there is a matrix transform that outputs z values between 0.0 and 1.0, and this is what gets written in the zbuffer.


sorry, but it's not... I think you didn't understand my point... it's not about how the depth values are stored, it's about how they are mapped...
about this "is scaled", about the way the values are actually scaled....

quote:
All it knows is there is a matrix transform that outputs z values between 0.0 and 1.0


yes, and this matrix transforms those values in a non linear way... having a near plane of 0.0001 and a far plane of 1 or a near plane of 1 and a far plane of 10000 with the appropriate scale changes will NOT produce the same depth values mapping at all! you'll have a much higher precision around the near plane in the first case, but it will degrade much quicker than in the second case, where it will be much more linear...

go read this if you don't see what I'm talking about: http://www.sjbaker.org/steve/omniv/love_your_z_buffer.html


[edited by - sBibi on May 11, 2004 7:39:35 PM]
Drilian
Drilian
Actually, on that page, it has a ZBuffer value calculator.

I used the following three sets of data


Near: 1 Far: 2000 A: 500 B: 1000 C: 1500

Near: .1 Far: 200 A: 50 B: 100 C: 150

Near: .01 Far: 20 A: 5 B: 10 C: 15


Where A, B, and C were sample distances, for which I recorded the depth values.

The returned values written to the depth buffer, in all three cases were:

A: 25178
B: 8392
C: 2797


Which shows that, as long as ALL coordinates scale equally, it doesn''t matter what units you use. As long as the ratio from near to far is the same, you''ll get the same results.

It''s the ratio that matters, not the values themselves.
sBibi
sBibi
yes, I agree with that, that''s why I said:

quote:
if you need to see stuff 1 cm away from your camera, you shouldn''t touch the near plane if you don''t want Z-fighting to occur everywhere... keep it over 1, and instead, scale your units, and make 1 unit equal 1 or 0.5 centimeter.
Coincoin
Coincoin
sBibi:
I know the values aren''t linear, but that doesn''t change a thing, mathematical rules stay valid.

What I''m trying to make you understand is, no matter what scaling you use, the mapping stays the same. There is no such things as scaling in a video card. If you multiply or divide everything by 100 (including far and near clip distance), no one gives a *** about it.

Well, unless your own page is lying, scaling as nothing to do with zbuffer mapping. IN NO WAY. Try entering values, and multiply all of them by 100... see the result being exactly the same.

If you need one unit to be one meter, do so. Just scale your near and far clip planes too and everything will work perfectly. I invite you to analyse the rendering pipeline. As I said, before sending the triangle to the rasterizer (which is the one that writes to the zbuffer), all Z values are clamped to 0.0 and 1.0 (that''s what we call screen space z coordinates).

Tell me now, how could the scaling affect the screen space coordinates?
Drilian
Drilian
Yes, that is correct. The OpenGL transforms map to a perfect cube with min and max (-1, -1, -1) and (1, 1, 1) respectively.

DirectX actually maps values to a half-cube, with min and max (-1,-1,0) and (1,1,1) respectively.

I'm not sure why there's a difference.

[edited by - Drilian on May 12, 2004 6:20:50 PM]
sBibi
sBibi
Coincoin> your post just made me realize I read Max payne''s post too quickly, I understood him the other way round..

"If you multiply or divide everything by 100 (including far and near clip distance)"

ok, I didn''t understand you were scaling both by the same factor...
I have the bad habit to post before having some sleep when I''ve got my head in my ass...
in fact I just re-read my own posts and found them confusing, sorry about that...

"Tell me now, how could the scaling affect the screen space coordinates?"
if you use the same scale everywhere (as in Drilian''s post), then I agree, that''s fine...

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.