Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 18 additions & 22 deletions .github/workflows/build-sdl3.yml
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ jobs:
strategy:
fail-fast: false # if a particular matrix build fails, don't skip the rest
matrix:
os: [ubuntu-24.04, windows-latest, macos-14]
os: [ubuntu-24.04, windows-latest, macos-15]

env:
# Pip now forces us to either make a venv or set this flag, so we will do
Expand All @@ -54,25 +54,24 @@ jobs:
steps:
- uses: actions/[email protected]

- name: Install pygame deps (linux)
- name: Fix apt issues (linux)
if: matrix.os == 'ubuntu-24.04'
run: |
sudo apt-get update --fix-missing
sudo apt-get install libfreetype6-dev libportmidi-dev python3-dev
run: sudo apt-get update --fix-missing

- name: Install pygame deps (mac)
if: matrix.os == 'macos-14'
run: brew install freetype portmidi
- name: Install pygame & SDL deps (mac)
if: matrix.os == 'macos-15'
run: brew install freetype harfbuzz portmidi libtiff webp

# taken from dependencies of the 'libsdl2-dev' package
- name: Install SDL deps (linux)
- name: Install pygame & SDL deps (linux)
if: matrix.os == 'ubuntu-24.04'
run: >
sudo apt-get install libasound2-dev libdbus-1-dev libdecor-0-dev libdrm-dev
libegl-dev libgbm-dev libgl-dev libgles-dev libibus-1.0-dev libpulse-dev
libsamplerate0-dev libsndio-dev libudev-dev libwayland-dev libx11-dev
libxcursor-dev libxext-dev libxfixes-dev libxi-dev libxinerama-dev
libxkbcommon-dev libxrandr-dev libxss-dev libxt-dev libxv-dev libxxf86vm-dev
libfreetype-dev libharfbuzz-dev libportmidi-dev libtiff-dev libwebp-dev
python3-dev

# taken from https://wiki.libsdl.org/SDL3/Installation
- name: Install SDL3
Expand All @@ -93,7 +92,9 @@ jobs:
cd SDL_image
mkdir build
cd build
cmake -DCMAKE_BUILD_TYPE=Release ..
cmake -DCMAKE_BUILD_TYPE=Release -DSDLIMAGE_VENDORED=0 \
-DSDLIMAGE_BACKEND_STB=1 -DSDLIMAGE_BACKEND_IMAGEIO=0 \
-DSDLIMAGE_AVIF=0 -DSDLIMAGE_JXL=0 -DSDLIMAGE_TIF=1 -DSDLIMAGE_WEBP=1 ..
cmake --build . --config Release --parallel
sudo cmake --install . --config Release

Expand All @@ -104,20 +105,15 @@ jobs:
cd SDL_ttf
mkdir build
cd build
cmake -DCMAKE_BUILD_TYPE=Release ..
cmake -DCMAKE_BUILD_TYPE=Release -DSDLTTF_VENDORED=0 -DSDLTTF_HARFBUZZ=1 ..
cmake --build . --config Release --parallel
sudo cmake --install . --config Release

- name: Build with SDL3
run: python3 dev.py build --sdl3

# eventually we need to run all tests, but for now test that importing pygame
# works
- name: Test import works
run: python3 -c 'import pygame'

# - name: Run tests
# env:
# SDL_VIDEODRIVER: "dummy"
# SDL_AUDIODRIVER: "disk"
# run: python3 -m pygame.tests -v --exclude opengl,music,timing --time_out 300
- name: Run tests
env:
SDL_VIDEODRIVER: "dummy"
SDL_AUDIODRIVER: "disk"
run: python3 -m pygame.tests -v --exclude opengl,music,timing --time_out 300
3 changes: 3 additions & 0 deletions buildconfig/stubs/pygame/display.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -745,6 +745,9 @@ def set_window_position(position: Point) -> None:
still be able to move the window after this call. See also
:func:`pygame.display.get_window_position()`.

.. note:: This function is not supported on some video drivers (like wayland)
and a :exc:`pygame.error` exception may be raised in such cases.

.. versionadded:: 2.5.0
"""

Expand Down
2 changes: 2 additions & 0 deletions buildconfig/stubs/pygame/mouse.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -292,4 +292,6 @@ def set_relative_mode(enable: bool, /) -> None:
``True`` will exit relative mouse mode.

.. versionadded:: 2.4.0
.. versionchanged:: 2.5.6 calling this function before calling
:func:`pygame.display.set_mode` is deprecated and may error in the future.
"""
12 changes: 11 additions & 1 deletion buildconfig/stubs/pygame/window.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -222,6 +222,9 @@ class Window:

