[LIB] Affine transformations with pivot point

I had a problem few days ago and I couldn’t find anything that handle the problem in a consistent and complete way (if there is one I really couldn’t find it).

So I’ve developed (and I’ve just published) a small library to handle affine transformations (rotate, scale, skew, flip…) with a pivot point.

(Since I am a newbie this was also a good exercise that allowed me also to learn a lot)

akifox-transform

It is cool because you can set an arbitrary pivot point or an anchored one (topleft, middlecenter, bottomleft and so on… all the nine typical positions).

It is transparent to the user because it handle the translation to keep the pivot point consistent behind the scenes.

You can try it by yourself from my repo (live example, code and docs)


README.md for all the links and infos.

It is on haxelib obiously.

If you have suggestions or ideas don’t be shy and tell me.

Thanks,
have a nice day :wink:

5 Likes

Update: v1.0.1 Added support for motion.Actuate

I’ve added the properties rotation, skewingX, skewingY, translationX, translationY, scalingX, scalingY
So now it is possible to use Actuate to animate these properties.

In the example (see the README.md) I’ve mapped a tween on translationX and Y on the keys T and G.

Cheers.
yup

Hello !

I’ve seen your libraries and I’m asking myself about one thing, is it possible to make the same things with only a Matrix ?

Because if you want to change many object by the same way, like a tile in a Tilesheet, you will want to use only one Matrix if you can no ? :smile:

I’m actually trying to make this code work without Display, in inheritence of the class Matrix. :wink:

I hope it will work with the tile of a Tilesheet this way, and if it, I’ll give you the source, if you want of course. :wink:

The library works on a Matrix.
I’ve made it like this.

Since it was useful to me to apply that directly to a DisplayObject I’ve made a .bind method, but you don’t have to use it :wink:

package ;
import com.akifox.transform.Transformation;

class Main {

    public function new() {
            var trf = new Transformation();
            trf.rotation = 90;
            trace(trf.matrix);
        }

}
```

---

These assignments modify the target/matrix property according to the pivot point (all of the degree ones are provided in Rad as well)

trf.x = valuePixels;
trf.y = valuePixels;
trf.rotation = valueDegrees;
trf.skewingX = valueDegrees;
trf.skewingY = valueDegrees;
trf.scaling = valueFactor; //set X and Y scale to this factor
trf.scalingX = valueFactor;
trf.scalingY = valueFactor;


The methods provide instead a algebric sum change according to the pivot point (all of the degree ones are provided in Rad as well)

trf.translate(addPixelsX,addPixelsY);
trf.translateX(addPixels);
trf.translateY(addPixels);
trf.rotate(addDegrees);
trf.skewX(addDegree);
trf.skewY(addDegree);
trf.scale(multiplyFactor);
trf.scaleX(multiplyFactor);
trf.scaleY(multiplyFactor);

and here’s the full doc
https://dl.dropboxusercontent.com/u/683344/akifox/akifox-transform/docs/index.html

I was wondering why .bind was appart, I understand now. :smile:

But I don’t like to use something with things that I havn’t to use, so, I’ve made a Matrix class with all your libraries, I’ve juste to check if it’s working like your’s. :wink:

Thanks to you, I’ve learn some things usefull in Haxe, I’ve started to learn the last week. :smile:

Actually there is not so much overhead to justify making a different library (the .bind part just copy the Transformation's matrix to the Display object's matrix, that’s all).

But since the library (as most of my work) is under MIT licence, feel free to do as you want, but if I may say please share what you do with the community so other people could learn from your code as you may have learnt from mine.

have a good one mate :wink:

So I’ve try this but nothing happend on the debug view :

class Main extends Sprite {

	public function new () {
	
		super ();
    		var trans:Transformation = new Transformation(new Matrix(),50,40);
    		trans.skewingX=50;
		trans.scalingX=2.5;
		trans.rotation=50;
		trans.debugDraw(true,true,true,true,true);
		trans.spriteDebug.x=trans.spriteDebug.y=150;
		addChild(trans.spriteDebug);
	}
}

There is a problem in what I wrote ?

Edit (You write at the same time as me) : Yes, of course. :wink:

You forget this

Lib.current.stage.addChild(this);

after super();

otherwise your Sprite Main will not be on stage


also, I don’t know what you expect from the debugDraw, but probably it works a little bit different from what you want.

It does not draw the transformation, just the rectangle that include the final transformed object (in your case a rectangle 50x40)

It’s what I actually want, to try after the system with the Matrix. :wink:

Thanks you, I feel dumb for that right now. :smile:

Erratum : I’ve forgot that the problem isn’t the drawing really, but the fact that the debugDraw don’t show the transformation, I’ve not two but only one Rectangle drawn. :confused:

there is a ‘bug’ in the debug draw about the width and height of the transformed rect (if you don’t use a display object but just a plain matrix)

I am trying to fix it, I’ve seen it as well.

Everything works fine about the matrix, it is just a problem in the debug draw.

Ok, so I would try my things with a displayable Objects. :smile:

I’ve fixed it. It is updated on haxelib as well.

I’ve seen some incompatibilities with OpenFL 3, so if you can use -Dlegacy when you compile
The matrix should work (there were known problems in OpenFL3 with skewing, it seems most of that is fixed now), the debugDraw will work in strange ways.