Skip to content

Simple DirectMedia Layer

List of SDL API

심플 다이렉트미디어 레이어(Simple DirectMedia Layer), SDL는 C 프로그래밍 언어로 짜여진 크로스플랫폼 멀티미디어 라이브러리이다. 이 라이브러리는 비디오, 오디오, 사용자 입력 등의 계층을 추상화하여, 리눅스, 마이크로소프트 윈도, 맥 OS X 등 여러 운영 체제에서 실행이 가능하도록 한다. 이 라이브러리는 비디오, 이벤트, 디지털 오디오, CD-ROM, 사운드, 스레드, 공유 객체 불러오기, 네트워킹, 타이머를 관리한다.

SDL 2.0 API by Category

Basics

Video

Input Events

Force Feedback

  • Initialization and Shutdown
    • SDL_Init
    • SDL_InitSubSystem
    • SDL_Quit
    • SDL_QuitSubSystem
  • Configuration Variables
    • SDL_GetHint
    • SDL_SetHint
    • SDL_SetHintWithPriority
  • Error Handling
    • SDL_ClearError
    • SDL_GetError
    • SDL_SetError
  • Log Handling
    • SDL_Log
    • SDL_LogCritical
    • SDL_LogDebug
    • SDL_LogError
    • SDL_LogInfo
    • SDL_LogMessage
    • SDL_LogVerbose
    • SDL_LogWarn
  • Assertions
    • SDL_assert
  • Querying SDL Version
    • SDL_GetVersion
  • Display and Window Management
    • SDL_CreateWindow
    • SDL_DestroyWindow
    • SDL_GetWindowPixelFormat
    • SDL_GetWindowPosition
    • SDL_GetWindowSize
  • 2D Accelerated Rendering
    • SDL_CreateRenderer
    • SDL_CreateSoftwareRenderer
    • SDL_CreateTexture
    • SDL_LockTexture
    • SDL_RenderClear
    • SDL_RenderCopy
    • SDL_RenderCopyEx
    • SDL_RenderDrawLine
    • SDL_RenderDrawLines
    • SDL_RenderDrawPoint
    • SDL_RenderDrawPoints
    • SDL_RenderDrawRect
    • SDL_RenderDrawRects
    • SDL_RenderFillRect
    • SDL_RenderFillRects
    • SDL_SetRenderDrawBlendMode
    • SDL_SetRenderDrawColor
    • SDL_SetRenderTarget
    • SDL_SetTextureAlphaMod
    • SDL_SetTextureBlendMode
    • SDL_SetTextureColorMod
    • SDL_UnlockTexture
    • SDL_UpdateTexture
    • SDL_UpdateYUVTexture
  • Pixel Formats and Conversion Routines
  • Rectangle Functions
  • Surface Creation and Simple Drawing
  • Platform-specific Window Management
  • Clipboard Handling
  • Force Feedback Support

Audio

Threads

Timers

File Abstraction

  • Audio Device Management,
    Playing and Recording
  • Thread Management
  • Thread Synchronization Primitives
  • Atomic Operations
  • Thread Issue
  • Timer Support
  • Filesystem Paths
  • File I/O Abstraction

Shared Object Support

Platform and CPU Information

Power Management

Additional

  • Shared Object Loading
    and Function Lookup
  • Platform Detection
  • CPU Feature Detection
  • Byte Order and Byte Swapping
  • Bit Manipulation
  • Power Management Status
  • Platform-specific functionality
  • Other

SDL_image

SDL_ttf

SDL_mixer

OpenGL

Structure

Libraries

SDL3

Local Download

SDL2 2.0.4
SDL2-2.0.4.tar.gz

SDL 환경변수 자동 감지 및 설정

pygame + opengl + linux 에서 실행하면 SDL 관련 환경변수를 설정해야 정상적으로 실행되는 이슈가 있음.

이런 환경변수 알아서 잘 찾아서 설정하여 실행되게 하는 방법이 필요함.

WARNING

Claude-Code에서 자동 생성한 답변이다

주요 문제 패턴들

# 흔히 발생하는 케이스들
SDL_VIDEODRIVER=wayland    X11 앱이 깨지는 경우
SDL_VIDEODRIVER=x11        Wayland 전용 환경에서 필요
DISPLAY=:0                 X11 디스플레이 미설정
LIBGL_ALWAYS_SOFTWARE=1    GPU 드라이버 문제
SDL_VIDEO_X11_FORCE_EGL=1  EGL 강제 필요한 경우

자동 감지 Python 모듈

import os
import subprocess
import sys
from pathlib import Path


def detect_display_server() -> str:
    """
    Detect current display server (Wayland or X11)
    현재 디스플레이 서버 감지
    """
    # Wayland 세션 확인
    if os.environ.get("WAYLAND_DISPLAY"):
        return "wayland"
    if os.environ.get("XDG_SESSION_TYPE", "").lower() == "wayland":
        return "wayland"
    # X11 세션 확인
    if os.environ.get("DISPLAY"):
        return "x11"
    return "unknown"