Setting the always-on-top mode requires SDL 2.0.16+.

.. note:: Setting this property is not supported on some video drivers (like wayland)
and a :exc:`pygame.error` exception may be raised in such cases.

.. versionadded:: 2.3.1
"""

Expand Down Expand Up @@ -296,12 +299,19 @@ class Window:

The position may be a tuple of (x, y) coordinates or ``WINDOWPOS_CENTERED`` or
``WINDOWPOS_UNDEFINED``. The origin is the topleft of the main display.

.. note:: Setting this property is not supported on some video drivers (like wayland)
and a :exc:`pygame.error` exception may be raised in such cases.
"""

@position.setter
def position(self, value: Union[int, Point]) -> None: ...
opacity: float
"""Get or set the window opacity, between 0.0 (fully transparent) and 1.0 (fully opaque)."""
"""Get or set the window opacity, between 0.0 (fully transparent) and 1.0 (fully opaque).

.. note:: Setting this property is not supported on some video drivers (like wayland)
and a :exc:`pygame.error` exception may be raised in such cases.
"""

@property
def opengl(self) -> bool:
Expand Down
2 changes: 1 addition & 1 deletion docs/reST/c_api/surface.rst
Original file line number Diff line number Diff line change
Expand Up @@ -56,4 +56,4 @@ Header file: src_c/include/pygame.h
by the blit.
The C version of the :py:meth:`pygame.Surface.blit` method.
Return ``1`` on success, ``0`` on an exception.
Return ``0`` on success, ``1`` on an exception.
111 changes: 92 additions & 19 deletions src_c/_pygame.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,13 @@
#include "stdbool.h"

#if SDL_VERSION_ATLEAST(3, 0, 0)

#include "include/SDL_gesture.h"

#define SDL_DOLLARGESTURE GESTURE_DOLLARGESTURE
#define SDL_DOLLARRECORD GESTURE_DOLLARRECORD
#define SDL_MULTIGESTURE GESTURE_MULTIGESTURE

#define PG_ShowCursor SDL_ShowCursor
#define PG_HideCursor SDL_HideCursor
#define PG_CursorVisible SDL_CursorVisible
Expand All @@ -68,17 +75,19 @@
#define PG_AUDIO_ALLOW_CHANNELS_CHANGE 0
#define PG_AUDIO_ALLOW_ANY_CHANGE 0

// Todo: deal with multigesture.. See
// https://github.com/pygame-community/pygame-ce/issues/2420
#define PG_MULTIGESTURE 0

#define PG_JOYBALLMOTION 0

#define PG_CreateSurface SDL_CreateSurface
#define PG_CreateSurfaceFrom SDL_CreateSurfaceFrom
#define PG_ConvertSurface SDL_ConvertSurface
#define PG_ConvertSurfaceFormat SDL_ConvertSurface

/* Convert surface using palette and format of dst */
static inline SDL_Surface *
PG_ConvertSurface(SDL_Surface *surface, SDL_Surface *dst)
{
return SDL_ConvertSurfaceAndColorspace(surface, dst->format,
SDL_GetSurfacePalette(dst),
SDL_GetSurfaceColorspace(dst), 0);
}

#define PG_PixelFormatEnum SDL_PixelFormat

#define PG_SurfaceHasRLE SDL_SurfaceHasRLE
Expand All @@ -105,7 +114,17 @@ PG_UnlockMutex(SDL_mutex *mutex)
return 0;
}

#define PG_SURF_BitsPerPixel(surf) SDL_BITSPERPIXEL(surf->format)
static inline int
PG_SURF_BitsPerPixel(SDL_Surface *surf)
{
if (SDL_BYTESPERPIXEL(surf->format) == 4) {
/* Compat with SDL2: for 24-bit images SDL3 returns 24 when SDL2
* returned 32 */
return 32;
}
return SDL_BITSPERPIXEL(surf->format);
}

#define PG_SURF_BytesPerPixel(surf) SDL_BYTESPERPIXEL(surf->format)
#define PG_FORMAT_BitsPerPixel(format) format->bits_per_pixel
#define PG_FORMAT_BytesPerPixel(format) format->bytes_per_pixel
Expand All @@ -118,11 +137,23 @@ PG_UnlockMutex(SDL_mutex *mutex)

#define PG_PixelFormat const SDL_PixelFormatDetails

static inline SDL_Palette *
PG_GetSurfacePalette(SDL_Surface *surf)
{
SDL_Palette *ret = SDL_GetSurfacePalette(surf);
if (!ret && SDL_ISPIXELFORMAT_INDEXED(surf->format)) {
/* Palette doesn't exist but is expected, so create it.
* SDL will associate the newly created palette with the surface */
ret = SDL_CreateSurfacePalette(surf);
}
return ret;
}

