Tag Archives: sdl4fp

Chapter 6: Event handling (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

If the user is moving the mouse, pressing/releasing a button on the keyboard or pressing/releasing the fire key on the joystick then you speak of events. Further events are resizing a window or switching between several applications. For games though the events described first are much more important. SDL provides a quite easy way to notice and react to such events, which is called event handling.

First of all using event handling means to understand the concept of event handling. Events have a special structure you should know about. For example an pressed key is an event or a moved mouse is an event. SDL differs altogether fourteen such events. Every event stores different information depending on its kind. For example the key board event stores the information which key was pressed. The mouse motion event stores the information to which position the mouse got moved. If you got a mouse motion event you can’t read out key information and so on. Therefore you have the following general structure to the event data: event.eventstructure.data.

To make event handling possible you have to include the unit SDL_EVENTS. The event handling subsystem is automatically initialized along with the video subsystem.

We have to create an event variable which is of pointer type pSDL_EVENT. We will create a second variable of boolean type just to control the while loop.

PROGRAM chap6_1;
USES crt, SDL, SDL_VIDEO, SDL_EVENTS;

VAR
screen:pSDL_SURFACE;
loopstop:boolean=FALSE;
test_event:pSDL_EVENT;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
IF screen=NIL THEN HALT;

NEW(test_event);

DISPOSE(test_event);
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

We want to check the program if any event occured and if so, we want to know which kind of event happened. So we make a while loop which will run until loopstop gets true.

The command SDL_POLLEVENT(parameter) checks if there are pending events and if so it will take the oldest and save it to parameter which is an event record of pSDL_EVENT type. For example if the user presses (then releases) left mouse button, then presses (then releases) space button on keyboard and finally moves the mouse there are altogether five events: 1. left mouse button pressed, 2. left mouse button released, 3. space key pressed, 4. space key released, 5. mouse moved. If you poll for events now you will get the first event (left mouse button pressed) and saved it’s properties to the event variable we specified as parameter. The next poll will save the properties of next event (left mouse button released) to event variable and so on. SDL_POLLEVENT(parameter) will return 1 if it has found pending event or 0 if there wasn’t any pending event.

Fortunately you don’t have to notice any event which is made by the user ;). By event^.eventtype you can easily check which type of event you got. In the case described before it would be 1. SDL_MOUSEBUTTONDOWN, 2. SDL_MOUSEBUTTONUP, 3. SDL_KEYDOWN, 4. SDL_KEYUP, 5. SDL_MOUSEMOTION. It should be senseful to check for the event kind by using the case command.

PROGRAM chap6_1;
USES crt, SDL, SDL_VIDEO, SDL_EVENTS;

VAR
screen:pSDL_SURFACE;
loopstop:boolean=FALSE;
test_event:pSDL_EVENT;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
IF screen=NIL THEN HALT;

NEW(test_event);

WHILE loopstop=FALSE DO
BEGIN
IF SDL_POLLEVENT(test_event)=1 THEN
BEGIN
write('pending event: ');

