From e7d805a88ca71a0e6499fe72830e58fe594ef05b Mon Sep 17 00:00:00 2001 From: Michael R Sweet Date: Tue, 6 Oct 1998 18:46:47 +0000 Subject: Commited Gustavo Hime's NT patches/fixes. git-svn-id: file:///fltk/svn/fltk/trunk@7 ea41ed52-d2ee-0310-a9c1-e6b18d33e121 --- src/Fl_Double_Window.cxx | 320 ++++++++++++++++++++++++----------------------- 1 file changed, 163 insertions(+), 157 deletions(-) (limited to 'src/Fl_Double_Window.cxx') diff --git a/src/Fl_Double_Window.cxx b/src/Fl_Double_Window.cxx index aa285a5d2..864ba1019 100644 --- a/src/Fl_Double_Window.cxx +++ b/src/Fl_Double_Window.cxx @@ -1,157 +1,163 @@ -// Fl_Double_Window.C - -// A double-buffered window. This is achieved by using the Xdbe extension, -// or a pixmap if that is not available. - -// On systems that support double buffering "naturally" the base -// Fl_Window class will probably do double-buffer and this subclass -// does nothing. - -#include -#include -#include -#include -#include - -#if USE_XDBE - -#include - -static int use_xdbe; - -static int can_xdbe() { - static int tried; - if (!tried) { - tried = 1; - int event_base, error_base; - if (!XdbeQueryExtension(fl_display, &event_base, &error_base)) return 0; - Drawable root = RootWindow(fl_display,fl_screen); - int numscreens = 1; - XdbeScreenVisualInfo *a = XdbeGetVisualInfo(fl_display,&root,&numscreens); - if (!a) return 0; - for (int j = 0; j < a->count; j++) - if (a->visinfo[j].visual == fl_visual->visualid - /*&& a->visinfo[j].perflevel > 0*/) {use_xdbe = 1; break;} - XdbeFreeVisualInfo(a); - } - return use_xdbe; -} -#endif - -void Fl_Double_Window::show() { -#ifndef WIN32 - if (!shown()) { // don't set the background pixel - fl_open_display(); - Fl_X::make_xid(this); - return; - } -#endif - Fl_Window::show(); -} - -#ifdef WIN32 - -// Code to switch output to an off-screen window: -// this is lame, I allow two to exist... - -static HDC blt_gc[2]; - -void fl_switch_offscreen(HBITMAP bitmap) { - if (!blt_gc[0]) for (int i = 0; i < 2; i++) { - blt_gc[i] = CreateCompatibleDC(fl_gc); - SetTextAlign(blt_gc[i], TA_BASELINE|TA_LEFT); - SetBkMode(blt_gc[i], TRANSPARENT); -#if USE_COLORMAP - if (fl_palette) SelectPalette(blt_gc[i], fl_palette, FALSE); -#endif - } - int which = 0; if (fl_gc == blt_gc[0]) which = 1; - SelectObject(blt_gc[which], bitmap); - fl_gc = blt_gc[which]; -} - -void fl_copy_offscreen(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) { - int which = 0; if (fl_gc == blt_gc[0]) which = 1; - SelectObject(blt_gc[which], bitmap); - BitBlt(fl_gc, x, y, w, h, blt_gc[which], srcx, srcy, SRCCOPY); -} - -#endif - -// protected method used by Fl_Overlay_Window to fake overlay: -void Fl_Double_Window::_flush(int eraseoverlay) { - make_current(); // make sure fl_gc is non-zero - Fl_X *i = Fl_X::i(this); - if (!i->other_xid) { -#if USE_XDBE - if (can_xdbe()) i->other_xid = - XdbeAllocateBackBufferName(fl_display, fl_xid(this), XdbeCopied); - else -#endif - i->other_xid = fl_create_offscreen(w(), h()); - clear_damage(~0); - } - XRectangle rect = {0,0,w(),h()}; - if (damage()) { - if (i->region && !eraseoverlay) XClipBox(i->region, &rect); - if ( // don't draw if back buffer is ok -#if USE_XDBE - use_xdbe || -#endif - damage() != 2) { -#ifdef WIN32 - fl_begin_offscreen(i->other_xid); - fl_clip_region(i->region); i->region = 0; - draw(); - fl_end_offscreen(); -#else - fl_window = i->other_xid; - fl_clip_region(i->region); i->region = 0; - draw(); - fl_window = i->xid; -#endif - } - } - fl_clip_region(0); -#if USE_XDBE - if (use_xdbe) { - XdbeSwapInfo s; - s.swap_window = fl_xid(this); - s.swap_action = XdbeCopied; - XdbeSwapBuffers(fl_display,&s,1); - } else -#endif - fl_copy_offscreen(rect.x, rect.y, rect.width, rect.height, - i->other_xid, rect.x, rect.y); -} - -void Fl_Double_Window::flush() {_flush(0);} - -void Fl_Double_Window::resize(int X,int Y,int W,int H) { - int ow = w(); - int oh = h(); - Fl_Window::resize(X,Y,W,H); -#if USE_XDBE - if (use_xdbe) return; -#endif - Fl_X* i = Fl_X::i(this); - if (i && i->other_xid && (ow != w() || oh != h())) { - fl_delete_offscreen(i->other_xid); - i->other_xid = 0; - } -} - -void Fl_Double_Window::hide() { - Fl_X* i = Fl_X::i(this); - if (i && i->other_xid) { -#if USE_XDBE - if (!use_xdbe) -#endif - fl_delete_offscreen(i->other_xid); - } - Fl_Window::hide(); -} - -Fl_Double_Window::~Fl_Double_Window() { - hide(); -} +// Fl_Double_Window.C + +// A double-buffered window. This is achieved by using the Xdbe extension, +// or a pixmap if that is not available. + +// On systems that support double buffering "naturally" the base +// Fl_Window class will probably do double-buffer and this subclass +// does nothing. + +#include +#include +#include +#include +#include + +#if USE_XDBE + +#include + +static int use_xdbe; + +static int can_xdbe() { + static int tried; + if (!tried) { + tried = 1; + int event_base, error_base; + if (!XdbeQueryExtension(fl_display, &event_base, &error_base)) return 0; + Drawable root = RootWindow(fl_display,fl_screen); + int numscreens = 1; + XdbeScreenVisualInfo *a = XdbeGetVisualInfo(fl_display,&root,&numscreens); + if (!a) return 0; + for (int j = 0; j < a->count; j++) + if (a->visinfo[j].visual == fl_visual->visualid + /*&& a->visinfo[j].perflevel > 0*/) {use_xdbe = 1; break;} + XdbeFreeVisualInfo(a); + } + return use_xdbe; +} +#endif + +void Fl_Double_Window::show() { +#ifndef WIN32 + if (!shown()) { // don't set the background pixel + fl_open_display(); + Fl_X::make_xid(this); + return; + } +#endif + Fl_Window::show(); +} + +#ifdef WIN32 + +// I've removed the second one (never understool why +// it was there to begin with). + +static HDC blt_gc; + +void fl_switch_offscreen(HBITMAP bitmap) { + if (!blt_gc) { + blt_gc = CreateCompatibleDC(fl_gc); + SetTextAlign(blt_gc, TA_BASELINE|TA_LEFT); + SetBkMode(blt_gc, TRANSPARENT); +#if USE_COLORMAP + if (fl_palette) SelectPalette(blt_gc, fl_palette, FALSE); +#endif + } + SelectObject(blt_gc, bitmap); + fl_gc = blt_gc; +} + +void fl_copy_offscreen(int x,int y,int w,int h,HBITMAP bitmap,int srcx,int srcy) { + SelectObject(blt_gc, bitmap); + BitBlt(window_dc, x, y, w, h, blt_gc, srcx, srcy, SRCCOPY); +} + +#endif + +// protected method used by Fl_Overlay_Window to fake overlay: +void Fl_Double_Window::_flush(int eraseoverlay) { + make_current(); // make sure fl_gc is non-zero + Fl_X *i = Fl_X::i(this); + if (!i->other_xid) { +#if USE_XDBE + if (can_xdbe()) i->other_xid = + XdbeAllocateBackBufferName(fl_display, fl_xid(this), XdbeCopied); + else +#endif + i->other_xid = fl_create_offscreen(w(), h()); + clear_damage(~0); + } + XRectangle rect = {0,0,w(),h()}; + if (damage()) { + if ( // don't draw if back buffer is ok +#if USE_XDBE + use_xdbe || +#endif + damage() != 2) { +/* +#ifdef WIN32 + fl_begin_offscreen(i->other_xid); + fl_clip_region(i->region); i->region = 0; + draw(); + fl_end_offscreen(); +#else +*/ +#ifdef WIN32 + fl_begin_offscreen(i->other_xid); +#endif + fl_window = i->other_xid; + fl_clip_region(i->region); i->region = 0; + draw(); + fl_window = i->xid; +#ifdef WIN32 + fl_end_offscreen(); +#endif +//#endif + } + } + fl_clip_region(0); +#if USE_XDBE + if (i->region && !eraseoverlay) XClipBox(i->region, &rect); + if (use_xdbe) { + XdbeSwapInfo s; + s.swap_window = fl_xid(this); + s.swap_action = XdbeCopied; + XdbeSwapBuffers(fl_display,&s,1); + } else +#endif + fl_copy_offscreen(rect.x, rect.y, rect.width, rect.height, + i->other_xid, rect.x, rect.y); +} + +void Fl_Double_Window::flush() {_flush(0);} + +void Fl_Double_Window::resize(int X,int Y,int W,int H) { + int ow = w(); + int oh = h(); + Fl_Window::resize(X,Y,W,H); +#if USE_XDBE + if (use_xdbe) return; +#endif + Fl_X* i = Fl_X::i(this); + if (i && i->other_xid && (ow != w() || oh != h())) { + fl_delete_offscreen(i->other_xid); + i->other_xid = 0; + } +} + +void Fl_Double_Window::hide() { + Fl_X* i = Fl_X::i(this); + if (i && i->other_xid) { +#if USE_XDBE + if (!use_xdbe) +#endif + fl_delete_offscreen(i->other_xid); + } + Fl_Window::hide(); +} + +Fl_Double_Window::~Fl_Double_Window() { + hide(); +} -- cgit v1.2.3