Bug 19341 - CGAffineTransformScale is Incorrect
Summary: CGAffineTransformScale is Incorrect
Status: VERIFIED FIXED
Alias: None
Product: iOS
Classification: Xamarin
Component: Xamarin.iOS.dll ()
Version: 7.2.2
Hardware: All All
: Normal normal
Target Milestone: Untriaged
Assignee: Bugzilla
URL:
: 7832 ()
Depends on:
Blocks:
 
Reported: 2014-04-28 11:07 UTC by Darlene
Modified: 2014-07-14 15:15 UTC (History)
6 users (show)

Tags:
Is this bug a regression?: ---
Last known good build:

Notice (2018-05-24): bugzilla.xamarin.com is now in read-only mode.

Please join us on Visual Studio Developer Community and in the Xamarin and Mono organizations on GitHub to continue tracking issues. Bugzilla will remain available for reference in read-only mode. We will continue to work on open Bugzilla bugs, copy them to the new locations as needed for follow-up, and add the new items under Related Links.

Our sincere thanks to everyone who has contributed on this bug tracker over the years. Thanks also for your understanding as we make these adjustments and improvements for the future.


Please create a new report on Developer Community or GitHub with your current version information, steps to reproduce, and relevant error messages or log files if you are hitting an issue that looks similar to this resolved bug and you do not yet see a matching new report.

Related Links:
Status:
VERIFIED FIXED

Description Darlene 2014-04-28 11:07:25 UTC
Hello.  I am converting part of an XCode project into C# via Xamarin and have traced a bug occurring in a mission critical part of the program to the MonoTouch framework.  The CGAffineTransform.Scale function does not properly calculate its values.  Mono runtime is 3.2.6.  I have prepared unit tests to demonstrate the bug:

XCODE UNIT TEST (Objective-C):
==============================

// Tests that the CGAffineTransformScale function computes the correct output.
- (void)testCGAffineTransformScale_Correct
{
	// Create a translation to scale
	CGAffineTransform transform = CGAffineTransformMakeTranslation(0, 200);
	
	// Verify transformation
	XCTAssertEqual(1, transform.a);
	XCTAssertEqual(0, transform.b);
	XCTAssertEqual(0, transform.c);
	XCTAssertEqual(1, transform.d);
	XCTAssertEqual(0, transform.tx);
	XCTAssertEqual(200, transform.ty);
	
	// Flip the transform
	transform = CGAffineTransformScale(transform, 1.0f, -1.0f);
	
	// Verify transformation
	XCTAssertEqual(1, transform.a);
	XCTAssertEqual(0, transform.b);
	XCTAssertEqual(0, transform.c);			// or -0
	XCTAssertEqual(-1, transform.d);
	XCTAssertEqual(0, transform.tx);
	XCTAssertEqual(200, transform.ty);		// Correct output
}

