diff options
| author | ManoloFLTK <41016272+ManoloFLTK@users.noreply.github.com> | 2022-03-15 06:42:06 +0100 |
|---|---|---|
| committer | ManoloFLTK <41016272+ManoloFLTK@users.noreply.github.com> | 2022-08-29 12:15:32 +0200 |
| commit | c720aae51515907ae82ee02df80bd084f291d4b1 (patch) | |
| tree | 7fbf3569f35966891df68490b047b30c9ec20bcd /src/drivers/Wayland | |
| parent | 28981f6fd3971aaf7ff6527ee1cdeb9d886c4a4a (diff) | |
Make hybrid Wayland/X11 platform.
Diffstat (limited to 'src/drivers/Wayland')
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Copy_Surface_Driver.cxx | 2 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Gl_Window_Driver.cxx | 20 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Graphics_Driver.cxx | 3 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Image_Surface_Driver.cxx | 37 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Screen_Driver.H | 4 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Screen_Driver.cxx | 44 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_System_Driver.cxx | 3 | ||||
| -rw-r--r-- | src/drivers/Wayland/Fl_Wayland_Window_Driver.cxx | 86 | ||||
| -rw-r--r-- | src/drivers/Wayland/fl_wayland_clipboard_dnd.cxx | 17 | ||||
| -rw-r--r-- | src/drivers/Wayland/fl_wayland_gl_platform_init.cxx | 5 | ||||
| -rw-r--r-- | src/drivers/Wayland/fl_wayland_platform_init.cxx | 88 |
11 files changed, 200 insertions, 109 deletions
diff --git a/src/drivers/Wayland/Fl_Wayland_Copy_Surface_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Copy_Surface_Driver.cxx index 07b3038f0..60a0cad51 100644 --- a/src/drivers/Wayland/Fl_Wayland_Copy_Surface_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Copy_Surface_Driver.cxx @@ -43,7 +43,7 @@ Fl_Wayland_Copy_Surface_Driver::~Fl_Wayland_Copy_Surface_Driver() { void Fl_Wayland_Copy_Surface_Driver::set_current() { Fl_Surface_Device::set_current(); - ((Fl_Wayland_Graphics_Driver*)driver())->set_buffer(img_surf->offscreen()); + ((Fl_Wayland_Graphics_Driver*)driver())->set_buffer((struct fl_wld_buffer *)img_surf->offscreen()); } diff --git a/src/drivers/Wayland/Fl_Wayland_Gl_Window_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Gl_Window_Driver.cxx index 979cef3d8..89014826f 100644 --- a/src/drivers/Wayland/Fl_Wayland_Gl_Window_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Gl_Window_Driver.cxx @@ -94,7 +94,7 @@ char *Fl_Wayland_Gl_Window_Driver::alpha_mask_for_string(const char *str, int n, { // write str to a bitmap just big enough Fl_Image_Surface *surf = new Fl_Image_Surface(w, h); - Fl_Font f=fl_font(); + Fl_Font f = fl_font(); Fl_Surface_Device::push_current(surf); fl_color(FL_BLACK); fl_rectf(0, 0, w, h); @@ -104,7 +104,8 @@ char *Fl_Wayland_Gl_Window_Driver::alpha_mask_for_string(const char *str, int n, // get the R channel only of the bitmap char *alpha_buf = new char[w*h], *r = alpha_buf, *q; for (int i = 0; i < h; i++) { - q = (char*)surf->offscreen()->draw_buffer + i * surf->offscreen()->stride; + struct fl_wld_buffer *off = (struct fl_wld_buffer *)surf->offscreen(); + q = (char*)off->draw_buffer + i * off->stride; for (int j = 0; j < w; j++) { *r++ = *q; q += 4; @@ -174,7 +175,7 @@ GLContext Fl_Wayland_Gl_Window_Driver::create_gl_context(Fl_Window* window, cons if (context_list && nContext) shared_ctx = context_list[0]; static const EGLint context_attribs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; - GLContext ctx = (GLContext)eglCreateContext(egl_display, ((Fl_Wayland_Gl_Choice*)g)->egl_conf, shared_ctx?shared_ctx:EGL_NO_CONTEXT, context_attribs); + GLContext ctx = (GLContext)eglCreateContext(egl_display, ((Fl_Wayland_Gl_Choice*)g)->egl_conf, shared_ctx?(EGLContext)shared_ctx:EGL_NO_CONTEXT, context_attribs); //fprintf(stderr, "eglCreateContext=%p shared_ctx=%p\n", ctx, shared_ctx); if (ctx) add_context(ctx); @@ -183,7 +184,7 @@ GLContext Fl_Wayland_Gl_Window_Driver::create_gl_context(Fl_Window* window, cons void Fl_Wayland_Gl_Window_Driver::set_gl_context(Fl_Window* w, GLContext context) { - struct wld_window *win = fl_xid(w); + struct wld_window *win = fl_wl_xid(w); if (!win) return; Fl_Wayland_Window_Driver *dr = Fl_Wayland_Window_Driver::driver(w); EGLSurface target_egl_surface = NULL; @@ -221,7 +222,7 @@ void Fl_Wayland_Gl_Window_Driver::delete_gl_context(GLContext context) { cached_window = 0; } //EGLBoolean b = - eglDestroyContext(egl_display, context); + eglDestroyContext(egl_display, (EGLContext)context); //fprintf(stderr,"EGL context %p destroyed %s\n", context, b==EGL_TRUE?"successfully":"w/ error"); //b = eglDestroySurface(egl_display, egl_surface); @@ -246,7 +247,7 @@ void Fl_Wayland_Gl_Window_Driver::redraw_overlay() { void Fl_Wayland_Gl_Window_Driver::make_current_before() { if (!egl_window) { - struct wld_window *win = fl_xid(pWindow); + struct wld_window *win = fl_wl_xid(pWindow); struct wl_surface *surface = win->wl_surface; egl_window = wl_egl_window_create(surface, pWindow->pixel_w(), pWindow->pixel_h()); if (egl_window == EGL_NO_SURFACE) { @@ -270,7 +271,7 @@ void Fl_Wayland_Gl_Window_Driver::make_current_before() { float Fl_Wayland_Gl_Window_Driver::pixels_per_unit() { int ns = Fl_Window_Driver::driver(pWindow)->screen_num(); - int wld_scale = pWindow->shown() ? fl_xid(pWindow)->scale : 1; + int wld_scale = pWindow->shown() ? fl_wl_xid(pWindow)->scale : 1; return wld_scale * Fl::screen_driver()->scale(ns); } @@ -360,7 +361,7 @@ static void delayed_flush(Fl_Gl_Window *win) { void Fl_Wayland_Gl_Window_Driver::resize(int is_a_resize, int W, int H) { if (!egl_window) return; - struct wld_window *win = fl_xid(pWindow); + struct wld_window *win = fl_wl_xid(pWindow); float f = Fl::screen_scale(pWindow->screen_num()); W = (W * win->scale) * f; H = (H * win->scale) * f; @@ -404,4 +405,7 @@ void Fl_Wayland_Gl_Window_Driver::gl_start() { glClear(GL_COLOR_BUFFER_BIT); } + +FL_EXPORT EGLContext fl_wl_glcontext(GLContext rc) { return (EGLContext)rc; } + #endif // HAVE_GL diff --git a/src/drivers/Wayland/Fl_Wayland_Graphics_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Graphics_Driver.cxx index 78586dc59..986d25ddf 100644 --- a/src/drivers/Wayland/Fl_Wayland_Graphics_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Graphics_Driver.cxx @@ -149,8 +149,9 @@ void Fl_Wayland_Graphics_Driver::set_color(Fl_Color i, unsigned c) { } -void Fl_Wayland_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen osrc, int srcx, int srcy) { +void Fl_Wayland_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen src, int srcx, int srcy) { // draw portion srcx,srcy,w,h of osrc to position x,y (top-left) of the graphics driver's surface + struct fl_wld_buffer *osrc = (struct fl_wld_buffer *)src; int height = osrc->data_size / osrc->stride; cairo_matrix_t matrix; cairo_get_matrix(cairo_, &matrix); diff --git a/src/drivers/Wayland/Fl_Wayland_Image_Surface_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Image_Surface_Driver.cxx index 1638cf0d2..4f64434d8 100644 --- a/src/drivers/Wayland/Fl_Wayland_Image_Surface_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Image_Surface_Driver.cxx @@ -33,12 +33,13 @@ Fl_Wayland_Image_Surface_Driver::Fl_Wayland_Image_Surface_Driver(int w, int h, i w = int(w*d); h = int(h*d); } - offscreen = (struct fl_wld_buffer*)calloc(1, sizeof(struct fl_wld_buffer)); - offscreen->stride = cairo_format_stride_for_width(CAIRO_FORMAT_RGB24, w); - offscreen->data_size = offscreen->stride * h; - offscreen->draw_buffer = (uchar*)malloc(offscreen->data_size); - offscreen->width = w; - Fl_Wayland_Graphics_Driver::cairo_init(offscreen, w, h, offscreen->stride, CAIRO_FORMAT_RGB24); + struct fl_wld_buffer *off_ = (struct fl_wld_buffer*)calloc(1, sizeof(struct fl_wld_buffer)); + off_->stride = cairo_format_stride_for_width(CAIRO_FORMAT_RGB24, w); + off_->data_size = off_->stride * h; + off_->draw_buffer = (uchar*)malloc(off_->data_size); + off_->width = w; + offscreen = (Fl_Offscreen)off_; + Fl_Wayland_Graphics_Driver::cairo_init(off_, w, h, off_->stride, CAIRO_FORMAT_RGB24); } driver(new Fl_Wayland_Graphics_Driver()); if (d != 1 && high_res) driver()->scale(d); @@ -47,24 +48,24 @@ Fl_Wayland_Image_Surface_Driver::Fl_Wayland_Image_Surface_Driver(int w, int h, i Fl_Wayland_Image_Surface_Driver::~Fl_Wayland_Image_Surface_Driver() { if (offscreen && !external_offscreen) { - cairo_destroy(offscreen->cairo_); - free(offscreen->draw_buffer); - free(offscreen); + cairo_destroy(((struct fl_wld_buffer *)offscreen)->cairo_); + free(((struct fl_wld_buffer *)offscreen)->draw_buffer); + free((struct fl_wld_buffer *)offscreen); } delete driver(); } void Fl_Wayland_Image_Surface_Driver::set_current() { Fl_Surface_Device::set_current(); - ((Fl_Wayland_Graphics_Driver*)fl_graphics_driver)->set_buffer(offscreen); + ((Fl_Wayland_Graphics_Driver*)fl_graphics_driver)->set_buffer((struct fl_wld_buffer*)offscreen); pre_window = Fl_Wayland_Window_Driver::wld_window; - fl_window = Fl_Wayland_Window_Driver::wld_window = NULL; + Fl_Wayland_Window_Driver::wld_window = NULL; } void Fl_Wayland_Image_Surface_Driver::end_current() { - cairo_surface_t *surf = cairo_get_target(offscreen->cairo_); + cairo_surface_t *surf = cairo_get_target(((struct fl_wld_buffer *)offscreen)->cairo_); cairo_surface_flush(surf); - fl_window = Fl_Wayland_Window_Driver::wld_window = pre_window; + Fl_Wayland_Window_Driver::wld_window = pre_window; } void Fl_Wayland_Image_Surface_Driver::translate(int x, int y) { @@ -77,20 +78,20 @@ void Fl_Wayland_Image_Surface_Driver::untranslate() { Fl_RGB_Image* Fl_Wayland_Image_Surface_Driver::image() { // Convert depth-4 image in draw_buffer to a depth-3 image while exchanging R and B colors - int height = offscreen->data_size / offscreen->stride; - uchar *rgb = new uchar[offscreen->width * height * 3]; + int height = ((struct fl_wld_buffer *)offscreen)->data_size / ((struct fl_wld_buffer *)offscreen)->stride; + uchar *rgb = new uchar[((struct fl_wld_buffer *)offscreen)->width * height * 3]; uchar *p = rgb; uchar *q; for (int j = 0; j < height; j++) { - q = offscreen->draw_buffer + j*offscreen->stride; - for (int i = 0; i < offscreen->width; i++) { // exchange R and B colors, transmit G + q = ((struct fl_wld_buffer *)offscreen)->draw_buffer + j*((struct fl_wld_buffer *)offscreen)->stride; + for (int i = 0; i < ((struct fl_wld_buffer *)offscreen)->width; i++) { // exchange R and B colors, transmit G *p = *(q+2); *(p+1) = *(q+1); *(p+2) = *q; p += 3; q += 4; } } - Fl_RGB_Image *image = new Fl_RGB_Image(rgb, offscreen->width, height, 3); + Fl_RGB_Image *image = new Fl_RGB_Image(rgb, ((struct fl_wld_buffer *)offscreen)->width, height, 3); image->alloc_array = 1; return image; } diff --git a/src/drivers/Wayland/Fl_Wayland_Screen_Driver.H b/src/drivers/Wayland/Fl_Wayland_Screen_Driver.H index 196f07d5e..a7a3f9512 100644 --- a/src/drivers/Wayland/Fl_Wayland_Screen_Driver.H +++ b/src/drivers/Wayland/Fl_Wayland_Screen_Driver.H @@ -64,6 +64,10 @@ class Fl_Wayland_Screen_Driver : public Fl_Screen_Driver static bool insertion_point_location_is_valid; public: static struct wl_display *wl_display; + // use it to make sure the Wayland leg was selected and fl_open_display() has run + static struct wl_registry *wl_registry; + // true when an app is forbidden to use its Wayland leg + static bool wld_disabled; static void insertion_point_location(int x, int y, int height); static bool insertion_point_location(int *px, int *py, int *pwidth, int *pheight); int get_mouse_unscaled(int &xx, int &yy); diff --git a/src/drivers/Wayland/Fl_Wayland_Screen_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Screen_Driver.cxx index 372d08b32..821bdd56a 100644 --- a/src/drivers/Wayland/Fl_Wayland_Screen_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Screen_Driver.cxx @@ -227,13 +227,16 @@ static inline void checkdouble() { struct wl_display *Fl_Wayland_Screen_Driver::wl_display = NULL; +struct wl_registry *Fl_Wayland_Screen_Driver::wl_registry = NULL; +bool Fl_Wayland_Screen_Driver::wld_disabled = false; + Fl_Window *Fl_Wayland_Screen_Driver::surface_to_window(struct wl_surface *surface) { if (surface) { Fl_X *xp = Fl_X::first; while (xp) { - if (xp->xid->wl_surface == surface) return xp->w; + if (((struct wld_window*)xp->xid)->wl_surface == surface) return xp->w; xp = xp->next; } } @@ -335,9 +338,9 @@ static void pointer_button(void *data, win = win->top_window(); wld_event_time = time; if (button == BTN_LEFT && state == WL_POINTER_BUTTON_STATE_PRESSED && seat->pointer_focus == NULL && - fl_xid(win)->kind == Fl_Wayland_Window_Driver::DECORATED) { + (fl_wl_xid(win))->kind == Fl_Wayland_Window_Driver::DECORATED) { // click on titlebar - libdecor_frame_move(fl_xid(win)->frame, seat->wl_seat, serial); + libdecor_frame_move(fl_wl_xid(win)->frame, seat->wl_seat, serial); return; } int b = 0; @@ -907,7 +910,7 @@ static void output_done(void *data, struct wl_output *wl_output) //fprintf(stderr, "output_done output=%p\n",output); Fl_X *xp = Fl_X::first; while (xp) { // all mapped windows - struct wld_window *win = xp->xid; + struct wld_window *win = (struct wld_window*)xp->xid; wl_list_for_each(window_output, &(win->outputs), link) { // all Fl_Wayland_Window_Driver::window_output for this window if (window_output->output == output) { Fl_Wayland_Window_Driver *win_driver = Fl_Wayland_Window_Driver::driver(win->fl_win); @@ -1041,7 +1044,7 @@ static void registry_handle_global_remove(void *data, struct wl_registry *regist if (output->id == name) { // the screen being removed Fl_X *xp = Fl_X::first; while (xp) { // all mapped windows - struct wld_window *win = xp->xid; + struct wld_window *win = (struct wld_window*)xp->xid; wl_list_for_each_safe(window_output, tmp, &(win->outputs), link) { // all Fl_Wayland_Window_Driver::window_output for this window if (window_output->output == output) { wl_list_remove(&window_output->link); @@ -1086,16 +1089,16 @@ Fl_Wayland_Screen_Driver::Fl_Wayland_Screen_Driver() : Fl_Screen_Driver() { } void Fl_Wayland_Screen_Driver::open_display_platform() { - struct wl_registry *wl_registry; - static bool beenHereDoneThat = false; if (beenHereDoneThat) return; beenHereDoneThat = true; - wl_display = wl_display_connect(NULL); if (!wl_display) { - Fl::fatal("No Wayland connection\n"); + wl_display = wl_display_connect(NULL); + if (!wl_display) { + Fl::fatal("No Wayland connection\n"); + } } wl_list_init(&seats); wl_list_init(&outputs); @@ -1121,6 +1124,7 @@ void Fl_Wayland_Screen_Driver::close_display() { Fl::remove_fd(wl_display_get_fd(Fl_Wayland_Screen_Driver::wl_display)); wl_display_disconnect(Fl_Wayland_Screen_Driver::wl_display); Fl_Wayland_Screen_Driver::wl_display = NULL; + Fl_Wayland_Screen_Driver::wl_registry = NULL; } @@ -1141,7 +1145,7 @@ void Fl_Wayland_Screen_Driver::init_workarea() int Fl_Wayland_Screen_Driver::x() { - if (!Fl_Wayland_Screen_Driver::wl_display) open_display(); + if (!Fl_Wayland_Screen_Driver::wl_registry) open_display(); Fl_Wayland_Screen_Driver::output *output; wl_list_for_each(output, &outputs, link) { break; @@ -1150,7 +1154,7 @@ int Fl_Wayland_Screen_Driver::x() { } int Fl_Wayland_Screen_Driver::y() { - if (!Fl_Wayland_Screen_Driver::wl_display) open_display(); + if (!Fl_Wayland_Screen_Driver::wl_registry) open_display(); Fl_Wayland_Screen_Driver::output *output; wl_list_for_each(output, &outputs, link) { break; @@ -1159,7 +1163,7 @@ int Fl_Wayland_Screen_Driver::y() { } int Fl_Wayland_Screen_Driver::w() { - if (!Fl_Wayland_Screen_Driver::wl_display) open_display(); + if (!Fl_Wayland_Screen_Driver::wl_registry) open_display(); Fl_Wayland_Screen_Driver::output *output; wl_list_for_each(output, &outputs, link) { break; @@ -1168,7 +1172,7 @@ int Fl_Wayland_Screen_Driver::w() { } int Fl_Wayland_Screen_Driver::h() { - if (!Fl_Wayland_Screen_Driver::wl_display) open_display(); + if (!Fl_Wayland_Screen_Driver::wl_registry) open_display(); Fl_Wayland_Screen_Driver::output *output; wl_list_for_each(output, &outputs, link) { break; @@ -1178,7 +1182,7 @@ int Fl_Wayland_Screen_Driver::h() { void Fl_Wayland_Screen_Driver::init() { - if (!Fl_Wayland_Screen_Driver::wl_display) open_display(); + if (!Fl_Wayland_Screen_Driver::wl_registry) open_display(); } @@ -1315,8 +1319,8 @@ const char *Fl_Wayland_Screen_Driver::get_system_scheme() Fl_RGB_Image *Fl_Wayland_Screen_Driver::read_win_rectangle(int X, int Y, int w, int h, Fl_Window *win, bool ignore, bool *p_ignore) { - Window xid = win ? fl_xid(win) : NULL; - struct fl_wld_buffer *buffer = win ? xid->buffer : (Fl_Offscreen)Fl_Surface_Device::surface()->driver()->gc(); + struct wld_window* xid = win ? fl_wl_xid(win) : NULL; + struct fl_wld_buffer *buffer = win ? xid->buffer : (struct fl_wld_buffer *)Fl_Surface_Device::surface()->driver()->gc(); float s = win ? xid->scale * scale(win->screen_num()) : Fl_Surface_Device::surface()->driver()->scale(); int Xs, Ys, ws, hs; @@ -1346,8 +1350,9 @@ Fl_RGB_Image *Fl_Wayland_Screen_Driver::read_win_rectangle(int X, int Y, int w, } -void Fl_Wayland_Screen_Driver::offscreen_size(Fl_Offscreen off, int &width, int &height) +void Fl_Wayland_Screen_Driver::offscreen_size(Fl_Offscreen off_, int &width, int &height) { + struct fl_wld_buffer *off = (struct fl_wld_buffer *)off_; width = off->width; height = off->data_size / off->stride; } @@ -1457,3 +1462,8 @@ void Fl_Wayland_Screen_Driver::reset_spot() { Fl_Wayland_Screen_Driver::next_marked_length = 0; Fl_Wayland_Screen_Driver::insertion_point_location_is_valid = false; } + + +struct wl_display *fl_wl_display() { + return Fl_Wayland_Screen_Driver::wl_display; +} diff --git a/src/drivers/Wayland/Fl_Wayland_System_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_System_Driver.cxx index a54e2ac5f..4b26a17ea 100644 --- a/src/drivers/Wayland/Fl_Wayland_System_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_System_Driver.cxx @@ -18,6 +18,7 @@ #include "Fl_Wayland_System_Driver.H" #include <FL/Fl.H> #include "Fl_Wayland_Window_Driver.H" +#include "Fl_Wayland_Screen_Driver.H" #include <FL/platform.H> #include "../../../libdecor/src/libdecor.h" @@ -55,7 +56,7 @@ void *Fl_Wayland_System_Driver::control_maximize_button(void *data) { Fl_Window *win = Fl::first_window(); while (win) { if (!win->parent() && win->border() && - !(Fl_X::i(win)->xid->state & LIBDECOR_WINDOW_STATE_MAXIMIZED) ) { + !( ((struct wld_window*)Fl_X::i(win)->xid)->state & LIBDECOR_WINDOW_STATE_MAXIMIZED) ) { win_dims *dim = new win_dims; dim->tracker = new Fl_Widget_Tracker(win); Fl_Window_Driver *dr = Fl_Window_Driver::driver(win); diff --git a/src/drivers/Wayland/Fl_Wayland_Window_Driver.cxx b/src/drivers/Wayland/Fl_Wayland_Window_Driver.cxx index 38230b3db..96985c10b 100644 --- a/src/drivers/Wayland/Fl_Wayland_Window_Driver.cxx +++ b/src/drivers/Wayland/Fl_Wayland_Window_Driver.cxx @@ -49,7 +49,7 @@ extern "C" { #define fl_max(a,b) ((a) > (b) ? (a) : (b)) -Window fl_window; + struct wld_window *Fl_Wayland_Window_Driver::wld_window = NULL; @@ -112,7 +112,7 @@ void Fl_Wayland_Window_Driver::decorated_win_size(int &w, int &h) h = win->h(); if (!win->shown() || win->parent() || !win->border() || !win->visible()) return; int X, titlebar_height; - libdecor_frame_translate_coordinate(fl_xid(win)->frame, 0, 0, &X, &titlebar_height); + libdecor_frame_translate_coordinate(fl_wl_xid(win)->frame, 0, 0, &X, &titlebar_height); //printf("titlebar_height=%d\n",titlebar_height); h = win->h() + ceil(titlebar_height / Fl::screen_scale(win->screen_num())); } @@ -135,7 +135,7 @@ int Fl_Wayland_Window_Driver::decorated_w() } struct xdg_toplevel *Fl_Wayland_Window_Driver::xdg_toplevel() { - Window w = fl_xid(pWindow); + struct wld_window * w = fl_wl_xid(pWindow); struct xdg_toplevel *top = NULL; if (w->kind == DECORATED) top = libdecor_frame_get_xdg_toplevel(w->frame); else if (w->kind == UNFRAMED) top = w->xdg_toplevel; @@ -144,10 +144,10 @@ struct xdg_toplevel *Fl_Wayland_Window_Driver::xdg_toplevel() { void Fl_Wayland_Window_Driver::take_focus() { - Window w = fl_xid(pWindow); + struct wld_window *w = fl_wl_xid(pWindow); if (w) { Fl_Window *old_first = Fl::first_window(); - Window first_xid = (old_first ? fl_xid(old_first->top_window()) : NULL); + struct wld_window *first_xid = (old_first ? fl_wl_xid(old_first->top_window()) : NULL); if (first_xid && first_xid != w && xdg_toplevel()) { // this will move the target window to the front Fl_Wayland_Window_Driver *top_dr = Fl_Wayland_Window_Driver::driver(old_first->top_window()); @@ -157,7 +157,7 @@ void Fl_Wayland_Window_Driver::take_focus() xdg_toplevel_set_parent(xdg_toplevel(), NULL); } // this sets the first window - fl_find(w); + fl_wl_find(w); } } @@ -185,7 +185,7 @@ void Fl_Wayland_Window_Driver::flush_overlay() fl_copy_offscreen(0, 0, oWindow->w(), oWindow->h(), other_xid, 0, 0); } if (overlay() == oWindow) oWindow->draw_overlay(); - Window xid = fl_xid(pWindow); + struct wld_window * xid = fl_wl_xid(pWindow); wl_surface_damage_buffer(xid->wl_surface, 0, 0, pWindow->w() * xid->scale, pWindow->h() * xid->scale); } @@ -295,7 +295,7 @@ void Fl_Wayland_Window_Driver::capture_titlebar_and_borders(Fl_RGB_Image*& top, top = left = bottom = right = NULL; if (pWindow->decorated_h() == h()) return; int htop = pWindow->decorated_h() - pWindow->h(); - struct wld_window *wwin = fl_xid(pWindow); + struct wld_window *wwin = fl_wl_xid(pWindow); int width, height, stride; uchar *cairo_data = fl_libdecor_titlebar_buffer(wwin->frame, &width, &height, &stride); if (!cairo_data) return; @@ -342,7 +342,7 @@ void Fl_Wayland_Window_Driver::make_current() { Fl::fatal(err_message); } - struct wld_window *window = fl_xid(pWindow); + struct wld_window *window = fl_wl_xid(pWindow); if (window->buffer) { ((Fl_Cairo_Graphics_Driver*)fl_graphics_driver)->needs_commit_tag( &window->buffer->draw_buffer_needs_commit); @@ -355,7 +355,7 @@ void Fl_Wayland_Window_Driver::make_current() { } fl_graphics_driver->clip_region(0); - fl_window = Fl_Wayland_Window_Driver::wld_window = window; + Fl_Wayland_Window_Driver::wld_window = window; float scale = Fl::screen_scale(pWindow->screen_num()) * window->scale; if (!window->buffer) { window->buffer = Fl_Wayland_Graphics_Driver::create_shm_buffer( @@ -385,11 +385,11 @@ void Fl_Wayland_Window_Driver::flush() { if (scale != fl_graphics_driver->scale() || W != pWindow->w() || H != pWindow->h()) gl_plugin()->invalidate(pWindow); return; } - struct wld_window *window = fl_xid(pWindow); + struct wld_window *window = fl_wl_xid(pWindow); if (!window || !window->configured_width) return; Fl_X *i = Fl_X::i(pWindow); - Fl_Region r = i->region; + struct flCairoRegion* r = (struct flCairoRegion*)i->region; float f = Fl::screen_scale(pWindow->screen_num()); if (r && window->buffer) { for (int i = 0; i < r->count; i++) { @@ -440,7 +440,7 @@ void Fl_Wayland_Window_Driver::hide() { ip->region = 0; } screen_num_ = -1; - struct wld_window *wld_win = ip->xid; + struct wld_window *wld_win = (struct wld_window*)ip->xid; if (wld_win) { // this test makes sure ip->xid has not been destroyed already Fl_Wayland_Graphics_Driver::buffer_release(wld_win); //fprintf(stderr, "Before hide: sub=%p frame=%p xdg=%p top=%p pop=%p surf=%p\n", wld_win->subsurface, wld_win->frame, wld_win->xdg_surface, wld_win->xdg_toplevel, wld_win->xdg_popup, wld_win->wl_surface); @@ -479,7 +479,7 @@ void Fl_Wayland_Window_Driver::hide() { } free(wld_win); if (pWindow->as_gl_window() && in_flush) { - ip->xid = NULL; + ip->xid = 0; ip->next = NULL; // to end the loop in calling Fl::flush() Fl::add_timeout(.01, (Fl_Timeout_Handler)delayed_delete_Fl_X, ip); } else { @@ -490,9 +490,9 @@ void Fl_Wayland_Window_Driver::hide() { void Fl_Wayland_Window_Driver::map() { Fl_X* ip = Fl_X::i(pWindow); - struct wld_window *wl_win = ip->xid; + struct wld_window *wl_win = (struct wld_window*)ip->xid; if (wl_win->kind == SUBWINDOW && !wl_win->subsurface) { - struct wld_window *parent = fl_xid(pWindow->window()); + struct wld_window *parent = fl_wl_xid(pWindow->window()); if (parent) { Fl_Wayland_Screen_Driver *scr_driver = (Fl_Wayland_Screen_Driver*)Fl::screen_driver(); wl_win->subsurface = wl_subcompositor_get_subsurface(scr_driver->wl_subcompositor, wl_win->wl_surface, parent->wl_surface); @@ -512,7 +512,7 @@ void Fl_Wayland_Window_Driver::map() { void Fl_Wayland_Window_Driver::unmap() { Fl_X* ip = Fl_X::i(pWindow); - struct wld_window *wl_win = ip->xid; + struct wld_window *wl_win = (struct wld_window*)ip->xid; if (wl_win->kind == SUBWINDOW && wl_win->wl_surface) { wl_surface_attach(wl_win->wl_surface, NULL, 0, 0); Fl_Wayland_Graphics_Driver::buffer_release(wl_win); @@ -525,7 +525,7 @@ void Fl_Wayland_Window_Driver::unmap() { void Fl_Wayland_Window_Driver::size_range() { if (shown()) { Fl_X* ip = Fl_X::i(pWindow); - struct wld_window *wl_win = ip->xid; + struct wld_window *wl_win = (struct wld_window*)ip->xid; float f = Fl::screen_scale(pWindow->screen_num()); if (wl_win->kind == DECORATED && wl_win->frame) { int X,Y,W,H; @@ -553,7 +553,7 @@ void Fl_Wayland_Window_Driver::size_range() { void Fl_Wayland_Window_Driver::iconize() { Fl_X* ip = Fl_X::i(pWindow); - struct wld_window *wl_win = ip->xid; + struct wld_window *wl_win = (struct wld_window*)ip->xid; if (wl_win->kind == DECORATED) { libdecor_frame_set_minimized(wl_win->frame); Fl::handle(FL_HIDE, pWindow); @@ -577,7 +577,7 @@ void Fl_Wayland_Window_Driver::decoration_sizes(int *top, int *left, int *right int Fl_Wayland_Window_Driver::scroll(int src_x, int src_y, int src_w, int src_h, int dest_x, int dest_y, void (*draw_area)(void*, int,int,int,int), void* data) { - Window xid = fl_xid(pWindow); + struct wld_window * xid = fl_wl_xid(pWindow); struct fl_wld_buffer *buffer = xid->buffer; float s = xid->scale * fl_graphics_driver->scale(); if (s != 1) { @@ -781,7 +781,7 @@ static void handle_configure(struct libdecor_frame *frame, void Fl_Wayland_Window_Driver::wait_for_expose() { Fl_Window_Driver::wait_for_expose(); - Window xid = fl_xid(pWindow); + struct wld_window * xid = fl_wl_xid(pWindow); if (pWindow->fullscreen_active()) { if (xid->kind == DECORATED) { while (!(xid->state & LIBDECOR_WINDOW_STATE_FULLSCREEN) || !(xid->state & LIBDECOR_WINDOW_STATE_ACTIVE)) { @@ -897,7 +897,7 @@ static void popup_done(void *data, struct xdg_popup *xdg_popup) { #if USE_GRAB_POPUP if (mem_grabbing_popup == xdg_popup) { Fl_Wayland_Screen_Driver *scr_driver = (Fl_Wayland_Screen_Driver*)Fl::screen_driver(); - libdecor_frame_popup_ungrab(fl_xid(mem_parent)->frame, scr_driver->get_seat_name()); + libdecor_frame_popup_ungrab(fl_wl_xid(mem_parent)->frame, scr_driver->get_seat_name()); mem_grabbing_popup = NULL; mem_parent = NULL; } @@ -1003,7 +1003,7 @@ Fl_X *Fl_Wayland_Window_Driver::makeWindow() if (!target) target = Fl::first_window(); Fl_Window *parent_win = target->top_window(); while (parent_win && parent_win->menu_window()) parent_win = Fl::next_window(parent_win); - Window parent_xid = fl_xid(parent_win); + struct wld_window * parent_xid = fl_wl_xid(parent_win); struct xdg_surface *parent_xdg = parent_xid->xdg_surface; float f = Fl::screen_scale(parent_win->screen_num()); //fprintf(stderr, "menu parent_win=%p pos:%dx%d size:%dx%d\n", parent_win, pWindow->x(), pWindow->y(), pWindow->w(), pWindow->h()); @@ -1029,7 +1029,8 @@ Fl_X *Fl_Wayland_Window_Driver::makeWindow() } else if ( pWindow->border() && !pWindow->parent() ) { // a decorated window new_window->kind = DECORATED; - if (!scr_driver->libdecor_context) scr_driver->libdecor_context = libdecor_new(Fl_Wayland_Screen_Driver::wl_display, &libdecor_iface); + if (!scr_driver->libdecor_context) + scr_driver->libdecor_context = libdecor_new(Fl_Wayland_Screen_Driver::wl_display, &libdecor_iface); new_window->frame = libdecor_decorate(scr_driver->libdecor_context, new_window->wl_surface, &libdecor_frame_iface, new_window); //fprintf(stderr, "makeWindow: libdecor_decorate=%p pos:%dx%d\n", new_window->frame, pWindow->x(), pWindow->y()); @@ -1046,7 +1047,7 @@ Fl_X *Fl_Wayland_Window_Driver::makeWindow() } else if (pWindow->parent()) { // for subwindows (GL or non-GL) new_window->kind = SUBWINDOW; - struct wld_window *parent = fl_xid(pWindow->window()); + struct wld_window *parent = fl_wl_xid(pWindow->window()); new_window->subsurface = wl_subcompositor_get_subsurface(scr_driver->wl_subcompositor, new_window->wl_surface, parent->wl_surface); //fprintf(stderr, "makeWindow: subsurface=%p\n", new_window->subsurface); float f = Fl::screen_scale(pWindow->top_window()->screen_num()); @@ -1073,9 +1074,9 @@ Fl_X *Fl_Wayland_Window_Driver::makeWindow() } Fl_Window *old_first = Fl::first_window(); - Window first_xid = (old_first ? fl_xid(old_first) : NULL); + struct wld_window * first_xid = (old_first ? fl_wl_xid(old_first) : NULL); Fl_X *xp = new Fl_X; - xp->xid = new_window; + xp->xid = (fl_uintptr_t)new_window; other_xid = 0; xp->w = pWindow; i(xp); @@ -1244,7 +1245,7 @@ int Fl_Wayland_Window_Driver::set_cursor(Fl_Cursor c) { void Fl_Wayland_Window_Driver::update_scale() { - struct wld_window *window = fl_xid(pWindow); + struct wld_window *window = fl_wl_xid(pWindow); int scale = 0; Fl_Wayland_Window_Driver::window_output *window_output; @@ -1265,7 +1266,7 @@ void Fl_Wayland_Window_Driver::update_scale() void Fl_Wayland_Window_Driver::use_border() { if (!shown() || pWindow->parent()) return; pWindow->wait_for_expose(); // useful for border(0) just after show() - struct libdecor_frame *frame = fl_xid(pWindow)->frame; + struct libdecor_frame *frame = fl_wl_xid(pWindow)->frame; if (frame && Fl_Wayland_Screen_Driver::compositor != Fl_Wayland_Screen_Driver::KDE) { libdecor_frame_set_visibility(frame, pWindow->border()); pWindow->redraw(); @@ -1310,10 +1311,10 @@ void Fl_Wayland_Window_Driver::fullscreen_off(int X, int Y, int W, int H) { void Fl_Wayland_Window_Driver::label(const char *name, const char *iname) { - if (shown() && !parent() && fl_xid(pWindow)->kind == DECORATED) { + if (shown() && !parent() && fl_wl_xid(pWindow)->kind == DECORATED) { if (!name) name = ""; if (!iname) iname = fl_filename_name(name); - libdecor_frame_set_title(fl_xid(pWindow)->frame, name); + libdecor_frame_set_title(fl_wl_xid(pWindow)->frame, name); } } @@ -1322,7 +1323,7 @@ int Fl_Wayland_Window_Driver::set_cursor(const Fl_RGB_Image *rgb, int hotx, int // build a new wl_cursor and its image struct wl_cursor *new_cursor = (struct wl_cursor*)malloc(sizeof(struct wl_cursor)); struct cursor_image *new_image = (struct cursor_image*)calloc(1, sizeof(struct cursor_image)); - int scale = fl_xid(pWindow)->scale; + int scale = fl_wl_xid(pWindow)->scale; new_image->image.width = rgb->w() * scale; new_image->image.height = rgb->h() * scale; new_image->image.hotspot_x = hotx * scale; @@ -1338,7 +1339,7 @@ int Fl_Wayland_Window_Driver::set_cursor(const Fl_RGB_Image *rgb, int hotx, int new_cursor->images[0] = (struct wl_cursor_image*)new_image; new_cursor->name = strdup("custom cursor"); // draw the rgb image to the cursor's drawing buffer - Fl_Image_Surface *img_surf = new Fl_Image_Surface(new_image->image.width, new_image->image.height, 0, offscreen); + Fl_Image_Surface *img_surf = new Fl_Image_Surface(new_image->image.width, new_image->image.height, 0, (Fl_Offscreen)offscreen); Fl_Surface_Device::push_current(img_surf); Fl_Wayland_Graphics_Driver *driver = (Fl_Wayland_Graphics_Driver*)img_surf->driver(); cairo_scale(driver->cr(), scale, scale); @@ -1361,7 +1362,7 @@ int Fl_Wayland_Window_Driver::set_cursor(const Fl_RGB_Image *rgb, int hotx, int // This is only to fix a bug in libdecor where what libdecor_frame_set_min_content_size() // does is often destroyed by libdecor-cairo. static void delayed_minsize(Fl_Window *win) { - struct wld_window *wl_win = fl_xid(win); + struct wld_window *wl_win = fl_wl_xid(win); Fl_Window_Driver *driver = Fl_Window_Driver::driver(win); if (wl_win->kind == Fl_Wayland_Window_Driver::DECORATED) { float f = Fl::screen_scale(win->screen_num()); @@ -1377,7 +1378,7 @@ static void delayed_minsize(Fl_Window *win) { void Fl_Wayland_Window_Driver::resize(int X, int Y, int W, int H) { - struct wld_window *fl_win = fl_xid(pWindow); + struct wld_window *fl_win = fl_wl_xid(pWindow); if (fl_win && fl_win->kind == DECORATED && !xdg_toplevel()) { pWindow->wait_for_expose(); } @@ -1448,7 +1449,7 @@ void Fl_Wayland_Window_Driver::resize(int X, int Y, int W, int H) { } void Fl_Wayland_Window_Driver::reposition_menu_window(int x, int y) { - Window xid_menu = fl_xid(pWindow); + struct wld_window * xid_menu = fl_wl_xid(pWindow); if (y == pWindow->y() && y >= 0) return; int true_y = y; int y_offset = 0; @@ -1468,7 +1469,7 @@ void Fl_Wayland_Window_Driver::reposition_menu_window(int x, int y) { xid_menu->xdg_surface = xdg_wm_base_get_xdg_surface(scr_driver->xdg_wm_base, xid_menu->wl_surface); xdg_surface_add_listener(xid_menu->xdg_surface, &xdg_surface_listener, xid_menu); struct xdg_positioner *positioner = xdg_wm_base_create_positioner(scr_driver->xdg_wm_base); - Window parent_xid = fl_xid(Fl_Window_Driver::menu_parent()); + struct wld_window * parent_xid = fl_wl_xid(Fl_Window_Driver::menu_parent()); float f = Fl::screen_scale(Fl_Window_Driver::menu_parent()->screen_num()); int popup_x = x * f, popup_y = y * f; if (parent_xid->kind == DECORATED) @@ -1504,7 +1505,7 @@ void Fl_Wayland_Window_Driver::menu_window_area(int &X, int &Y, int &W, int &H, } -struct wl_surface *fl_wl_surface(Window xid) { +FL_EXPORT struct wl_surface *fl_wl_surface(struct wld_window *xid) { return xid->wl_surface; } @@ -1514,8 +1515,13 @@ cairo_t *fl_wl_cairo() { } -struct wl_display *fl_wl_display() { - return Fl_Wayland_Screen_Driver::wl_display; +Fl_Window *fl_wl_find(struct wld_window *xid) { + return Fl_Window_Driver::find((fl_uintptr_t)xid); +} + + +struct wld_window *fl_wl_xid(const Fl_Window *win) { + return (struct wld_window *)Fl_Window_Driver::xid(win); } diff --git a/src/drivers/Wayland/fl_wayland_clipboard_dnd.cxx b/src/drivers/Wayland/fl_wayland_clipboard_dnd.cxx index 07bcd3ed4..2dca84924 100644 --- a/src/drivers/Wayland/fl_wayland_clipboard_dnd.cxx +++ b/src/drivers/Wayland/fl_wayland_clipboard_dnd.cxx @@ -34,7 +34,6 @@ //////////////////////////////////////////////////////////////// // Code used for copy and paste and DnD into the program: -//static Window fl_dnd_source_window; static char *fl_selection_buffer[2]; static int fl_selection_length[2]; @@ -99,7 +98,7 @@ static void data_source_handle_cancelled(void *data, struct wl_data_source *sour wl_data_source_destroy(source); doing_dnd = false; if (dnd_icon) { - Fl_Offscreen off = (Fl_Offscreen)wl_surface_get_user_data(dnd_icon); + struct fl_wld_buffer * off = (struct fl_wld_buffer *)wl_surface_get_user_data(dnd_icon); struct wld_window fake_window; fake_window.buffer = off; Fl_Wayland_Graphics_Driver::buffer_release(&fake_window); @@ -190,9 +189,9 @@ static Fl_Offscreen offscreen_from_text(const char *text, int scale) { if (width > 300*scale) width = 300*scale; height = nl * fl_height() + 3; width += 6; - Fl_Offscreen off = Fl_Wayland_Graphics_Driver::create_shm_buffer(width, height); + struct fl_wld_buffer * off = Fl_Wayland_Graphics_Driver::create_shm_buffer(width, height); memset(off->draw_buffer, 0, off->data_size); - Fl_Image_Surface *surf = new Fl_Image_Surface(width, height, 0, off); + Fl_Image_Surface *surf = new Fl_Image_Surface(width, height, 0, (Fl_Offscreen)off); Fl_Surface_Device::push_current(surf); p = text; fl_font(FL_HELVETICA, 10 * scale); @@ -213,7 +212,7 @@ static Fl_Offscreen offscreen_from_text(const char *text, int scale) { delete surf; cairo_surface_flush( cairo_get_target(off->cairo_) ); memcpy(off->data, off->draw_buffer, off->data_size); - return off; + return (Fl_Offscreen)off; } @@ -226,13 +225,13 @@ int Fl_Wayland_Screen_Driver::dnd(int use_selection) { wl_data_source_add_listener(source, &data_source_listener, (void*)0); wl_data_source_offer(source, wld_plain_text_clipboard); wl_data_source_set_actions(source, WL_DATA_DEVICE_MANAGER_DND_ACTION_COPY); - Fl_Offscreen off = NULL; + struct fl_wld_buffer * off = NULL; int s = 1; if (use_selection) { // use the text as dragging icon Fl_Widget *current = Fl::pushed() ? Fl::pushed() : Fl::first_window(); - s = fl_xid(current->top_window())->scale; - off = offscreen_from_text(fl_selection_buffer[0], s); + s = fl_wl_xid(current->top_window())->scale; + off = (struct fl_wld_buffer *)offscreen_from_text(fl_selection_buffer[0], s); dnd_icon = wl_compositor_create_surface(scr_driver->wl_compositor); } else dnd_icon = NULL; doing_dnd = true; @@ -571,7 +570,7 @@ void Fl_Wayland_Screen_Driver::paste(Fl_Widget &receiver, int clipboard, const c receiver.handle(FL_PASTE); } else if (type == Fl::clipboard_image && clipboard_contains(Fl::clipboard_image)) { if (get_clipboard_image()) return; - Window xid = fl_xid(receiver.top_window()); + struct wld_window * xid = fl_wl_xid(receiver.top_window()); if (xid && xid->scale > 1) { Fl_RGB_Image *rgb = (Fl_RGB_Image*)Fl::e_clipboard_data; rgb->scale(rgb->data_w() / xid->scale, rgb->data_h() / xid->scale); diff --git a/src/drivers/Wayland/fl_wayland_gl_platform_init.cxx b/src/drivers/Wayland/fl_wayland_gl_platform_init.cxx index 5a2a78bee..f80ee67ba 100644 --- a/src/drivers/Wayland/fl_wayland_gl_platform_init.cxx +++ b/src/drivers/Wayland/fl_wayland_gl_platform_init.cxx @@ -16,9 +16,12 @@ #include "Fl_Wayland_Gl_Window_Driver.H" +#include "Fl_Wayland_Screen_Driver.H" +#include "../X11/Fl_X11_Gl_Window_Driver.H" Fl_Gl_Window_Driver *Fl_Gl_Window_Driver::newGlWindowDriver(Fl_Gl_Window *w) { - return new Fl_Wayland_Gl_Window_Driver(w); + if (Fl_Wayland_Screen_Driver::wl_display) return new Fl_Wayland_Gl_Window_Driver(w); + return new Fl_X11_Gl_Window_Driver(w); } diff --git a/src/drivers/Wayland/fl_wayland_platform_init.cxx b/src/drivers/Wayland/fl_wayland_platform_init.cxx index 4500a0f45..8c81ab331 100644 --- a/src/drivers/Wayland/fl_wayland_platform_init.cxx +++ b/src/drivers/Wayland/fl_wayland_platform_init.cxx @@ -22,10 +22,61 @@ #include "Fl_Wayland_Window_Driver.H" #include "Fl_Wayland_Image_Surface_Driver.H" +#include "../Xlib/Fl_Xlib_Copy_Surface_Driver.H" +#include <cairo-xlib.h> +#include "../Cairo/Fl_Display_Cairo_Graphics_Driver.H" +#include "../X11/Fl_X11_Screen_Driver.H" +#include "../X11/Fl_X11_System_Driver.H" +#include "../X11/Fl_X11_Window_Driver.H" +#include "../Xlib/Fl_Xlib_Image_Surface_Driver.H" + +#include <string.h> +#include <stdlib.h> +#include <stdio.h> + + +void fl_disable_wayland() { + if (Fl_Wayland_Screen_Driver::wl_display) { + wl_display_disconnect(Fl_Wayland_Screen_Driver::wl_display); + Fl_Wayland_Screen_Driver::wl_display = NULL; + delete Fl_Screen_Driver::system_driver; + Fl_Screen_Driver::system_driver = NULL; + } + Fl_Wayland_Screen_Driver::wld_disabled = true; + Fl::system_driver(); +} + -Fl_Copy_Surface_Driver *Fl_Copy_Surface_Driver::newCopySurfaceDriver(int w, int h) +Fl_System_Driver *Fl_System_Driver::newSystemDriver() { - return new Fl_Wayland_Copy_Surface_Driver(w, h); + const char *backend = ::getenv("FLTK_BACKEND"); + // fprintf(stderr, "FLTK_BACKEND='%s' XDG_RUNTIME_DIR='%s'\n",backend ? backend : "", xdg ? xdg : ""); + if (backend && strcmp(backend, "wayland") == 0) { + Fl_Wayland_Screen_Driver::wl_display = wl_display_connect(NULL); + if (!Fl_Wayland_Screen_Driver::wl_display) { + fprintf(stderr, "Error: no Wayland connection available, FLTK_BACKEND = '%s'\n", backend); + exit(1); + } + return new Fl_Wayland_System_Driver(); + } + else if (backend && strcmp(backend, "x11") == 0) { + return new Fl_X11_System_Driver(); + } + else if (!backend) { + if (!Fl_Wayland_Screen_Driver::wld_disabled && ::getenv("XDG_RUNTIME_DIR")) { + // env var XDG_RUNTIME_DIR is necessary for wayland + // is a Wayland connection available ? + Fl_Wayland_Screen_Driver::wl_display = wl_display_connect(NULL); + if (Fl_Wayland_Screen_Driver::wl_display) { // Yes, use Wayland drivers + // puts("using wayland"); + return new Fl_Wayland_System_Driver(); + } + } + return new Fl_X11_System_Driver(); + } + fprintf(stderr, "Error: unexpected value of FLTK_BACKEND: '%s'\n", backend); + exit(1); + return NULL; } @@ -52,32 +103,43 @@ static Fl_Fontdesc built_in_table[] = { // Pango font names FL_EXPORT Fl_Fontdesc *fl_fonts = built_in_table; -Fl_Graphics_Driver *Fl_Graphics_Driver::newMainGraphicsDriver() -{ - fl_graphics_driver = new Fl_Wayland_Graphics_Driver(); +Fl_Graphics_Driver *Fl_Graphics_Driver::newMainGraphicsDriver() { + if (Fl_Wayland_Screen_Driver::wl_display) { + fl_graphics_driver = new Fl_Wayland_Graphics_Driver(); +puts("using Fl_Wayland_Graphics_Driver"); + } else { + fl_graphics_driver = new Fl_Display_Cairo_Graphics_Driver(); +puts("using Fl_Display_Cairo_Graphics_Driver"); + } return fl_graphics_driver; } -Fl_Screen_Driver *Fl_Screen_Driver::newScreenDriver() -{ - return new Fl_Wayland_Screen_Driver(); +Fl_Copy_Surface_Driver *Fl_Copy_Surface_Driver::newCopySurfaceDriver(int w, int h) { + if (Fl_Wayland_Screen_Driver::wl_display) return new Fl_Wayland_Copy_Surface_Driver(w, h); + return new Fl_Xlib_Copy_Surface_Driver(w, h); } -Fl_System_Driver *Fl_System_Driver::newSystemDriver() -{ - return new Fl_Wayland_System_Driver(); +Fl_Screen_Driver *Fl_Screen_Driver::newScreenDriver() { + if (Fl_Wayland_Screen_Driver::wl_display) return new Fl_Wayland_Screen_Driver(); + + Fl_X11_Screen_Driver *d = new Fl_X11_Screen_Driver(); + for (int i = 0; i < MAX_SCREENS; i++) d->screens[i].scale = 1; + d->current_xft_dpi = 0.; // means the value of the Xft.dpi resource is still unknown + return d; } Fl_Window_Driver *Fl_Window_Driver::newWindowDriver(Fl_Window *w) { - return new Fl_Wayland_Window_Driver(w); + if (Fl_Wayland_Screen_Driver::wl_display) return new Fl_Wayland_Window_Driver(w); + return new Fl_X11_Window_Driver(w); } Fl_Image_Surface_Driver *Fl_Image_Surface_Driver::newImageSurfaceDriver(int w, int h, int high_res, Fl_Offscreen off) { - return new Fl_Wayland_Image_Surface_Driver(w, h, high_res, off); + if (Fl_Wayland_Screen_Driver::wl_display) return new Fl_Wayland_Image_Surface_Driver(w, h, high_res, off); + return new Fl_Xlib_Image_Surface_Driver(w, h, high_res, off); } |
