Moved the Fl_Window::decorated_*() functions teh Window_Driver

git-svn-id: file:///fltk/svn/fltk/branches/branch-1.3-porting@11356 ea41ed52-d2ee-0310-a9c1-e6b18d33e121
This commit is contained in:
Matthias Melcher 2016-03-12 22:24:20 +00:00
parent 4643f3e98c
commit e6631a0f7f
17 changed files with 208 additions and 226 deletions

View File

@ -37,36 +37,50 @@ class Fl_RGB_Image;
/**
\brief A base class for platform specific window handling code.
*/
class FL_EXPORT Fl_Window_Driver {
class FL_EXPORT Fl_Window_Driver
{
friend class Fl_Window;
friend class Fl_X;
protected:
Fl_Window *pWindow;
struct icon_data;
icon_data *icon_;
struct shape_data_type;
shape_data_type *shape_data_; ///< non-null means the window has a non-rectangular shape
public:
Fl_Window_Driver(Fl_Window *);
virtual ~Fl_Window_Driver();
static Fl_Window_Driver *newWindowDriver(Fl_Window *);
virtual Fl_X *makeWindow() { /* FIXME: move Fl_X::make(Fl_Window*) here for OSX, MSWin, and X11 */ return 0; }
virtual void flush() { /* FIXME: move Fl_X::flush() here for OSX, MSWin, and X11 */ }
// --- window data
virtual int decorated_w() = 0;
virtual int decorated_h() = 0;
virtual void take_focus() { }
virtual int double_flush(int eraseoverlay);
virtual void destroy_double_buffer();
virtual void draw();
void shape_pixmap_(Fl_Image* pixmap);
virtual void shape(const Fl_Image* img) {}
virtual void shape_alpha_(Fl_Image* img, int offset) {}
virtual void icons(const Fl_RGB_Image *icons[], int count) {}
virtual const void *icon() const {return NULL;}
virtual void icon(const void * ic) {}
virtual void free_icons() {}
virtual void capture_titlebar_and_borders(Fl_Shared_Image*& top, Fl_Shared_Image*& left, Fl_Shared_Image*& bottom, Fl_Shared_Image*& right);
virtual void wait_for_expose() {}
// --- window management
virtual void take_focus();
virtual void flush() { }
virtual Fl_X *makeWindow() { /* FIXME: move Fl_X::make(Fl_Window*) here for OSX, MSWin, and X11 */ return 0; }
virtual void wait_for_expose() {} // TODO: check
virtual int double_flush(int eraseoverlay); // TODO: check
virtual void destroy_double_buffer(); // TODO: check
virtual void draw(); // TODO: check
// --- window shape stuff
void shape_pixmap_(Fl_Image* pixmap); // TODO: check
virtual void shape(const Fl_Image* img) {} // TODO: check
virtual void shape_alpha_(Fl_Image* img, int offset) {} // TODO: check
// --- window icon stuff
virtual void icons(const Fl_RGB_Image *icons[], int count) {} // TODO: check
virtual const void *icon() const {return NULL;} // TODO: check
virtual void icon(const void * ic) {} // TODO: check
virtual void free_icons() {} // TODO: check
// --- window printing helper
virtual void capture_titlebar_and_borders(Fl_Shared_Image*& top, Fl_Shared_Image*& left, Fl_Shared_Image*& bottom, Fl_Shared_Image*& right); // TODO: check
};

View File

@ -428,6 +428,19 @@ void Fl_Window::wait_for_expose() {
pWindowDriver->wait_for_expose();
}
int Fl_Window::decorated_w()
{
return pWindowDriver->decorated_w();
}
int Fl_Window::decorated_h()
{
return pWindowDriver->decorated_h();
}
//
// End of "$Id$".
//

View File

@ -36,6 +36,18 @@ Fl_Window_Driver::~Fl_Window_Driver()
{
}
/*
Used in Fl::focus(Fl_Window).
Default implementation does not need to do anything.
- reimplemented for OS X Cocoa
- reimplemented for X11
*/
void Fl_Window_Driver::take_focus()
{
}
int Fl_Window_Driver::double_flush(int eraseoverlay) {
/* This is a working, platform-independent implementation.
Some platforms may re-implement it for their own logic:

View File

@ -4289,20 +4289,22 @@ Window fl_xid(const Fl_Window* w)
return temp ? temp->xid : 0;
}
int Fl_Window::decorated_w()
int Fl_Cocoa_Window_Driver::decorated_w()
{
if (!shown() || parent() || !border() || !visible()) return w();
if (!pWindow->shown() || pWindow->parent() || !pWindow->border() || !pWindow->visible())
return pWindow->w();
int bx, by, bt;
get_window_frame_sizes(bx, by, bt);
return w() + 2 * bx;
return pWindow->w() + 2 * bx;
}
int Fl_Window::decorated_h()
int Fl_Cocoa_Window_Driver::decorated_h()
{
if (!shown() || parent() || !border() || !visible()) return h();
if (!pWindow->shown() || pWindow->parent() || !pWindow->border() || !pWindow->visible())
return pWindow->h();
int bx, by, bt;
get_window_frame_sizes(bx, by, bt);
return h() + bt + by;
return pWindow->h() + bt + by;
}
// clip the graphics context to rounded corners

View File

@ -349,11 +349,6 @@ void Fl::get_mouse(int &x, int &y)
x = 0; y = 0;
}
void Fl_X::flush()
{
# pragma message "FL_PORTING: implement Fl_X::flush"
}
#endif // FL_DOXYGEN
//

View File

@ -2512,46 +2512,6 @@ FL_EXPORT Window fl_xid_(const Fl_Window *w) {
return temp ? temp->xid : 0;
}
static RECT border_width_title_bar_height(Fl_Window *win, int &bx, int &by, int &bt)
{
RECT r = {0,0,0,0};
bx = by = bt = 0;
if (win->shown() && !win->parent() && win->border() && win->visible()) {
static HMODULE dwmapi_dll = LoadLibrary("dwmapi.dll");
typedef HRESULT (WINAPI* DwmGetWindowAttribute_type)(HWND hwnd, DWORD dwAttribute, PVOID pvAttribute, DWORD cbAttribute);
static DwmGetWindowAttribute_type DwmGetWindowAttribute = dwmapi_dll ?
(DwmGetWindowAttribute_type)GetProcAddress(dwmapi_dll, "DwmGetWindowAttribute") : NULL;
int need_r = 1;
if (DwmGetWindowAttribute) {
const DWORD DWMWA_EXTENDED_FRAME_BOUNDS = 9;
if ( DwmGetWindowAttribute(fl_xid(win), DWMWA_EXTENDED_FRAME_BOUNDS, &r, sizeof(RECT)) == S_OK ) {
need_r = 0;
}
}
if (need_r) {
GetWindowRect(fl_xid(win), &r);
}
bx = (r.right - r.left - win->w())/2;
by = bx;
bt = r.bottom - r.top - win->h() - 2*by;
}
return r;
}
int Fl_Window::decorated_w()
{
int bt, bx, by;
border_width_title_bar_height(this, bx, by, bt);
return w() + 2 * bx;
}
int Fl_Window::decorated_h()
{
int bt, bx, by;
border_width_title_bar_height(this, bx, by, bt);
return h() + bt + 2 * by;
}
/* Returns images of the captures of the window title-bar, and the left, bottom and right window borders.
On the WIN32 platform, this function exploits a feature of fl_read_image() which, when called
with NULL first argument and when fl_gc is set to the screen device context, captures the window decoration.
@ -2562,7 +2522,7 @@ void Fl_WinAPI_Window_Driver::capture_titlebar_and_borders(Fl_Shared_Image*& top
top = left = bottom = right = NULL;
if (!pWindow->shown() || pWindow->parent() || !pWindow->border() || !pWindow->visible()) return;
int wsides, hbottom, bt;
RECT r = border_width_title_bar_height(pWindow, wsides, hbottom, bt);
RECT r = border_width_title_bar_height(wsides, hbottom, bt);
int htop = bt + hbottom;
Fl_Surface_Device *previous = Fl_Surface_Device::surface();
Window save_win = fl_window;

View File

@ -2951,38 +2951,6 @@ FL_EXPORT Window fl_xid_(const Fl_Window *w) {
return temp ? temp->xid : 0;
}
static void decorated_win_size(Fl_Window *win, int &w, int &h)
{
w = win->w();
h = win->h();
if (!win->shown() || win->parent() || !win->border() || !win->visible()) return;
Window root, parent, *children;
unsigned n = 0;
Status status = XQueryTree(fl_display, Fl_X::i(win)->xid, &root, &parent, &children, &n);
if (status != 0 && n) XFree(children);
// when compiz is used, root and parent are the same window
// and I don't know where to find the window decoration
if (status == 0 || root == parent) return;
XWindowAttributes attributes;
XGetWindowAttributes(fl_display, parent, &attributes);
w = attributes.width;
h = attributes.height;
}
int Fl_Window::decorated_h()
{
int w, h;
decorated_win_size(this, w, h);
return h;
}
int Fl_Window::decorated_w()
{
int w, h;
decorated_win_size(this, w, h);
return w;
}
#ifdef USE_PRINT_BUTTON
// to test the Fl_Printer class creating a "Print front window" button in a separate window
// contains also preparePrintFront call above

View File

@ -60,6 +60,11 @@ private:
public:
Fl_Cocoa_Window_Driver(Fl_Window*);
~Fl_Cocoa_Window_Driver();
// --- window data
virtual int decorated_w();
virtual int decorated_h();
virtual void take_focus();
virtual void shape(const Fl_Image* img);
virtual void draw();

View File

@ -21,6 +21,7 @@
#include "Fl_Pico_Screen_Driver.H"
Fl_Pico_Screen_Driver::Fl_Pico_Screen_Driver()
{
}

View File

@ -33,6 +33,10 @@ class FL_EXPORT Fl_Pico_Window_Driver : public Fl_Window_Driver
public:
Fl_Pico_Window_Driver(Fl_Window *win);
virtual ~Fl_Pico_Window_Driver();
// --- window data
virtual int decorated_w();
virtual int decorated_h();
};

View File

@ -20,6 +20,18 @@
#include "../../config_lib.h"
#include "Fl_Pico_Window_Driver.H"
#include <FL/x.H>
#include <FL/Fl_Window.H>
// TODO: move this to Fl_Window_Driver
void Fl_X::flush()
{
w->driver()->flush();
}
Fl_Pico_Window_Driver::Fl_Pico_Window_Driver(Fl_Window *win)
: Fl_Window_Driver(win)
@ -32,6 +44,20 @@ Fl_Pico_Window_Driver::~Fl_Pico_Window_Driver()
}
// --- window data
int Fl_Pico_Window_Driver::decorated_w()
{
return pWindow->w();
}
int Fl_Pico_Window_Driver::decorated_h()
{
return pWindow->h();
}
//
// End of "$Id: Fl_Pico_Window_Driver.cxx 11253 2016-03-01 00:54:21Z matt $".
//

View File

@ -561,11 +561,6 @@ int Fl_X::set_cursor(Fl_Cursor) { return 0; }
int Fl_X::set_cursor(Fl_RGB_Image const*, int, int) { return 0; }
void Fl_X::set_default_icons(Fl_RGB_Image const**, int) { }
void Fl_X::flush()
{
w->driver()->flush();
}
void Fl_X::set_icons() { }
void Fl_Window::size_range_() { }
void Fl_Window::fullscreen_x() { }
@ -615,16 +610,6 @@ void Fl::remove_fd(int)
{
}
int Fl_Window::decorated_h()
{
return h();
}
int Fl_Window::decorated_w()
{
return w();
}
// these pointers are set by the Fl::lock() function:
static void nothing() {}
void (*fl_lock_function)() = nothing;

View File

@ -43,61 +43,6 @@ Fl_PicoSDL_Screen_Driver::~Fl_PicoSDL_Screen_Driver()
}
#if 0
if (AInputEvent_getType(event) == AINPUT_EVENT_TYPE_MOTION) {
// fl_lock_function();
int x = AMotionEvent_getX(event, 0);
int y = AMotionEvent_getY(event, 0);
int action = AKeyEvent_getAction(event);
Fl_Window *window = Fl::first_window();
switch (action) {
case AMOTION_EVENT_ACTION_DOWN:
Fl::e_is_click = 1;
Fl::e_x = Fl::e_x_root = x/3;
Fl::e_y = (y-100)/3;
if (!window) break;
Fl::e_keysym = FL_Button+FL_LEFT_MOUSE;
Fl::e_state = FL_BUTTON1;
Fl::handle(FL_PUSH, window);
break;
case AMOTION_EVENT_ACTION_MOVE:
Fl::e_is_click = 1;
Fl::e_x = Fl::e_x_root = x/3;
Fl::e_y = (y-100)/3;
if (!window) break;
Fl::e_keysym = FL_Button+FL_LEFT_MOUSE;
Fl::e_state = FL_BUTTON1;
Fl::handle(FL_DRAG, window);
break;
case AMOTION_EVENT_ACTION_UP:
case AMOTION_EVENT_ACTION_CANCEL:
Fl::e_is_click = 1;
Fl::e_x = Fl::e_x_root = x/3;
Fl::e_y = (y-100)/3;
if (!window) break;
Fl::e_keysym = FL_Button+FL_LEFT_MOUSE;
Fl::e_state = 0;
Fl::handle(FL_RELEASE, window);
break;
// case AMOTION_EVENT_ACTION_HOVER_MOVE:
// Fl::e_is_click = 1;
// Fl::e_x = Fl::e_x_root = x/3;
// Fl::e_y = (y-100)/3;
// if (!window) break;
// Fl::e_keysym = 0;
// Fl::e_state = 0;
// Fl::handle(FL_MOVE, window);
// break;
}
// AMOTION_EVENT_ACTION_MASK
LOGI("Motion at %d, %d", x, y);
// fl_unlock_function();
Fl_X::first->w->redraw();
return 1;
}
return 0;
#endif
double Fl_PicoSDL_Screen_Driver::wait(double time_to_wait)
{
Fl::flush();
@ -214,11 +159,6 @@ int Fl_X::set_cursor(Fl_Cursor) { return 0; }
int Fl_X::set_cursor(Fl_RGB_Image const*, int, int) { return 0; }
void Fl_X::set_default_icons(Fl_RGB_Image const**, int) { }
void Fl_X::flush()
{
w->driver()->flush();
}
void Fl_X::set_icons() { }
void Fl_Window::size_range_() { }
void Fl_Window::fullscreen_x() { }
@ -264,57 +204,6 @@ void Fl::remove_fd(int)
{
}
int Fl_Window::decorated_h()
{
}
int Fl_Window::decorated_w()
{
}
/*
#define __APPLE__
#include <SDL2/SDL.h>
#undef __APPLE__
SDL_Window *win = NULL;
SDL_Renderer *renderer = NULL;
SDL_Texture *bitmapTex = NULL;
SDL_Surface *bitmapSurface = NULL;
int posX = 100, posY = 100, width = 320, height = 240;
SDL_Init(SDL_INIT_VIDEO);
win = SDL_CreateWindow("Hello World", posX, posY, width, height, 0);
renderer = SDL_CreateRenderer(win, -1, SDL_RENDERER_ACCELERATED);
bitmapSurface = SDL_LoadBMP("img/hello.bmp");
bitmapTex = SDL_CreateTextureFromSurface(renderer, bitmapSurface);
SDL_FreeSurface(bitmapSurface);
while (1) {
SDL_Event e;
if (SDL_PollEvent(&e)) {
if (e.type == SDL_QUIT) {
break;
}
}
SDL_RenderClear(renderer);
SDL_RenderCopy(renderer, bitmapTex, NULL, NULL);
SDL_RenderPresent(renderer);
}
SDL_DestroyTexture(bitmapTex);
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(win);
SDL_Quit();
return 0;
*/
//
// End of "$Id: Fl_PicoSDL_Screen_Driver.cxx 11253 2016-03-01 00:54:21Z matt $".

View File

@ -61,11 +61,17 @@ struct Fl_Window_Driver::shape_data_type {
class FL_EXPORT Fl_WinAPI_Window_Driver : public Fl_Window_Driver
{
private:
RECT border_width_title_bar_height(int &bx, int &by, int &bt);
void shape_bitmap_(Fl_Image* b);
void shape_alpha_(Fl_Image* img, int offset);
public:
Fl_WinAPI_Window_Driver(Fl_Window*);
~Fl_WinAPI_Window_Driver();
// --- window data
virtual int decorated_w();
virtual int decorated_h();
virtual void shape(const Fl_Image* img);
virtual void draw();
virtual void icons(const Fl_RGB_Image *icons[], int count);

View File

@ -19,6 +19,7 @@
#include "../../config_lib.h"
#include <FL/Fl.H>
#include <FL/Fl_Window.H>
#include <FL/Fl_Image.H>
#include <FL/Fl_Bitmap.H>
#include <FL/Fl_Window.H>
@ -47,6 +48,57 @@ Fl_WinAPI_Window_Driver::~Fl_WinAPI_Window_Driver()
}
}
// --- private
RECT Fl_WinAPI_Window_Driver::border_width_title_bar_height(int &bx, int &by, int &bt)
{
Fl_Window *win = pWindow;
RECT r = {0,0,0,0};
bx = by = bt = 0;
if (win->shown() && !win->parent() && win->border() && win->visible()) {
static HMODULE dwmapi_dll = LoadLibrary("dwmapi.dll");
typedef HRESULT (WINAPI* DwmGetWindowAttribute_type)(HWND hwnd, DWORD dwAttribute, PVOID pvAttribute, DWORD cbAttribute);
static DwmGetWindowAttribute_type DwmGetWindowAttribute = dwmapi_dll ?
(DwmGetWindowAttribute_type)GetProcAddress(dwmapi_dll, "DwmGetWindowAttribute") : NULL;
int need_r = 1;
if (DwmGetWindowAttribute) {
const DWORD DWMWA_EXTENDED_FRAME_BOUNDS = 9;
if ( DwmGetWindowAttribute(fl_xid(win), DWMWA_EXTENDED_FRAME_BOUNDS, &r, sizeof(RECT)) == S_OK ) {
need_r = 0;
}
}
if (need_r) {
GetWindowRect(fl_xid(win), &r);
}
bx = (r.right - r.left - win->w())/2;
by = bx;
bt = r.bottom - r.top - win->h() - 2*by;
}
return RECT(r);
}
// --- window data
int Fl_WinAPI_Window_Driver::decorated_w()
{
int bt, bx, by;
border_width_title_bar_height(bx, by, bt);
return pWindow->w() + 2 * bx;
}
int Fl_WinAPI_Window_Driver::decorated_h()
{
int bt, bx, by;
border_width_title_bar_height(bx, by, bt);
return pWindow->h() + bt + 2 * by;
}
void Fl_WinAPI_Window_Driver::shape_bitmap_(Fl_Image* b) {
shape_data_->shape_ = b;
}

View File

@ -60,13 +60,21 @@ struct Fl_Window_Driver::shape_data_type {
class FL_EXPORT Fl_X11_Window_Driver : public Fl_Window_Driver
{
friend class Fl_X;
private:
void decorated_win_size(int &w, int &h);
void combine_mask();
void shape_bitmap_(Fl_Image* b);
void shape_alpha_(Fl_Image* img, int offset);
public:
Fl_X11_Window_Driver(Fl_Window*);
~Fl_X11_Window_Driver();
// --- window data
virtual int decorated_w();
virtual int decorated_h();
virtual void take_focus();
virtual void shape(const Fl_Image* img);
virtual void draw();

View File

@ -72,6 +72,48 @@ Fl_X11_Window_Driver::~Fl_X11_Window_Driver()
delete icon_;
}
// --- private
void Fl_X11_Window_Driver::decorated_win_size(int &w, int &h)
{
Fl_Window *win = pWindow;
w = win->w();
h = win->h();
if (!win->shown() || win->parent() || !win->border() || !win->visible()) return;
Window root, parent, *children;
unsigned n = 0;
Status status = XQueryTree(fl_display, Fl_X::i(win)->xid, &root, &parent, &children, &n);
if (status != 0 && n) XFree(children);
// when compiz is used, root and parent are the same window
// and I don't know where to find the window decoration
if (status == 0 || root == parent) return;
XWindowAttributes attributes;
XGetWindowAttributes(fl_display, parent, &attributes);
w = attributes.width;
h = attributes.height;
}
// --- window data
int Fl_X11_Window_Driver::decorated_h()
{
int w, h;
decorated_win_size(w, h);
return h;
}
int Fl_X11_Window_Driver::decorated_w()
{
int w, h;
decorated_win_size(w, h);
return w;
}
void Fl_X11_Window_Driver::take_focus()
{
Fl_X *i = Fl_X::i(pWindow);