CASE test_event^.eventtype OF
SDL_EVENTACTIVE: writeln('Application is/is not active');
SDL_KEYDOWN: writeln('Key pressed ');
SDL_KEYUP: writeln('Key released');
SDL_MOUSEMOTION: writeln('Mouse motion');
SDL_MOUSEBUTTONDOWN: writeln('Mouse button down');
SDL_MOUSEBUTTONUP: writeln('Mouse button up');
SDL_JOYAXISMOTION: writeln('Joystick axis motion');
SDL_JOYBALLMOTION: writeln('Joystick's trackball motion');
SDL_JOYHATMOTION: writeln('Joystick's hat position changed');
SDL_JOYBUTTONDOWN: writeln('Joystick button pressed');
SDL_JOYBUTTONUP: writeln('Joystick button released');
SDL_EVENTQUIT: writeln('User-requested quit');
END;

END ELSE writeln('no pending events');
DELAY(150);
END;
DISPOSE(test_event);
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

Actually you shouldn’t try this source as it is written there because it will end up in an endless loop. The DELAY command is used because otherwise you won’t notice any pending events because they are polled too fast and it seems as if there would never be any pending events (just remove DELAY to confirm).

We now want to try the program to read out which key the user pressed on the keyboard. If the key is the escape-key (Esc) the program should stop. We already check the type of the event we polled. So if the event is a keyboard event the further checking should proceed. In our case especially if a key gets pressed. An keyboard event record contains a field called keysym. Keysym is a record of SDL_KEYSYM. SDL_KEYSYM is defined in SDL_KEYBOARD unit. It contains four fields. Scancode which is hardware dependent scancode should be avoided if you want to make hardware independent programs. It is usual integer variable. Next is sym which stores SDLKEY. These SDL keys are independent and it is strongly recommended to use them! In the example we want break up if escape key gets pressed. Its SDL key code is 27. If you want to know what SDL keys are defined look up in the table page. The variable modifier stores modifier keys (like shift, ctrl,…) pressed and stores SDLMod. SDL modifier keys can be found at table page as well. The fourth variable is unicode which may be used to read out unicode characters but to use this you have to enable it what is not described in this tutorial.

To read out or compare the key the user pressed we must use the expression test_event^.key.keysym.sym. Do you remember the general structure of an event (event.eventstructure.data)? – test_event^ is the event, the event structure is defined as an key event by key and the data we want to know is the key pressed contained in keysym.sym.

PROGRAM chap6_1;
USES crt, SDL, SDL_VIDEO, SDL_EVENTS;

VAR
screen:pSDL_SURFACE;
loopstop:boolean=FALSE;
test_event:pSDL_EVENT;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
IF screen=NIL THEN HALT;

NEW(test_event);

WHILE loopstop=FALSE DO
BEGIN
IF SDL_POLLEVENT(test_event)=1 THEN
BEGIN
write('pending event: ');

CASE test_event^.eventtype OF
SDL_EVENTACTIVE: writeln('Application is/is not active');
SDL_KEYDOWN:

BEGIN
write('Key pressed ');
writeln('(SDLKey=',test_event^.key.keysym.sym,')');
IF test_event^.key.keysym.sym=27 THEN loopstop:=true;
END;

SDL_KEYUP: writeln('Key released');
SDL_MOUSEMOTION: writeln('Mouse motion');
SDL_MOUSEBUTTONDOWN: writeln('Mouse button down');
SDL_MOUSEBUTTONUP: writeln('Mouse button up');
SDL_JOYAXISMOTION: writeln('Joystick axis motion');
SDL_JOYBALLMOTION: writeln('Joystick's trackball motion');
SDL_JOYHATMOTION: writeln('Joystick's hat position changed');
SDL_JOYBUTTONDOWN: writeln('Joystick button pressed');
SDL_JOYBUTTONUP: writeln('Joystick button released');
SDL_EVENTQUIT: writeln('User-requested quit');
END;

END ELSE writeln('no pending events');
DELAY(150);
END;
DISPOSE(test_event);
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

Actually this is easy, isn’t it?

This file contains the source code: chap6_1.pas (right click and “save as”)
This file is the executable: chap6_1.exe (right click and “save as”)

ATTENTION: This is just the first part. The second part will describe mouse handling, which is much easier.

Chapter 3: Displaying a picture (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

Working with the video subsystem assumes that you understand the concept behind. The screen is supposed to be a surface (everything on this surface gets displayed on the physical screen!). Every object you want to display on the screen can be an own surface. Every object can be copied to the screen surface. Surfaces can be manipulated.

For example in the demo03.pp from the SDL4Freepascal files the ball, the paddle and the black background (screen) are surfaces. The ball and the paddle are copied onto the screen surface again and again slightly moved up. So the ball and the paddle are giving the impression that they are moving.

So our task is to create a screen surface. Furthermore we need a surface that contains a picture. Eventually the picture should get copied onto the screen surface. After that the picture should be displayed at the physical screen.

PROGRAM test;
USES crt, SDL, SDL_video;

BEGIN
SDL_INIT(SDL_INIT_VIDEO);

{further code}

SDL_QUIT;
END.

That is where we stopped last chapter. Now we need a command to create a screen surface. Creating a surface is always introduced by setting up a surface variable. The variable type is pSDL_SURFACE and is kind of pointer type as indicated by the “p” in front of it.

The screen surface is a special kind of surface. It has some special properties that can be set. You can set appearance, height, width and colordepth that is displayed by it. The command to make a surface to a screen surface is SDL_SETVIDEOMODE(parameters).

Similar to the SDL_QUIT procedure, after using surfaces you have to clean the memory if you don’t need them anymore. Therefore you use SDL_FREESURFACE(surface).

PROGRAM test;
USES crt, SDL, SDL_video;

VAR
screen:pSDL_SURFACE;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

readln;
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

The function to set the screen surface returns nil if an errors occurs. The first parameter determines the width, the second one the height. The third parameter determines the colordepth (8 bit for now) and the last one the appearance (video mode) and space handling. The first three parameters are longint typ, the last one Uint32, where the U stands for “unsigned” (values greater or euqal nil only!), the int stands for “integer” and the number stands for the bit per pixel count. So it is an 32 bit unsigned integer. There are some very interesting values. The chosen one, SDL_SWSURFACE, is used if you want to store the surface in system memory (RAM). Alternatively you could chose SDL_HWSURFACE what causes a storage in video memory. Both will create windowed screens that cannot be resized. SDL_NOFRAME would create a windowed screen without a frame. Eventually there is SDL_FULLSCREEN which leads to a fullscreen display. There are some other possibilities which may be told about in further chapters.

If you run the program you see a black window because nothing is located on the screen surface.

It is necessary to create another surface that contains the picture. Then we need a possibility to load the picture to the surface. Fourtunately there is a command called SDL_LOADBMP(file). The corresponding command is called SDL_SAVEBMP(surface,file) if you drew something onto the screen and would like to save it as a bitmap file. Incidentally there is no such import/export feature for other graphic formats (that doesn’t mean there are no other easy ways to use other important graphic formats ;)).

Free Pascal meets SDL sample image bmp format
download (right click and “save as”)

This picture (8 bit) is the one that will be copied to the screen. The pictures width and height are both exactly 200 pixels.

PROGRAM test;
USES crt, SDL, SDL_video;

VAR
screen,picture:pSDL_SURFACE;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

picture:=SDL_LOADBMP('fpsdl.bmp');
if picture=nil then HALT;

readln;
SDL_FREESURFACE(picture);
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

The surface is named “picture” here and the file fpsdl.bmp is located in the same directory as the source file. As already known from setting of the screen variable the SDL_LOADBMP command returns nil if something’s wrong.

In the end we need to copy the loaded picture from the picture surface to the screen surface. This process is called blitting and is made by this command: SDL_BLITSURFACE(parameters).

After the blit process the screen surface has to be refreshed. SDL_UPDATERECT(parameters) is doing that.

PROGRAM test;
USES crt, SDL, SDL_video;

VAR
screen,picture:pSDL_SURFACE;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

picture:=SDL_LOADBMP('fpsdl.bmp');
if picture=nil then HALT;

SDL_BLITSURFACE(picture,nil,screen,nil);
SDL_UPDATERECT(screen,15,15,170,170);

readln;
SDL_FREESURFACE(picture);
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

For successful blitting four parameters are requested. The first determines the source surface, the third the destination surface. The second and the fourth parameter can be used if you don’t want to blit the whole surface but a certain rectangle. So you could determine that you want to blit just the upper left quarter of the picture surface (second parameter). Furthermore you could want it copied to the lower right quarter of the screen surface (fourth parameter). If these parameters are nil it means the whole surface is blitted.

As you can see the SDL_UPDATERECT command requests five parameters. The first of them determines which surface has to be refreshed. The next four determine a rectangel with: x-direction, y-direction (from top to bottom), width (relative to x,y-position), height (relative to x,y.position). If all of these paramters are “0” the whole surface will get updated.

This file contains the source code: test.pas (right click and “save as”). The file and the graphic file have to be in the same folder.

Hope you are successful and have fun.

Chapter 5: Writing and using fonts (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

What you need:

Software Source Description
sdl_ttf.pp http://cvs.sourceforge.net/viewcvs.py/sdl4fp/extras/
Downloads
Unit file to handle fonts.
SDL_ttf.dll http://www.freetype.org/index2.html
Windows: http://gnuwin32.sourceforge.net/packages/freetype.htm
This is the corresponding dynamic link library file.

This chapter will introduce you on how to load fonts and write to the screen. There are two things to do for preparation. First of all we have to change the compiler settings because a new unit, called SDL_TTF, gets included. This unit uses the “result” command to return values of functions. This is a command from Object Pascal. So the compiler has to support it’s syntax otherwise he won’t accept this command. To let the compiler support the Object Pascal syntax go to “Options” and then “Compiler…” A new window will pop up. From “Syntax” mark the option “Object pascal support”. Now SDL_TTF can be used.

In version 1.2.0.0 of SDL4Freepascal this unit isn’t included. It has to be separately downloaded. You can download it here: http://cvs.sourceforge.net/viewcvs.py/sdl4fp/extras/ or from the download section. The file “sdl_ttf.pp” has to be copied to the sdl unit folder where all the other sdl units are located (e.g. C:\FPC\units\).

Analogous to SDL.dll in chapter 1 you have to download the last stable release of FreeType which can be found here: http://www.freetype.org/index2.html (Windows: http://gnuwin32.sourceforge.net/packages/freetype.htm ). You should extract the file and get two files. A text file and the important SDL_ttf.dll. These files you copy to the system32-folder.

Now let’s begin with the interessting part. The goal is to get a text with a certain font and colour to the screen. Of course we need the screen surface again and a surface onto which can be written. Furthermore the new unit has to be loaded.

PROGRAM chap5;
USES crt, SDL, SDL_VIDEO, SDL_TTF;

VAR
screen,fontface:pSDL_SURFACE;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

readln;
SDL_FREESURFACE(screen);
SDL_FREESURFACE(fontface);
SDL_QUIT;
END.

To initialize the TTF (True type font) system you have to use TTF_INIT which returns -1 if something goes wrong. Notice that the whole true type support is an own additional project to the SDL library, so this has not to be initilized by the SDL_INIT command.

To load a certain font you use TTF_OPENFONT(font,point size). This command is a function that returns a usual pointer! The parameters are the path to the font (e.g. C:\WINDOWS\fonts\arial.ttf) and the point size which detemines the size of the letters. Furthermore as SDL surface has to be free’d and SDL system has to be quit so has TTF system. The commands TTF_CLOSEFONT(font) and TTF_QUIT have to be used to do this.

PROGRAM chap5;
USES crt, SDL, SDL_VIDEO, SDL_TTF;

VAR
screen,fontface:pSDL_SURFACE;
loaded_font:pointer;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

if TTF_INIT=-1 then HALT(1);
loaded_font:=TTF_OPENFONT('C:\WINDOWS\fonts\arial.ttf',12);

readln;
SDL_FREESURFACE(screen);
SDL_FREESURFACE(fontface);
TTF_CLOSEFONT(loaded_font);
TTF_QUIT;
SDL_QUIT;
END.

So next we have to determine the colour of the letters and the messege itself. The colour is determined by a pSDL_COLOR record, which is of course kind of pointer. In pSDL_COLOR record there are three elements (actually four, but the forth is unused) which can be accessed by .r,.g and .b and determine as common the shares of red, green and blue colour. You will agree that writing a function for this can be senseful, especially if you have to handle many different colours. The fact that pSDL_COLOR is a pointer type we have to set up it by NEW command and free it finally by DISPOSE. This commands you should familiar with because they are usual Pascal commands.

PROGRAM chap5;
USES crt, SDL, SDL_VIDEO, SDL_TTF;

VAR
screen,fontface:pSDL_SURFACE;
loaded_font:pointer;
colour_font:pSDL_COLOR;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

if TTF_INIT=-1 then HALT;
loaded_font:=TTF_OPENFONT('C:\WINDOWS\fonts\arial.ttf',12);

NEW(colour_font);
colour_font^.r:=255; colour_font^.g:=0; colour_font^.b:=0;

readln;
DISPOSE(colour_font);
SDL_FREESURFACE(screen);
SDL_FREESURFACE(fontface);
TTF_CLOSEFONT(loaded_font);
TTF_QUIT;
SDL_QUIT;
END.

Now we use TTF_RENDERTEXT_SOLID which returns a pSDL_SURFACE. We return it to fontface. The parameters are the used font as pointer (loaded_font), the messege string and the colour as value of pSDL_COLOR (colour_font).

Finally we have to blit the fontface surface, on which now the messege is written, to the screen surface and update the screen surface.

PROGRAM chap5;
USES crt, SDL, SDL_VIDEO, SDL_TTF;

VAR
screen,fontface:pSDL_SURFACE;
loaded_font:pointer;
colour_font:pSDL_COLOR;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT;

if TTF_INIT=-1 then HALT;
loaded_font:=TTF_OPENFONT('C:\WINDOWS\fonts\arial.ttf',12);

NEW(colour_font);
colour_font^.r:=255; colour_font^.g:=0; colour_font^.b:=0;

fontface:=TTF_RENDERTEXT_SOLID(loaded_font,'HELLO WORLD',colour_font^);

SDL_BLITSURFACE(fontface,NIL,screen,NIL);
SDL_UPDATERECT(screen,0,0,0,0);

readln;
DISPOSE(colour_font);
SDL_FREESURFACE(screen);
SDL_FREESURFACE(fontface);
TTF_CLOSEFONT(loaded_font);
TTF_QUIT;
SDL_QUIT;
END.

Now you are able to write ;).

This file contains the source code: chap5.pas (right click and “save as”)
This file is the executable: chap5.exe (right click and “save as”)

[Downloads transferred from old website]

sdl_ttf.zip; FOR OUTDATED SDL4FP PACKAGE! Unit file for font support. (right click and “save as”)

Chapter 4: Drawing pixels (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

Okay. Maybe you think, why to learn how to display pictures first and then learning about the more basic feature to draw single pixels to the screen? – In chapter 3 you learned beside displaying a picture how common SDL programs are strctured. Furthermore this chapter will get a little bit longer because several things have to explained more detailed to impart a fully understanding. In chapter 3 that was not necessary.

So here we go. First of all we have to know about the meaning of pixels. The physical screen consists of many small units. Every unit consists itself of three different coloured lights. These colours are red, green and blue. If you mix them (additive) you can get every colour. For example if you mix red and green you receive yellow. For three colours that can be mixed with each other there are eight combinations possible which lead to different colours (RGB, RG, RB, R, GB, G, B, all lights off). Some of you may say RGB (white) and all lights off (black) are no colours. That is right but doesn’t matter here and to keep simpliness I will talk of colours even if I talk of black and white.

Did you get confused? Your screen definitvly has more than eight colours, doesn’t it? The reason is, your screen isn’t just able to put on or off lights. Besides it is in position to differ the intensities of the lights. The more intensity levels you have the more colours you can display. The case that you have eight colours as discussed before means that you just have one intensity level. If your screen is in 8 bit mode every pixel on the screen has the possibility to display 2 power 8 colours. That are 256 different colours. Every of the three lights has therefore a certain amount of different intensity levels. There are the red and the green light with eight intensity levels each and the blue light with four intensity levels. If you have 16 bit mode you have 2 power 16 and that are 65536 colours. Each light therefore must have the appropriate amount of intensity levels.

All the examples will be made in 8 bit mode. If you want to write directly to the screen surface it is possibly necessary that you lock it. We work in software mode (SDL_SWSURFACE) so we can leave locking the screen surface. The screen surface is a RECORD of many different data types. To read or write pixels of or to a surface there is a typ marker called “pixels” which is of pointer type. It points at some pixel of the surface. The location gets allocated to a pointer of WORD, namely “pixellocation” we define.

PROGRAM chap4;
USES crt, SDL, SDL_video;

VAR
screen:pSDL_SURFACE;
pixellocation:^WORD;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT(1);

pixellocation:=screen^.pixels;

readln;
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

It is unknown to us where to the surface it is pointing. This may not matter now; this we will treat later. Before we should allocate a colour to the pixel. Up to now we just have handed over the location to “pixellocation”. Yellow is the pixel colour we want to get. Red has to be 255, green has to be 255 and blue has to be 0 to get yellow. The function SDL_MAPRGB(pixel format, red, green, blue) is used to transform that input values into one longinteger (Uint32) code. The pixel format is given by the screen surface. We will use its pixel format by using screen^.format what contains the pixel format information of the screen surface. The calculated “colour code” is handed over to a new defined variable called “pixelcolor”.

So you have stored the location of the pixel to manipulate in variable pixellocation. You have stored the information of the colour you want to receive in pixelcolor. Eventually you have to allocate the pixel colour to the pointed pixel at the surface. That’s it. Of course we have to update the screen surface after the drawing.

PROGRAM chap4;
USES crt, SDL, SDL_video;

VAR
screen:pSDL_SURFACE;
pixellocation:^WORD;
pixelcolor:WORD;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT(1);

pixellocation:=screen^.pixels;
pixelcolor:=SDL_MAPRGB(screen^.format,255,255,0);
pixellocation^:=pixelcolor;

SDL_UPDATERECT(screen,0,0,0,0);
readln;
SDL_FREESURFACE(screen);
SDL_QUIT;
END.

If you look careful to the screen (when running program) you may see the pixel (left upper corner). After this success we want to see the pixel run along the screen! That will help you understand easily how the positioning of the pixel works, probably better as if I try to explain. We define a repeat-unitl loop what will delete old pixel (colour: black) and write a new one exaktly moved up by one pixel.

PROGRAM chap4;
USES crt, SDL, SDL_video;

VAR
screen:pSDL_SURFACE;
pixellocation:^WORD;
pixelcolor,i:WORD;

BEGIN
CLRSCR;
SDL_INIT(SDL_INIT_VIDEO);
screen:=SDL_SETVIDEOMODE(200,200,8,SDL_SWSURFACE);
if screen=nil then HALT(1);

i:=-1;
REPEAT
inc(i); IF i>39999 THEN i:=0;

pixellocation:=screen^.pixels+i;
pixelcolor:=SDL_MAPRGB(screen^.format,0,0,0);
pixellocation^:=pixelcolor;

pixellocation:=screen^.pixels+i+1;
pixelcolor:=SDL_MAPRGB(screen^.format,255,255,0);
pixellocation^:=pixelcolor;

SDL_UPDATERECT(screen,0,0,0,0);
delay(5);
UNTIL keypressed;

SDL_FREESURFACE(screen);
SDL_QUIT;
END.

So the position which is pointed by pixels pointer is set by adding to or substratcing from the position before. As can be seen in the program the pixel position is increased by one and so is the value of where screen^.pixels pointer is pointing at.

If you create a surface of width and height of 200 pixels as in the example the true surface can be a little bit wider. This means you have a window of width and height of 200 pixels displayed but there is an additional unvisible piece of surface. Maybe its width is 210, so the moving pixel in the last example would restart a few lines before end of window. To solve problems cause by this pitch to the surface you can read it out. The data type pitch will allow you to (e.g. screen^.pitch).

This file contains the source code: chap4.pas (right click and “save as”)
This file is the executable: chap4.exe (right click and “save as”)

Chapter 2: First steps using SDL (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

You should be slightly experienced in programming Freepascal. That means you should be familiar with the usual commands of Freepascal. If this is not the case you may have problems because this tutorial deals with the features of the usage of the SDL library.

Now let us begin. There are several units given that can be used. If you want to use SDL library you must include the unit “SDL”. It is needed to initialize any other component of the library. For example there are units called “SDL_audio”, “SDL_video”, “SDL_keyboard” and so on. You can draw conclusions on their meaning from their names. So let us start with the initialization of the SDL video system. The command needed to initialize any component is SDL_INIT(component);

PROGRAM test;
USES crt, SDL, SDL_video;

BEGIN

SDL_INIT(SDL_INIT_VIDEO);

END.

Instead of SDL_INIT_VIDEO you could initilize the respective component by using SDL_INIT_AUDIO, SDL_INIT_CDROM, SDL_INIT_JOYSTICK, SDL_INIT_TIMER, SDL_INIT_NOPARACHUTE, SDL_INIT_EVENTTHREAD, SDL_INIT_EVERYTHING. So if you want to use the features provided by the library for sound handling you should init it SDL_INIT_AUDIO. If you use SDL_INIT_EVERYTHING all subsystems are initialized.

There is another very important command: SDL_QUIT. Every program have to be closed by using this command. It cleans up your system! Never fotget it. This procedure ensures that all subsystems initilized get unloaded. There is a corresponding command to unload specific subsystems called SDL_QUITSUBSYSTEM(component).

PROGRAM test;
USES crt, SDL, SDL_video;

BEGIN
SDL_INIT(SDL_INIT_VIDEO);

{further code}

SDL_QUIT;
END.

Well, we have initilized the video subsystem and released it after that. Simple Directmedia Layer deserves its name, isn’t it?

Chapter 1: Introduction, installation and configuration (SDL4FP)

This is an SDL 1.2 chapter. SDL 1.2 is obsolete since it has been replaced by SDL 2.0. Unless you have good reasons to stay here you may prefer to go for the modern SDL 2.0 :-).

The introduction is short. SDL library gives you the ability to program powerful applications for many different operating systems (OS) only by learning one set of commands. The SDL library takes on the assignment to translate your commands to the specific OS commands. It’s especially meaningful to use the SDL library if you plan to develop games or similar software.

Now this Chapter concerns on the installation of all necessary software on your system for programming SDL applications with Freepascal under Windows XP (probably this will work for other windows systems as well; please report if you tried out).

First of all, we have to consider which software is needed. We need three different software packages. We need the Freepascal compiler of course. Furthermore we need the SDL library files and finally we need something what translates our pascal programs to the SDL library (written in C/C++). This will be taken on by a few units.

1) Download the latest stable Freepascal compiler (Version 2.0.0). You
get it here: http://www.freepascal.org/
2) Download the latest version of SDL4Freepascal (Version 1.2.0.0). You
get it here: http://sdl4fp.sourceforge.net/
3) Download the latest version of SDL runtime library (Version 1.2.8). You
get it here: http://www.libsdl.org/ (German readers may prefer: http://www.libsdl.de/)

Of course, if you have installed Freepascal already you haven’t to download it again and you can skip step 4.

4) Execute “fpc-2.0.0.i386-win32.exe” to install Freepascal. Let the self-installer create a shortcut on your desktop.
5) Extract “SDL-1.2.8-win32.zip” to get the SDL runtime library. This leads to two extracted files. There is a text file and the very important SDL.dll.
6) Copy those files (especially the SDL.dll!) to your
system32-folder! Usually you find it at “C:\WINDOWS\system32\”.
Don’t confuse it with the similar system-folder. (This works for
WinXP, probably for NT-series and Win2000 as well; if you use Win9x
or WinME you should copy it to system-folder instead of system32-folder)

