11local rotationFixes = {}
22local elementQuat = {}
3+ local fromQuatThreshold = 0.499999999
34
45function loadRotationFixXML ()
56 local xmlRoot = xmlLoadFile (" client/rotation_fix.xml" )
67 if not xmlRoot then
78 outputDebugString (" Cannot load rotation_fix.xml" )
89 return false
910 end
10-
11+
1112 rotationFixes = {}
12-
13+
1314 local models = xmlNodeGetChildren (xmlRoot )
1415 for k ,model in ipairs (models ) do
1516 local id = tonumber (xmlNodeGetAttribute (model , " id" ))
@@ -24,9 +25,9 @@ function loadRotationFixXML()
2425 outputDebugString (" Incorrect entry in rotation_fix.xml" )
2526 end
2627 end
27-
28+
2829 xmlUnloadFile (xmlRoot )
29-
30+
3031 return true
3132end
3233
@@ -43,7 +44,7 @@ function applyIncrementalRotation(element, axis, angle, world_space)
4344 local offset_quat -- Normalized
4445 local arad = math.rad (angle )
4546 local sina = math.sin (arad / 2 )
46-
47+
4748 if axis == " yaw" then
4849 offset_quat = {
4950 sina , 0 , 0
@@ -60,7 +61,10 @@ function applyIncrementalRotation(element, axis, angle, world_space)
6061 return false
6162 end
6263 offset_quat [4 ] = math.cos (arad / 2 )
63-
64+
65+ -- Get rotation patch userdata
66+ local enableRotPatch = exports [" editor_gui" ]:sx_getOptionData (" enableRotPatch" )
67+
6468 -- Get current rotation
6569 local cur_quat
6670 if elementQuat [element ] then
@@ -71,7 +75,7 @@ function applyIncrementalRotation(element, axis, angle, world_space)
7175 if euler_rot [1 ] == 0 and euler_rot [2 ] == 0 and euler_rot [3 ] == 0 then
7276 -- Is there a fix and are rotation patches enabled
7377 local id = getElementModel (element )
74- if rotationFixes [id ] and exports [ " editor_gui " ]: sx_getOptionData ( " enableRotPatch" ) then
78+ if rotationFixes [id ] and enableRotPatch then
7579 -- Rotate from the fix
7680 cur_quat = {unpack (rotationFixes [id ])}
7781 else
@@ -83,20 +87,27 @@ function applyIncrementalRotation(element, axis, angle, world_space)
8387 cur_quat = getQuatFromEuler (euler_rot )
8488 end
8589 end
86-
87- -- Rotate by the offset quaternion
88- -- Right or left multiplication for world or local space
89- if world_space then
90- cur_quat = quatMul (cur_quat , offset_quat )
90+
91+ -- Check if rotation patch is enabled
92+ if enableRotPatch then
93+ -- Rotate by the offset quaternion
94+ -- Right or left multiplication for world or local space
95+ cur_quat = world_space == true and quatMul (cur_quat , offset_quat ) or quatMul (offset_quat , cur_quat )
9196 else
92- cur_quat = quatMul (offset_quat , cur_quat )
97+ -- Do the old rotation behaviour
98+ if world_space then
99+ cur_quat = axis == " yaw" and quatMul (cur_quat , offset_quat ) or quatMul (offset_quat , cur_quat )
100+ else
101+ cur_quat = quatMul (offset_quat , cur_quat )
102+ end
93103 end
104+
94105 elementQuat [element ] = cur_quat
95-
106+
96107 -- Convert to euler and apply
97108 local cur_euler = getEulerFromQuat (cur_quat )
98109 setElementRotation (element , cur_euler [1 ], cur_euler [2 ], cur_euler [3 ], " ZYX" )
99-
110+
100111 return unpack (cur_euler )
101112end
102113
@@ -128,16 +139,16 @@ end
128139
129140function getEulerFromQuat (quat )
130141 local q0 , q1 , q2 , q3 = quat [1 ], quat [2 ], quat [3 ], quat [4 ]
131- local treshold = q0 * q2 - q3 * q1
132-
133- if treshold > 0.499 then
142+ local threshold = q0 * q2 - q3 * q1
143+
144+ if threshold > fromQuatThreshold then
134145 return {math.deg (2 * math.atan2 (q1 , q0 )), 90 , 0 }
135- elseif treshold < - 0.499 then
136- return {math.deg (- 2 * math.atan2 (q1 , q0 )), - 90 , 0 }
146+ elseif threshold < - fromQuatThreshold then
147+ return {math.deg (2 * math.atan2 (q1 , q0 )), - 90 , 0 }
137148 else
138149 return {
139150 math.deg (math.atan2 (2 * (q0 * q1 + q2 * q3 ), 1 - 2 * (q1 ^ 2 + q2 ^ 2 ))),
140- math.deg (math.asin (2 * treshold )),
151+ math.deg (math.asin (2 * threshold )),
141152 math.deg (math.atan2 (2 * (q0 * q3 + q1 * q2 ), 1 - 2 * (q2 ^ 2 + q3 ^ 2 )))
142153 }
143154 end
0 commit comments