XAMARIN STUDIO UNIT TEST (C#):
==============================

/// <summary>
/// 	Tests that the CGAffineTransformScale function computes the correct output.
/// </summary>
[Test]
public void CGAffineTransformScale_Correct()
{
	// Create a translation to scale
	var transform = CGAffineTransform.MakeTranslation (0, 200);

	// Verify transformation
	Assert.AreEqual (1, transform.xx);		// a
	Assert.AreEqual (0, transform.yx);		// b
	Assert.AreEqual (0, transform.xy);		// c
	Assert.AreEqual (1, transform.yy);		// d
	Assert.AreEqual (0, transform.x0);		// tx
	Assert.AreEqual (200, transform.y0);		// ty

	// Flip the transform
	transform.Scale (1.0f, -1.0f);

	// Verify transformation
	Assert.AreEqual (1, transform.xx);		// a
	Assert.AreEqual (0, transform.yx);		// b
	Assert.AreEqual (0, transform.xy);		// c
	Assert.AreEqual (-1, transform.yy);		// d
	Assert.AreEqual (0, transform.x0);		// tx
	Assert.AreEqual (200, transform.y0);		// ty - BUG:  this value should not be negated
}

The test output from Xamarin is that ty/y0 is -200, when it should be 200.  These tests were done on a Mac, but the bug occurs using Visual Studio as well.

This is high priority.  The expectation is that the same logic used in Objective-C should translate to C# one-to-one, especially for a basic math function.  Previous research indicates this was reported before (8386) and nothing was done.  The Scale static method option is not even implemented in the 18 months since.  As it stands right now, the API in this particular instance is NOT CORRECT and that is NOT ACCEPTABLE.  Not correcting this behaviour will cause more problems in the future.

Thank you
Comment 1 Rolf Bjarne Kvinge [MSFT] 2014-04-29 08:03:56 UTC
Fixed.

I've added a new overload (a static CGAffineTransform.Scale method) that behaves like the native CGAffineTransformScale function.

maccore/master: 34e33ca28d86abe66bd308ceade235f2d45e9a33
monotouch/master: dcc7d102e77acd02648b900e846903b057a28b61

The fix will be included in Xamarin.iOS 7.4.
Comment 2 Rolf Bjarne Kvinge [MSFT] 2014-04-29 08:04:41 UTC
*** Bug 7832 has been marked as a duplicate of this bug. ***
Comment 3 Darlene 2014-04-29 08:48:15 UTC
Thank you Rolf :)
Comment 4 Udham Singh 2014-07-08 14:15:29 UTC
I have checked this issue with the code provided in bug description. I have debug the code and observed that we are still getting negative value for transform.y0, Hence I am reopening this issue.

Screencast : http://screencast.com/t/NQOr72WXctMt

Environment Info : 

=== Xamarin Studio ===

