Sorry your browser is not supported!

You are using an outdated browser that does not support modern web technologies, in order to use this site please update to a new browser.

Browsers supported include Chrome, FireFox, Safari, Opera, Internet Explorer 10+ or Microsoft Edge.

AppGameKit Classic Chat / Turning screen co-ordinates into 3D space?

Author
Message
Scraggle
Moderator
20
Years of Service
User Offline
Joined: 10th Jul 2003
Location: Yorkshire
Posted: 4th Jul 2016 10:41 Edited at: 4th Jul 2016 12:52
I need a little help from a 3D maths wizard!

What I need is a function to place a 3D object in the world by specifying screen co-ordinates not 3D co-ordinates. So something like:
x# = Get3DXFromScreen( x, y, z )
y# = Get3DYFromScreen( x, y, z )
Where x and y are screen co-ordinates and z is the depth in 3D space.

No need for a Get3DZFromScreen( x, y, z ) because that is our personal choice.

The reason for this (as I'm sure you're wondering) is because I want to create 2D games using 3D objects. Think classic 8 bit games like 'Space Invaders'. It's simple enough using sprites but when you convert to 3D objects, knowing the position of objects relative to the screen is not as easy to calculate.
With trial and error I can work it out for a specific screen but I want this to work on multiple devices so trial and error is not an option.

It may be possible that this can be achieved using Get3DVectorXFromScreen(), Get3DVectorYFromScreen() and Get3DVectorZFromScreen() but since they return a directional vector I'm unsure of how to turn that into a point in 3D space at my desired depth.

Any 3D maths wizards out there?
Thanks!

[Edit] This might be easier than I thought. Using the directional vector from the above commands combined with a plane positioned at my required z depth it would be a simple ray/plain collision test. I will have a play with this after work tonight.... unless someone beats me to it
AGK V2 user - Tier 1 (mostly)
Stab in the Dark software
Valued Member
21
Years of Service
User Offline
Joined: 12th Dec 2002
Playing: Badges, I don't need no stinkin badges
Posted: 4th Jul 2016 15:12 Edited at: 4th Jul 2016 15:14
This is what I do for picking an object using ray casting with physics.
The code below is the raycasting demo I posted here.

https://forum.thegamecreators.com/thread/216683

Look at the PickJointCreateAndUpdate() function, I get the screen coordinates which are returned as a directional vector,
then turn it into a point in 3d space.

The coffee is lovely dark and deep,and I have code to write before I sleep.
Scraggle
Moderator
20
Years of Service
User Offline
Joined: 10th Jul 2003
Location: Yorkshire
Posted: 5th Jul 2016 09:45
Thanks for the code Stab but I'm not sure it's what I'm looking for.
Maybe I'm missing something but your code seems to cast a ray from the screen and check for collision with an object from it.
What I'm trying to do is cast a ray from the screen and establish the 3D point that the ray intersect a particular zdepth or distance from the camera (but since my camera is fixed they are both essentially the same thing) so that I can place an object there.

My edited suggestion about it being easier than I thought is wrong. I still need to calculate the size of the view frustum at the desired depth in order to create a plain for collision tests, then I need to know the position within the plain that the ray intersected.

I'm reading "Real-Time Collision Detection" by Christer Ericson (great book!) which I'm sure has all the info I need but it's heavy reading!
AGK V2 user - Tier 1 (mostly)
Scraggle
Moderator
20
Years of Service
User Offline
Joined: 10th Jul 2003
Location: Yorkshire
Posted: 5th Jul 2016 21:00 Edited at: 5th Jul 2016 21:17
I've solved it - sort of!
Since I wanted a one off job for a fixed camera position I decided to use brute force.
I created a one unit sphere, positioned at in the centre of the view port then moved it left/right/up/down until it left the screen and stored each dimension.
Id still prefer a mathematical solution that would be suitable for any situation if anyone would care to take up the challenge but this will do for now.

