Preventing aspect ratio distortion

Blitz3D Forums/Blitz3D Beginners Area/Preventing aspect ratio distortion

fox95871(Posted 2010) [#1]
Hi, are there any ways to prevent computers with non 4:3 screens from distorting fullscreen Blitz3d programs? It makes me furious that such monitors even exist, but anyway. I was thinking maybe CameraViewport, but I haven't had time to try it yet. Or might some parameter of Graphics3D work?

Last edited 2010


_PJ_(Posted 2010) [#2]
CameraViewport would only limit the use of the number of pixels used.

What distortion do you actually mean, since the only real difference might be when you are scaling positions or sizes of things on the 2D screen?

You can adjust this by only scaling to a 4/3 ratio, but positioning to the full 16:9 or whatever?


Yasha(Posted 2010) [#3]
As long as you call Graphics3D with the same width/height ratio as the monitor has, there will be no distortion at all.

Really it's best just to let the user set this in the themselves in the program options - there's no reason at all to have the graphics resolution hardcoded... certainly not to a 4:3 aspect ratio. Be furious all you want, but the majority of gaming monitors in use are 16:9 or 16:10.

If you're really concerned about first appearances being perfect before the user gets to your app and suffers a few seconds in the wrong resolution (not sarcasm, I feel this way), you can use a separate popup window to check their settings the first time the program is run.


fox95871(Posted 2010) [#4]
I don't want to be furious, it's just that every time I try one of my games on a laptop or something, everything gets stretched out and looks terrible. Round objects become oval, etc. My laptop has a 1024 x 600 setting, and when I run a 640 x 480 game on it, it ends up being 640 x 375, including visible distortion of 3d objects. Could I use GfxMode3DExists and have it go through a list of all possible fullscreen resolutions? I thought all fullscreen modes were 4:3.

Last edited 2010


chi(Posted 2010) [#5]
You could try...
Global monratio# = api_GetSystemMetrics(0) / Float(api_GetSystemMetrics(1))

Graphics3D 800,600,0,1

cam=CreateCamera()
PositionEntity cam,0,0,-4

AspectRatio(cam)

cube=CreateCube()

Repeat
	RenderWorld
	Flip
Until KeyHit(1)
End

Function AspectRatio(Camera%)
	multiX# = monratio#/1.33333
	multiY# = GraphicsWidth()/Float(GraphicsHeight())/1.33333
	ScaleEntity(Camera%, multiX#, multiY#, multiX#)
End Function



Yasha(Posted 2010) [#6]
I thought all fullscreen modes were 4:3


Nope, fullscreen modes are whatever the card decrees are available (Blitz3D doesn't offer any ratio restrictions, but you can only take advantage of ridiculous resolutions like 1900x2 in windowed mode). It's even possible, but unlikely, that a card might not support 4:3 at all. Checking GfxModeExists (or whatever the precise command is) is the generally accepted way to do this.

The only restriction is that DirectX7 can't necessarily use all of the modes available on a modern graphics card and some will return as "junk" values. I've found that these only seem to be at the very bottom and very top of the scale, so you can filter your results to be within a given range, e.g. X must be greater than 640 and less than 2048. (The minimum seems to vary; the highest resolution you can have in DirectX7 and therefore Blitz3D is 2048 x 1536).

One other note - you have to call CountGfxModes and then iterate through the list. CountGfxModes creates the graphics mode list for you to examine, so GfxModeExists or whatever the command is won't work properly until that's done.

Last edited 2010


BIG BUG(Posted 2010) [#7]
CameraZoom camera, Float#(c_screen_height) / c_screen_width + 0.25



fox95871(Posted 2010) [#8]
Thank you all, I'm very grateful. This has been worrying me for a while because my game engine and games are all going to use a 2d overlay over a 3d backdrop system, and it's been starting to look like they're only going to end up working on old monitors like mine. But now I have some possible fixes I can try. I'll post my results once I have them.

Last edited 2010


fox95871(Posted 2010) [#9]
Okay, I've discovered that some laptops stretch out the image, and others don't, creating a black border around the CameraClsColor area in 640 x 480 mode. Since I can't rely on that though, I think I'll use the CountGfxModes3D GfxMode3DExists method, then center my 2d overlays so they line up with the 3d backdrop if a screen's 3d area is a little bigger than 640 x 480, not get drawn at 0 0.

Last edited 2010


Robert Cummings(Posted 2010) [#10]
I just support 16:9, with 16:10 showing a tiny bit more, and 4:3 showing borders, or just showing more on the height side of things.


_PJ_(Posted 2010) [#11]
Sorry I didn't quite understand in my first post.

As Robert kind of suggests, you might want to try a 4:3 ratio viewport with borders, though of course, naturally this would waste a bit of available screen.
Stretching of objects is natural for widescreen modes. The camera itself essentially shows a square image there's no fov/camerazoom equivalent for JUST the vertical, most often squashed into a 4:3 ratio but thios is more acceptable than the 16:9 etc. When using widescreen resolutions, the apparent 'squashing' is more noticeable. You will always therefore get some distrtion around the edges since (to my knowledge) there aren't any 1:1 valid ratios (and if there are, they would be less likely to be supported by the majority of cards/monitors).


Yasha(Posted 2010) [#12]
Stretching of objects is natural for widescreen modes. The camera itself essentially shows a square image there's no fov/camerazoom equivalent for JUST the vertical, most often squashed into a 4:3 ratio but thios is more acceptable than the 16:9 etc. When using widescreen resolutions, the apparent 'squashing' is more noticeable.


I hate to be a downer Malice, but this is completely untrue...

The camera vertical FOV will always be correct for the resolution you used when calling Graphics3D. If you're getting stretched images, it's because you called Graphics3D with values different from what your monitor supports natively.

Distortion around the edges is also unrelated to resolution - it's a side-effect of perspective projection and won't go away unless you also get rid of perspective (although you can mitigate it with zoom). Since it happens in real life, this is generally considered "correct" behaviour.


_PJ_(Posted 2010) [#13]
Oh I know the distortion around the edges is just parallax, since the 3D world is projected onto a 2D flat surface, and there will ALWAYS be elements of this, unless you have a FOV angle so small, and a range so short that ony an object dead in front of the camera and right up close can be rendered.

What I was referring to was the FOV will not change, only the ratio of pixels to angle to account for the aspect ratio. This includes vertical as well as horizontal, since aspect ratio involves both dimensions.
The result is that objects (regardless of whrether at the edge of screen or not) will appear squashed/stretched by varied amounts as the ratio changes.

If you want to, you can test this:
For n=1 To CountGfxModes3D()

Graphics3D GfxModeWidth(n),GfxModeHeight(n),32,2
SetBuffer BackBuffer()

cam=CreateCamera()
;CameraViewport cam,0,0,480,480
sphere=CreateSphere()
PositionEntity sphere,0,0,2
While Not KeyHit(57)
RenderWorld
Flip
Wend
FreeEntity camera
FreeEntity sphere
FlushKeys()

Next


See how the shape changes? This isn't an effect of parallax, but of the FOV (Which doesn't change even with different Graphics3D calls) compared to the aspect ratio of the render viewport.
By uncommenting the Viewport line, to maintain a square ratio, you can see how the distortion then ceases.

Last edited 2010


Yasha(Posted 2010) [#14]
See how the shape changes? This isn't an effect of parallax, but of the FOV (Which doesn't change even with different Graphics3D calls) compared to the aspect ratio of the render viewport.


The shape doesn't change on my computer. If it is changing on your computer, then that's a serious B3D bug/error and you should put it in the Bug Reports forum...


jfk EO-11110(Posted 2010) [#15]
As long as a Graphics Resolution is used that has the same ratio between width and height, it will be correct. But you cannot display a 4:3 ratio on a 16:9 physical display, because Blitz will never know of the 16:9, but simply draw everything to eg. 800*600 and the hardware will then stretch it to the full screen size.

The only way to prevent this is to allow the user to choose a resolution and to suggest to choose one that fits his physical RATIO best.

Actually you could use API calls to check the Desktop Resolution, or the physical Pixel resolution somehow and then automaticly choose the one that fits best. You could even do a speed test and choose a smaller one if neccessary.

Last edited 2010


_PJ_(Posted 2010) [#16]



Last edited 2010


jfk EO-11110(Posted 2010) [#17]
So what you say is not the width of the screen is diffrent, but the height? I agree, it may be a problem in some situations, eg. HUD sprites etc. But isn't it a rather simple task to calculate some kind of correction factor?


Yasha(Posted 2010) [#18]
Uh, Malice - what you've posted is an example of the image not being distorted. That's correct behaviour!

The top and bottom of the screen are cut off because the image is wider/shorter... what did you want to happen? If the camera had the same vertical FOV in both images, the sphere would appear squashed.

Last edited 2010


_PJ_(Posted 2010) [#19]
Yeah, sorry Yasha, I think we got our wires crossed somewhere. That'll teach me to read in future, and explain myself better.

The vertical FOV is diminished in order to prevent the distortion caused by the scaling of the horizontal FOV to fit the width of the resolution.

In my personal preference, though, distorted views with Horizontal and Verttical FOV preserved, are more 'correct', if not particularly aesthetic.


As long as a Graphics Resolution is used that has the same ratio between width and height, it will be correct. But you cannot display a 4:3 ratio on a 16:9 physical display, because Blitz will never know of the 16:9

:) sums it all up nicely!


fox95871(Posted 2010) [#20]
It looks like all I need now then is a list of all possible screen resolutions. Anyone know of a good comprehensive list?

Last edited 2010


Yasha(Posted 2010) [#21]
That's what CountGfxModes creates for you (give or take the aforementioned extreme values).

If you're worried about positioning HUD elements over a variable-sized 3D display, there is another way - using a virtual HUD resolution, you can position your 2D items proportionally to the screen without having to know it's actual size. Draw3D (see the userlibs section) is one drawing library that includes this feature.

Most cards will also support 640x480, 800x600 and 1024x768 (640x480 isn't guaranteed any more though as it's totally obsolete - 1024x768 is the safest option). However, as is the whole point of this thread, assuming resolutions in advance will lock you into the distortion problem - I'd strongly recommend against assuming figures at all (except possibly for an initial default setup).


jfk EO-11110(Posted 2010) [#22]
I would also suggest to force the user to select a resolution, esp. when he chooses Fullscreen. Because, even when you determine the real physical Ratio and then find a resolution that has about the same ratio, you will not know if this resolution will cover the entire screen, or if there will be bars. I just tried a 16/17:10 resolution (eg. 800x480 and 640x400, or 1280x800) on a 16:10 Monitor, but the card added bars at the top and bottom for some strange reason, resulting in stretched Ratio, regardless of the correct Ratio of the choosen Resolution.One single solution may be to use the Desktops Resolution (using some API Calls), assuming the Ratio is ok there.


fox95871(Posted 2010) [#23]
Tricky stuff. Now I know why Silent Hill 2 PC has so many visible flaws on my computer, and a huge patch file for all the different videocards it might be run on. If it's hard for a big company like Konami to get everything right, what are my chances? But I'll keep trying. Thank you for all the help so far.

Last edited 2010


Sledge(Posted 2010) [#24]
I'm unaware of any way to determine whether your users' monitor drivers support the preservation of a non-native resolution's aspect ratio or, further, whether the user has that option selected where it is switchable. I think the expedient way to deliver a correctly ratio'ed game on systems that don't automatically flit to the correct aspect ratio is to offer a windowed mode.