def find_x11_display() -> str | None:
    """
    Find available X11 DISPLAY value
    사용 가능한 X11 DISPLAY 값 찾기
    """
    # 이미 설정된 경우
    if os.environ.get("DISPLAY"):
        return os.environ["DISPLAY"]

    # /tmp/.X11-unix 소켓 탐색
    x11_dir = Path("/tmp/.X11-unix")
    if x11_dir.exists():
        sockets = sorted(x11_dir.glob("X*"))
        if sockets:
            # X0 -> :0, X1 -> :1 ...
            display_num = sockets[0].name[1:]  # 'X' 제거
            return f":{display_num}"

    return None


def check_opengl_support() -> dict:
    """
    Check OpenGL driver availability via glxinfo
    glxinfo로 OpenGL 드라이버 가용성 확인
    """
    result = {"has_glx": False, "has_egl": False, "renderer": "unknown"}

    try:
        out = subprocess.check_output(
            ["glxinfo", "-B"],
            stderr=subprocess.DEVNULL,
            timeout=3,
        ).decode()
        result["has_glx"] = True
        for line in out.splitlines():
            if "OpenGL renderer" in line:
                result["renderer"] = line.split(":", 1)[-1].strip()
    except (FileNotFoundError, subprocess.CalledProcessError, subprocess.TimeoutExpired):
        pass

    # EGL 확인
    try:
        out = subprocess.check_output(
            ["eglinfo"],
            stderr=subprocess.DEVNULL,
            timeout=3,
        ).decode()
        result["has_egl"] = "EGL_VERSION" in out
    except (FileNotFoundError, subprocess.CalledProcessError, subprocess.TimeoutExpired):
        pass

    return result


def is_ssh_session() -> bool:
    """
    Detect if running inside SSH session
    SSH 세션 여부 감지
    """
    return bool(os.environ.get("SSH_CLIENT") or os.environ.get("SSH_TTY"))


def is_virtual_machine() -> bool:
    """
    Detect if running inside a virtual machine (VirtualBox, VMware, etc.)
    가상머신 여부 감지
    """
    try:
        out = subprocess.check_output(
            ["systemd-detect-virt", "--vm"],
            stderr=subprocess.DEVNULL,
            timeout=2,
        ).decode().strip()
        return out not in ("none", "")
    except Exception:
        pass

    # /sys/class/dmi로 폴백
    try:
        dmi = Path("/sys/class/dmi/id/product_name").read_text().lower()
        return any(v in dmi for v in ("virtualbox", "vmware", "kvm", "qemu"))
    except Exception:
        return False


def resolve_sdl_env() -> dict[str, str]:
    """
    Automatically resolve required SDL environment variables
    필요한 SDL 환경변수 자동 결정

    Returns:
        dict: 설정해야 할 환경변수 딕셔너리
    """
    env_patch: dict[str, str] = {}

    display_server = detect_display_server()
    opengl_info = check_opengl_support()
    ssh = is_ssh_session()
    vm = is_virtual_machine()

    print(f"[sdl_env] Display server : {display_server}")
    print(f"[sdl_env] SSH session    : {ssh}")
    print(f"[sdl_env] Virtual machine: {vm}")
    print(f"[sdl_env] OpenGL renderer: {opengl_info['renderer']}")

    # ── DISPLAY 설정 (X11) ──────────────────────────────────────
    if not os.environ.get("DISPLAY"):
        found = find_x11_display()
        if found:
            env_patch["DISPLAY"] = found
            print(f"[sdl_env] DISPLAY 자동 설정: {found}")

    # ── SDL_VIDEODRIVER ──────────────────────────────────────────
    if not os.environ.get("SDL_VIDEODRIVER"):
        if ssh or vm:
            # SSH/VM 환경: offscreen 또는 x11 강제
            env_patch["SDL_VIDEODRIVER"] = "x11"
        elif display_server == "wayland":
            # Wayland + OpenGL 조합은 x11로 강제하는 게 안정적
            env_patch["SDL_VIDEODRIVER"] = "x11"
        elif display_server == "x11":
            env_patch["SDL_VIDEODRIVER"] = "x11"

    # ── EGL 강제 (Wayland 환경 또는 Mesa 환경) ──────────────────
    if display_server == "wayland" or "mesa" in opengl_info["renderer"].lower():
        if not os.environ.get("SDL_VIDEO_X11_FORCE_EGL"):
            env_patch["SDL_VIDEO_X11_FORCE_EGL"] = "1"

    # ── 소프트웨어 렌더링 폴백 ───────────────────────────────────
    # GPU 드라이버 없고 EGL도 없는 경우
    if not opengl_info["has_glx"] and not opengl_info["has_egl"]:
        print("[sdl_env] ⚠️  HW OpenGL 불가 → 소프트웨어 렌더링 폴백")
        env_patch["LIBGL_ALWAYS_SOFTWARE"] = "1"
        env_patch["SDL_RENDER_DRIVER"] = "software"

    return env_patch


