SDL:Tutorials:2D Graphics

From GPWiki
Jump to: navigation, search

-- Work In Progress --

  1. include <cstdlib> // For some useful functions such as atexit :)
  2. include "SDL.h" // main SDL header
  1. define SCREEN_WIDTH 640
  2. define SCREEN_HEIGHT 480
  3. define true 1
  4. define false 0 //You might have to declare True and False.
  5. define COLORKEY 255, 0, 255 //Your Transparent colour

SDL_Surface *screen; //This pointer will reference the backbuffer

int InitVideo(Uint32 flags = SDL_DOUBLEBUF | SDL_FULLSCREEN) {

 // Load SDL
 if (SDL_Init(SDL_INIT_VIDEO) != 0) {
   fprintf(stderr, "Unable to initialize SDL: %s\n", SDL_GetError());
   return false;
 }
 atexit(SDL_Quit); // Clean it up nicely :)
 // fullscreen can be toggled at run time :) any you might want to change the flags with params?
 //set the main screen to SCREEN_WIDTHxSCREEN_HEIGHT with a colour depth of 16:
 screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, 16, flags);
 if (!screen) {
   fprintf(stderr, "Unable to set video mode: %s\n", SDL_GetError());
   return false;
 }
 return true;

}

Loading an Image: (Bitmap) SDL_Surface* LoadImage(char *file, int &exitstate) {

 SDL_Surface *tmp;
 tmp = SDL_LoadBMP(file);
 if (!tmp) {
   fprintf(stderr, "Error: '%s' could not be opened: %s\n", file, SDL_GetError());
   exitstate = false;
   return NULL;
 } else {
   if(SDL_SetColorKey(tmp, SDL_SRCCOLORKEY | SDL_RLEACCEL, SDL_MapRGB(tmp->format, COLORKEY)) == -1)
   fprintf(stderr, "Warning: colorkey will not be used, reason: %s\n", SDL_GetError());
 }
 exitstate = true;
 return tmp;

}

Loading an Image: (bmp,pnm,xpm,xcf,pcx,gif,jpg,tif,png,tga,lbm) in order to use these images in your program you must include the SDL_image library.

NB: This library converts the images into a SDL_Surface layer, where as the bitmap one above just copies the data across to a SDL_Surface. It is also NOT advised putting a LoadImage into a eventloop, and to precache your images you're going to use.

  1. include "SDL_image.h"

SDL_Surface* LoadImage(char *file, int &exitstate) {

 SDL_Surface *tmp;
 tmp = IMG_Load(file);
 if (!tmp) {
   fprintf(stderr, "Error: '%s' could not be opened: %s\n", file, IMG_GetError());
   exitstate = false;
   return NULL;
 } else {
   if(SDL_SetColorKey(tmp, SDL_SRCCOLORKEY | SDL_RLEACCEL, SDL_MapRGB(tmp->format, COLORKEY)) == -1)
   fprintf(stderr, "Warning: colorkey will not be used, reason: %s\n", SDL_GetError());
 }
 exitstate = true;
 return tmp;

}

Drawing An Image:

void DrawImage(SDL_Surface *srcimg, int sx, int sy, int sw, int sh, SDL_Surface *dstimg, int dx, int dy, int alpha = 255) {

 if ((!srcimg) || (alpha == 0)) return; //If theres no image, or its 100% transparent.
 SDL_Rect src, dst;
 
 src.x = sx;  src.y = sy;  src.w = sw;  src.h = sh;
 dst.x = dx;  dst.y = dy;  dst.w = src.w;  dst.h = src.h;
 //if (alpha != 255) SDL_SetAlpha(srcimg, SDL_SRCALPHA, alpha);
 // - This is incorrect, if alpha is 10, then set to 255, the image alpha will still be 10.
 SDL_SetAlpha(srcimg, SDL_SRCALPHA, alpha);
 SDL_BlitSurface(srcimg, &src, dstimg, &dst);

}

Clean Up Your Image:

... SDL_FreeSurface(img_name); ...

It's that simple! Want it easier? Well, you can just copy everything below into a file:

// SDL_Functions: Copied from gpwiki.org.

  1. include <cstdlib> // For some useful functions such as atexit :)
  2. include "SDL.h" // main SDL header
  3. include "SDL_image.h" // image library, if your only using BMP's, get ride of this.
  1. define SCREEN_WIDTH 640
  2. define SCREEN_HEIGHT 480
  3. define true 1
  4. define false 0 //You might have to declaire True and False.
  5. define COLORKEY 255, 0, 255 //Your Transparent colour

SDL_Surface *screen; //This pointer will reference the backbuffer

//I have set the flag SDL_SWSURFACE for a window :) int InitVideo(Uint32 flags = SDL_DOUBLEBUF | SDL_SWSURFACE) {

 // Load SDL
 if (SDL_Init(SDL_INIT_VIDEO) != 0) {
   fprintf(stderr, "Unable to initialize SDL: %s\n", SDL_GetError());
   return false;
 }
 atexit(SDL_Quit); // Clean it up nicely :)
 // fullscreen can be toggled at run time :) any you might want to change the flags with params?
 //set the main screen to SCREEN_WIDTHxSCREEN_HEIGHT with a colour depth of 16:
 screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, 16, flags);
 if (screen == NULL) {
   fprintf(stderr, "Unable to set video mode: %s\n", SDL_GetError());
   return false;
 }
 return true;

}

//--------------------------- Drawing Stuff ------------------------- SDL_Surface* LoadImage(char *file, int &exitstate) {

 SDL_Surface *tmp;
 tmp = IMG_Load(file);
 exitstate = false;
 
 if (tmp == NULL) {
   fprintf(stderr, "Error: '%s' could not be opened: %s\n", file, IMG_GetError());
 } else {
   if(SDL_SetColorKey(tmp, SDL_SRCCOLORKEY | SDL_RLEACCEL, SDL_MapRGB(tmp->format, COLORKEY)) == -1)
   fprintf(stderr, "Warning: colorkey will not be used, reason: %s\n", SDL_GetError());
   exitstate = true;
 }
 return tmp;

}

void DrawImage(SDL_Surface *srcimg, int sx, int sy, int sw, int sh, SDL_Surface *dstimg, int dx, int dy, int alpha = 255) {

 if ((srcimg == NULL) || (alpha == 0)) return; //If theres no image, or its 100% transparent.
 SDL_Rect src, dst;
 
 src.x = sx;  src.y = sy;  src.w = sw;  src.h = sh;
 dst.x = dx;  dst.y = dy;  dst.w = src.w;  dst.h = src.h;
 if (alpha != 255) SDL_SetAlpha(srcimg, SDL_SRCALPHA, alpha);
 SDL_BlitSurface(srcimg, &src, dstimg, &dst);

} //------------------------ The Game -----------------------

int main(int argc, char *argv[]) {

 int res = 0; //Results
 if (InitVideo() == false) return 1;
 SDL_Surface *tux = LoadImage("tux.bmp",res);
 if (res == false) return 1; 
 DrawImage(tux, 0,0, tux->w, tux->h, screen, 10, 10, 128);
 SDL_Flip(screen); //Refresh the screen
 SDL_Delay(2500); //Wait a bit :)
 //cleanup
 SDL_FreeSurface(tux);
 return 0;

} //Remember the blank line at the end! gcc always bugs me about it :)