Version 5.2 (build 364)
Installation UUID: 561c7a69-0a91-4bae-ad7c-f0c79d594337
Runtime:
	Mono 3.6.0 ((no/5ff701f)
	GTK+ 2.24.23 (Raleigh theme)

	Package version: 306000037

=== Xamarin.Android ===

Version: 4.12.5 (Trial Edition)
Android SDK: /Users/tajinder/Desktop/android-sdk-macosx
	Supported Android versions:
		2.1   (API level 7)
		2.2   (API level 8)
		2.3   (API level 10)
		3.1   (API level 12)
		3.2   (API level 13)
		4.0   (API level 14)
		4.0.3 (API level 15)
		4.1   (API level 16)
		4.2   (API level 17)
		4.3   (API level 18)
		4.4   (API level 19)
Java SDK: /usr
java version "1.6.0_65"
Java(TM) SE Runtime Environment (build 1.6.0_65-b14-462-11M4609)
Java HotSpot(TM) 64-Bit Server VM (build 20.65-b04-462, mixed mode)

=== Apple Developer Tools ===

Xcode 5.1.1 (5085)
Build 5B1008

=== Xamarin.iOS ===

Version: 7.2.6.19 (Business Edition)
Hash: 36961c5
Branch: 
Build date: 2014-07-07 10:41:50-0400

=== Xamarin.Mac ===

Version:

=== Build Information ===

Release ID: 502000364
Git revision: fd8641a35ed89a183d04290f046a3aab5b09a867
Build date: 2014-07-07 13:16:52-04
Xamarin addins: 68026ad1ccee9923e927d9cfcca408d673d5ab61

=== Operating System ===

Mac OS X 10.8.4
Darwin Tajinders-iMac.local 12.4.2 Darwin Kernel Version 12.4.2
    Mon Jun 17 18:00:12 PDT 2013
    root:xnu-2050.45.8~1/RELEASE_X86_64 x86_64
Comment 5 PJ 2014-07-08 17:42:57 UTC
C1:
> The fix will be included in Xamarin.iOS 7.4.

C4:
> Version: 7.2.6.19 (Business Edition)

The reason Udham REOPENED for 7.2.6 is because the release notes for 7.2.6 [1] state that this fix made it in, and that is incorrect.

The action here is to remove the note for 7.2.6 (if my assessment is correct) and re-RESOLVE.

[1] http://developer.xamarin.com/releases/ios/xamarin.ios_7/xamarin.ios_7.2/#6
Comment 6 Rolf Bjarne Kvinge [MSFT] 2014-07-14 09:10:28 UTC
The behavior of the test case as reported in the initial description does not change since it would be a backwards incompatible change.

Instead new API was introduced in order to provide the expected behavior.

So a verification of the fix would be to ensure that a static CGAffineTransform.Scale method exists.
Comment 7 Udham Singh 2014-07-14 15:15:32 UTC
Thanks Rolf,

I have checked this issue and now we are getting the new static CGAffineTransform.Scale method and expected behavior mentioned in bug description. To check this issue I have implemented the code below

 // Create a translation to scale
var transform = CGAffineTransform.MakeTranslation(0, 200);

CGAffineTransform.Scale(transform,1,1);
// Verify transformation
Assert.AreEqual (1, transform.xx);        // a
Assert.AreEqual (0, transform.yx);        // b
Assert.AreEqual (0, transform.xy);        // c
Assert.AreEqual (1, transform.yy);        // d
Assert.AreEqual (0, transform.x0);        // tx
Assert.AreEqual (200, transform.y0);        // ty

// Flip the transform
//transform.Scale (1.0f, -1.0f);
CGAffineTransform.Scale(transform,1.0f, -1.0f);

// Verify transformation
Assert.AreEqual (1, transform.xx);        // a
Assert.AreEqual (0, transform.yx);        // b
Assert.AreEqual (0, transform.xy);        // c
//Assert.AreEqual (-1, transform.yy);        // d
Assert.AreEqual (0, transform.x0);        // tx
Assert.AreEqual (200, transform.y0);        // ty :  Now this value is getting as 200(+ve)

Screencast : http://screencast.com/t/NMPTPFZaO0G

Please let me know if I have to check anything else.

Environment Info : 

=== Xamarin Studio ===

Version 5.2 (build 375)
Installation UUID: 449f40dd-b3f1-4028-9a6b-cca0d1a2307d
Runtime:
	Mono 3.6.0 ((no/5ff701f)
	GTK+ 2.24.23 (Raleigh theme)

	Package version: 306000037

=== Apple Developer Tools ===

Xcode 5.1.1 (5085)
Build 5B1008

=== Xamarin.iOS ===

Version: 7.2.6.22 (Enterprise Edition)
Hash: b983743
Branch: 
Build date: 2014-07-13 20:15:09-0400

=== Xamarin.Android ===

Version: 4.14.0 (Enterprise Edition)
Android SDK: /Users/360logicaxamarinmacmini/Desktop/android-sdk-macosx
	Supported Android versions:
		1.6   (API level 4)
		2.1   (API level 7)
		2.2   (API level 8)
		2.3   (API level 10)
		3.1   (API level 12)
		3.2   (API level 13)
		4.0   (API level 14)
		4.0.3 (API level 15)
		4.1   (API level 16)
		4.2   (API level 17)
		4.3   (API level 18)
		4.4   (API level 19)
Java SDK: /usr
java version "1.6.0_65"
Java(TM) SE Runtime Environment (build 1.6.0_65-b14-462-11M4609)
Java HotSpot(TM) 64-Bit Server VM (build 20.65-b04-462, mixed mode)

=== Xamarin.Mac ===

Version: 1.8.0.8

=== Build Information ===

Release ID: 502000375
Git revision: 17e52b669da0b4437af9b3dc4f01b5b953ad13c1
Build date: 2014-07-14 12:47:32-04
Xamarin addins: 8d7daca6f45b75639988b66d681ec7cdb9641f9b

=== Operating System ===

Mac OS X 10.8.4
Darwin 360Logicas-Mac-mini.local 12.4.0 Darwin Kernel Version 12.4.0
    Sun Mar 10 18:01:10 PDT 2013
    root:xnu-2050.24.6~1/RELEASE_X86_64 x86_64