If it for any reason isn’t possible to copy the files into this folder you later have to have that file into the same folder where the application is. Now you have installed Freepascal and the SDL runtime library on your system. Finally SDL4Freepascal have to be installed.

7) Extract “SDL4Freepascal-1.2.0.0.tar.gz” to get the units and some demo programs. There should be about 20 files and a folder “demos” which contains five more files.
8) Open the folder where you have installed Freepascal (e.g. C:\FPC\)
9) Open the folder “units” (e.g. C:\FPC\units\)
10) Create a new folder called “sdl” (e.g. C:\FPC\units\sdl\)
11) Copy the whole former extracted files (including the folder “demos”) from SDL4Freepascal into the sdl-Folder.

Now the compiler has to be told about where to find the new units.

12) Open the Freepascal IDE (for example by clicking the shortcut on desktop).
13) In the menue choose the following item “Options”. From “Options” choose “Directories…”. Now a window should pop up.
14) The last row is called “Unit directories”. There you should write in the full path to your SDL-units (e.g. C:\FPC\units\sdl). Leave the last backslash out.

Congratulations! You have configured your system for developing SDL applications with Freepascal! Now let’s check if it really was that easy…

15) Open the file “demo02.pp” in demos-folder (e.g. C:\FPC\units\sdl\demos\). Run it.

If you see some cool colourful red and blue lines you have done everything as it has to be done :)! Have fun with your configured system!

For those of you who try running the demo and get an abortion together with a messege saying “exitcode = 309”: You skipped step 6! Did you copy the SDL.dll to your system32- or system-folder respectively? If so and the error still occurs you should copy the SDL.dll into the folder where the demos are placed. Now it should work.

[Downloads transferred from old website]

SDL4Freepascal-1.2.0.0.tar.gz; OUTDATED: SDL4Free Pascal Version 1.2.0.0 (most recent)