summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Fl_Double_Window.cxx249
-rw-r--r--src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx86
-rw-r--r--src/drivers/GDI/Fl_GDI_Graphics_Driver.h1
-rw-r--r--src/drivers/Quartz/Fl_Quartz_Graphics_Driver.cxx112
-rw-r--r--src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h1
-rw-r--r--src/drivers/Xlib/Fl_Xlib_Graphics_Driver.cxx41
-rw-r--r--src/drivers/Xlib/Fl_Xlib_Graphics_Driver.h1
7 files changed, 243 insertions, 248 deletions
diff --git a/src/Fl_Double_Window.cxx b/src/Fl_Double_Window.cxx
index 9bdbf4406..c8e0dabcc 100644
--- a/src/Fl_Double_Window.cxx
+++ b/src/Fl_Double_Window.cxx
@@ -105,257 +105,10 @@ void Fl_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen
delete[] img;
}
-#if defined(USE_X11)
-
-#include "drivers/Xlib/Fl_Xlib_Graphics_Driver.h"
-
-#if HAVE_XRENDER
-#include <X11/extensions/Xrender.h>
-#endif
-
-void Fl_Xlib_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen pixmap, int srcx, int srcy) {
- XCopyArea(fl_display, pixmap, fl_window, fl_gc, srcx, srcy, w, h, x, y);
-}
-
-void Fl_Xlib_Graphics_Driver::copy_offscreen_with_alpha(int x, int y, int w, int h,
- Fl_Offscreen pixmap, int srcx, int srcy) {
-#if HAVE_XRENDER
- XRenderPictureAttributes srcattr;
- memset(&srcattr, 0, sizeof(XRenderPictureAttributes));
- static XRenderPictFormat *srcfmt = XRenderFindStandardFormat(fl_display, PictStandardARGB32);
- static XRenderPictFormat *dstfmt = XRenderFindStandardFormat(fl_display, PictStandardRGB24);
-
- Picture src = XRenderCreatePicture(fl_display, pixmap, srcfmt, 0, &srcattr);
- Picture dst = XRenderCreatePicture(fl_display, fl_window, dstfmt, 0, &srcattr);
-
- if (!src || !dst) {
- fprintf(stderr, "Failed to create Render pictures (%lu %lu)\n", src, dst);
- return;
- }
-
- const Fl_Region clipr = fl_clip_region();
- if (clipr)
- XRenderSetPictureClipRegion(fl_display, dst, clipr);
-
- XRenderComposite(fl_display, PictOpOver, src, None, dst, srcx, srcy, 0, 0,
- x, y, w, h);
-
- XRenderFreePicture(fl_display, src);
- XRenderFreePicture(fl_display, dst);
-#endif
-}
-
-char fl_can_do_alpha_blending() {
- return Fl_X::xrender_supported();
-}
-#elif defined(WIN32)
-
-#include "drivers/GDI/Fl_GDI_Graphics_Driver.h"
-
-// Code used to switch output to an off-screen window. See macros in
-// win32.H which save the old state in local variables.
-
-typedef struct { BYTE a; BYTE b; BYTE c; BYTE d; } FL_BLENDFUNCTION;
-typedef BOOL (WINAPI* fl_alpha_blend_func)
- (HDC,int,int,int,int,HDC,int,int,int,int,FL_BLENDFUNCTION);
-static fl_alpha_blend_func fl_alpha_blend = NULL;
-static FL_BLENDFUNCTION blendfunc = { 0, 0, 255, 1};
-
-/*
- * This function checks if the version of MSWindows that we
- * curently run on supports alpha blending for bitmap transfers
- * and finds the required function if so.
- */
-char fl_can_do_alpha_blending() {
- static char been_here = 0;
- static char can_do = 0;
- // do this test only once
- if (been_here) return can_do;
- been_here = 1;
- // load the library that implements alpha blending
- HMODULE hMod = LoadLibrary("MSIMG32.DLL");
- // give up if that doesn't exist (Win95?)
- if (!hMod) return 0;
- // now find the blending function inside that dll
- fl_alpha_blend = (fl_alpha_blend_func)GetProcAddress(hMod, "AlphaBlend");
- // give up if we can't find it (Win95)
- if (!fl_alpha_blend) return 0;
- // we have the call, but does our display support alpha blending?
- // get the desktop's device context
- HDC dc = GetDC(0L);
- if (!dc) return 0;
- // check the device capabilities flags. However GetDeviceCaps
- // does not return anything useful, so we have to do it manually:
-
- HBITMAP bm = CreateCompatibleBitmap(dc, 1, 1);
- HDC new_gc = CreateCompatibleDC(dc);
- int save = SaveDC(new_gc);
- SelectObject(new_gc, bm);
- /*COLORREF set = */ SetPixel(new_gc, 0, 0, 0x01010101);
- BOOL alpha_ok = fl_alpha_blend(dc, 0, 0, 1, 1, new_gc, 0, 0, 1, 1, blendfunc);
- RestoreDC(new_gc, save);
- DeleteDC(new_gc);
- DeleteObject(bm);
- ReleaseDC(0L, dc);
-
- if (alpha_ok) can_do = 1;
- return can_do;
-}
-
-HDC fl_makeDC(HBITMAP bitmap) {
- HDC new_gc = CreateCompatibleDC(fl_gc);
- SetTextAlign(new_gc, TA_BASELINE|TA_LEFT);
- SetBkMode(new_gc, TRANSPARENT);
-#if USE_COLORMAP
- if (fl_palette) SelectPalette(new_gc, fl_palette, FALSE);
-#endif
- SelectObject(new_gc, bitmap);
- return new_gc;
-}
-
-void Fl_GDI_Graphics_Driver::copy_offscreen(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) {
- HDC new_gc = CreateCompatibleDC(fl_gc);
- int save = SaveDC(new_gc);
- SelectObject(new_gc, bitmap);
- BitBlt(fl_gc, x, y, w, h, new_gc, srcx, srcy, SRCCOPY);
- RestoreDC(new_gc, save);
- DeleteDC(new_gc);
-}
-
-void Fl_GDI_Graphics_Driver::copy_offscreen_with_alpha(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) {
- HDC new_gc = CreateCompatibleDC(fl_gc);
- int save = SaveDC(new_gc);
- SelectObject(new_gc, bitmap);
- BOOL alpha_ok = 0;
- // first try to alpha blend
- if ( fl_can_do_alpha_blending() ) {
- alpha_ok = fl_alpha_blend(fl_gc, x, y, w, h, new_gc, srcx, srcy, w, h, blendfunc);
- }
- // if that failed (it shouldn't), still copy the bitmap over, but now alpha is 1
- if (!alpha_ok) {
- BitBlt(fl_gc, x, y, w, h, new_gc, srcx, srcy, SRCCOPY);
- }
- RestoreDC(new_gc, save);
- DeleteDC(new_gc);
-}
-
-
-#elif defined(__APPLE_QUARTZ__) || defined(FL_DOXYGEN)
-
-#include "src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h"
-
char fl_can_do_alpha_blending() {
- return 1;
-}
-
-/** \addtogroup fl_drawings
- @{
- */
-
-/**
- Creation of an offscreen graphics buffer.
- \param w,h width and height in pixels of the buffer.
- \return the created graphics buffer.
- */
-Fl_Offscreen fl_create_offscreen(int w, int h) {
- void *data = calloc(w*h,4);
- CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
- CGContextRef ctx = CGBitmapContextCreate(
- data, w, h, 8, w*4, lut, kCGImageAlphaNoneSkipLast);
- CGColorSpaceRelease(lut);
- return (Fl_Offscreen)ctx;
-}
-
-static void bmProviderRelease (void *src, const void *data, size_t size) {
- CFIndex count = CFGetRetainCount(src);
- CFRelease(src);
- if(count == 1) free((void*)data);
-}
-
-void Fl_Quartz_Graphics_Driver::copy_offscreen(int x,int y,int w,int h,Fl_Offscreen osrc,int srcx,int srcy) {
- CGContextRef src = (CGContextRef)osrc;
- void *data = CGBitmapContextGetData(src);
- int sw = CGBitmapContextGetWidth(src);
- int sh = CGBitmapContextGetHeight(src);
- CGImageAlphaInfo alpha = CGBitmapContextGetAlphaInfo(src);
- CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
- // when output goes to a Quartz printercontext, release of the bitmap must be
- // delayed after the end of the print page
- CFRetain(src);
- CGDataProviderRef src_bytes = CGDataProviderCreateWithData( src, data, sw*sh*4, bmProviderRelease);
- CGImageRef img = CGImageCreate( sw, sh, 8, 4*8, 4*sw, lut, alpha,
- src_bytes, 0L, false, kCGRenderingIntentDefault);
- // fl_push_clip();
- CGRect rect = CGRectMake(x, y, w, h);
- Fl_X::q_begin_image(rect, srcx, srcy, sw, sh);
- CGContextDrawImage(fl_gc, rect, img);
- Fl_X::q_end_image();
- CGImageRelease(img);
- CGColorSpaceRelease(lut);
- CGDataProviderRelease(src_bytes);
-}
-
-/** Deletion of an offscreen graphics buffer.
- \param ctx the buffer to be deleted.
- */
-void fl_delete_offscreen(Fl_Offscreen ctx) {
- if (!ctx) return;
- void *data = CGBitmapContextGetData((CGContextRef)ctx);
- CFIndex count = CFGetRetainCount(ctx);
- CGContextRelease((CGContextRef)ctx);
- if(count == 1) free(data);
-}
-
-const int stack_max = 16;
-static int stack_ix = 0;
-static CGContextRef stack_gc[stack_max];
-static Window stack_window[stack_max];
-static Fl_Surface_Device *_ss;
-
-/** Send all subsequent drawing commands to this offscreen buffer.
- \param ctx the offscreen buffer.
- */
-void fl_begin_offscreen(Fl_Offscreen ctx) {
- _ss = Fl_Surface_Device::surface();
- Fl_Display_Device::display_device()->set_current();
- if (stack_ix<stack_max) {
- stack_gc[stack_ix] = fl_gc;
- stack_window[stack_ix] = fl_window;
- } else
- fprintf(stderr, "FLTK CGContext Stack overflow error\n");
- stack_ix++;
-
- fl_gc = (CGContextRef)ctx;
- fl_window = 0;
- CGContextSaveGState(fl_gc);
- fl_push_no_clip();
-}
-
-/** Quit sending drawing commands to the current offscreen buffer.
- */
-void fl_end_offscreen() {
- fl_pop_clip();
- CGContextRestoreGState(fl_gc); // matches CGContextSaveGState in fl_begin_offscreen()
- CGContextFlush(fl_gc);
- if (stack_ix>0)
- stack_ix--;
- else
- fprintf(stderr, "FLTK CGContext Stack underflow error\n");
- if (stack_ix<stack_max) {
- fl_gc = stack_gc[stack_ix];
- fl_window = stack_window[stack_ix];
- }
- _ss->set_current();
+ return Fl_Display_Device::display_device()->driver()->can_do_alpha_blending();
}
-/** @} */
-
-#elif defined(FL_PORTING)
-# pragma message "FL_PORTING: implement offscreen render space generation and management"
-#else
-# error unsupported platform
-#endif
-
/**
Forces the window to be redrawn.
*/
diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx
index 6e782b2b5..0eaf23752 100644
--- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx
+++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx
@@ -36,6 +36,92 @@ Fl_Graphics_Driver *Fl_Graphics_Driver::newMainGraphicsDriver()
return new Fl_GDI_Graphics_Driver();
}
+// Code used to switch output to an off-screen window. See macros in
+// win32.H which save the old state in local variables.
+
+typedef struct { BYTE a; BYTE b; BYTE c; BYTE d; } FL_BLENDFUNCTION;
+typedef BOOL (WINAPI* fl_alpha_blend_func)
+(HDC,int,int,int,int,HDC,int,int,int,int,FL_BLENDFUNCTION);
+static fl_alpha_blend_func fl_alpha_blend = NULL;
+static FL_BLENDFUNCTION blendfunc = { 0, 0, 255, 1};
+
+/*
+ * This function checks if the version of MSWindows that we
+ * curently run on supports alpha blending for bitmap transfers
+ * and finds the required function if so.
+ */
+char Fl_GDI_Graphics_Driver::can_do_alpha_blending() {
+ static char been_here = 0;
+ static char can_do = 0;
+ // do this test only once
+ if (been_here) return can_do;
+ been_here = 1;
+ // load the library that implements alpha blending
+ HMODULE hMod = LoadLibrary("MSIMG32.DLL");
+ // give up if that doesn't exist (Win95?)
+ if (!hMod) return 0;
+ // now find the blending function inside that dll
+ fl_alpha_blend = (fl_alpha_blend_func)GetProcAddress(hMod, "AlphaBlend");
+ // give up if we can't find it (Win95)
+ if (!fl_alpha_blend) return 0;
+ // we have the call, but does our display support alpha blending?
+ // get the desktop's device context
+ HDC dc = GetDC(0L);
+ if (!dc) return 0;
+ // check the device capabilities flags. However GetDeviceCaps
+ // does not return anything useful, so we have to do it manually:
+
+ HBITMAP bm = CreateCompatibleBitmap(dc, 1, 1);
+ HDC new_gc = CreateCompatibleDC(dc);
+ int save = SaveDC(new_gc);
+ SelectObject(new_gc, bm);
+ /*COLORREF set = */ SetPixel(new_gc, 0, 0, 0x01010101);
+ BOOL alpha_ok = fl_alpha_blend(dc, 0, 0, 1, 1, new_gc, 0, 0, 1, 1, blendfunc);
+ RestoreDC(new_gc, save);
+ DeleteDC(new_gc);
+ DeleteObject(bm);
+ ReleaseDC(0L, dc);
+
+ if (alpha_ok) can_do = 1;
+ return can_do;
+}
+
+HDC fl_makeDC(HBITMAP bitmap) {
+ HDC new_gc = CreateCompatibleDC(fl_gc);
+ SetTextAlign(new_gc, TA_BASELINE|TA_LEFT);
+ SetBkMode(new_gc, TRANSPARENT);
+#if USE_COLORMAP
+ if (fl_palette) SelectPalette(new_gc, fl_palette, FALSE);
+#endif
+ SelectObject(new_gc, bitmap);
+ return new_gc;
+}
+
+void Fl_GDI_Graphics_Driver::copy_offscreen(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) {
+ HDC new_gc = CreateCompatibleDC(fl_gc);
+ int save = SaveDC(new_gc);
+ SelectObject(new_gc, bitmap);
+ BitBlt(fl_gc, x, y, w, h, new_gc, srcx, srcy, SRCCOPY);
+ RestoreDC(new_gc, save);
+ DeleteDC(new_gc);
+}
+
+void Fl_GDI_Graphics_Driver::copy_offscreen_with_alpha(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) {
+ HDC new_gc = CreateCompatibleDC(fl_gc);
+ int save = SaveDC(new_gc);
+ SelectObject(new_gc, bitmap);
+ BOOL alpha_ok = 0;
+ // first try to alpha blend
+ if ( fl_can_do_alpha_blending() ) {
+ alpha_ok = fl_alpha_blend(fl_gc, x, y, w, h, new_gc, srcx, srcy, w, h, blendfunc);
+ }
+ // if that failed (it shouldn't), still copy the bitmap over, but now alpha is 1
+ if (!alpha_ok) {
+ BitBlt(fl_gc, x, y, w, h, new_gc, srcx, srcy, SRCCOPY);
+ }
+ RestoreDC(new_gc, save);
+ DeleteDC(new_gc);
+}
//
// End of "$Id$".
diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.h b/src/drivers/GDI/Fl_GDI_Graphics_Driver.h
index 1dd62a4e6..2dbdbe430 100644
--- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.h
+++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.h
@@ -41,6 +41,7 @@ public:
static const char *class_id;
const char *class_name() {return class_id;};
virtual int has_feature(driver_feature mask) { return mask & NATIVE; }
+ char can_do_alpha_blending();
// --- bitmap stuff
Fl_Bitmask create_bitmask(int w, int h, const uchar *array);
diff --git a/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.cxx b/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.cxx
index f2d68eaa1..a8ed4185e 100644
--- a/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.cxx
+++ b/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.cxx
@@ -42,6 +42,118 @@ Fl_Offscreen Fl_Quartz_Graphics_Driver::create_offscreen_with_alpha(int w, int h
return (Fl_Offscreen)ctx;
}
+char Fl_Quartz_Graphics_Driver::can_do_alpha_blending() {
+ return 1;
+}
+
+static void bmProviderRelease (void *src, const void *data, size_t size) {
+ CFIndex count = CFGetRetainCount(src);
+ CFRelease(src);
+ if(count == 1) free((void*)data);
+}
+
+void Fl_Quartz_Graphics_Driver::copy_offscreen(int x,int y,int w,int h,Fl_Offscreen osrc,int srcx,int srcy) {
+ CGContextRef src = (CGContextRef)osrc;
+ void *data = CGBitmapContextGetData(src);
+ int sw = CGBitmapContextGetWidth(src);
+ int sh = CGBitmapContextGetHeight(src);
+ CGImageAlphaInfo alpha = CGBitmapContextGetAlphaInfo(src);
+ CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
+ // when output goes to a Quartz printercontext, release of the bitmap must be
+ // delayed after the end of the print page
+ CFRetain(src);
+ CGDataProviderRef src_bytes = CGDataProviderCreateWithData( src, data, sw*sh*4, bmProviderRelease);
+ CGImageRef img = CGImageCreate( sw, sh, 8, 4*8, 4*sw, lut, alpha,
+ src_bytes, 0L, false, kCGRenderingIntentDefault);
+ // fl_push_clip();
+ CGRect rect = CGRectMake(x, y, w, h);
+ Fl_X::q_begin_image(rect, srcx, srcy, sw, sh);
+ CGContextDrawImage(fl_gc, rect, img);
+ Fl_X::q_end_image();
+ CGImageRelease(img);
+ CGColorSpaceRelease(lut);
+ CGDataProviderRelease(src_bytes);
+}
+
+/** \addtogroup fl_drawings
+ @{
+ */
+
+// FIXME: driver system
+/**
+ Creation of an offscreen graphics buffer.
+ \param w,h width and height in pixels of the buffer.
+ \return the created graphics buffer.
+ */
+Fl_Offscreen fl_create_offscreen(int w, int h) {
+ void *data = calloc(w*h,4);
+ CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
+ CGContextRef ctx = CGBitmapContextCreate(
+ data, w, h, 8, w*4, lut, kCGImageAlphaNoneSkipLast);
+ CGColorSpaceRelease(lut);
+ return (Fl_Offscreen)ctx;
+}
+
+// FIXME: driver system
+/** Deletion of an offscreen graphics buffer.
+ \param ctx the buffer to be deleted.
+ */
+void fl_delete_offscreen(Fl_Offscreen ctx) {
+ if (!ctx) return;
+ void *data = CGBitmapContextGetData((CGContextRef)ctx);
+ CFIndex count = CFGetRetainCount(ctx);
+ CGContextRelease((CGContextRef)ctx);
+ if(count == 1) free(data);
+}
+
+// FIXME: driver system
+const int stack_max = 16;
+static int stack_ix = 0;
+static CGContextRef stack_gc[stack_max];
+static Window stack_window[stack_max];
+static Fl_Surface_Device *_ss;
+
+// FIXME: driver system
+/** Send all subsequent drawing commands to this offscreen buffer.
+ \param ctx the offscreen buffer.
+ */
+void fl_begin_offscreen(Fl_Offscreen ctx) {
+ _ss = Fl_Surface_Device::surface();
+ Fl_Display_Device::display_device()->set_current();
+ if (stack_ix<stack_max) {
+ stack_gc[stack_ix] = fl_gc;
+ stack_window[stack_ix] = fl_window;
+ } else
+ fprintf(stderr, "FLTK CGContext Stack overflow error\n");
+ stack_ix++;
+
+ fl_gc = (CGContextRef)ctx;
+ fl_window = 0;
+ CGContextSaveGState(fl_gc);
+ fl_graphics_driver->push_no_clip();
+}
+
+// FIXME: driver system
+/** Quit sending drawing commands to the current offscreen buffer.
+ */
+void fl_end_offscreen() {
+ fl_graphics_driver->pop_clip();
+ CGContextRestoreGState(fl_gc); // matches CGContextSaveGState in fl_begin_offscreen()
+ CGContextFlush(fl_gc);
+ if (stack_ix>0)
+ stack_ix--;
+ else
+ fprintf(stderr, "FLTK CGContext Stack underflow error\n");
+ if (stack_ix<stack_max) {
+ fl_gc = stack_gc[stack_ix];
+ fl_window = stack_window[stack_ix];
+ }
+ _ss->set_current();
+}
+
+/** @} */
+
+
//
// End of "$Id$".
diff --git a/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h b/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h
index 04d214504..5d2c0ccb0 100644
--- a/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h
+++ b/src/drivers/Quartz/Fl_Quartz_Graphics_Driver.h
@@ -43,6 +43,7 @@ public:
static const char *class_id;
const char *class_name() {return class_id;};
virtual int has_feature(driver_feature mask) { return mask & NATIVE; }
+ char can_do_alpha_blending();
// --- bitmap stuff
Fl_Bitmask create_bitmask(int w, int h, const uchar *array);
diff --git a/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.cxx b/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.cxx
index 0385413f1..cdcfd4548 100644
--- a/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.cxx
+++ b/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.cxx
@@ -21,6 +21,10 @@
#include "../../config_lib.h"
#include "Fl_Xlib_Graphics_Driver.h"
+#if HAVE_XRENDER
+#include <X11/extensions/Xrender.h>
+#endif
+
const char *Fl_Xlib_Graphics_Driver::class_id = "Fl_Xlib_Graphics_Driver";
@@ -34,6 +38,43 @@ Fl_Graphics_Driver *Fl_Graphics_Driver::newMainGraphicsDriver()
return new Fl_Xlib_Graphics_Driver();
}
+char Fl_Xlib_Graphics_Driver::can_do_alpha_blending() {
+ return Fl_X::xrender_supported();
+}
+
+
+void Fl_Xlib_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen pixmap, int srcx, int srcy) {
+ XCopyArea(fl_display, pixmap, fl_window, fl_gc, srcx, srcy, w, h, x, y);
+}
+
+void Fl_Xlib_Graphics_Driver::copy_offscreen_with_alpha(int x, int y, int w, int h,
+ Fl_Offscreen pixmap, int srcx, int srcy) {
+#if HAVE_XRENDER
+ XRenderPictureAttributes srcattr;
+ memset(&srcattr, 0, sizeof(XRenderPictureAttributes));
+ static XRenderPictFormat *srcfmt = XRenderFindStandardFormat(fl_display, PictStandardARGB32);
+ static XRenderPictFormat *dstfmt = XRenderFindStandardFormat(fl_display, PictStandardRGB24);
+
+ Picture src = XRenderCreatePicture(fl_display, pixmap, srcfmt, 0, &srcattr);
+ Picture dst = XRenderCreatePicture(fl_display, fl_window, dstfmt, 0, &srcattr);
+
+ if (!src || !dst) {
+ fprintf(stderr, "Failed to create Render pictures (%lu %lu)\n", src, dst);
+ return;
+ }
+
+ const Fl_Region clipr = fl_clip_region();
+ if (clipr)
+ XRenderSetPictureClipRegion(fl_display, dst, clipr);
+
+ XRenderComposite(fl_display, PictOpOver, src, None, dst, srcx, srcy, 0, 0,
+ x, y, w, h);
+
+ XRenderFreePicture(fl_display, src);
+ XRenderFreePicture(fl_display, dst);
+#endif
+}
+
//
// End of "$Id$".
//
diff --git a/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.h b/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.h
index 577f5f573..8cd086a2a 100644
--- a/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.h
+++ b/src/drivers/Xlib/Fl_Xlib_Graphics_Driver.h
@@ -37,6 +37,7 @@ public:
static const char *class_id;
const char *class_name() {return class_id;};
virtual int has_feature(driver_feature mask) { return mask & NATIVE; }
+ char can_do_alpha_blending();
// --- bitmap stuff
Fl_Bitmask create_bitmask(int w, int h, const uchar *array);