If anyone is interested in my brute force method, its below.
It presumes a camera at 0, 0, -175 looking back at 0, 0, 0 but it works for any screen size and dimension



Obviously that's not exactly what I asked for in the initial post but knowing the size of the view frustrum at the desired depth and knowing the size of the display is enough to calculate the required coordinates
AGK V2 user - Tier 1 (mostly)
Markus
Valued Member
20
Years of Service
User Offline
Joined: 10th Apr 2004
Location: Germany
Posted: 5th Jul 2016 21:51 Edited at: 5th Jul 2016 21:55
there is also
GetScreenXFrom3D ( x, y, z )
GetScreenYFrom3D ( x, y, z )

GetVirtualHeight ()
GetVirtualWidth ()
GetScreenBoundsBottom ()
GetScreenBoundsLeft ()
GetScreenBoundsRight ()
GetScreenBoundsTop ()
AGK (Steam) V2.0.19 : Windows 10 Pro 64 Bit : AMD (16.3.2) Radeon R7 265 : Mac mini OS X 10.10 (Yosemite)
Scraggle
Moderator
20
Years of Service
User Offline
Joined: 10th Jul 2003
Location: Yorkshire
Posted: 6th Jul 2016 08:08 Edited at: 6th Jul 2016 08:09
Thanks Markus but all those commands do the opposite of what I am trying to achieve.
Ideally I would like the commands:
Get3DXFromScreen(x, y, z)
Get3DYFromScreen(x, y, z)
Where x & y are screen co-ordinates and z is the distance from the camera.
AGK V2 user - Tier 1 (mostly)
Mobiius
Valued Member
21
Years of Service
User Offline
Joined: 27th Feb 2003
Location: The Cold North
Posted: 6th Jul 2016 09:18
I know that 2dX = 3dX / 3dZ, and 2dY = 3dY / 3dZ. So maybe 3dX = 2dX * 3dZ & 3dY = 2dY * 3dZ. (Which only works with the camera at 0, 0, 0 and 0, 0, 0 rotation.
Paul Johnston
TGC Developer
21
Years of Service
User Offline
Joined: 16th Nov 2002
Location: United Kingdom
Posted: 6th Jul 2016 14:25
Would this work?

although that would produce a series of points that form a sphere around the camera. If you need the points to lie on a plane then the following should work

Markus
Valued Member
20
Years of Service
User Offline
Joined: 10th Apr 2004
Location: Germany
Posted: 6th Jul 2016 18:25
Quote: "those commands do the opposite"

it belongs your code snippet / GetBruteForce3DscreenSize
instead of moving a 3d object you can also use GetScreenXFrom3D there and look if the x,y result is inside your "screen", so your get a border.

Quote: "
Ideally I would like the commands:
Get3DXFromScreen(x, y, z)
Get3DYFromScreen(x, y, z)
Where x & y are screen co-ordinates and z is the distance from the camera.
"

yes, z should be the plane you will see in the screen.
z its more the front of the 3d object you will fit into the screen if you think in tiles.

may you can use orthographic view for 3d, see SetCameraOrthoWidth
there you will have no room warp.
AGK (Steam) V2.0.19 : Windows 10 Pro 64 Bit : AMD (16.3.2) Radeon R7 265 : Mac mini OS X 10.10 (Yosemite)
Scraggle
Moderator
20
Years of Service
User Offline
Joined: 10th Jul 2003
Location: Yorkshire
Posted: 7th Jul 2016 08:31
Thanks Paul,
That 2nd example is perfect! Exactly what I was looking for, you're are a star!

I turned it into a function so that it can be called easier, in case anyone else wants it:
AGK V2 user - Tier 1 (mostly)
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 8th Jul 2016 02:53
Quote: "

although that would produce a series of points that form a sphere around the camera. If you need the points to lie on a plane then the following should work"


Nice! I've been using the equivalent of the top method, but have been wanting it to work like the bottom this is handy

Login to post a reply

Server time is: 2024-05-04 10:41:48
Your offset time is: 2024-05-04 10:41:48