Warning: Undefined array key "HTTP_ACCEPT_LANGUAGE" in /var/www/vhosts/bilgigunlugum.net/httpdocs/index.php on line 43
SDL Game Programming

SDL3 Oyun Programlama sayfalarımız yayında...

Ana sayfa > Oyun programlama > SDL3 programming > Keyboard key states

Keyboard key states

In this section, we will examine a program that moves a texture created from a .png image file loaded into the main window with the arrow keys and displays the status of these keys in the main window title.

When the program runs, in addition to the basic operations, the following operations occur:

  1. At the beginning of the program, the global variable shown below is first defined:
    • float x, y: Coordinates variables
    • const bool *kb_state;: Keyboard state variable
    • int move_size: Movement size variable
  2. The init_vars() function initializes the move_size global variable.
  3. In the load_img() function, an image is loaded into the texture variable with the IMG_LoadTexture() function.
  4. In the process_event() function, when the mouse movement and click are performed,
    • The state of the keyboard keys is retrieved with the SDL_GetKeyboardState() function and assigned to the kb_stat variable.
    • If any of the arrow keys are pressed, the kb_state variable value is checked and increases or decreases the coordinate values ​​of the image according to the direction indicated by the pressed keys.
  5. In the draw_screen() function,
    • The SDL_RenderTexture() function copies the texture to the main window according to the coordinates of the x and y values.
    • The state of the arrow keys is shown in the main window bar.

The user can move the texture up, down, can be moved left, right, left up, right up, left down and right down.

main.c file content will be as follows:


#include <stdio.h>
#include <SDL3/SDL.h>
#include <SDL3_image/SDL_image.h>

// Window width and height
#define WINDOW_WIDTH 640
#define WINDOW_HEIGHT 480

// Global variables
int is_running = false;        // Variable that controls the execution of the main loop of the program
SDL_Window *window = NULL;     // Main window variable
SDL_Texture *texture = NULL;   // Texture variable
SDL_Renderer *renderer = NULL; // Renderer variable

float x, y;                    // Coordinates variables
const bool *kb_state;          // Keyboard state variable
int move_size;                 // Move size variable

// Function prototypes
int init_window(void);         // Create window and renderer
void init_vars(void);          // Initialize variables
void load_img(void);           // Load image to texture
void process_event(void);      // Process events
void update_screen();          // Update values
void draw_screen(void);        // Draw screen
void destroy_window(void);     // Destroy window

int main(int argc, char* argv[])
{
    // Create window and renderer
    is_running = init_window();

    // Initialize variables
    init_vars();

    // Load .png file to texture
    load_img();

    // Main loop
    while (is_running) {
       process_event(); // Processing SDL events (Here keyboard inputs)
       update_screen(); // Updating variables
       draw_screen();   // Drawing objects on the window (Rendering)
    }

    // Destroy renderer and SDL window
    destroy_window();

    return 0;
}

// Create window and renderer
int init_window(void)
{
    // Initialize the SDL library.
    if(SDL_Init(SDL_INIT_VIDEO) == false) {
       SDL_Log("SDL init error: %s\n", SDL_GetError());
       return false;
    }

    // Create a window and a 2D rendering context for the window.
    if(!SDL_CreateWindowAndRenderer("SDL3 window", WINDOW_WIDTH, WINDOW_HEIGHT, 0, &window, &renderer)) {
       return false;
    }

    return true;
}

// Initialization function that runs only once at the beginning of the program
void init_vars(void)
{
    move_size = 10;
}

// Load image to texture
void load_img(void)
{
    // Loading image to texture
    texture = IMG_LoadTexture(renderer, "pigeon.png");

	if(texture == NULL) {
       SDL_Log("IMG_LoadTexture error: %s\n", SDL_GetError());
	}
}

// Function to control SDL events and process keyboard inputs
void process_event(void)
{
    SDL_Event event;

    kb_state = SDL_GetKeyboardState(NULL);

    // Creating a loop to process user inputs
    while (SDL_PollEvent(&event)) {
       switch (event.type) {
          case SDL_EVENT_QUIT: // Logout action by the user (x button at the top right of the window)
               is_running = false; // Terminates the execution of the program main loop.
               break;

          case SDL_EVENT_KEY_DOWN: // Key pressed.
               if(event.key.key==SDLK_UP || event.key.key==SDLK_LEFT || event.key.key==SDLK_RIGHT || event.key.key==SDLK_DOWN) {
                  if(kb_state[SDL_SCANCODE_UP]) {
                     if(y - move_size > 0) {
                        y -= move_size;
                     }
                     else y = 0;
                  }
                  if(kb_state[SDL_SCANCODE_LEFT]) {
                     if(x - move_size  > 0) {
                        x -= move_size;
                     }
                     else x = 0;
                  }
                  if(kb_state[SDL_SCANCODE_RIGHT]) {
                     if(x + move_size + 300 <= WINDOW_WIDTH) {
                        x += move_size;
                     }
                     else {
                        x = WINDOW_WIDTH - 300;
                     }
                  }
                  if(kb_state[SDL_SCANCODE_DOWN]) {
                     if(y + move_size + 300 <= WINDOW_HEIGHT) {
                        y += move_size;
                     }
                     else {
                        y = WINDOW_HEIGHT - 300;
                     }
                  }
               }
               else if(event.key.key==SDLK_ESCAPE) {
                  is_running = false;
               }
               break;
       }
    }
}

// Updates objects in the main window
void update_screen(void)
{

}

// Render function used to draw game objects in the main window
void draw_screen(void)
{
    SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); // Set the color used for drawing operations.
    SDL_RenderClear(renderer); // Clear the current rendering target with the drawing color.

    SDL_FRect frect_dst = { x, y, 300, 300 };
 	SDL_RenderTexture(renderer, texture, NULL, &frect_dst);

    // Loading all objects drawn one by one to the back buffer to the front buffer at once and loading them onto the screen
    // This process prevents each drawn object from being displayed on the screen one by one.
    SDL_RenderPresent(renderer); // Update on screen all operations performed since the previous call

    char cdizi[100];
    sprintf(cdizi, "SDL3 window - Up: %s, Down: %s, Left: %s, Right: %s",
                    kb_state[ SDL_SCANCODE_UP] ? "Down" : "Up", kb_state[ SDL_SCANCODE_DOWN] ? "Down" : "Up",
                    kb_state[ SDL_SCANCODE_LEFT] ? "Down" : "Up", kb_state[ SDL_SCANCODE_RIGHT] ? "Down" : "Up");
    SDL_SetWindowTitle(window, cdizi);
}

// Destroy Renderer and SDL window, exit from SDL3
void destroy_window(void)
{
    SDL_DestroyTexture(texture);
    SDL_DestroyRenderer(renderer);
    SDL_DestroyWindow(window);
    SDL_Quit();
}