static inline bool
PG_GetSurfaceDetails(SDL_Surface *surf, PG_PixelFormat **format_p,
SDL_Palette **palette_p)
{
*palette_p = SDL_GetSurfacePalette(surf);
*palette_p = PG_GetSurfacePalette(surf);
*format_p = SDL_GetPixelFormatDetails(surf->format);
return *format_p != NULL;
}
Expand All @@ -133,7 +164,6 @@ PG_GetSurfaceFormat(SDL_Surface *surf)
return SDL_GetPixelFormatDetails(surf->format);
}

#define PG_GetSurfacePalette SDL_GetSurfacePalette
#define PG_SetPaletteColors SDL_SetPaletteColors
#define PG_SetSurfacePalette SDL_SetSurfacePalette
#define PG_SetSurfaceColorKey SDL_SetSurfaceColorKey
Expand Down Expand Up @@ -166,6 +196,8 @@ PG_GetSurfaceFormat(SDL_Surface *surf)

#define PG_GetSurfaceClipRect SDL_GetSurfaceClipRect

#define PG_GL_SetSwapInterval SDL_GL_SetSwapInterval

#else /* ~SDL_VERSION_ATLEAST(3, 0, 0)*/
#define PG_ShowCursor() SDL_ShowCursor(SDL_ENABLE)
#define PG_HideCursor() SDL_ShowCursor(SDL_DISABLE)
Expand All @@ -183,18 +215,19 @@ PG_GetSurfaceFormat(SDL_Surface *surf)
#define PG_AUDIO_ALLOW_CHANNELS_CHANGE SDL_AUDIO_ALLOW_CHANNELS_CHANGE
#define PG_AUDIO_ALLOW_ANY_CHANGE SDL_AUDIO_ALLOW_ANY_CHANGE

#define PG_MULTIGESTURE SDL_MULTIGESTURE

#define PG_JOYBALLMOTION SDL_JOYBALLMOTION

#define PG_CreateSurface(width, height, format) \
SDL_CreateRGBSurfaceWithFormat(0, width, height, 0, format)
#define PG_CreateSurfaceFrom(width, height, format, pixels, pitch) \
SDL_CreateRGBSurfaceWithFormatFrom(pixels, width, height, 0, pitch, format)
#define PG_ConvertSurface(src, fmt) SDL_ConvertSurface(src, fmt, 0)
#define PG_ConvertSurfaceFormat(src, pixel_format) \
SDL_ConvertSurfaceFormat(src, pixel_format, 0)

static inline SDL_Surface *
PG_ConvertSurface(SDL_Surface *surface, SDL_Surface *dst)
{
return SDL_ConvertSurface(surface, dst->format, 0);
}

#define PG_PixelFormatEnum SDL_PixelFormatEnum

#define PG_SoftStretchNearest(src, srcrect, dst, dstrect) \
Expand Down Expand Up @@ -378,6 +411,12 @@ PG_GetSurfaceClipRect(SDL_Surface *surface, SDL_Rect *rect)
*rect = surface->clip_rect;
return true;
}

static inline bool
PG_GL_SetSwapInterval(int interval)
{
return SDL_GL_SetSwapInterval(interval) == 0;
}
#endif

