avm1: Use f64 when calculating scale/rotation (fix #1622)

This commit is contained in:
Mike Welsh 2020-11-20 20:32:07 -08:00
parent 5ea3814097
commit 8d78ee5172
5 changed files with 20 additions and 13 deletions

View File

@ -171,10 +171,10 @@ impl<'gc> DisplayObjectBase<'gc> {
fn cache_scale_rotation(&mut self) {
if !self.flags.contains(DisplayObjectFlags::ScaleRotationCached) {
let (a, b, c, d) = (
self.transform.matrix.a,
self.transform.matrix.b,
self.transform.matrix.c,
self.transform.matrix.d,
f64::from(self.transform.matrix.a),
f64::from(self.transform.matrix.b),
f64::from(self.transform.matrix.c),
f64::from(self.transform.matrix.d),
);
// If this object's transform matrix is:
// [[a c tx]
@ -190,14 +190,14 @@ impl<'gc> DisplayObjectBase<'gc> {
// This can produce some surprising results due to the overlap between flipping/rotation/skewing.
// For example, in Flash, using Modify->Transform->Flip Horizontal and then tracing _xscale, _yscale, and _rotation
// will output 100, 100, and 180. (a horizontal flip could also be a 180 degree skew followed by 180 degree rotation!)
let rotation_x = f32::atan2(b, a);
let rotation_y = f32::atan2(-c, d);
let scale_x = f32::sqrt(a * a + b * b);
let scale_y = f32::sqrt(c * c + d * d);
self.rotation = Degrees::from_radians(rotation_x.into());
self.scale_x = Percent::from_unit(scale_x.into());
self.scale_y = Percent::from_unit(scale_y.into());
self.skew = (rotation_y - rotation_x).into();
let rotation_x = f64::atan2(b, a);
let rotation_y = f64::atan2(-c, d);
let scale_x = f64::sqrt(a * a + b * b);
let scale_y = f64::sqrt(c * c + d * d);
self.rotation = Degrees::from_radians(rotation_x);
self.scale_x = Percent::from_unit(scale_x);
self.scale_y = Percent::from_unit(scale_y);
self.skew = rotation_y - rotation_x;
self.flags.insert(DisplayObjectFlags::ScaleRotationCached);
}
}

View File

@ -416,7 +416,7 @@ swf_tests! {
// Some will probably always need to be approx. (if they rely on trig functions, etc.)
swf_tests_approx! {
(local_to_global, "avm1/local_to_global", 1, epsilon = 0.051),
(stage_object_properties, "avm1/stage_object_properties", 5, epsilon = 0.051),
(stage_object_properties, "avm1/stage_object_properties", 6, epsilon = 0.051),
(stage_object_properties_swf6, "avm1/stage_object_properties_swf6", 4, epsilon = 0.051),
(movieclip_getbounds, "avm1/movieclip_getbounds", 1, epsilon = 0.051),
(edittext_letter_spacing, "avm1/edittext_letter_spacing", 1, epsilon = 15.0), // TODO: Discrepancy in wrapping in letterSpacing = 0.1 test.

View File

@ -233,3 +233,10 @@ _yscale:
_root._target:
/
90-degree rotations:
// clip1: 0
// clip2: 90
// clip3: 180
// clip4: -90