Commit fea6781d authored by Sam Lantinga's avatar Sam Lantinga

Implemented SDL_SetWindowIcon(), with translucent icon support under X11.

--HG--
extra : convert_revision : svn%3Ac70aab31-4412-0410-b14c-859654838e24/trunk%403429
parent 3c555c88
...@@ -591,13 +591,13 @@ extern DECLSPEC void SDLCALL SDL_SetWindowTitle(SDL_WindowID windowID, ...@@ -591,13 +591,13 @@ extern DECLSPEC void SDLCALL SDL_SetWindowTitle(SDL_WindowID windowID,
extern DECLSPEC const char *SDLCALL SDL_GetWindowTitle(SDL_WindowID windowID); extern DECLSPEC const char *SDLCALL SDL_GetWindowTitle(SDL_WindowID windowID);
/** /**
* \fn void SDL_SetWindowIcon(SDL_Surface *icon) * \fn void SDL_SetWindowIcon(SDL_WindowID windowID, SDL_Surface *icon)
* *
* \brief Set the icon of the window. * \brief Set the icon of the window.
* *
* \param icon The icon for the window * \param icon The icon for the window
*/ */
extern DECLSPEC void SDLCALL SDL_SetWindowIcon(SDL_Surface * icon); extern DECLSPEC void SDLCALL SDL_SetWindowIcon(SDL_WindowID windowID, SDL_Surface * icon);
/** /**
* \fn void SDL_SetWindowData(SDL_WindowID windowID, void *userdata) * \fn void SDL_SetWindowData(SDL_WindowID windowID, void *userdata)
......
...@@ -39,6 +39,7 @@ static SDL_Surface *SDL_PublicSurface = NULL; ...@@ -39,6 +39,7 @@ static SDL_Surface *SDL_PublicSurface = NULL;
static SDL_GLContext *SDL_VideoContext = NULL; static SDL_GLContext *SDL_VideoContext = NULL;
static Uint32 SDL_VideoFlags = 0; static Uint32 SDL_VideoFlags = 0;
static char *wm_title = NULL; static char *wm_title = NULL;
static SDL_Surface *SDL_VideoIcon;
char * char *
SDL_AudioDriverName(char *namebuf, int maxlen) SDL_AudioDriverName(char *namebuf, int maxlen)
...@@ -522,6 +523,7 @@ SDL_SetVideoMode(int width, int height, int bpp, Uint32 flags) ...@@ -522,6 +523,7 @@ SDL_SetVideoMode(int width, int height, int bpp, Uint32 flags)
if (!SDL_VideoWindow) { if (!SDL_VideoWindow) {
return NULL; return NULL;
} }
SDL_SetWindowIcon(SDL_VideoWindow, SDL_VideoIcon);
window_flags = SDL_GetWindowFlags(SDL_VideoWindow); window_flags = SDL_GetWindowFlags(SDL_VideoWindow);
surface_flags = 0; surface_flags = 0;
...@@ -868,7 +870,7 @@ SDL_WM_GetCaption(const char **title, const char **icon) ...@@ -868,7 +870,7 @@ SDL_WM_GetCaption(const char **title, const char **icon)
void void
SDL_WM_SetIcon(SDL_Surface * icon, Uint8 * mask) SDL_WM_SetIcon(SDL_Surface * icon, Uint8 * mask)
{ {
/* FIXME */ SDL_VideoIcon = icon;
} }
int int
......
...@@ -397,23 +397,20 @@ SDL_SaveBMP_RW(SDL_Surface * saveme, SDL_RWops * dst, int freedst) ...@@ -397,23 +397,20 @@ SDL_SaveBMP_RW(SDL_Surface * saveme, SDL_RWops * dst, int freedst)
) { ) {
surface = saveme; surface = saveme;
} else { } else {
SDL_PixelFormat *format; SDL_PixelFormat format;
/* Convert to 24 bits per pixel */ /* Convert to 24 bits per pixel */
format = SDL_AllocFormat(24, SDL_InitFormat(&format, 24,
#if SDL_BYTEORDER == SDL_LIL_ENDIAN #if SDL_BYTEORDER == SDL_LIL_ENDIAN
0x00FF0000, 0x0000FF00, 0x000000FF, 0x00FF0000, 0x0000FF00, 0x000000FF,
#else #else
0x000000FF, 0x0000FF00, 0x00FF0000, 0x000000FF, 0x0000FF00, 0x00FF0000,
#endif #endif
0); 0);
if (format != NULL) { surface = SDL_ConvertSurface(saveme, &format, 0);
surface = SDL_ConvertSurface(saveme, format, 0);
if (!surface) { if (!surface) {
SDL_SetError("Couldn't convert image to 24 bpp"); SDL_SetError("Couldn't convert image to 24 bpp");
} }
SDL_FreeFormat(format);
}
} }
} }
......
...@@ -347,16 +347,25 @@ SDL_AllocFormat(int bpp, ...@@ -347,16 +347,25 @@ SDL_AllocFormat(int bpp,
Uint32 Rmask, Uint32 Gmask, Uint32 Bmask, Uint32 Amask) Uint32 Rmask, Uint32 Gmask, Uint32 Bmask, Uint32 Amask)
{ {
SDL_PixelFormat *format; SDL_PixelFormat *format;
Uint32 mask;
/* Allocate an empty pixel format structure */ /* Allocate an empty pixel format structure */
format = SDL_calloc(1, sizeof(*format)); format = SDL_malloc(sizeof(*format));
if (format == NULL) { if (format == NULL) {
SDL_OutOfMemory(); SDL_OutOfMemory();
return (NULL); return (NULL);
} }
/* Set up the format */ /* Set up the format */
return SDL_InitFormat(format, bpp, Rmask, Gmask, Bmask, Amask);
}
SDL_PixelFormat *
SDL_InitFormat(SDL_PixelFormat *format, int bpp, Uint32 Rmask, Uint32 Gmask, Uint32 Bmask, Uint32 Amask)
{
Uint32 mask;
/* Set up the format */
SDL_zerop(format);
format->BitsPerPixel = bpp; format->BitsPerPixel = bpp;
format->BytesPerPixel = (bpp + 7) / 8; format->BytesPerPixel = (bpp + 7) / 8;
if (Rmask || Bmask || Gmask) { /* Packed pixels with custom mask */ if (Rmask || Bmask || Gmask) { /* Packed pixels with custom mask */
...@@ -426,7 +435,7 @@ SDL_AllocFormat(int bpp, ...@@ -426,7 +435,7 @@ SDL_AllocFormat(int bpp,
} }
format->palette = NULL; format->palette = NULL;
return (format); return format;
} }
/* /*
......
...@@ -29,6 +29,9 @@ ...@@ -29,6 +29,9 @@
extern SDL_PixelFormat *SDL_AllocFormat(int bpp, extern SDL_PixelFormat *SDL_AllocFormat(int bpp,
Uint32 Rmask, Uint32 Gmask, Uint32 Rmask, Uint32 Gmask,
Uint32 Bmask, Uint32 Amask); Uint32 Bmask, Uint32 Amask);
extern SDL_PixelFormat *SDL_InitFormat(SDL_PixelFormat *format, int bpp,
Uint32 Rmask, Uint32 Gmask,
Uint32 Bmask, Uint32 Amask);
extern void SDL_FormatChanged(SDL_Surface * surface); extern void SDL_FormatChanged(SDL_Surface * surface);
extern void SDL_FreeFormat(SDL_PixelFormat * format); extern void SDL_FreeFormat(SDL_PixelFormat * format);
......
...@@ -238,6 +238,7 @@ struct SDL_VideoDevice ...@@ -238,6 +238,7 @@ struct SDL_VideoDevice
int (*CreateWindow) (_THIS, SDL_Window * window); int (*CreateWindow) (_THIS, SDL_Window * window);
int (*CreateWindowFrom) (_THIS, SDL_Window * window, const void *data); int (*CreateWindowFrom) (_THIS, SDL_Window * window, const void *data);
void (*SetWindowTitle) (_THIS, SDL_Window * window); void (*SetWindowTitle) (_THIS, SDL_Window * window);
void (*SetWindowIcon) (_THIS, SDL_Window * window, SDL_Surface * icon);
void (*SetWindowPosition) (_THIS, SDL_Window * window); void (*SetWindowPosition) (_THIS, SDL_Window * window);
void (*SetWindowSize) (_THIS, SDL_Window * window); void (*SetWindowSize) (_THIS, SDL_Window * window);
void (*ShowWindow) (_THIS, SDL_Window * window); void (*ShowWindow) (_THIS, SDL_Window * window);
......
...@@ -965,6 +965,19 @@ SDL_GetWindowTitle(SDL_WindowID windowID) ...@@ -965,6 +965,19 @@ SDL_GetWindowTitle(SDL_WindowID windowID)
return window->title; return window->title;
} }
void
SDL_SetWindowIcon(SDL_WindowID windowID, SDL_Surface * icon)
{
SDL_Window *window = SDL_GetWindowFromID(windowID);
if (!window) {
return;
}
if (_this->SetWindowIcon) {
_this->SetWindowIcon(_this, window, icon);
}
}
void void
SDL_SetWindowData(SDL_WindowID windowID, void *userdata) SDL_SetWindowData(SDL_WindowID windowID, void *userdata)
{ {
...@@ -1590,33 +1603,30 @@ SDL_CreateTextureFromSurface(Uint32 format, SDL_Surface * surface) ...@@ -1590,33 +1603,30 @@ SDL_CreateTextureFromSurface(Uint32 format, SDL_Surface * surface)
surface->pitch); surface->pitch);
} }
} else { } else {
SDL_PixelFormat *dst_fmt; SDL_PixelFormat dst_fmt;
SDL_Surface *dst = NULL; SDL_Surface *dst = NULL;
/* Set up a destination surface for the texture update */ /* Set up a destination surface for the texture update */
dst_fmt = SDL_AllocFormat(bpp, Rmask, Gmask, Bmask, Amask); SDL_InitFormat(&dst_fmt, bpp, Rmask, Gmask, Bmask, Amask);
if (dst_fmt) {
if (SDL_ISPIXELFORMAT_INDEXED(format)) { if (SDL_ISPIXELFORMAT_INDEXED(format)) {
dst_fmt->palette = dst_fmt.palette =
SDL_AllocPalette((1 << SDL_BITSPERPIXEL(format))); SDL_AllocPalette((1 << SDL_BITSPERPIXEL(format)));
if (dst_fmt->palette) { if (dst_fmt.palette) {
/* /*
* FIXME: Should we try to copy * FIXME: Should we try to copy
* fmt->palette? * fmt->palette?
*/ */
SDL_DitherColors(dst_fmt->palette->colors, SDL_DitherColors(dst_fmt.palette->colors,
SDL_BITSPERPIXEL(format)); SDL_BITSPERPIXEL(format));
} }
} }
dst = SDL_ConvertSurface(surface, dst_fmt, 0); dst = SDL_ConvertSurface(surface, &dst_fmt, 0);
if (dst) { if (dst) {
SDL_UpdateTexture(textureID, NULL, dst->pixels, dst->pitch); SDL_UpdateTexture(textureID, NULL, dst->pixels, dst->pitch);
SDL_FreeSurface(dst); SDL_FreeSurface(dst);
} }
if (dst_fmt->palette) { if (dst_fmt.palette) {
SDL_FreePalette(dst_fmt->palette); SDL_FreePalette(dst_fmt.palette);
}
SDL_FreeFormat(dst_fmt);
} }
if (!dst) { if (!dst) {
SDL_DestroyTexture(textureID); SDL_DestroyTexture(textureID);
......
...@@ -87,7 +87,7 @@ typedef struct ...@@ -87,7 +87,7 @@ typedef struct
Pixmap pixmaps[3]; Pixmap pixmaps[3];
int current_pixmap; int current_pixmap;
Drawable drawable; Drawable drawable;
SDL_PixelFormat *format; SDL_PixelFormat format;
GC gc; GC gc;
SDL_DirtyRectList dirty; SDL_DirtyRectList dirty;
SDL_bool makedirty; SDL_bool makedirty;
...@@ -251,11 +251,7 @@ X11_CreateRenderer(SDL_Window * window, Uint32 flags) ...@@ -251,11 +251,7 @@ X11_CreateRenderer(SDL_Window * window, Uint32 flags)
X11_DestroyRenderer(renderer); X11_DestroyRenderer(renderer);
return NULL; return NULL;
} }
data->format = SDL_AllocFormat(bpp, Rmask, Gmask, Bmask, Amask); SDL_InitFormat(&data->format, bpp, Rmask, Gmask, Bmask, Amask);
if (!data->format) {
X11_DestroyRenderer(renderer);
return NULL;
}
/* Create the drawing context */ /* Create the drawing context */
gcv.graphics_exposures = False; gcv.graphics_exposures = False;
...@@ -583,11 +579,11 @@ renderdrawcolor(SDL_Renderer * renderer, int premult) ...@@ -583,11 +579,11 @@ renderdrawcolor(SDL_Renderer * renderer, int premult)
Uint8 b = renderer->b; Uint8 b = renderer->b;
Uint8 a = renderer->a; Uint8 a = renderer->a;
if (premult) if (premult)
return SDL_MapRGBA(data->format, ((int) r * (int) a) / 255, return SDL_MapRGBA(&data->format, ((int) r * (int) a) / 255,
((int) g * (int) a) / 255, ((int) g * (int) a) / 255,
((int) b * (int) a) / 255, 255); ((int) b * (int) a) / 255, 255);
else else
return SDL_MapRGBA(data->format, r, g, b, a); return SDL_MapRGBA(&data->format, r, g, b, a);
} }
static int static int
...@@ -852,9 +848,6 @@ X11_DestroyRenderer(SDL_Renderer * renderer) ...@@ -852,9 +848,6 @@ X11_DestroyRenderer(SDL_Renderer * renderer)
XFreePixmap(data->display, data->pixmaps[i]); XFreePixmap(data->display, data->pixmaps[i]);
} }
} }
if (data->format) {
SDL_FreeFormat(data->format);
}
if (data->gc) { if (data->gc) {
XFreeGC(data->display, data->gc); XFreeGC(data->display, data->gc);
} }
......
...@@ -174,6 +174,7 @@ X11_CreateDevice(int devindex) ...@@ -174,6 +174,7 @@ X11_CreateDevice(int devindex)
device->CreateWindow = X11_CreateWindow; device->CreateWindow = X11_CreateWindow;
device->CreateWindowFrom = X11_CreateWindowFrom; device->CreateWindowFrom = X11_CreateWindowFrom;
device->SetWindowTitle = X11_SetWindowTitle; device->SetWindowTitle = X11_SetWindowTitle;
device->SetWindowIcon = X11_SetWindowIcon;
device->SetWindowPosition = X11_SetWindowPosition; device->SetWindowPosition = X11_SetWindowPosition;
device->SetWindowSize = X11_SetWindowSize; device->SetWindowSize = X11_SetWindowSize;
device->ShowWindow = X11_ShowWindow; device->ShowWindow = X11_ShowWindow;
......
...@@ -645,6 +645,43 @@ X11_SetWindowTitle(_THIS, SDL_Window * window) ...@@ -645,6 +645,43 @@ X11_SetWindowTitle(_THIS, SDL_Window * window)
} }
} }
void
X11_SetWindowIcon(_THIS, SDL_Window * window, SDL_Surface * icon)
{
SDL_WindowData *data = (SDL_WindowData *) window->driverdata;
Display *display = data->videodata->display;
Atom _NET_WM_ICON = XInternAtom(display, "_NET_WM_ICON", False);
if (icon) {
SDL_PixelFormat format;
SDL_Surface *surface;
int propsize;
Uint32 *propdata;
/* Convert the icon to ARGB for modern window managers */
SDL_InitFormat(&format, 32, 0x00FF0000, 0x0000FF00, 0x000000FF, 0xFF000000);
surface = SDL_ConvertSurface(icon, &format, 0);
if (!surface) {
return;
}
/* Set the _NET_WM_ICON property */
propsize = 2+(icon->w*icon->h);
propdata = SDL_malloc(propsize * sizeof(Uint32));
if (propdata) {
propdata[0] = icon->w;
propdata[1] = icon->h;
SDL_memcpy(&propdata[2], surface->pixels, surface->h*surface->pitch);
XChangeProperty(display, data->window, _NET_WM_ICON,
XA_CARDINAL, 32, PropModeReplace,
(unsigned char *) propdata, propsize);
}
SDL_FreeSurface(surface);
} else {
XDeleteProperty(display, data->window, _NET_WM_ICON);
}
}
void void
X11_SetWindowPosition(_THIS, SDL_Window * window) X11_SetWindowPosition(_THIS, SDL_Window * window)
{ {
......
...@@ -36,6 +36,7 @@ typedef struct ...@@ -36,6 +36,7 @@ typedef struct
extern int X11_CreateWindow(_THIS, SDL_Window * window); extern int X11_CreateWindow(_THIS, SDL_Window * window);
extern int X11_CreateWindowFrom(_THIS, SDL_Window * window, const void *data); extern int X11_CreateWindowFrom(_THIS, SDL_Window * window, const void *data);
extern void X11_SetWindowTitle(_THIS, SDL_Window * window); extern void X11_SetWindowTitle(_THIS, SDL_Window * window);
extern void X11_SetWindowIcon(_THIS, SDL_Window * window, SDL_Surface * icon);
extern void X11_SetWindowPosition(_THIS, SDL_Window * window); extern void X11_SetWindowPosition(_THIS, SDL_Window * window);
extern void X11_SetWindowSize(_THIS, SDL_Window * window); extern void X11_SetWindowSize(_THIS, SDL_Window * window);
extern void X11_ShowWindow(_THIS, SDL_Window * window); extern void X11_ShowWindow(_THIS, SDL_Window * window);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment