Advertisement

Calculate points of rotated shape

Started by September 18, 2014 12:07 AM
6 comments, last by alvaro 10 years, 5 months ago

I have a shape(width and height always the same), looking like this:

[attachment=23668:org.png]

I then rotate it by 45 degrees and want to calculate the edge of each pillar.

[attachment=23669:rot.png]

The top-left corner of the shape is x:0 y:0.


want to calculate the edge..

The edge (i.e., a line) or the location of the red points?


The top-left corner of the shape is x:0 y:0.

Which direction are the axes? +Y up? down? Or +X up? down?

Clarification needed as mentioned.

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.

Advertisement

The red points is what I want to calculate.

Going down increases Y and moving right increases X.

I'll tell you how to perform the computation in coordinates where the center of rotation is also the origin. We can figure out how to adapt that for your case later. I'll also use the common convention in Math, where y grows going up and x grows going to the right.

Let's identify the point (x,y) with the complex number z = x+y*i. A rotation is also a complex number: r = cos(angle)+sin(angle)*i. The rotated point is simply z' = z*r. If you can use a data type for complex numbers, I would just do it that way. If you can only use real numbers, you can expand the formulas yourself:

x' = real(z*r) = x*cos(angle) - y*sin(angle)
y' = imag(z*r) = y*cos(angle) + x*sin(angle)


In order to rotate around any other point c (again as a complex number), first compute z-c, then multiply by r and finally add c back in.

z' = (z-c)*r+c

You can handle the flip in the y coordinate yourself.

I appreciate the help. But with very limited math skills, this is hard to understand. Particularly the complex-number part and the mathematical terms.

Its just throw me off. The results I get ingame are absurd.

Could you please explain in a way that is more basic?

Let's say you start with the top point of the first image, with coordinates (40,0). First we apply a translation that would bring the center of rotation (40,40) to the origin. That is, we subtract 40 from each coordinate. Our point is now (0,-40). Next we flip the sign of the y coordinate, to adhere to the usual mathematical convention for 2D axes, giving us (0,40). Now we apply the rotation formulas I gave you in my previous post:

x' = x*cos(angle) - y*sin(angle) = 0*cos(45 degrees) - 40*sin(45 degrees) = -28.28
y' = y*cos(angle) + x*sin(angle) = 40*cos(45 degrees) + 0*sin(45 degrees) = 28.28

So the point is now (-28.28,28.28).

Next we undo the flip of the y coordinate: (-28,28,-28.28). Finally, we undo the translation by adding back 40 to each coordinate. The coordinates of the upper-left red point are then (11.72,11.72).

I cannot make it any more basic than that. But the list of steps may seem arbitrary if you don't follow the description on my other post.

Advertisement

The example below returns 11.72, 11.72:


		double rot = Math.toRadians(45);
		float unitX = 40;
		float unitY = 0;
		
		float x = unitX - unitX;
		float y = unitY - unitX;
		
		y = Math.abs(y);
		
		float resX = (float) (x * Math.cos(rot) - y * Math.sin(rot));
		float resY = (float) (y * Math.cos(rot) + x * Math.sin(rot));
		
		resY = -resY;
		resX += unitX;
		resY += unitX;
		
		System.out.println(resX + " " + resY);

But when used in the game, the results are a bit off.

Ingame, replacing 40 and 0 with the entity´s position in the world gave wrong results.
Furthermore, tried replacing them with width and height, and at the end, add the entity´s position. Gave better results, but was about 10 pixels to much:


	private Point2D.Float getSpawnPos(int rotation)
	{
		double rot = Math.toRadians(rotation);
		float unitX = width; //Entity´s width
		float unitY = height; //Entity´s height
		
		float x = unitX - unitX;
		float y = unitY - unitX;
		
		y = Math.abs(y);
		
		float resX = (float) (x * Math.cos(rot) - y * Math.sin(rot));
		float resY = (float) (y * Math.cos(rot) + x * Math.sin(rot));
		
		resY = -resY;
		resX += unitX;
		resY += unitX;
		
		resX += currX;//Entity´s position(x)
		resY += currY;//Entity´s position(y)
		
		return new Point2D.Float(resX, resY);
	}
When I subtracted or added 40 to each coordinate, that's because the center of rotation is (40,40), not because 40 is the x coordinate of the example I used. And I never mentioned using the absolute value.

Try this:
		double rot = Math.toRadians(45);
		float unitX = whatever;
		float unitY = whatever_else;
		
		float x = unitX - 40.0f;
		float y = unitY - 40.0f;
		
		y = -y;
		
		float resX = x * Math.cos(rot) - y * Math.sin(rot);
		float resY = y * Math.cos(rot) + x * Math.sin(rot);
		
		resY = -resY;
		resX += 40.0f;
		resY += 40.0f;
		
		System.out.println(resX + " " + resY);

This topic is closed to new replies.

Advertisement