From 45c2dd9be7846c708019754f1c6e96b3012541b2 Mon Sep 17 00:00:00 2001
From: faiface <faiface@ksp.sk>
Date: Wed, 21 Dec 2016 20:31:09 +0100
Subject: [PATCH] add InvMat3, Project and Unproject methods to Transform

---
 transform.go | 26 ++++++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/transform.go b/transform.go
index 2d73b56..0f1c657 100644
--- a/transform.go
+++ b/transform.go
@@ -98,6 +98,22 @@ func (t Transform) Rotate(angle float64) Transform {
 	return t
 }
 
+// Project transforms a vector by a transform.
+func (t Transform) Project(v Vec) Vec {
+	mat := t.Mat3()
+	vec := mgl32.Vec3{float32(v.X()), float32(v.Y()), 1}
+	pro := mat.Mul3x1(vec)
+	return V(float64(pro.X()), float64(pro.Y()))
+}
+
+// Unproject does the inverse operation to Project.
+func (t Transform) Unproject(v Vec) Vec {
+	mat := t.InvMat3()
+	vec := mgl32.Vec3{float32(v.X()), float32(v.Y()), 1}
+	unp := mat.Mul3x1(vec)
+	return V(float64(unp.X()), float64(unp.Y()))
+}
+
 // Mat3 returns a transformation matrix that satisfies previously set transform properties.
 func (t Transform) Mat3() mgl32.Mat3 {
 	mat := mgl32.Ident3()
@@ -108,6 +124,16 @@ func (t Transform) Mat3() mgl32.Mat3 {
 	return mat
 }
 
+// InvMat3 returns an inverse transformation matrix to the matrix returned by Mat3 method.
+func (t Transform) InvMat3() mgl32.Mat3 {
+	mat := mgl32.Ident3()
+	mat = mat.Mul3(mgl32.Translate2D(float32(t.anc.X()), float32(t.anc.Y())))
+	mat = mat.Mul3(mgl32.Scale2D(float32(1/t.sca.X()), float32(1/t.sca.Y())))
+	mat = mat.Mul3(mgl32.Rotate3DZ(float32(-t.rot)))
+	mat = mat.Mul3(mgl32.Translate2D(float32(-t.pos.X()), float32(-t.pos.Y())))
+	return mat
+}
+
 // Camera is a convenience function, that returns a Transform that acts like a camera.
 // Center is the position in the world coordinates, that will be projected onto the center of the screen.
 // One unit in world coordinates will be projected onto zoom pixels.
-- 
GitLab