From f97eb6d881b59391bb61847ff9d16a5cd72a357f Mon Sep 17 00:00:00 2001 From: Aaron Franke Date: Tue, 12 Feb 2019 12:39:10 -0500 Subject: [PATCH] [Mono] Fix Transform2D rotation and scale --- .../mono/glue/Managed/Files/Transform2D.cs | 62 +++++++++++++++---- 1 file changed, 50 insertions(+), 12 deletions(-) diff --git a/modules/mono/glue/Managed/Files/Transform2D.cs b/modules/mono/glue/Managed/Files/Transform2D.cs index f89c99cff2a..df7ba3402d1 100644 --- a/modules/mono/glue/Managed/Files/Transform2D.cs +++ b/modules/mono/glue/Managed/Files/Transform2D.cs @@ -17,12 +17,40 @@ namespace Godot public real_t Rotation { - get { return Mathf.Atan2(y.x, origin.y); } + get + { + real_t det = BasisDeterminant(); + Transform2D t = Orthonormalized(); + if (det < 0) + { + t.ScaleBasis(new Vector2(1, -1)); + } + return Mathf.Atan2(t.x.y, t.x.x); + } + set + { + Vector2 scale = Scale; + x.x = y.y = Mathf.Cos(value); + x.y = y.x = Mathf.Sin(value); + y.x *= -1; + Scale = scale; + } } public Vector2 Scale { - get { return new Vector2(x.Length(), y.Length()); } + get + { + real_t detSign = Mathf.Sign(BasisDeterminant()); + return new Vector2(x.Length(), detSign * y.Length()); + } + set + { + x = x.Normalized(); + y = y.Normalized(); + x *= value.x; + y *= value.y; + } } public Vector2 this[int index] @@ -95,7 +123,7 @@ namespace Godot { var inv = this; - real_t det = this[0, 0] * this[1, 1] - this[1, 0] * this[0, 1]; + real_t det = BasisDeterminant(); if (det == 0) { @@ -107,20 +135,25 @@ namespace Godot ); } - real_t idet = 1.0f / det; + real_t detInv = 1.0f / det; real_t temp = this[0, 0]; this[0, 0] = this[1, 1]; this[1, 1] = temp; - this[0] *= new Vector2(idet, -idet); - this[1] *= new Vector2(-idet, idet); + this[0] *= new Vector2(detInv, -detInv); + this[1] *= new Vector2(-detInv, detInv); this[2] = BasisXform(-this[2]); return inv; } + private real_t BasisDeterminant() + { + return x.x * y.y - x.y * y.x; + } + public Vector2 BasisXform(Vector2 v) { return new Vector2(Tdotx(v), Tdoty(v)); @@ -220,6 +253,14 @@ namespace Godot return copy; } + private void ScaleBasis(Vector2 scale) + { + x.x *= scale.x; + x.y *= scale.y; + y.x *= scale.x; + y.y *= scale.y; + } + private real_t Tdotx(Vector2 with) { return this[0, 0] * with[0] + this[1, 0] * with[1]; @@ -274,12 +315,9 @@ namespace Godot public Transform2D(real_t rot, Vector2 pos) { - real_t cr = Mathf.Cos(rot); - real_t sr = Mathf.Sin(rot); - x.x = cr; - x.y = -sr; - y.x = sr; - y.y = cr; + x.x = y.y = Mathf.Cos(rot); + x.y = y.x = Mathf.Sin(rot); + y.x *= -1; origin = pos; }