diff options
| author | ManoloFLTK <41016272+ManoloFLTK@users.noreply.github.com> | 2019-09-15 15:57:29 +0200 |
|---|---|---|
| committer | ManoloFLTK <41016272+ManoloFLTK@users.noreply.github.com> | 2019-09-15 15:57:29 +0200 |
| commit | c549b7acbd65674019b731c6648a9e8eb22f70dd (patch) | |
| tree | 7e6b8745573d2b8c1f9a61a7393b1e7c2b0d8f69 /src | |
| parent | 000807cc1d1a1c2f00274763f3e8e24145f1af00 (diff) | |
X11 platform: use Gnome printer dialog when the GTK library is available at run-time
The code to determine whether the GTK library is available is now in Fl_X11_System_Driver::probe_for_GTK()
called both by Fl_Printer::begin_job() and Fl_Native_File_Chooser.
New Fl::option OPTION_PRINTER_USES_GTK allows to deactivate use of
the Gnome print dialog.
Minor change in Fl_Native_File_Chooser: GTK version 3 is searched before version 2,
whereas the search order was the opposite before.
Diffstat (limited to 'src')
| -rw-r--r-- | src/Fl.cxx | 8 | ||||
| -rw-r--r-- | src/Fl_Native_File_Chooser_GTK.cxx | 72 | ||||
| -rw-r--r-- | src/drivers/Posix/Fl_Posix_Printer_Driver.cxx | 180 | ||||
| -rw-r--r-- | src/drivers/X11/Fl_X11_System_Driver.H | 4 | ||||
| -rw-r--r-- | src/drivers/X11/Fl_X11_System_Driver.cxx | 57 |
5 files changed, 261 insertions, 60 deletions
diff --git a/src/Fl.cxx b/src/Fl.cxx index 1327509e8..0a4e22ee9 100644 --- a/src/Fl.cxx +++ b/src/Fl.cxx @@ -1866,7 +1866,9 @@ bool Fl::option(Fl_Option opt) options_[OPTION_SHOW_TOOLTIPS] = tmp; opt_prefs.get("FNFCUsesGTK", tmp, 1); // default: on options_[OPTION_FNFC_USES_GTK] = tmp; - + opt_prefs.get("PrintUsesGTK", tmp, 1); // default: on + options_[OPTION_PRINTER_USES_GTK] = tmp; + opt_prefs.get("ShowZoomFactor", tmp, 1); // default: on options_[OPTION_SHOW_SCALING] = tmp; } @@ -1888,7 +1890,9 @@ bool Fl::option(Fl_Option opt) if (tmp >= 0) options_[OPTION_SHOW_TOOLTIPS] = tmp; opt_prefs.get("FNFCUsesGTK", tmp, -1); if (tmp >= 0) options_[OPTION_FNFC_USES_GTK] = tmp; - + opt_prefs.get("PrintUsesGTK", tmp, -1); + if (tmp >= 0) options_[OPTION_PRINTER_USES_GTK] = tmp; + opt_prefs.get("ShowZoomFactor", tmp, -1); if (tmp >= 0) options_[OPTION_SHOW_SCALING] = tmp; } diff --git a/src/Fl_Native_File_Chooser_GTK.cxx b/src/Fl_Native_File_Chooser_GTK.cxx index 2d6b819f9..575ab4c70 100644 --- a/src/Fl_Native_File_Chooser_GTK.cxx +++ b/src/Fl_Native_File_Chooser_GTK.cxx @@ -24,6 +24,7 @@ #if HAVE_DLSYM && HAVE_DLFCN_H #include <dlfcn.h> // for dlopen et al +#include "drivers/X11/Fl_X11_System_Driver.H" #endif #include <locale.h> // for setlocale @@ -159,10 +160,6 @@ static XX_g_slist_length fl_g_slist_length = NULL; typedef void (*XX_g_slist_free) (GSList *); static XX_g_slist_free fl_g_slist_free = NULL; -// gboolean gtk_init_check (int *argc, char ***argv); -typedef gboolean (*XX_gtk_init_check)(int *, char ***); -static XX_gtk_init_check fl_gtk_init_check = NULL; - // void gtk_widget_destroy (GtkWidget *widget); typedef void (*XX_gtk_widget_destroy) (GtkWidget *); static XX_gtk_widget_destroy fl_gtk_widget_destroy = NULL; @@ -262,9 +259,9 @@ static XX_gtk_widget_show_now fl_gtk_widget_show_now = NULL; typedef GdkWindow* (*XX_gtk_widget_get_window)(GtkWidget *); static XX_gtk_widget_get_window fl_gtk_widget_get_window = NULL; -// Window gdk_x11_drawable_get_xid(GdkWindow *); -typedef Window (*XX_gdk_x11_drawable_get_xid)(GdkWindow *); -static XX_gdk_x11_drawable_get_xid fl_gdk_x11_drawable_get_xid = NULL; +// Window gdk_x11_drawable_get_xid(GdkWindow *); or gdk_x11_window_get_xid +typedef Window (*gdk_to_X11_t)(GdkWindow*); +static gdk_to_X11_t fl_gdk_to_X11 = NULL; // GtkWidget *gtk_check_button_new_with_label(const gchar *); typedef GtkWidget* (*XX_gtk_check_button_new_with_label)(const gchar *); @@ -492,15 +489,8 @@ static void run_response_handler(GtkDialog *dialog, gint response_id, gpointer d int Fl_GTK_Native_File_Chooser_Driver::fl_gtk_chooser_wrapper() { int result = 1; - static int have_gtk_init = 0; char *p; - - if(!have_gtk_init) { - have_gtk_init = -1; - int ac = 0; - fl_gtk_init_check(&ac, NULL); - } - + if(gtkw_ptr) { // discard the previous dialog widget fl_gtk_widget_destroy (gtkw_ptr); gtkw_ptr = NULL; @@ -611,7 +601,7 @@ int Fl_GTK_Native_File_Chooser_Driver::fl_gtk_chooser_wrapper() fl_gtk_widget_show_now(gtkw_ptr); // map the GTK window on screen if (firstw) { GdkWindow* gdkw = fl_gtk_widget_get_window(gtkw_ptr); - Window xw = fl_gdk_x11_drawable_get_xid(gdkw); // get the X11 ref of the GTK window + Window xw = fl_gdk_to_X11(gdkw); // get the X11 ref of the GTK window XSetTransientForHint(fl_display, xw, fl_xid(firstw)); // set the GTK window transient for the last FLTK win } gboolean state = fl_gtk_file_chooser_get_show_hidden((GtkFileChooser *)gtkw_ptr); @@ -701,57 +691,22 @@ fprintf(stderr, "%s\n", pc_dl_error); \ did_find_GTK_libs = 0; \ return; } -static void* fl_dlopen(const char *filename1, const char *filename2) -{ - void *ptr = dlopen(filename1, RTLD_LAZY | RTLD_GLOBAL); - if (!ptr) ptr = dlopen(filename2, RTLD_LAZY | RTLD_GLOBAL); - return ptr; -} + #endif // HAVE_DLSYM && HAVE_DLFCN_H -/* +/* * Use dlopen to see if we can load the gtk dynamic libraries that * will allow us to create a GtkFileChooserDialog() on the fly, * without linking to the GTK libs at compile time. */ void Fl_GTK_Native_File_Chooser_Driver::probe_for_GTK_libs(void) { #if HAVE_DLSYM && HAVE_DLFCN_H - void *ptr_glib = NULL; - void *ptr_gtk = NULL; - -# ifdef __APPLE_CC__ // allows testing on Darwin + X11 - ptr_glib = dlopen("/sw/lib/libglib-2.0.dylib", RTLD_LAZY | RTLD_GLOBAL); -# else - ptr_glib = fl_dlopen("libglib-2.0.so", "libglib-2.0.so.0"); -# endif - // Try first with GTK2 -# ifdef __APPLE_CC__ // allows testing on Darwin + X11 - ptr_gtk = dlopen("/sw/lib/libgtk-x11-2.0.dylib", RTLD_LAZY | RTLD_GLOBAL); -#else - ptr_gtk = fl_dlopen("libgtk-x11-2.0.so", "libgtk-x11-2.0.so.0"); -#endif - if (ptr_gtk && ptr_glib) { -#ifdef DEBUG - puts("selected GTK-2\n"); -#endif - } - else {// Try then with GTK3 - ptr_gtk = fl_dlopen("libgtk-3.so", "libgtk-3.so.0"); -#ifdef DEBUG - if (ptr_gtk && ptr_glib) { - puts("selected GTK-3\n"); - } -#endif - } - - if((!ptr_glib) || (!ptr_gtk)) { -#ifdef DEBUG - puts("Failure to load libglib or libgtk"); -#endif + void *ptr_gtk; + if ( !Fl_X11_System_Driver::probe_for_GTK(2, 4, &ptr_gtk)) { did_find_GTK_libs = 0; return; } - + void *ptr_glib = ptr_gtk; char *pc_dl_error; // used to report errors by the GET_SYM macro... // items we need from GLib GET_SYM(g_free, ptr_glib); @@ -759,7 +714,6 @@ void Fl_GTK_Native_File_Chooser_Driver::probe_for_GTK_libs(void) { GET_SYM(g_slist_length, ptr_glib); GET_SYM(g_slist_free, ptr_glib); // items we need from GTK - GET_SYM(gtk_init_check, ptr_gtk); GET_SYM(gtk_widget_destroy, ptr_gtk); GET_SYM(gtk_file_chooser_set_select_multiple, ptr_gtk); GET_SYM(gtk_file_chooser_set_do_overwrite_confirmation, ptr_gtk); @@ -784,7 +738,9 @@ void Fl_GTK_Native_File_Chooser_Driver::probe_for_GTK_libs(void) { GET_SYM(gtk_file_chooser_set_extra_widget, ptr_gtk); GET_SYM(gtk_widget_show_now, ptr_gtk); GET_SYM(gtk_widget_get_window, ptr_gtk); - GET_SYM(gdk_x11_drawable_get_xid, ptr_gtk); + fl_gdk_to_X11 = (gdk_to_X11_t)dlsym(ptr_gtk, "gdk_x11_drawable_get_xid"); + if (!fl_gdk_to_X11) fl_gdk_to_X11 = (gdk_to_X11_t)dlsym(ptr_gtk, "gdk_x11_window_get_xid"); + if (!fl_gdk_to_X11) { did_find_GTK_libs = 0; return; } GET_SYM(gtk_check_button_new_with_label, ptr_gtk); GET_SYM(g_signal_connect_data, ptr_gtk); GET_SYM(gtk_toggle_button_get_active, ptr_gtk); diff --git a/src/drivers/Posix/Fl_Posix_Printer_Driver.cxx b/src/drivers/Posix/Fl_Posix_Printer_Driver.cxx index 835529be1..926f1b3d6 100644 --- a/src/drivers/Posix/Fl_Posix_Printer_Driver.cxx +++ b/src/drivers/Posix/Fl_Posix_Printer_Driver.cxx @@ -31,8 +31,188 @@ class Fl_Posix_Printer_Driver : public Fl_PostScript_File_Device { virtual int begin_job(int pagecount, int *frompage = NULL, int *topage = NULL); }; +#if HAVE_DLSYM && HAVE_DLFCN_H +// GTK types +#include <dlfcn.h> // for dlopen et al +#include <unistd.h> // for mkstemp +#include <FL/filename.H> +#include "../X11/Fl_X11_System_Driver.H" +#define GTK_PAPER_NAME_LETTER "na_letter" +#define GTK_RESPONSE_NONE 0 +#define GTK_RESPONSE_OK -5 +#define GTK_PRINT_PAGES_RANGES 2 +class Fl_GTK_Printer_Driver : public Fl_PostScript_File_Device { +public: + typedef int gboolean; + typedef struct _GtkPrintUnixDialog GtkPrintUnixDialog; + typedef struct _GtkDialog GtkDialog; + typedef struct _GtkPrintSettings GtkPrintSettings; + typedef struct _GtkPageSetup GtkPageSetup; + enum GtkPageOrientation {GTK_PAGE_ORIENTATION_PORTRAIT, GTK_PAGE_ORIENTATION_LANDSCAPE}; + typedef struct _GtkPaperSize GtkPaperSize; + typedef struct _GtkPrinter GtkPrinter; + typedef struct _GtkPrintJob GtkPrintJob; + typedef struct _GtkWidget GtkWidget; + struct GError; + + GtkPrintJob *pjob; // data shared between begin_job() and end_job() + char tmpfilename[50]; // name of temporary PostScript file containing to-be-printed data + virtual int begin_job(int pagecount, int *frompage = NULL, int *topage = NULL); + virtual void end_job(); + static bool probe_for_GTK(); + static void *ptr_gtk; // points to the GTK dynamic lib or NULL + + typedef GtkPrintUnixDialog* (*gtk_print_unix_dialog_new_t)(const char*, void*); + typedef int (*gtk_dialog_run_t)(GtkDialog*); + typedef GtkPrintSettings *(*gtk_print_unix_dialog_get_settings_t)(GtkPrintUnixDialog*); + typedef void (*gtk_print_unix_dialog_set_settings_t)(GtkPrintUnixDialog*, GtkPrintSettings*); + typedef GtkPageSetup *(*gtk_print_unix_dialog_get_page_setup_t)(GtkPrintUnixDialog*); + typedef GtkPageOrientation (*gtk_page_setup_get_orientation_t)(GtkPageSetup*); + typedef GtkPaperSize* (*gtk_page_setup_get_paper_size_t)(GtkPageSetup*); + typedef const char * (*gtk_paper_size_get_name_t)(GtkPaperSize*); + typedef GtkPrinter * (*gtk_print_unix_dialog_get_selected_printer_t)(GtkPrintUnixDialog*); + typedef int (*gtk_printer_accepts_ps_t)(GtkPrinter*); + typedef int (*gtk_printer_is_active_t)(GtkPrinter*); + typedef GtkPrintJob *(*gtk_print_job_new_t)(const char *, GtkPrinter *, GtkPrintSettings *, GtkPageSetup *); + typedef void (*gtk_widget_hide_t)(GtkWidget*); + typedef void (*gtk_widget_destroy_t)(GtkWidget*); + typedef gboolean (*gtk_events_pending_t)(void); + typedef void (*gtk_main_iteration_t)(void); + typedef int (*gtk_print_job_set_source_file_t)(GtkPrintJob *job, const char *filename, GError **error); + typedef void (*gtk_print_job_send_t)(GtkPrintJob *, void* , gboolean* , void* ); + typedef void (*gtk_print_settings_set_t) (GtkPrintSettings *settings, const char *key, const char *value); + typedef const char * (*gtk_print_settings_get_t) (GtkPrintSettings *settings, const char *key ); + typedef int (*gtk_print_settings_get_print_pages_t)(GtkPrintSettings*); + struct GtkPageRange { int start, end; }; + typedef GtkPageRange* (*gtk_print_settings_get_page_ranges_t)(GtkPrintSettings*, int*); + typedef void (*g_object_unref_t)(void* object); +}; + +// the CALL_GTK macro produces the source code to call a GTK function given its name +// or to get a pointer to this function : +// CALL_GTK(gtk_my_function) produces ((gtk_my_function_t)dlsym(ptr_gtk, "gtk_my_function")) +#define CALL_GTK(NAME) ((NAME##_t)dlsym(ptr_gtk, #NAME)) + +void *Fl_GTK_Printer_Driver::ptr_gtk = NULL; + +// test wether GTK is available at run-time +bool Fl_GTK_Printer_Driver::probe_for_GTK() { + return Fl_X11_System_Driver::probe_for_GTK(2, 10, &ptr_gtk); +} + + +int Fl_GTK_Printer_Driver::begin_job(int pagecount, int *firstpage, int *lastpage) { + enum Fl_Paged_Device::Page_Format format = Fl_Paged_Device::A4; + enum Fl_Paged_Device::Page_Layout layout = Fl_Paged_Device::PORTRAIT ; + + GtkPrintUnixDialog *pdialog = CALL_GTK(gtk_print_unix_dialog_new)(Fl_Printer::dialog_title, NULL); //2.10 + GtkPrintSettings *psettings = CALL_GTK(gtk_print_unix_dialog_get_settings)(pdialog); //2.10 + CALL_GTK(gtk_print_settings_set)(psettings, "output-file-format", "ps"); //2.10 + char line[FL_PATH_MAX + 20], cwd[FL_PATH_MAX]; + sprintf(line, "file://%s/FLTK.ps", fl_getcwd(cwd, FL_PATH_MAX)); + CALL_GTK(gtk_print_settings_set)(psettings, "output-uri", line); //2.10 + CALL_GTK(gtk_print_unix_dialog_set_settings)(pdialog, psettings); //2.10 + CALL_GTK(g_object_unref)(psettings); + int response_id = CALL_GTK(gtk_dialog_run)((GtkDialog*)pdialog); + if (response_id == GTK_RESPONSE_OK) { + GtkPageSetup *psetup = CALL_GTK(gtk_print_unix_dialog_get_page_setup)(pdialog); //2.10 + GtkPageOrientation orient = CALL_GTK(gtk_page_setup_get_orientation)(psetup); //2.10 + if (orient == GTK_PAGE_ORIENTATION_LANDSCAPE) layout = Fl_Paged_Device::LANDSCAPE; + GtkPaperSize* psize = CALL_GTK(gtk_page_setup_get_paper_size)(psetup); //2.10 + const char *pname = CALL_GTK(gtk_paper_size_get_name)(psize); //2.10 + if (strcmp(pname, GTK_PAPER_NAME_LETTER) == 0) format = Fl_Paged_Device::LETTER; + GtkPrinter *gprinter = CALL_GTK(gtk_print_unix_dialog_get_selected_printer)(pdialog); //2.10 + psettings = CALL_GTK(gtk_print_unix_dialog_get_settings)(pdialog); //2.10 + const char* p = CALL_GTK(gtk_print_settings_get)(psettings, "output-uri"); //2.10 + bool printing_to_file = (p != NULL); + if (printing_to_file) { + p += 6; // skip "file://" prefix + strcpy(line, p); + int l = strlen(p); + if (strcmp(p+l-4, "/.ps") == 0) { + line[l-3] = 0; + strcat(line, "FLTK.ps"); + } + } + if (firstpage && lastpage) { + *firstpage = 1; *lastpage = pagecount; + if (CALL_GTK(gtk_print_settings_get_print_pages)(psettings) == GTK_PRINT_PAGES_RANGES) { // 2.10 + int num_ranges; + GtkPageRange *ranges = CALL_GTK(gtk_print_settings_get_page_ranges)(psettings, &num_ranges); //2.10 + if (num_ranges > 0) { + *firstpage = ranges[0].start + 1; + *lastpage = ranges[0].end + 1; + free(ranges); + } + } + } + response_id = GTK_RESPONSE_NONE; + if (printing_to_file) { + pjob = NULL; + FILE *output = fopen(line, "w"); + if (output) { + Fl_PostScript_File_Device::begin_job(output, 0, format, layout); + response_id = GTK_RESPONSE_OK; + } + } else if ( CALL_GTK(gtk_printer_accepts_ps)(gprinter) && //2.10 + CALL_GTK(gtk_printer_is_active)(gprinter) ) { // 2.10 + strcpy(tmpfilename, "/tmp/FLTKprintjobXXXXXX"); + int fd = mkstemp(tmpfilename); + if (fd >= 0) { + FILE *output = fdopen(fd, "w"); + Fl_PostScript_File_Device::begin_job(output, 0, format, layout); + pjob = CALL_GTK(gtk_print_job_new)("FLTK print job", gprinter, psettings, psetup); //2.10 + response_id = GTK_RESPONSE_OK; + } + } + CALL_GTK(g_object_unref)(psettings); + } + CALL_GTK(gtk_widget_hide)((GtkWidget*)pdialog); + gtk_events_pending_t fl_gtk_events_pending = CALL_GTK(gtk_events_pending); + gtk_main_iteration_t fl_gtk_main_iteration = CALL_GTK(gtk_main_iteration); + while (fl_gtk_events_pending()) fl_gtk_main_iteration(); + CALL_GTK(gtk_widget_destroy)((GtkWidget*)pdialog); + Fl_Window *first = Fl::first_window(); + if (first) { + Fl_Surface_Device::push_current(Fl_Display_Device::display_device()); + first->show(); + while (Fl::ready()) Fl::check(); + Fl_Surface_Device::pop_current(); + } + return (response_id == GTK_RESPONSE_OK ? 0 : 1); +} + +static void pJobCompleteFunc(Fl_GTK_Printer_Driver::GtkPrintJob *print_job, Fl_GTK_Printer_Driver::gboolean *user_data, const Fl_GTK_Printer_Driver::GError *error) { + *user_data = true; +} +static void pDestroyNotify(void* data) {} + +void Fl_GTK_Printer_Driver::end_job() { + Fl_PostScript_File_Device::end_job(); + Fl_PostScript_Graphics_Driver *psgd = driver(); + fclose(psgd->output); + if (!pjob) return; + GError *gerr; + gboolean gb = CALL_GTK(gtk_print_job_set_source_file)(pjob, tmpfilename, &gerr); //2.10 + if (gb) { + gb = false; + CALL_GTK(gtk_print_job_send)(pjob, (void*)pJobCompleteFunc, &gb, (void*)pDestroyNotify); //2.10 + gtk_main_iteration_t fl_gtk_main_iteration = CALL_GTK(gtk_main_iteration); + while (!gb) { + fl_gtk_main_iteration(); + } + } + fl_unlink(tmpfilename); +} +#endif // HAVE_DLSYM && HAVE_DLFCN_H + + Fl_Paged_Device* Fl_Printer::newPrinterDriver(void) { +#if HAVE_DLSYM && HAVE_DLFCN_H + static bool gtk = ( Fl::option(Fl::OPTION_PRINTER_USES_GTK) ? Fl_GTK_Printer_Driver::probe_for_GTK() : false); + if (gtk) return new Fl_GTK_Printer_Driver(); +#endif return new Fl_Posix_Printer_Driver(); } diff --git a/src/drivers/X11/Fl_X11_System_Driver.H b/src/drivers/X11/Fl_X11_System_Driver.H index b7d6e9ff7..138959d75 100644 --- a/src/drivers/X11/Fl_X11_System_Driver.H +++ b/src/drivers/X11/Fl_X11_System_Driver.H @@ -20,6 +20,7 @@ #ifndef FL_X11_SYSTEM_DRIVER_H #define FL_X11_SYSTEM_DRIVER_H +#include "../../config_lib.h" #include "../Posix/Fl_Posix_System_Driver.H" class Fl_X11_System_Driver : public Fl_Posix_System_Driver { @@ -63,6 +64,9 @@ public: virtual void add_fd(int fd, Fl_FD_Handler cb, void* = 0); virtual void remove_fd(int, int when); virtual void remove_fd(int); +#if HAVE_DLSYM && HAVE_DLFCN_H + static bool probe_for_GTK(int major, int minor, void **ptr_gtk); +#endif }; #endif /* FL_X11_SYSTEM_DRIVER_H */ diff --git a/src/drivers/X11/Fl_X11_System_Driver.cxx b/src/drivers/X11/Fl_X11_System_Driver.cxx index 42d403299..f406dce02 100644 --- a/src/drivers/X11/Fl_X11_System_Driver.cxx +++ b/src/drivers/X11/Fl_X11_System_Driver.cxx @@ -517,6 +517,63 @@ int Fl_X11_System_Driver::utf8locale() { return ret; } +#if HAVE_DLSYM && HAVE_DLFCN_H +#include <dlfcn.h> // for dlopen et al + +static void* fl_dlopen(const char *filename1, const char *filename2) +{ + void *ptr = dlopen(filename1, RTLD_LAZY | RTLD_GLOBAL); + if (!ptr) ptr = dlopen(filename2, RTLD_LAZY | RTLD_GLOBAL); + return ptr; +} + +bool Fl_X11_System_Driver::probe_for_GTK(int major, int minor, void **ptr_gtk) { + typedef void (*init_t)(int*, void*); + *ptr_gtk = NULL; + // was GTK previously loaded? + init_t init_f = (init_t)dlsym(RTLD_DEFAULT, "gtk_init_check"); + if (init_f) { // yes it was. + *ptr_gtk = RTLD_DEFAULT; // Caution: NULL under linux, not-NULL under Darwin + } else { + // Try first with GTK3 + *ptr_gtk = fl_dlopen("libgtk-3.so", "libgtk-3.so.0"); + if (*ptr_gtk) { +#ifdef DEBUG + puts("selected GTK-3\n"); +#endif + } else { + // Try then with GTK2 +# ifdef __APPLE_CC__ // allows testing on Darwin + X11 + *ptr_gtk = ::dlopen("/sw/lib/libgtk-x11-2.0.dylib", RTLD_LAZY | RTLD_GLOBAL); +#else + *ptr_gtk = fl_dlopen("libgtk-x11-2.0.so", "libgtk-x11-2.0.so.0"); +#endif + } + if (*ptr_gtk) { +#ifdef DEBUG + puts("selected GTK-2\n"); +#endif + } else { +#ifdef DEBUG + puts("Failure to load libgtk"); +#endif + return false; + } + init_f = (init_t)dlsym(*ptr_gtk, "gtk_init_check"); + if (!init_f) return false; + } + int ac = 0; + init_f(&ac, NULL); + // now check if running version is high enough + if (dlsym(*ptr_gtk, "gtk_get_major_version") == NULL) { // YES indicates V 3 + typedef const char* (*check_t)(int, int, int); + check_t check_f = (check_t)dlsym(*ptr_gtk, "gtk_check_version"); + if (!check_f || check_f(major, minor, 0) ) return false; + } + return true; +} +#endif // HAVE_DLSYM && HAVE_DLFCN_H + #if !defined(FL_DOXYGEN) const char *Fl_X11_System_Driver::shortcut_add_key_name(unsigned key, char *p, char *buf, const char **eom) |
