- Added SDL_WINDOW_TRANSPARENT to request a window with transparent framebuffer
- Remove SDL_VIDEO_EGL_ALLOW_TRANSPARENCY hint, EGL now checks 'window->flags & SDL_WINDOW_TRANSPARENT'main
parent
4dededd345
commit
2cafa52598
|
@ -1602,17 +1602,6 @@ extern "C" {
|
||||||
*/
|
*/
|
||||||
#define SDL_HINT_VIDEO_DOUBLE_BUFFER "SDL_VIDEO_DOUBLE_BUFFER"
|
#define SDL_HINT_VIDEO_DOUBLE_BUFFER "SDL_VIDEO_DOUBLE_BUFFER"
|
||||||
|
|
||||||
/**
|
|
||||||
* \brief A variable controlling whether the EGL window is allowed to be
|
|
||||||
* composited as transparent, rather than opaque.
|
|
||||||
*
|
|
||||||
* Most window systems will always render windows opaque, even if the surface
|
|
||||||
* format has an alpha channel. This is not always true, however, so by default
|
|
||||||
* SDL will try to enforce opaque composition. To override this behavior, you
|
|
||||||
* can set this hint to "1".
|
|
||||||
*/
|
|
||||||
#define SDL_HINT_VIDEO_EGL_ALLOW_TRANSPARENCY "SDL_VIDEO_EGL_ALLOW_TRANSPARENCY"
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief If eglGetPlatformDisplay fails, fall back to calling eglGetDisplay.
|
* \brief If eglGetPlatformDisplay fails, fall back to calling eglGetDisplay.
|
||||||
*
|
*
|
||||||
|
|
|
@ -152,6 +152,7 @@ typedef enum
|
||||||
SDL_WINDOW_KEYBOARD_GRABBED = 0x00100000, /**< window has grabbed keyboard input */
|
SDL_WINDOW_KEYBOARD_GRABBED = 0x00100000, /**< window has grabbed keyboard input */
|
||||||
SDL_WINDOW_VULKAN = 0x10000000, /**< window usable for Vulkan surface */
|
SDL_WINDOW_VULKAN = 0x10000000, /**< window usable for Vulkan surface */
|
||||||
SDL_WINDOW_METAL = 0x20000000, /**< window usable for Metal view */
|
SDL_WINDOW_METAL = 0x20000000, /**< window usable for Metal view */
|
||||||
|
SDL_WINDOW_TRANSPARENT = 0x40000000, /**< window with transparent buffer */
|
||||||
|
|
||||||
} SDL_WindowFlags;
|
} SDL_WindowFlags;
|
||||||
|
|
||||||
|
|
|
@ -1057,7 +1057,7 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeSurfaceChanged)(JNIEnv *env, j
|
||||||
|
|
||||||
/* If the surface has been previously destroyed by onNativeSurfaceDestroyed, recreate it here */
|
/* If the surface has been previously destroyed by onNativeSurfaceDestroyed, recreate it here */
|
||||||
if (data->egl_surface == EGL_NO_SURFACE) {
|
if (data->egl_surface == EGL_NO_SURFACE) {
|
||||||
data->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)data->native_window);
|
data->egl_surface = SDL_EGL_CreateSurface(_this, Android_Window, (NativeWindowType)data->native_window);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* GL Context handling is done in the event loop because this function is run from the Java thread */
|
/* GL Context handling is done in the event loop because this function is run from the Java thread */
|
||||||
|
|
|
@ -33,7 +33,8 @@ static const char *video_usage[] = {
|
||||||
"[--logical-presentation disabled|match|stretch|letterbox|overscan|integer_scale]",
|
"[--logical-presentation disabled|match|stretch|letterbox|overscan|integer_scale]",
|
||||||
"[--logical-scale-quality nearest|linear|best]",
|
"[--logical-scale-quality nearest|linear|best]",
|
||||||
"[--scale N]", "[--depth N]", "[--refresh R]", "[--vsync]", "[--noframe]",
|
"[--scale N]", "[--depth N]", "[--refresh R]", "[--vsync]", "[--noframe]",
|
||||||
"[--resizable]", "[--minimize]", "[--maximize]", "[--grab]", "[--keyboard-grab]",
|
"[--resizable]", "[--transparent]",
|
||||||
|
"[--minimize]", "[--maximize]", "[--grab]", "[--keyboard-grab]",
|
||||||
"[--hidden]", "[--input-focus]", "[--mouse-focus]",
|
"[--hidden]", "[--input-focus]", "[--mouse-focus]",
|
||||||
"[--flash-on-focus-loss]", "[--allow-highdpi]", "[--confine-cursor X,Y,W,H]",
|
"[--flash-on-focus-loss]", "[--allow-highdpi]", "[--confine-cursor X,Y,W,H]",
|
||||||
"[--usable-bounds]"
|
"[--usable-bounds]"
|
||||||
|
@ -490,6 +491,10 @@ int SDLTest_CommonArg(SDLTest_CommonState *state, int index)
|
||||||
state->window_flags |= SDL_WINDOW_RESIZABLE;
|
state->window_flags |= SDL_WINDOW_RESIZABLE;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
if (SDL_strcasecmp(argv[index], "--transparent") == 0) {
|
||||||
|
state->window_flags |= SDL_WINDOW_TRANSPARENT;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
if (SDL_strcasecmp(argv[index], "--minimize") == 0) {
|
if (SDL_strcasecmp(argv[index], "--minimize") == 0) {
|
||||||
state->window_flags |= SDL_WINDOW_MINIMIZED;
|
state->window_flags |= SDL_WINDOW_MINIMIZED;
|
||||||
return 1;
|
return 1;
|
||||||
|
|
|
@ -1218,7 +1218,7 @@ int SDL_EGL_DeleteContext(_THIS, SDL_GLContext context)
|
||||||
}
|
}
|
||||||
|
|
||||||
EGLSurface *
|
EGLSurface *
|
||||||
SDL_EGL_CreateSurface(_THIS, NativeWindowType nw)
|
SDL_EGL_CreateSurface(_THIS, SDL_Window *window, NativeWindowType nw)
|
||||||
{
|
{
|
||||||
#if SDL_VIDEO_DRIVER_ANDROID
|
#if SDL_VIDEO_DRIVER_ANDROID
|
||||||
EGLint format_wanted;
|
EGLint format_wanted;
|
||||||
|
@ -1260,7 +1260,10 @@ SDL_EGL_CreateSurface(_THIS, NativeWindowType nw)
|
||||||
|
|
||||||
#ifdef EGL_EXT_present_opaque
|
#ifdef EGL_EXT_present_opaque
|
||||||
if (SDL_EGL_HasExtension(_this, SDL_EGL_DISPLAY_EXTENSION, "EGL_EXT_present_opaque")) {
|
if (SDL_EGL_HasExtension(_this, SDL_EGL_DISPLAY_EXTENSION, "EGL_EXT_present_opaque")) {
|
||||||
const SDL_bool allow_transparent = SDL_GetHintBoolean(SDL_HINT_VIDEO_EGL_ALLOW_TRANSPARENCY, SDL_FALSE);
|
SDL_bool allow_transparent = SDL_FALSE;
|
||||||
|
if (window && (window->flags & SDL_WINDOW_TRANSPARENT)) {
|
||||||
|
allow_transparent = SDL_TRUE;
|
||||||
|
}
|
||||||
attribs[attr++] = EGL_PRESENT_OPAQUE_EXT;
|
attribs[attr++] = EGL_PRESENT_OPAQUE_EXT;
|
||||||
attribs[attr++] = allow_transparent ? EGL_FALSE : EGL_TRUE;
|
attribs[attr++] = allow_transparent ? EGL_FALSE : EGL_TRUE;
|
||||||
}
|
}
|
||||||
|
|
|
@ -129,7 +129,7 @@ extern int SDL_EGL_ChooseConfig(_THIS);
|
||||||
extern int SDL_EGL_SetSwapInterval(_THIS, int interval);
|
extern int SDL_EGL_SetSwapInterval(_THIS, int interval);
|
||||||
extern int SDL_EGL_GetSwapInterval(_THIS, int *interval);
|
extern int SDL_EGL_GetSwapInterval(_THIS, int *interval);
|
||||||
extern int SDL_EGL_DeleteContext(_THIS, SDL_GLContext context);
|
extern int SDL_EGL_DeleteContext(_THIS, SDL_GLContext context);
|
||||||
extern EGLSurface *SDL_EGL_CreateSurface(_THIS, NativeWindowType nw);
|
extern EGLSurface *SDL_EGL_CreateSurface(_THIS, SDL_Window *window, NativeWindowType nw);
|
||||||
extern void SDL_EGL_DestroySurface(_THIS, EGLSurface egl_surface);
|
extern void SDL_EGL_DestroySurface(_THIS, EGLSurface egl_surface);
|
||||||
|
|
||||||
extern EGLSurface SDL_EGL_CreateOffscreenSurface(_THIS, int width, int height);
|
extern EGLSurface SDL_EGL_CreateOffscreenSurface(_THIS, int width, int height);
|
||||||
|
|
|
@ -206,6 +206,7 @@ static int SDL_CreateWindowTexture(SDL_VideoDevice *_this, SDL_Window *window, U
|
||||||
{
|
{
|
||||||
SDL_RendererInfo info;
|
SDL_RendererInfo info;
|
||||||
SDL_WindowTextureData *data = SDL_GetWindowData(window, SDL_WINDOWTEXTUREDATA);
|
SDL_WindowTextureData *data = SDL_GetWindowData(window, SDL_WINDOWTEXTUREDATA);
|
||||||
|
const int transparent = (window->flags & SDL_WINDOW_TRANSPARENT) ? SDL_TRUE : SDL_FALSE;
|
||||||
int i;
|
int i;
|
||||||
int w, h;
|
int w, h;
|
||||||
|
|
||||||
|
@ -274,12 +275,12 @@ static int SDL_CreateWindowTexture(SDL_VideoDevice *_this, SDL_Window *window, U
|
||||||
SDL_free(data->pixels);
|
SDL_free(data->pixels);
|
||||||
data->pixels = NULL;
|
data->pixels = NULL;
|
||||||
|
|
||||||
/* Find the first format without an alpha channel */
|
/* Find the first format with or without an alpha channel */
|
||||||
*format = info.texture_formats[0];
|
*format = info.texture_formats[0];
|
||||||
|
|
||||||
for (i = 0; i < (int)info.num_texture_formats; ++i) {
|
for (i = 0; i < (int)info.num_texture_formats; ++i) {
|
||||||
if (!SDL_ISPIXELFORMAT_FOURCC(info.texture_formats[i]) &&
|
if (!SDL_ISPIXELFORMAT_FOURCC(info.texture_formats[i]) &&
|
||||||
!SDL_ISPIXELFORMAT_ALPHA(info.texture_formats[i])) {
|
transparent == SDL_ISPIXELFORMAT_ALPHA(info.texture_formats[i])) {
|
||||||
*format = info.texture_formats[i];
|
*format = info.texture_formats[i];
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -1646,7 +1647,7 @@ Uint32 SDL_GetWindowPixelFormat(SDL_Window *window)
|
||||||
}
|
}
|
||||||
|
|
||||||
#define CREATE_FLAGS \
|
#define CREATE_FLAGS \
|
||||||
(SDL_WINDOW_OPENGL | SDL_WINDOW_BORDERLESS | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI | SDL_WINDOW_ALWAYS_ON_TOP | SDL_WINDOW_SKIP_TASKBAR | SDL_WINDOW_POPUP_MENU | SDL_WINDOW_UTILITY | SDL_WINDOW_TOOLTIP | SDL_WINDOW_VULKAN | SDL_WINDOW_MINIMIZED | SDL_WINDOW_METAL)
|
(SDL_WINDOW_OPENGL | SDL_WINDOW_BORDERLESS | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI | SDL_WINDOW_ALWAYS_ON_TOP | SDL_WINDOW_SKIP_TASKBAR | SDL_WINDOW_POPUP_MENU | SDL_WINDOW_UTILITY | SDL_WINDOW_TOOLTIP | SDL_WINDOW_VULKAN | SDL_WINDOW_MINIMIZED | SDL_WINDOW_METAL | SDL_WINDOW_TRANSPARENT)
|
||||||
|
|
||||||
static SDL_INLINE SDL_bool IsAcceptingDragAndDrop(void)
|
static SDL_INLINE SDL_bool IsAcceptingDragAndDrop(void)
|
||||||
{
|
{
|
||||||
|
|
|
@ -79,7 +79,7 @@ int Android_CreateWindow(_THIS, SDL_Window *window)
|
||||||
incompatible with vkCreateAndroidSurfaceKHR */
|
incompatible with vkCreateAndroidSurfaceKHR */
|
||||||
#if SDL_VIDEO_OPENGL_EGL
|
#if SDL_VIDEO_OPENGL_EGL
|
||||||
if (window->flags & SDL_WINDOW_OPENGL) {
|
if (window->flags & SDL_WINDOW_OPENGL) {
|
||||||
data->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)data->native_window);
|
data->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)data->native_window);
|
||||||
|
|
||||||
if (data->egl_surface == EGL_NO_SURFACE) {
|
if (data->egl_surface == EGL_NO_SURFACE) {
|
||||||
ANativeWindow_release(data->native_window);
|
ANativeWindow_release(data->native_window);
|
||||||
|
|
|
@ -43,7 +43,8 @@
|
||||||
|
|
||||||
- (instancetype)initWithFrame:(NSRect)frame
|
- (instancetype)initWithFrame:(NSRect)frame
|
||||||
highDPI:(BOOL)highDPI
|
highDPI:(BOOL)highDPI
|
||||||
windowID:(Uint32)windowID;
|
windowID:(Uint32)windowID
|
||||||
|
opaque:(BOOL)opaque;
|
||||||
|
|
||||||
- (void)updateDrawableSize;
|
- (void)updateDrawableSize;
|
||||||
- (NSView *)hitTest:(NSPoint)point;
|
- (NSView *)hitTest:(NSPoint)point;
|
||||||
|
|
|
@ -76,7 +76,8 @@ static int SDLCALL SDL_MetalViewEventWatch(void *userdata, SDL_Event *event)
|
||||||
|
|
||||||
- (instancetype)initWithFrame:(NSRect)frame
|
- (instancetype)initWithFrame:(NSRect)frame
|
||||||
highDPI:(BOOL)highDPI
|
highDPI:(BOOL)highDPI
|
||||||
windowID:(Uint32)windowID;
|
windowID:(Uint32)windowID
|
||||||
|
opaque:(BOOL)opaque
|
||||||
{
|
{
|
||||||
self = [super initWithFrame:frame];
|
self = [super initWithFrame:frame];
|
||||||
if (self != nil) {
|
if (self != nil) {
|
||||||
|
@ -87,6 +88,8 @@ static int SDLCALL SDL_MetalViewEventWatch(void *userdata, SDL_Event *event)
|
||||||
/* Allow resize. */
|
/* Allow resize. */
|
||||||
self.autoresizingMask = NSViewWidthSizable | NSViewHeightSizable;
|
self.autoresizingMask = NSViewWidthSizable | NSViewHeightSizable;
|
||||||
|
|
||||||
|
self.layer.opaque = opaque;
|
||||||
|
|
||||||
SDL_AddEventWatch(SDL_MetalViewEventWatch, (__bridge void *)(self));
|
SDL_AddEventWatch(SDL_MetalViewEventWatch, (__bridge void *)(self));
|
||||||
|
|
||||||
[self updateDrawableSize];
|
[self updateDrawableSize];
|
||||||
|
@ -136,13 +139,15 @@ Cocoa_Metal_CreateView(_THIS, SDL_Window *window)
|
||||||
SDL_CocoaWindowData *data = (__bridge SDL_CocoaWindowData *)window->driverdata;
|
SDL_CocoaWindowData *data = (__bridge SDL_CocoaWindowData *)window->driverdata;
|
||||||
NSView *view = data.nswindow.contentView;
|
NSView *view = data.nswindow.contentView;
|
||||||
BOOL highDPI = (window->flags & SDL_WINDOW_ALLOW_HIGHDPI) != 0;
|
BOOL highDPI = (window->flags & SDL_WINDOW_ALLOW_HIGHDPI) != 0;
|
||||||
|
BOOL opaque = (window->flags & SDL_WINDOW_TRANSPARENT) == 0;
|
||||||
Uint32 windowID = SDL_GetWindowID(window);
|
Uint32 windowID = SDL_GetWindowID(window);
|
||||||
SDL_cocoametalview *newview;
|
SDL_cocoametalview *newview;
|
||||||
SDL_MetalView metalview;
|
SDL_MetalView metalview;
|
||||||
|
|
||||||
newview = [[SDL_cocoametalview alloc] initWithFrame:view.frame
|
newview = [[SDL_cocoametalview alloc] initWithFrame:view.frame
|
||||||
highDPI:highDPI
|
highDPI:highDPI
|
||||||
windowID:windowID];
|
windowID:windowID
|
||||||
|
opaque:opaque];
|
||||||
if (newview == nil) {
|
if (newview == nil) {
|
||||||
SDL_OutOfMemory();
|
SDL_OutOfMemory();
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
|
@ -270,6 +270,7 @@ SDL_GLContext Cocoa_GL_CreateContext(_THIS, SDL_Window *window)
|
||||||
int glversion_minor;
|
int glversion_minor;
|
||||||
NSOpenGLPixelFormatAttribute profile;
|
NSOpenGLPixelFormatAttribute profile;
|
||||||
int interval;
|
int interval;
|
||||||
|
int opaque;
|
||||||
|
|
||||||
if (_this->gl_config.profile_mask == SDL_GL_CONTEXT_PROFILE_ES) {
|
if (_this->gl_config.profile_mask == SDL_GL_CONTEXT_PROFILE_ES) {
|
||||||
#if SDL_VIDEO_OPENGL_EGL
|
#if SDL_VIDEO_OPENGL_EGL
|
||||||
|
@ -381,6 +382,9 @@ SDL_GLContext Cocoa_GL_CreateContext(_THIS, SDL_Window *window)
|
||||||
interval = 0;
|
interval = 0;
|
||||||
[context setValues:&interval forParameter:NSOpenGLCPSwapInterval];
|
[context setValues:&interval forParameter:NSOpenGLCPSwapInterval];
|
||||||
|
|
||||||
|
opaque = (window->flags & SDL_WINDOW_TRANSPARENT) ? 0 : 1;
|
||||||
|
[context setValues:&opaque forParameter:NSOpenGLCPSurfaceOpacity];
|
||||||
|
|
||||||
if (Cocoa_GL_MakeCurrent(_this, window, sdlcontext) < 0) {
|
if (Cocoa_GL_MakeCurrent(_this, window, sdlcontext) < 0) {
|
||||||
SDL_GL_DeleteContext(sdlcontext);
|
SDL_GL_DeleteContext(sdlcontext);
|
||||||
SDL_SetError("Failed making OpenGL context current");
|
SDL_SetError("Failed making OpenGL context current");
|
||||||
|
|
|
@ -137,7 +137,7 @@ int Cocoa_GLES_SetupWindow(_THIS, SDL_Window *window)
|
||||||
|
|
||||||
/* Create the GLES window surface */
|
/* Create the GLES window surface */
|
||||||
v = windowdata.nswindow.contentView;
|
v = windowdata.nswindow.contentView;
|
||||||
windowdata.egl_surface = SDL_EGL_CreateSurface(_this, (__bridge NativeWindowType)[v layer]);
|
windowdata.egl_surface = SDL_EGL_CreateSurface(_this, window, (__bridge NativeWindowType)[v layer]);
|
||||||
|
|
||||||
if (windowdata.egl_surface == EGL_NO_SURFACE) {
|
if (windowdata.egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("Could not create GLES window surface");
|
return SDL_SetError("Could not create GLES window surface");
|
||||||
|
|
|
@ -1600,11 +1600,14 @@ static int Cocoa_SendMouseButtonClicks(SDL_Mouse *mouse, NSEvent *theEvent, SDL_
|
||||||
/* Force the graphics context to clear to black so we don't get a flash of
|
/* Force the graphics context to clear to black so we don't get a flash of
|
||||||
white until the app is ready to draw. In practice on modern macOS, this
|
white until the app is ready to draw. In practice on modern macOS, this
|
||||||
only gets called for window creation and other extraordinary events. */
|
only gets called for window creation and other extraordinary events. */
|
||||||
|
BOOL transparent = (_sdlWindow->flags & SDL_WINDOW_TRANSPARENT) != 0;
|
||||||
if ([NSGraphicsContext currentContext]) {
|
if ([NSGraphicsContext currentContext]) {
|
||||||
[[NSColor blackColor] setFill];
|
NSColor *fillColor = transparent ? [NSColor clearColor] : [NSColor blackColor];
|
||||||
|
[fillColor setFill];
|
||||||
NSRectFill(dirtyRect);
|
NSRectFill(dirtyRect);
|
||||||
} else if (self.layer) {
|
} else if (self.layer) {
|
||||||
self.layer.backgroundColor = CGColorGetConstantColor(kCGColorBlack);
|
CFStringRef color = transparent ? kCGColorClear : kCGColorBlack;
|
||||||
|
self.layer.backgroundColor = CGColorGetConstantColor(color);
|
||||||
}
|
}
|
||||||
|
|
||||||
SDL_SendWindowEvent(_sdlWindow, SDL_EVENT_WINDOW_EXPOSED, 0, 0);
|
SDL_SendWindowEvent(_sdlWindow, SDL_EVENT_WINDOW_EXPOSED, 0, 0);
|
||||||
|
@ -1621,7 +1624,9 @@ static int Cocoa_SendMouseButtonClicks(SDL_Mouse *mouse, NSEvent *theEvent, SDL_
|
||||||
/* Force the graphics context to clear to black so we don't get a flash of
|
/* Force the graphics context to clear to black so we don't get a flash of
|
||||||
white until the app is ready to draw. In practice on modern macOS, this
|
white until the app is ready to draw. In practice on modern macOS, this
|
||||||
only gets called for window creation and other extraordinary events. */
|
only gets called for window creation and other extraordinary events. */
|
||||||
self.layer.backgroundColor = CGColorGetConstantColor(kCGColorBlack);
|
BOOL transparent = (_sdlWindow->flags & SDL_WINDOW_TRANSPARENT) != 0;
|
||||||
|
CFStringRef color = transparent ? kCGColorClear : kCGColorBlack;
|
||||||
|
self.layer.backgroundColor = CGColorGetConstantColor(color);
|
||||||
ScheduleContextUpdates((__bridge SDL_CocoaWindowData *)_sdlWindow->driverdata);
|
ScheduleContextUpdates((__bridge SDL_CocoaWindowData *)_sdlWindow->driverdata);
|
||||||
SDL_SendWindowEvent(_sdlWindow, SDL_EVENT_WINDOW_EXPOSED, 0, 0);
|
SDL_SendWindowEvent(_sdlWindow, SDL_EVENT_WINDOW_EXPOSED, 0, 0);
|
||||||
}
|
}
|
||||||
|
@ -1744,6 +1749,12 @@ static int SetupWindowData(_THIS, SDL_Window *window, NSWindow *nswindow, NSView
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (nswindow.isOpaque) {
|
||||||
|
window->flags &= ~SDL_WINDOW_TRANSPARENT;
|
||||||
|
} else {
|
||||||
|
window->flags |= SDL_WINDOW_TRANSPARENT;
|
||||||
|
}
|
||||||
|
|
||||||
/* SDL_CocoaWindowData will be holding a strong reference to the NSWindow, and
|
/* SDL_CocoaWindowData will be holding a strong reference to the NSWindow, and
|
||||||
* it will also call [NSWindow close] in DestroyWindow before releasing the
|
* it will also call [NSWindow close] in DestroyWindow before releasing the
|
||||||
* NSWindow, so the extra release provided by releasedWhenClosed isn't
|
* NSWindow, so the extra release provided by releasedWhenClosed isn't
|
||||||
|
@ -1841,6 +1852,12 @@ int Cocoa_CreateWindow(_THIS, SDL_Window *window)
|
||||||
[nswindow setLevel:NSFloatingWindowLevel];
|
[nswindow setLevel:NSFloatingWindowLevel];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (window->flags & SDL_WINDOW_TRANSPARENT) {
|
||||||
|
nswindow.opaque = NO;
|
||||||
|
nswindow.hasShadow = NO;
|
||||||
|
nswindow.backgroundColor = [NSColor clearColor];
|
||||||
|
}
|
||||||
|
|
||||||
/* Create a default view for this window */
|
/* Create a default view for this window */
|
||||||
rect = [nswindow contentRectForFrameRect:[nswindow frame]];
|
rect = [nswindow contentRectForFrameRect:[nswindow frame]];
|
||||||
contentView = [[SDLView alloc] initWithFrame:rect];
|
contentView = [[SDLView alloc] initWithFrame:rect];
|
||||||
|
|
|
@ -1198,7 +1198,7 @@ int KMSDRM_CreateSurfaces(_THIS, SDL_Window *window)
|
||||||
but we need an EGL surface NOW, or GL won't be able to render into any surface
|
but we need an EGL surface NOW, or GL won't be able to render into any surface
|
||||||
and we won't see the first frame. */
|
and we won't see the first frame. */
|
||||||
SDL_EGL_SetRequiredVisualId(_this, surface_fmt);
|
SDL_EGL_SetRequiredVisualId(_this, surface_fmt);
|
||||||
windata->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)windata->gs);
|
windata->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)windata->gs);
|
||||||
|
|
||||||
if (windata->egl_surface == EGL_NO_SURFACE) {
|
if (windata->egl_surface == EGL_NO_SURFACE) {
|
||||||
ret = SDL_SetError("Could not create EGL window surface");
|
ret = SDL_SetError("Could not create EGL window surface");
|
||||||
|
|
|
@ -287,7 +287,7 @@ int RPI_CreateWindow(_THIS, SDL_Window *window)
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
wdata->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)&wdata->dispman_window);
|
wdata->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)&wdata->dispman_window);
|
||||||
|
|
||||||
if (wdata->egl_surface == EGL_NO_SURFACE) {
|
if (wdata->egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("Could not create GLES window surface");
|
return SDL_SetError("Could not create GLES window surface");
|
||||||
|
|
|
@ -275,7 +275,7 @@ int VITA_CreateWindow(_THIS, SDL_Window *window)
|
||||||
_this->gl_config.minor_version = 1;
|
_this->gl_config.minor_version = 1;
|
||||||
_this->gl_config.profile_mask = SDL_GL_CONTEXT_PROFILE_ES;
|
_this->gl_config.profile_mask = SDL_GL_CONTEXT_PROFILE_ES;
|
||||||
}
|
}
|
||||||
wdata->egl_surface = SDL_EGL_CreateSurface(_this, &win);
|
wdata->egl_surface = SDL_EGL_CreateSurface(_this, window, &win);
|
||||||
if (wdata->egl_surface == EGL_NO_SURFACE) {
|
if (wdata->egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("Could not create GLES window surface");
|
return SDL_SetError("Could not create GLES window surface");
|
||||||
}
|
}
|
||||||
|
|
|
@ -267,7 +267,7 @@ int VIVANTE_CreateWindow(_THIS, SDL_Window *window)
|
||||||
|
|
||||||
#if SDL_VIDEO_OPENGL_EGL
|
#if SDL_VIDEO_OPENGL_EGL
|
||||||
if (window->flags & SDL_WINDOW_OPENGL) {
|
if (window->flags & SDL_WINDOW_OPENGL) {
|
||||||
data->egl_surface = SDL_EGL_CreateSurface(_this, data->native_window);
|
data->egl_surface = SDL_EGL_CreateSurface(_this, window, data->native_window);
|
||||||
if (data->egl_surface == EGL_NO_SURFACE) {
|
if (data->egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("VIVANTE: Can't create EGL surface");
|
return SDL_SetError("VIVANTE: Can't create EGL surface");
|
||||||
}
|
}
|
||||||
|
|
|
@ -948,7 +948,6 @@ int Wayland_VideoInit(_THIS)
|
||||||
WAYLAND_wl_display_flush(data->display);
|
WAYLAND_wl_display_flush(data->display);
|
||||||
|
|
||||||
Wayland_InitKeyboard(_this);
|
Wayland_InitKeyboard(_this);
|
||||||
Wayland_InitWin(data);
|
|
||||||
|
|
||||||
data->initializing = SDL_FALSE;
|
data->initializing = SDL_FALSE;
|
||||||
|
|
||||||
|
@ -981,7 +980,6 @@ static void Wayland_VideoCleanup(_THIS)
|
||||||
SDL_VideoData *data = _this->driverdata;
|
SDL_VideoData *data = _this->driverdata;
|
||||||
int i, j;
|
int i, j;
|
||||||
|
|
||||||
Wayland_QuitWin(data);
|
|
||||||
Wayland_FiniMouse(data);
|
Wayland_FiniMouse(data);
|
||||||
|
|
||||||
for (i = _this->num_displays - 1; i >= 0; --i) {
|
for (i = _this->num_displays - 1; i >= 0; --i) {
|
||||||
|
|
|
@ -97,7 +97,6 @@ struct SDL_VideoData
|
||||||
char *classname;
|
char *classname;
|
||||||
|
|
||||||
int relative_mouse_mode;
|
int relative_mouse_mode;
|
||||||
SDL_bool egl_transparency_enabled;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct SDL_DisplayData
|
struct SDL_DisplayData
|
||||||
|
|
|
@ -224,7 +224,7 @@ static void ConfigureWindowGeometry(SDL_Window *window)
|
||||||
xdg_surface_set_window_geometry(data->shell_surface.xdg.surface, 0, 0, data->wl_window_width, data->wl_window_height);
|
xdg_surface_set_window_geometry(data->shell_surface.xdg.surface, 0, 0, data->wl_window_width, data->wl_window_height);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!viddata->egl_transparency_enabled) {
|
if (!(window->flags & SDL_WINDOW_TRANSPARENT)) {
|
||||||
region = wl_compositor_create_region(viddata->compositor);
|
region = wl_compositor_create_region(viddata->compositor);
|
||||||
wl_region_add(region, 0, 0,
|
wl_region_add(region, 0, 0,
|
||||||
data->wl_window_width, data->wl_window_height);
|
data->wl_window_width, data->wl_window_height);
|
||||||
|
@ -2010,12 +2010,18 @@ int Wayland_CreateWindow(_THIS, SDL_Window *window)
|
||||||
}
|
}
|
||||||
#endif /* SDL_VIDEO_DRIVER_WAYLAND_QT_TOUCH */
|
#endif /* SDL_VIDEO_DRIVER_WAYLAND_QT_TOUCH */
|
||||||
|
|
||||||
|
if (window->flags & SDL_WINDOW_TRANSPARENT) {
|
||||||
|
if (_this->gl_config.alpha_size == 0) {
|
||||||
|
_this->gl_config.alpha_size = 8;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (window->flags & SDL_WINDOW_OPENGL) {
|
if (window->flags & SDL_WINDOW_OPENGL) {
|
||||||
data->egl_window = WAYLAND_wl_egl_window_create(data->surface, data->drawable_width, data->drawable_height);
|
data->egl_window = WAYLAND_wl_egl_window_create(data->surface, data->drawable_width, data->drawable_height);
|
||||||
|
|
||||||
#if SDL_VIDEO_OPENGL_EGL
|
#if SDL_VIDEO_OPENGL_EGL
|
||||||
/* Create the GLES window surface */
|
/* Create the GLES window surface */
|
||||||
data->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)data->egl_window);
|
data->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)data->egl_window);
|
||||||
|
|
||||||
if (data->egl_surface == EGL_NO_SURFACE) {
|
if (data->egl_surface == EGL_NO_SURFACE) {
|
||||||
return -1; /* SDL_EGL_CreateSurface should have set error */
|
return -1; /* SDL_EGL_CreateSurface should have set error */
|
||||||
|
@ -2247,43 +2253,4 @@ void Wayland_DestroyWindow(_THIS, SDL_Window *window)
|
||||||
window->driverdata = NULL;
|
window->driverdata = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void EGLTransparencyChangedCallback(void *userdata, const char *name, const char *oldValue, const char *newValue)
|
|
||||||
{
|
|
||||||
const SDL_bool oldval = SDL_GetStringBoolean(oldValue, SDL_FALSE);
|
|
||||||
const SDL_bool newval = SDL_GetStringBoolean(newValue, SDL_FALSE);
|
|
||||||
|
|
||||||
if (oldval != newval) {
|
|
||||||
SDL_Window *window;
|
|
||||||
SDL_VideoData *viddata = (SDL_VideoData *)userdata;
|
|
||||||
SDL_VideoDevice *dev = SDL_GetVideoDevice();
|
|
||||||
|
|
||||||
viddata->egl_transparency_enabled = newval;
|
|
||||||
|
|
||||||
/* Iterate over all windows and update the surface opaque regions */
|
|
||||||
for (window = dev->windows; window != NULL; window = window->next) {
|
|
||||||
SDL_WindowData *wind = window->driverdata;
|
|
||||||
|
|
||||||
if (!newval) {
|
|
||||||
struct wl_region *region = wl_compositor_create_region(wind->waylandData->compositor);
|
|
||||||
wl_region_add(region, 0, 0, wind->wl_window_width, wind->wl_window_height);
|
|
||||||
wl_surface_set_opaque_region(wind->surface, region);
|
|
||||||
wl_region_destroy(region);
|
|
||||||
} else {
|
|
||||||
wl_surface_set_opaque_region(wind->surface, NULL);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Wayland_InitWin(SDL_VideoData *data)
|
|
||||||
{
|
|
||||||
data->egl_transparency_enabled = SDL_GetHintBoolean(SDL_HINT_VIDEO_EGL_ALLOW_TRANSPARENCY, SDL_FALSE);
|
|
||||||
SDL_AddHintCallback(SDL_HINT_VIDEO_EGL_ALLOW_TRANSPARENCY, EGLTransparencyChangedCallback, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
void Wayland_QuitWin(SDL_VideoData *data)
|
|
||||||
{
|
|
||||||
SDL_DelHintCallback(SDL_HINT_VIDEO_EGL_ALLOW_TRANSPARENCY, EGLTransparencyChangedCallback, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif /* SDL_VIDEO_DRIVER_WAYLAND */
|
#endif /* SDL_VIDEO_DRIVER_WAYLAND */
|
||||||
|
|
|
@ -155,7 +155,4 @@ extern int Wayland_GetWindowWMInfo(_THIS, SDL_Window *window, SDL_SysWMinfo *inf
|
||||||
extern int Wayland_SetWindowHitTest(SDL_Window *window, SDL_bool enabled);
|
extern int Wayland_SetWindowHitTest(SDL_Window *window, SDL_bool enabled);
|
||||||
extern int Wayland_FlashWindow(_THIS, SDL_Window *window, SDL_FlashOperation operation);
|
extern int Wayland_FlashWindow(_THIS, SDL_Window *window, SDL_FlashOperation operation);
|
||||||
|
|
||||||
extern void Wayland_InitWin(SDL_VideoData *data);
|
|
||||||
extern void Wayland_QuitWin(SDL_VideoData *data);
|
|
||||||
|
|
||||||
#endif /* SDL_waylandwindow_h_ */
|
#endif /* SDL_waylandwindow_h_ */
|
||||||
|
|
|
@ -125,7 +125,7 @@ int WIN_GLES_SetupWindow(_THIS, SDL_Window *window)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Create the GLES window surface */
|
/* Create the GLES window surface */
|
||||||
windowdata->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)windowdata->hwnd);
|
windowdata->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)windowdata->hwnd);
|
||||||
|
|
||||||
if (windowdata->egl_surface == EGL_NO_SURFACE) {
|
if (windowdata->egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("Could not create GLES window surface");
|
return SDL_SetError("Could not create GLES window surface");
|
||||||
|
|
|
@ -345,7 +345,7 @@ static void X11_GL_InitExtensions(_THIS)
|
||||||
const char *(*glXQueryExtensionsStringFunc)(Display *, int);
|
const char *(*glXQueryExtensionsStringFunc)(Display *, int);
|
||||||
const char *extensions;
|
const char *extensions;
|
||||||
|
|
||||||
vinfo = X11_GL_GetVisual(_this, display, screen);
|
vinfo = X11_GL_GetVisual(_this, display, screen, SDL_FALSE);
|
||||||
if (vinfo) {
|
if (vinfo) {
|
||||||
GLXContext (*glXGetCurrentContextFunc)(void) =
|
GLXContext (*glXGetCurrentContextFunc)(void) =
|
||||||
(GLXContext(*)(void))
|
(GLXContext(*)(void))
|
||||||
|
@ -484,7 +484,7 @@ static void X11_GL_InitExtensions(_THIS)
|
||||||
* In case of failure, if that pointer is not NULL, set that pointer to None
|
* In case of failure, if that pointer is not NULL, set that pointer to None
|
||||||
* and try again.
|
* and try again.
|
||||||
*/
|
*/
|
||||||
static int X11_GL_GetAttributes(_THIS, Display *display, int screen, int *attribs, int size, Bool for_FBConfig, int **_pvistypeattr)
|
static int X11_GL_GetAttributes(_THIS, Display *display, int screen, int *attribs, int size, Bool for_FBConfig, int **_pvistypeattr, SDL_bool transparent)
|
||||||
{
|
{
|
||||||
int i = 0;
|
int i = 0;
|
||||||
const int MAX_ATTRIBUTES = 64;
|
const int MAX_ATTRIBUTES = 64;
|
||||||
|
@ -583,14 +583,16 @@ static int X11_GL_GetAttributes(_THIS, Display *display, int screen, int *attrib
|
||||||
attribs[i++] = _this->gl_config.accelerated ? GLX_NONE_EXT : GLX_SLOW_VISUAL_EXT;
|
attribs[i++] = _this->gl_config.accelerated ? GLX_NONE_EXT : GLX_SLOW_VISUAL_EXT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Un-wanted when we request a transparent buffer */
|
||||||
|
if (!transparent) {
|
||||||
/* If we're supposed to use DirectColor visuals, and we've got the
|
/* If we're supposed to use DirectColor visuals, and we've got the
|
||||||
EXT_visual_info extension, then add GLX_X_VISUAL_TYPE_EXT. */
|
EXT_visual_info extension, then add GLX_X_VISUAL_TYPE_EXT. */
|
||||||
if (X11_UseDirectColorVisuals() &&
|
if (X11_UseDirectColorVisuals() && _this->gl_data->HAS_GLX_EXT_visual_info) {
|
||||||
_this->gl_data->HAS_GLX_EXT_visual_info) {
|
|
||||||
pvistypeattr = &attribs[i];
|
pvistypeattr = &attribs[i];
|
||||||
attribs[i++] = GLX_X_VISUAL_TYPE_EXT;
|
attribs[i++] = GLX_X_VISUAL_TYPE_EXT;
|
||||||
attribs[i++] = GLX_DIRECT_COLOR_EXT;
|
attribs[i++] = GLX_DIRECT_COLOR_EXT;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
attribs[i++] = None;
|
attribs[i++] = None;
|
||||||
|
|
||||||
|
@ -603,7 +605,7 @@ static int X11_GL_GetAttributes(_THIS, Display *display, int screen, int *attrib
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen)
|
XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen, SDL_bool transparent)
|
||||||
{
|
{
|
||||||
/* 64 seems nice. */
|
/* 64 seems nice. */
|
||||||
int attribs[64];
|
int attribs[64];
|
||||||
|
@ -620,13 +622,30 @@ XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen)
|
||||||
GLXFBConfig *framebuffer_config = NULL;
|
GLXFBConfig *framebuffer_config = NULL;
|
||||||
int fbcount = 0;
|
int fbcount = 0;
|
||||||
|
|
||||||
X11_GL_GetAttributes(_this, display, screen, attribs, 64, SDL_TRUE, &pvistypeattr);
|
X11_GL_GetAttributes(_this, display, screen, attribs, 64, SDL_TRUE, &pvistypeattr, transparent);
|
||||||
framebuffer_config = _this->gl_data->glXChooseFBConfig(display, screen, attribs, &fbcount);
|
framebuffer_config = _this->gl_data->glXChooseFBConfig(display, screen, attribs, &fbcount);
|
||||||
if (!framebuffer_config && (pvistypeattr != NULL)) {
|
if (!framebuffer_config && (pvistypeattr != NULL)) {
|
||||||
*pvistypeattr = None;
|
*pvistypeattr = None;
|
||||||
framebuffer_config = _this->gl_data->glXChooseFBConfig(display, screen, attribs, &fbcount);
|
framebuffer_config = _this->gl_data->glXChooseFBConfig(display, screen, attribs, &fbcount);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (transparent) {
|
||||||
|
/* Return the first transparent Visual */
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < fbcount; i++) {
|
||||||
|
Uint32 format;
|
||||||
|
vinfo = _this->gl_data->glXGetVisualFromFBConfig(display, framebuffer_config[i]);
|
||||||
|
format = X11_GetPixelFormatFromVisualInfo(display, vinfo);
|
||||||
|
if (SDL_ISPIXELFORMAT_ALPHA(format)) { /* found! */
|
||||||
|
X11_XFree(framebuffer_config);
|
||||||
|
framebuffer_config = NULL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
X11_XFree(vinfo);
|
||||||
|
vinfo = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (framebuffer_config) {
|
if (framebuffer_config) {
|
||||||
vinfo = _this->gl_data->glXGetVisualFromFBConfig(display, framebuffer_config[0]);
|
vinfo = _this->gl_data->glXGetVisualFromFBConfig(display, framebuffer_config[0]);
|
||||||
}
|
}
|
||||||
|
@ -635,7 +654,7 @@ XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!vinfo) {
|
if (!vinfo) {
|
||||||
X11_GL_GetAttributes(_this, display, screen, attribs, 64, SDL_FALSE, &pvistypeattr);
|
X11_GL_GetAttributes(_this, display, screen, attribs, 64, SDL_FALSE, &pvistypeattr, transparent);
|
||||||
vinfo = _this->gl_data->glXChooseVisual(display, screen, attribs);
|
vinfo = _this->gl_data->glXChooseVisual(display, screen, attribs);
|
||||||
|
|
||||||
if (!vinfo && (pvistypeattr != NULL)) {
|
if (!vinfo && (pvistypeattr != NULL)) {
|
||||||
|
@ -696,6 +715,7 @@ SDL_GLContext X11_GL_CreateContext(_THIS, SDL_Window *window)
|
||||||
XVisualInfo v, *vinfo;
|
XVisualInfo v, *vinfo;
|
||||||
int n;
|
int n;
|
||||||
GLXContext context = NULL, share_context;
|
GLXContext context = NULL, share_context;
|
||||||
|
const int transparent = (window->flags & SDL_WINDOW_TRANSPARENT) ? SDL_TRUE : SDL_FALSE;
|
||||||
|
|
||||||
if (_this->gl_config.share_with_current_context) {
|
if (_this->gl_config.share_with_current_context) {
|
||||||
share_context = (GLXContext)SDL_GL_GetCurrentContext();
|
share_context = (GLXContext)SDL_GL_GetCurrentContext();
|
||||||
|
@ -716,7 +736,7 @@ SDL_GLContext X11_GL_CreateContext(_THIS, SDL_Window *window)
|
||||||
if (vinfo) {
|
if (vinfo) {
|
||||||
if (_this->gl_config.major_version < 3 &&
|
if (_this->gl_config.major_version < 3 &&
|
||||||
_this->gl_config.profile_mask == 0 &&
|
_this->gl_config.profile_mask == 0 &&
|
||||||
_this->gl_config.flags == 0) {
|
_this->gl_config.flags == 0 && !transparent) {
|
||||||
/* Create legacy context */
|
/* Create legacy context */
|
||||||
context =
|
context =
|
||||||
_this->gl_data->glXCreateContext(display, vinfo, share_context, True);
|
_this->gl_data->glXCreateContext(display, vinfo, share_context, True);
|
||||||
|
@ -776,7 +796,7 @@ SDL_GLContext X11_GL_CreateContext(_THIS, SDL_Window *window)
|
||||||
int fbcount = 0;
|
int fbcount = 0;
|
||||||
int *pvistypeattr = NULL;
|
int *pvistypeattr = NULL;
|
||||||
|
|
||||||
X11_GL_GetAttributes(_this, display, screen, glxAttribs, 64, SDL_TRUE, &pvistypeattr);
|
X11_GL_GetAttributes(_this, display, screen, glxAttribs, 64, SDL_TRUE, &pvistypeattr, transparent);
|
||||||
|
|
||||||
if (_this->gl_data->glXChooseFBConfig) {
|
if (_this->gl_data->glXChooseFBConfig) {
|
||||||
framebuffer_config = _this->gl_data->glXChooseFBConfig(display,
|
framebuffer_config = _this->gl_data->glXChooseFBConfig(display,
|
||||||
|
|
|
@ -72,7 +72,7 @@ extern int X11_GL_LoadLibrary(_THIS, const char *path);
|
||||||
extern SDL_FunctionPointer X11_GL_GetProcAddress(_THIS, const char *proc);
|
extern SDL_FunctionPointer X11_GL_GetProcAddress(_THIS, const char *proc);
|
||||||
extern void X11_GL_UnloadLibrary(_THIS);
|
extern void X11_GL_UnloadLibrary(_THIS);
|
||||||
extern SDL_bool X11_GL_UseEGL(_THIS);
|
extern SDL_bool X11_GL_UseEGL(_THIS);
|
||||||
extern XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen);
|
extern XVisualInfo *X11_GL_GetVisual(_THIS, Display *display, int screen, SDL_bool transparent);
|
||||||
extern SDL_GLContext X11_GL_CreateContext(_THIS, SDL_Window *window);
|
extern SDL_GLContext X11_GL_CreateContext(_THIS, SDL_Window *window);
|
||||||
extern int X11_GL_MakeCurrent(_THIS, SDL_Window *window,
|
extern int X11_GL_MakeCurrent(_THIS, SDL_Window *window,
|
||||||
SDL_GLContext context);
|
SDL_GLContext context);
|
||||||
|
|
|
@ -56,7 +56,7 @@ int X11_GLES_LoadLibrary(_THIS, const char *path)
|
||||||
}
|
}
|
||||||
|
|
||||||
XVisualInfo *
|
XVisualInfo *
|
||||||
X11_GLES_GetVisual(_THIS, Display *display, int screen)
|
X11_GLES_GetVisual(_THIS, Display *display, int screen, SDL_bool transparent)
|
||||||
{
|
{
|
||||||
|
|
||||||
XVisualInfo *egl_visualinfo = NULL;
|
XVisualInfo *egl_visualinfo = NULL;
|
||||||
|
@ -79,6 +79,23 @@ X11_GLES_GetVisual(_THIS, Display *display, int screen)
|
||||||
egl_visualinfo = X11_XGetVisualInfo(display,
|
egl_visualinfo = X11_XGetVisualInfo(display,
|
||||||
VisualScreenMask,
|
VisualScreenMask,
|
||||||
&vi_in, &out_count);
|
&vi_in, &out_count);
|
||||||
|
|
||||||
|
/* Return the first transparent Visual */
|
||||||
|
if (transparent) {
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < out_count; i++) {
|
||||||
|
XVisualInfo *v = &egl_visualinfo[i];
|
||||||
|
Uint32 format = X11_GetPixelFormatFromVisualInfo(display, v);
|
||||||
|
if (SDL_ISPIXELFORMAT_ALPHA(format)) { /* found! */
|
||||||
|
/* re-request it to have a copy that can be X11_XFree'ed later */
|
||||||
|
vi_in.screen = screen;
|
||||||
|
vi_in.visualid = v->visualid;
|
||||||
|
X11_XFree(egl_visualinfo);
|
||||||
|
egl_visualinfo = X11_XGetVisualInfo(display, VisualScreenMask | VisualIDMask, &vi_in, &out_count);
|
||||||
|
return egl_visualinfo;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
vi_in.screen = screen;
|
vi_in.screen = screen;
|
||||||
vi_in.visualid = visual_id;
|
vi_in.visualid = visual_id;
|
||||||
|
|
|
@ -44,7 +44,7 @@ typedef struct SDL_PrivateGLESData
|
||||||
#define X11_GLES_DeleteContext SDL_EGL_DeleteContext
|
#define X11_GLES_DeleteContext SDL_EGL_DeleteContext
|
||||||
|
|
||||||
extern int X11_GLES_LoadLibrary(_THIS, const char *path);
|
extern int X11_GLES_LoadLibrary(_THIS, const char *path);
|
||||||
extern XVisualInfo *X11_GLES_GetVisual(_THIS, Display *display, int screen);
|
extern XVisualInfo *X11_GLES_GetVisual(_THIS, Display *display, int screen, SDL_bool transparent);
|
||||||
extern SDL_GLContext X11_GLES_CreateContext(_THIS, SDL_Window *window);
|
extern SDL_GLContext X11_GLES_CreateContext(_THIS, SDL_Window *window);
|
||||||
extern int X11_GLES_SwapWindow(_THIS, SDL_Window *window);
|
extern int X11_GLES_SwapWindow(_THIS, SDL_Window *window);
|
||||||
extern int X11_GLES_MakeCurrent(_THIS, SDL_Window *window, SDL_GLContext context);
|
extern int X11_GLES_MakeCurrent(_THIS, SDL_Window *window, SDL_GLContext context);
|
||||||
|
|
|
@ -431,6 +431,7 @@ int X11_CreateWindow(_THIS, SDL_Window *window)
|
||||||
SDL_WindowData *windowdata;
|
SDL_WindowData *windowdata;
|
||||||
Display *display = data->display;
|
Display *display = data->display;
|
||||||
int screen = displaydata->screen;
|
int screen = displaydata->screen;
|
||||||
|
const int transparent = (window->flags & SDL_WINDOW_TRANSPARENT) ? SDL_TRUE : SDL_FALSE;
|
||||||
Visual *visual;
|
Visual *visual;
|
||||||
int depth;
|
int depth;
|
||||||
XSetWindowAttributes xattr;
|
XSetWindowAttributes xattr;
|
||||||
|
@ -477,12 +478,12 @@ int X11_CreateWindow(_THIS, SDL_Window *window)
|
||||||
&& (!_this->gl_data || X11_GL_UseEGL(_this))
|
&& (!_this->gl_data || X11_GL_UseEGL(_this))
|
||||||
#endif
|
#endif
|
||||||
) {
|
) {
|
||||||
vinfo = X11_GLES_GetVisual(_this, display, screen);
|
vinfo = X11_GLES_GetVisual(_this, display, screen, transparent);
|
||||||
} else
|
} else
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
#if SDL_VIDEO_OPENGL_GLX
|
#if SDL_VIDEO_OPENGL_GLX
|
||||||
vinfo = X11_GL_GetVisual(_this, display, screen);
|
vinfo = X11_GL_GetVisual(_this, display, screen, transparent);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -720,7 +721,7 @@ int X11_CreateWindow(_THIS, SDL_Window *window)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Create the GLES window surface */
|
/* Create the GLES window surface */
|
||||||
windowdata->egl_surface = SDL_EGL_CreateSurface(_this, (NativeWindowType)w);
|
windowdata->egl_surface = SDL_EGL_CreateSurface(_this, window, (NativeWindowType)w);
|
||||||
|
|
||||||
if (windowdata->egl_surface == EGL_NO_SURFACE) {
|
if (windowdata->egl_surface == EGL_NO_SURFACE) {
|
||||||
return SDL_SetError("Could not create GLES window surface");
|
return SDL_SetError("Could not create GLES window surface");
|
||||||
|
|
|
@ -92,7 +92,7 @@ static void Render(void)
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Do our drawing, too. */
|
/* Do our drawing, too. */
|
||||||
ctx.glClearColor(0.0, 0.0, 0.0, 1.0);
|
ctx.glClearColor(0.0, 0.0, 0.0, 0.0 /* used with --transparent */);
|
||||||
ctx.glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
ctx.glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||||
|
|
||||||
ctx.glBegin(GL_QUADS);
|
ctx.glBegin(GL_QUADS);
|
||||||
|
|
|
@ -126,7 +126,7 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Draw a gray background */
|
/* Draw a gray background */
|
||||||
SDL_SetRenderDrawColor(renderer, 0xA0, 0xA0, 0xA0, 0xFF);
|
SDL_SetRenderDrawColor(renderer, 0xA0, 0xA0, 0xA0, 0x00 /* used with --transparent */);
|
||||||
SDL_RenderClear(renderer);
|
SDL_RenderClear(renderer);
|
||||||
|
|
||||||
/* Test points */
|
/* Test points */
|
||||||
|
|
|
@ -624,6 +624,7 @@ static SDL_bool createSwapchain(void)
|
||||||
int w, h;
|
int w, h;
|
||||||
VkSwapchainCreateInfoKHR createInfo = { 0 };
|
VkSwapchainCreateInfoKHR createInfo = { 0 };
|
||||||
VkResult result;
|
VkResult result;
|
||||||
|
Uint32 flags;
|
||||||
|
|
||||||
// pick an image count
|
// pick an image count
|
||||||
vulkanContext->swapchainDesiredImageCount = vulkanContext->surfaceCapabilities.minImageCount + 1;
|
vulkanContext->swapchainDesiredImageCount = vulkanContext->surfaceCapabilities.minImageCount + 1;
|
||||||
|
@ -651,6 +652,9 @@ static SDL_bool createSwapchain(void)
|
||||||
// get size
|
// get size
|
||||||
SDL_GetWindowSizeInPixels(vulkanContext->window, &w, &h);
|
SDL_GetWindowSizeInPixels(vulkanContext->window, &w, &h);
|
||||||
|
|
||||||
|
// get flags
|
||||||
|
flags = SDL_GetWindowFlags(vulkanContext->window);
|
||||||
|
|
||||||
// Clamp the size to the allowable image extent.
|
// Clamp the size to the allowable image extent.
|
||||||
// SDL_GetWindowSizeInPixels()'s result it not always in this range (bug #3287)
|
// SDL_GetWindowSizeInPixels()'s result it not always in this range (bug #3287)
|
||||||
vulkanContext->swapchainSize.width = SDL_clamp((uint32_t)w,
|
vulkanContext->swapchainSize.width = SDL_clamp((uint32_t)w,
|
||||||
|
@ -677,7 +681,11 @@ static SDL_bool createSwapchain(void)
|
||||||
createInfo.imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
|
createInfo.imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
|
||||||
createInfo.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE;
|
createInfo.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE;
|
||||||
createInfo.preTransform = vulkanContext->surfaceCapabilities.currentTransform;
|
createInfo.preTransform = vulkanContext->surfaceCapabilities.currentTransform;
|
||||||
|
if (flags & SDL_WINDOW_TRANSPARENT) {
|
||||||
|
createInfo.compositeAlpha = VK_COMPOSITE_ALPHA_PRE_MULTIPLIED_BIT_KHR;
|
||||||
|
} else {
|
||||||
createInfo.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR;
|
createInfo.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR;
|
||||||
|
}
|
||||||
createInfo.presentMode = VK_PRESENT_MODE_FIFO_KHR;
|
createInfo.presentMode = VK_PRESENT_MODE_FIFO_KHR;
|
||||||
createInfo.clipped = VK_TRUE;
|
createInfo.clipped = VK_TRUE;
|
||||||
createInfo.oldSwapchain = vulkanContext->swapchain;
|
createInfo.oldSwapchain = vulkanContext->swapchain;
|
||||||
|
@ -1037,7 +1045,7 @@ static SDL_bool render(void)
|
||||||
clearColor.float32[0] = (float)(0.5 + 0.5 * SDL_sin(currentTime));
|
clearColor.float32[0] = (float)(0.5 + 0.5 * SDL_sin(currentTime));
|
||||||
clearColor.float32[1] = (float)(0.5 + 0.5 * SDL_sin(currentTime + SDL_PI_D * 2 / 3));
|
clearColor.float32[1] = (float)(0.5 + 0.5 * SDL_sin(currentTime + SDL_PI_D * 2 / 3));
|
||||||
clearColor.float32[2] = (float)(0.5 + 0.5 * SDL_sin(currentTime + SDL_PI_D * 4 / 3));
|
clearColor.float32[2] = (float)(0.5 + 0.5 * SDL_sin(currentTime + SDL_PI_D * 4 / 3));
|
||||||
clearColor.float32[3] = 1;
|
clearColor.float32[3] = 0.5; // for SDL_WINDOW_TRANSPARENT, ignored with VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR
|
||||||
rerecordCommandBuffer(frameIndex, &clearColor);
|
rerecordCommandBuffer(frameIndex, &clearColor);
|
||||||
submitInfo.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
|
submitInfo.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
|
||||||
submitInfo.waitSemaphoreCount = 1;
|
submitInfo.waitSemaphoreCount = 1;
|
||||||
|
|
Loading…
Reference in New Issue