RotateSprite() » rotate 2D Sprites by 90°, 180° or 270°

Share your advanced PureBasic knowledge/code with the community.
AND51
Addict
Addict
Posts: 1040
Joined: Sun Oct 15, 2006 8:56 pm
Location: Germany
Contact:

RotateSprite() » rotate 2D Sprites by 90°, 180° or 270°

Post by AND51 »

Hello!

It was more work than I thought, but I proudly provide my RotateSprite(). It can turn 2D Sprites by 90°, 180° und 270°!
It's pure PureBasic, so it runs on Windows and Linux (DrawingBuffer() is not supported on Mac).
  • Parameter
  • 90, 180, 270 turns X degrees to the right
  • -90, -180, -270 turns X degrees to the left
    easier to remember is this:
  • 3 aligns the image to "3 o'clock" = 90°
  • 6 aligns the image to "6 o'clock" = 180°
  • 9 aligns the image to "9 o'clock" = 270°
  • Improvement:
    You can now turn the image by x*90 degrees, e. g. 450° (=90°) or -1260° (= -180°)
  • Using 0°, 360° and "12 o'clock" provokes nothing
  • Using any other degrees provokes nothing, too
  • Returning values
  • If the sprite was turned successfully, the returning value is <> 0
  • In fact, the returning value is the address of the DrawingBuffer
Important: The sprite mus be quadratic (height = width)!

Code: Select all

Procedure RotateSprite(SpriteID, Rotate=90) ; AND51, Feb/2008
	Protected *buffer, x, y, border=SpriteWidth(SpriteID)-1, bytesPerPixel=1, *px1.Long, *px2.Long
	*buffer=DrawingBuffer()
	If *buffer
		Select DrawingBufferPixelFormat()
			Case #PB_PixelFormat_32Bits_BGR, #PB_PixelFormat_32Bits_RGB
				bytesPerPixel=4
			Case #PB_PixelFormat_15Bits, #PB_PixelFormat_16Bits
				bytesPerPixel=2
			Case #PB_PixelFormat_24Bits_BGR, #PB_PixelFormat_24Bits_RGB
				bytesPerPixel=3
		EndSelect
		Select rotate%360
			Case 90, 3, -270 ; turn right
				For y=0 To border/2
					For x=0 To border/2
						*px1=*buffer+x*bytesPerPixel+y*DrawingBufferPitch()
						*px2=*buffer+(border-y)*bytesPerPixel+x*DrawingBufferPitch()
						Swap *px1\l, *px2\l
						*px2=*buffer+(border-x)*bytesPerPixel+(border-y)*DrawingBufferPitch()
						Swap *px1\l, *px2\l
						*px2=*buffer+y*bytesPerPixel+(border-x)*DrawingBufferPitch()
						Swap *px1\l, *px2\l
					Next
				Next
			Case 180, 6, -180 ; turn around
				For y=0 To border/2
					For x=0 To border
						*px1=*buffer+x*bytesPerPixel+y*DrawingBufferPitch()
						*px2=*buffer+(border-y)*DrawingBufferPitch()+(border-x)*bytesPerPixel
						Swap *px1\l, *px2\l
					Next
				Next
			Case 270, 9, -90 ; turn left
				For y=0 To border/2
					For x=0 To border/2
						*px1=*buffer+x*bytesPerPixel+y*DrawingBufferPitch()
						*px2=*buffer+y*bytesPerPixel+(border-x)*DrawingBufferPitch()
						Swap *px1\l, *px2\l
						*px2=*buffer+(border-x)*bytesPerPixel+(border-y)*DrawingBufferPitch()
						Swap *px1\l, *px2\l
						*px2=*buffer+(border-y)*bytesPerPixel+x*DrawingBufferPitch()
						Swap *px1\l, *px2\l
					Next
				Next
		EndSelect
	EndIf
	ProcedureReturn *buffer
EndProcedure
PB 4.30

Code: Select all

onErrorGoto(?Fred)