def apply_sdl_env(verbose: bool = True) -> dict[str, str]:
    """
    Apply resolved SDL env vars to the current process environment
    해결된 SDL 환경변수를 현재 프로세스에 적용

    Must be called BEFORE importing pygame
    pygame import 전에 반드시 호출해야 함
    """
    patch = resolve_sdl_env()

    for key, val in patch.items():
        os.environ[key] = val
        if verbose:
            print(f"[sdl_env] SET {key}={val}")

    return patch

사용법:

# ── main.py ──────────────────────────────────────────────────────
# IMPORTANT: apply_sdl_env() must be called before importing pygame
# 중요: pygame import 전에 반드시 apply_sdl_env() 호출

from sdl_env import apply_sdl_env
apply_sdl_env()  # ← 여기서 먼저 설정

import pygame
from pygame.locals import *
from OpenGL.GL import *

def main():
    pygame.init()
    screen = pygame.display.set_mode(
        (1280, 720),
        DOUBLEBUF | OPENGL,
    )
    pygame.display.set_caption("pygame + OpenGL")

    running = True
    while running:
        for event in pygame.event.get():
            if event.type == QUIT:
                running = False

        glClearColor(0.1, 0.1, 0.15, 1.0)
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)

        pygame.display.flip()

    pygame.quit()

if __name__ == "__main__":
    main()

환경별 동작 요약:

환경

자동 설정

X11 일반

DISPLAY=:0, SDL_VIDEODRIVER=x11

Wayland 세션

SDL_VIDEODRIVER=x11, SDL_VIDEO_X11_FORCE_EGL=1

SSH 원격

DISPLAY=:0, SDL_VIDEODRIVER=x11

VM (VirtualBox 등)

SDL_VIDEODRIVER=x11

GPU 드라이버 없음

LIBGL_ALWAYS_SOFTWARE=1

imgui_bundle 과 함께 쓸 때:

from sdl_env import apply_sdl_env
apply_sdl_env()  # hello_imgui.run() 전에 호출

from imgui_bundle import hello_imgui, imgui
# ...
hello_imgui.run(runner_params)

Troubleshooting

main() LINKER ERROR

아래와 같은 에러 메시지가 출력될 수 있다.

xxx error LNK2019: _WinMain@16 외부 기호(_WinMainCRTStartup 함수에서 참조)를 확인하지 못했습니다. 
xxx fatal error LNK1120: 1개의 확인할 수 없는 외부 참조입니다. 

SDL에서 mainWinMain으로 Define하여 발생되는 에러이다. SDL.lib, SDLmain.lib 을 링크하면 된다.

MinGW에서 사용할 경우 아래와 같이 사용하면 된다.

$ g++ -std=c++11 main.cpp -lmingw32 -lSDL2main -lSDL2 -lopengl32

implicit entry/start for main executable

clang에서 SDL을 사용할 경우 아래와 같은 에러 메시지가 출력될 수 있다.

Undefined symbols for architecture x86_64:
  "_main", referenced from:
    implicit entry/start for main executable.
    maybe you meant: _SDL_main
ld: symbol(s) not found for architecture x86_64

이 경우, main이 매크로로 등록되어 나타나는 현상이다. 아래와 같이 매크로 등록을 해제한다.

#ifdef main
#undef main
#endif

Renderer already associated with window

SDL_GetError()를 통하여 아래와 같은 에러 메시지를 확인할 수 있다.

Renderer already associated with window

이 경우, 이미 해당 Window에서 Renderer를 생성했다는 의미이다. 이미 생성된 Renderer를 찾아봐야 한다.

MSYS DirectX Symbol error

./configure
make
make install

MSYS에서 위와같이 설치할 경우 DirectX 관련 심볼(__in 등)을 찾을 수 없을 경우가 있다. 이 경우 DirectX를 정상적으로 설치해야 한다.

OpenGL.error.Error: Attempt to retrieve context when no valid context

Ubuntu 20.04 이상에서 Wayland 로 실행된다면 다음과 같은 에러가 출력될 수 있다:

pygame-ce 2.4.1 (SDL 2.28.5, Python 3.11.4)
/home/yourname/Project/ddrm/test.py:13: Warning: PyGame seems to be running through X11 on top of wayland, instead of wayland directly
...
OpenGL.error.Error: Attempt to retrieve context when no valid context

간단히, SDL_VIDEO_X11_FORCE_EGL=1 환경변수 설정하면 된다.

See also

Favorite site

SDL Wiki

Tutorial

Guide

Guide: Initialize

References


  1. Lazyfoo.net.140828.backup.7z 

  2. Inside_linux-happy_hacking-maso200109-use_sdl_library_02.pdf 

  3. CODEpendent-wx-sdl_tutorial_part_1.pdf 

  4. Demonstration_of_SDL2+FFmpeg_player_based_on.pdf