/* DictProxy is useful for event posting with an arbitrary dict. Maintains
Expand Down Expand Up @@ -425,6 +464,40 @@ typedef enum {
PGM_BUTTON_KEEP = 0x80
} PygameMouseFlags;

#if SDL_VERSION_ATLEAST(3, 0, 0)
typedef enum {
PGE_WINDOWSHOWN = SDL_EVENT_WINDOW_SHOWN,
PGE_WINDOWHIDDEN = SDL_EVENT_WINDOW_HIDDEN,
PGE_WINDOWEXPOSED = SDL_EVENT_WINDOW_EXPOSED,
PGE_WINDOWMOVED = SDL_EVENT_WINDOW_MOVED,
PGE_WINDOWRESIZED = SDL_EVENT_WINDOW_RESIZED,
PGE_WINDOWSIZECHANGED = SDL_EVENT_WINDOW_PIXEL_SIZE_CHANGED,
PGE_WINDOWMINIMIZED = SDL_EVENT_WINDOW_MINIMIZED,
PGE_WINDOWMAXIMIZED = SDL_EVENT_WINDOW_MAXIMIZED,
PGE_WINDOWRESTORED = SDL_EVENT_WINDOW_RESTORED,
PGE_WINDOWENTER = SDL_EVENT_WINDOW_MOUSE_ENTER,
PGE_WINDOWLEAVE = SDL_EVENT_WINDOW_MOUSE_LEAVE,
PGE_WINDOWFOCUSGAINED = SDL_EVENT_WINDOW_FOCUS_GAINED,
PGE_WINDOWFOCUSLOST = SDL_EVENT_WINDOW_FOCUS_LOST,
PGE_WINDOWCLOSE = SDL_EVENT_WINDOW_CLOSE_REQUESTED,
PGE_WINDOWTAKEFOCUS = -1, /* No SDL3 equivalent */
PGE_WINDOWHITTEST = SDL_EVENT_WINDOW_HIT_TEST,
PGE_WINDOWICCPROFCHANGED = SDL_EVENT_WINDOW_ICCPROF_CHANGED,
PGE_WINDOWDISPLAYCHANGED = SDL_EVENT_WINDOW_DISPLAY_CHANGED,
} PygameWindowEventCode;
/*
TODO: expose these window events in pygame API
SDL_EVENT_WINDOW_METAL_VIEW_RESIZED,
SDL_EVENT_WINDOW_DISPLAY_SCALE_CHANGED,
SDL_EVENT_WINDOW_SAFE_AREA_CHANGED,
SDL_EVENT_WINDOW_OCCLUDED,
SDL_EVENT_WINDOW_ENTER_FULLSCREEN,
SDL_EVENT_WINDOW_LEAVE_FULLSCREEN,
SDL_EVENT_WINDOW_DESTROYED,
SDL_EVENT_WINDOW_HDR_STATE_CHANGED,
*/
#endif

typedef enum {
/* Any SDL_* events here are for backward compatibility. */
SDL_NOEVENT = 0,
Expand All @@ -440,6 +513,9 @@ typedef enum {
PGE_MIDIIN,
PGE_MIDIOUT,

/* These PGE events are only needed on SDL2: SDL3 has dedicated events for
* these */
#if !SDL_VERSION_ATLEAST(3, 0, 0)
/* DO NOT CHANGE THE ORDER OF EVENTS HERE */
PGE_WINDOWSHOWN,
PGE_WINDOWHIDDEN,
Expand All @@ -459,6 +535,7 @@ typedef enum {
PGE_WINDOWHITTEST,
PGE_WINDOWICCPROFCHANGED,
PGE_WINDOWDISPLAYCHANGED,
#endif

/* Here we define PGPOST_* events, events that act as a one-to-one
* proxy for SDL events (and some extra events too!), the proxy is used
Expand Down Expand Up @@ -494,10 +571,8 @@ typedef enum {
PGPOST_CONTROLLERTOUCHPADMOTION,
PGPOST_CONTROLLERTOUCHPADUP,
PGPOST_CONTROLLERSENSORUPDATE,
#if !SDL_VERSION_ATLEAST(3, 0, 0)
PGPOST_DOLLARGESTURE,
PGPOST_DOLLARRECORD,
#endif
PGPOST_DROPFILE,
PGPOST_DROPTEXT,
PGPOST_DROPBEGIN,
Expand All @@ -522,9 +597,7 @@ typedef enum {
PGPOST_MOUSEBUTTONDOWN,
PGPOST_MOUSEBUTTONUP,
PGPOST_MOUSEWHEEL,
#if !SDL_VERSION_ATLEAST(3, 0, 0)
PGPOST_MULTIGESTURE,
#endif
PGPOST_NOEVENT,
PGPOST_QUIT,
PGPOST_RENDER_TARGETS_RESET,
Expand Down
4 changes: 2 additions & 2 deletions src_c/constants.c
Original file line number Diff line number Diff line change
Expand Up @@ -260,7 +260,7 @@ MODINIT_DEFINE(constants)
DEC_CONST(MOUSEBUTTONDOWN);
DEC_CONST(MOUSEBUTTONUP);
DEC_CONST(JOYAXISMOTION);
DEC_CONSTS(JOYBALLMOTION, PG_JOYBALLMOTION);
DEC_CONST(JOYBALLMOTION);
DEC_CONST(JOYHATMOTION);
DEC_CONST(JOYBUTTONDOWN);
DEC_CONST(JOYBUTTONUP);
Expand Down Expand Up @@ -302,7 +302,7 @@ MODINIT_DEFINE(constants)
DEC_CONST(FINGERMOTION);
DEC_CONST(FINGERDOWN);
DEC_CONST(FINGERUP);
DEC_CONSTS(MULTIGESTURE, PG_MULTIGESTURE);
DEC_CONST(MULTIGESTURE);
DEC_CONST(AUDIODEVICEADDED);
DEC_CONST(AUDIODEVICEREMOVED);
DEC_CONST(MOUSEWHEEL);
Expand Down
Loading
Loading