# Sprite Rotation

This topic is 3084 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

I am looking at how I could possibly rotate the following sprite by about 20 degrees. The width is 60 pixels and the height is 50 pixels.

I am using SDL.

The following apply.
1. I cannot use openGL.
2. I cannot use SDL_gfx.
3. I cannot use a paint package to rotate the image.

How would I do this?

[Edited by - popcorn on July 7, 2010 6:31:29 PM]

##### Share on other sites
tilt your monitor 20 degrees. Why are you restricted from using tools that were built to help you do such things?

##### Share on other sites
Denzin, I forgot:

4. You cannot tilt your monitor :)

The reason is I want to understand the theory behind this and how to program this. From searches here and on google what I've mentioned are always the most common answers.

##### Share on other sites
Use the Rotation Matrix and apply it to each point.

##### Share on other sites
Well I managed to do this:

Can't say it was my own work though, this article is where all the code really came from so credit to the people involved. Rotating a bitmap with an angle of any value.

The code examples are written for windows but I managed to convert it to SDL.

Heres my code in case anyone is interested:

#include "SDL.h"#include "SDL_ttf.h"#include <iostream>#include <cmath>using namespace std;#define min(a, b)  (((a) < (b)) ? (a) : (b)) #define max(a, b)  (((a) > (b)) ? (a) : (b))const int SCREEN_WIDTH = 640;const int SCREEN_HEIGHT = 480;const int SCREEN_BPP = 32;Uint32 getpixel(SDL_Surface *surface, int x, int y){    int bpp = surface->format->BytesPerPixel;    /* Here p is the address to the pixel we want to retrieve */    Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;    switch(bpp) {    case 1:        return *p;    case 2:        return *(Uint16 *)p;    case 3:        if(SDL_BYTEORDER == SDL_BIG_ENDIAN)            return p[0] << 16 | p[1] << 8 | p[2];        else            return p[0] | p[1] << 8 | p[2] << 16;    case 4:        return *(Uint32 *)p;    default:        return 0;       /* shouldn't happen, but avoids warnings */    }}void putpixel(SDL_Surface *surface, int x, int y, Uint32 pixel){    int bpp = surface->format->BytesPerPixel;    /* Here p is the address to the pixel we want to set */    Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;    switch(bpp) {    case 1:        *p = pixel;        break;    case 2:        *(Uint16 *)p = pixel;        break;    case 3:        if(SDL_BYTEORDER == SDL_BIG_ENDIAN) {            p[0] = (pixel >> 16) & 0xff;            p[1] = (pixel >> 8) & 0xff;            p[2] = pixel & 0xff;        } else {            p[0] = pixel & 0xff;            p[1] = (pixel >> 8) & 0xff;            p[2] = (pixel >> 16) & 0xff;        }        break;    case 4:        *(Uint32 *)p = pixel;        break;    }}SDL_Surface *createSurface(int width, int height){	SDL_Surface *surface = SDL_CreateRGBSurface(SDL_SWSURFACE, width, height, 32, 0, 0, 0, 0);		return surface;}int main( int argc, char* args[] ){    //Start SDL    SDL_Init(SDL_INIT_EVERYTHING);	SDL_Surface *screen = NULL;	screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_BPP, SDL_SWSURFACE);	SDL_WM_SetCaption("SDL Rotation Test", NULL);		SDL_Event event;	bool quit = false;	SDL_Surface *surface = createSurface(60, 50);	SDL_Surface *temp = NULL;	temp = SDL_LoadBMP("disasteroids2_master.bmp");	SDL_Rect userClip;	userClip.x = 448;	userClip.y = 295;	userClip.w = 60;	userClip.h = 50;	SDL_BlitSurface(temp, &userClip, surface, NULL);	SDL_FillRect(screen, NULL, SDL_MapRGB(SDL_GetVideoSurface()->format, 75, 150, 255));	int angle = 45;	float radians=(2*3.1416*angle)/360; 	float cosine=(float)cos(radians); 	float sine=(float)sin(radians); 	float Point1x=(-surface->h*sine); 	float Point1y=(surface->h*cosine); 	float Point2x=(surface->w*cosine-surface->h*sine); 	float Point2y=(surface->h*cosine+surface->w*sine); 	float Point3x=(surface->w*cosine); 	float Point3y=(surface->w*sine); 	float minx=min(0,min(Point1x,min(Point2x,Point3x))); 	float miny=min(0,min(Point1y,min(Point2y,Point3y))); 	float maxx=max(Point1x,max(Point2x,Point3x)); 	float maxy=max(Point1y,max(Point2y,Point3y)); 	int DestBitmapWidth=(int)ceil(fabs(maxx)-minx); 	int DestBitmapHeight=(int)ceil(fabs(maxy)-miny); 	SDL_Surface *rotate = createSurface(DestBitmapWidth, DestBitmapHeight);	cout << "Angle: " << angle << endl;	cout << "Surface width: " << rotate->w << endl;	cout << "Surface height: " << rotate->h << endl;	Uint32 pixel;	for(int x=0;x<DestBitmapWidth;x++) 	{ 		for(int y=0;y<DestBitmapHeight;y++) 		{ 			int SrcBitmapx=(int)((x+minx)*cosine+(y+miny)*sine); 			int SrcBitmapy=(int)((y+miny)*cosine-(x+minx)*sine); 			if(SrcBitmapx >= 0 && SrcBitmapx < surface->w && SrcBitmapy >= 0 && SrcBitmapy < surface->h) 			{ 				pixel = getpixel(surface, SrcBitmapx, SrcBitmapy);				putpixel(rotate, x, y, pixel);			} 		} 	} 	SDL_BlitSurface(rotate, NULL, screen, NULL);	SDL_Flip(screen);	while(!quit)	{		while(SDL_PollEvent(&event))		{			if(event.type == SDL_QUIT)			{				quit = true;			}    		}	}    SDL_FreeSurface(temp);    SDL_FreeSurface(surface);    SDL_FreeSurface(rotate);    //Quit SDL    SDL_Quit();        return 0;    }

I can only guess that it is related to the rotation matrix stuff that Concentrate links to in his post. I will need to take some time to see if I can really understand whats going on here....

Does anyone know if it is related to the rotation matrix stuff pointed out by Concentrate?

[Edited by - popcorn on July 8, 2010 12:23:22 AM]

1. 1
2. 2
Rutin
21
3. 3
4. 4
A4L
15
5. 5
khawk
14

• 13
• 26
• 10
• 11
• 9
• ### Forum Statistics

• Total Topics
633737
• Total Posts
3013612
×