Converting coordinates between matrix and pixels

Monkey Forums/Monkey Programming/Converting coordinates between matrix and pixels

ziggy(Posted 2013) [#1]
I need a way to translate a 2D vector representing a device pixel (x and y) to the current whatever transformed matrix, and a way to calculate backwards too. I need this for JungleGui, so it should be possible to calculate all this without modifing Monkey and in a transparent way. You know, Mojo users that add Jungle Gui should have to be able to use it without having to modify previous code.

Any suggestions? Am I missing anything?


dragon(Posted 2013) [#2]
?

screen pixel x,y to transformed matrix x,y
is inversed transformation:
http://www.monkeycoder.co.nz/Community/posts.php?topic=1992#39366

backwards what you mean is normal transformaton using normal matrix math (same that use mojo - see SetMatrix() or so)


ziggy(Posted 2013) [#3]
But how can I get all the matrix that are on the matrix stack? should I loop through them or something? I've been coding for hours so I think I'm missing something damn easy somewhere


dragon(Posted 2013) [#4]
every transformation is based on prev. transformation (multiplied matrices)

i do not know how this can be useful - or for what
push&pop is a good technique


benmc(Posted 2013) [#5]
Off Topic: I was trying to buy JungleIDE today, and on the checkout page, even tho I had all the fields filled in, it kept saying that I needed to fill in the red required fields and wouldn't let me buy it :(


ziggy(Posted 2013) [#6]
Ok so getting latest transformation matrix I cold just multiply somehow the X and Y vector and get the appropriate transformed vector, isn't it?

@benmc: I don't know what can be happening, it might be an issue with the Avangate checkout page or something? Let me know so I can contact them, if you have more problems


Skn3(Posted 2013) [#7]
Does this help?

http://www.monkeycoder.co.nz/Community/posts.php?topic=617


Tibit(Posted 2013) [#8]
I wrote a Transform class that I think might be doing what you want. I use it for my scene-node system that connects to the camera.

To get the "global" transform I save it in each node.

Do all transforms for each element, and each children then render. Then save the transform as you render it.

PushMatrix()
Render()
GlobalMatrix.transform = GetMatrix() 'GlobalMatrix is of the Transform Class below
RenderChildren()
PopMatrix()

To get an object's world location I'd go:
myObject.GlobalMatrix.X

To get an object's world rotation I'd go:
myObject.GlobalMatrix.Angle

To get an object's world scale I'd go:
myObject.GlobalMatrix.ScaleX




Took me a while to figure it out. If you can find use for it feel free to use however you like :)

Let me know if you want the sceneNode and Camera as well.


slenkar(Posted 2013) [#9]
if you use GetMatrix and save the results to an array
you can actually get the x and y coordinates

I think its local matrix[]:Float =GetMatrix()

screen_x:Int=matrix[3]
screen_y:Int=matrix[4]

I might have the array indices wrong, you can experiment to get the right ones.


Tibit(Posted 2013) [#10]
I think it should be:

screen_x = transform[4]
screen_y = transform[5]

(see my code above, it does exactly that!)


ziggy(Posted 2013) [#11]
First of all, thanks for all the info, samples and help. It's very apreciated!

I think it should be:

screen_x = transform[4]
screen_y = transform[5]

(see my code above, it does exactly that!)

As I understand this, this would give the translation coordinates of the current Matrix, won't they? I would also need to take into account rotation and scaling (and shearing if any).

I think I did not explained properly what I'm after.

What I do really need (not sure if it was explained properly) is this:

When a user clicks the mouse on the canvas (or touches it), I want to know WHERE it has been clicked inside the logical transformed coordinates, instead of having the device pixels information. And a way to get calculate back, given a logical location, get the device pixel of this logical location.

Any help on this? I'm a bit lost as it's been a long time since I used transformation matrixs


Samah(Posted 2013) [#12]
You need to apply the current transformation matrix to convert world-to-screen.

http://en.wikipedia.org/wiki/Transformation_matrix

Try something like this (untested) where sx,sy = screen x,y and wx,wy = world x,y:
[monkeycode]Local mat:Float[] = GetMatrix()
Local wx:Float = sx * mat[0] + sy * mat[2] + mat[4]
Local wy:Float = sx * mat[1] + sy * mat[3] + mat[5][/monkeycode]
To convert screen-to-world (which is what you want, I think), you will need to do the same thing, but with the inverse matrix.

http://stackoverflow.com/questions/12715447/how-to-create-an-inverse-transformation-matrix
https://github.com/libgdx/libgdx/blob/master/gdx/src/com/badlogic/gdx/math/Matrix3.java


ziggy(Posted 2013) [#13]
@Samah: It did not work, not sure why, also, I'm not sure if the Monkey matrix is row centric or columnb centric. Whatever, I've realised that Scissor commands are not scaled by the matrix, so my GUI can't be scaled properly without failing on the rendering state, unless I calculate the scrissor scaling and find a magic wey to allow subpixel viewports, wich doesn't exist on OpenGL AFAIK, so JungleGUI will automatically render always at pixel level, no mather what transforms are applied to the world.
I'm just adding current matrix to the stack, replacing it with a 1,0,0,1,0,0 matrix, and to the GUI stuff, then remove the matrix from the stack so the process is "transparent" to any program using Jungle Gui.

That said, I miss a world to device and device to world conversion commands on Mojo. If you want to interact with mouse/touch vectors and world vectors, it is a PITA right now.