From 682f95079691dd9c9b0677cb66e727397f910e0d Mon Sep 17 00:00:00 2001 From: Manolo Gouy Date: Fri, 26 Feb 2016 12:51:47 +0000 Subject: Create class Fl_Widget_Surface that supports draw(Fl_Widget *, int, int). This simplifies the implementation of Fl_Copy_Surface and Fl_Image_Surface which now are made to derive from Fl_Widget_Surface. git-svn-id: file:///fltk/svn/fltk/branches/branch-1.3-porting@11220 ea41ed52-d2ee-0310-a9c1-e6b18d33e121 --- src/CMakeLists.txt | 2 + src/Fl_Copy_Surface.cxx | 229 ++++----------------- src/Fl_Image_Surface.cxx | 68 +++--- src/Fl_Paged_Device.cxx | 194 ----------------- src/Fl_Printer.cxx | 8 +- src/Fl_Widget_Surface.cxx | 210 +++++++++++++++++++ src/Fl_cocoa.mm | 2 +- src/Makefile | 2 + src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx | 13 ++ src/drivers/GDI/Fl_GDI_Graphics_Driver.h | 9 + .../Xlib/Fl_Translated_Xlib_Graphics_Driver.H | 75 +++++++ .../Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx | 202 ++++++++++++++++++ 12 files changed, 589 insertions(+), 425 deletions(-) create mode 100644 src/Fl_Widget_Surface.cxx create mode 100644 src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H create mode 100644 src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 789331067..827394b5e 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -78,6 +78,7 @@ set(CPPFILES Fl_Value_Output.cxx Fl_Value_Slider.cxx Fl_Widget.cxx + Fl_Widget_Surface.cxx Fl_Window.cxx Fl_Window_Driver.cxx Fl_Window_fullscreen.cxx @@ -178,6 +179,7 @@ if (USE_X11) drivers/Xlib/Fl_Xlib_Graphics_Driver_line_style.cxx drivers/Xlib/Fl_Xlib_Graphics_Driver_rect.cxx drivers/Xlib/Fl_Xlib_Graphics_Driver_vertex.cxx + drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx ) if (USE_XFT) set(DRIVER_FILES ${DRIVER_FILES} diff --git a/src/Fl_Copy_Surface.cxx b/src/Fl_Copy_Surface.cxx index 1837e08ac..f05c6edc8 100644 --- a/src/Fl_Copy_Surface.cxx +++ b/src/Fl_Copy_Surface.cxx @@ -19,45 +19,23 @@ #include "config_lib.h" #include #include +#ifdef FL_CFG_GFX_QUARTZ +#include "drivers/Quartz/Fl_Quartz_Graphics_Driver.h" +#endif +#ifdef FL_CFG_GFX_XLIB +#include "drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H" +#endif +#ifdef FL_CFG_GFX_GDI +#include "drivers/GDI/Fl_GDI_Graphics_Driver.h" +#endif #if defined(__APPLE__) // PORTME: Fl_Surface_Driver - platform copy surface -#include - -Fl_Quartz_Surface_::Fl_Quartz_Surface_(int w, int h) : Fl_System_Printer(), width(w), height(h) { -} - -int Fl_Quartz_Surface_::printable_rect(int *w, int *h) { - *w = width; - *h = height; - return 0; -} - #elif defined(WIN32) -#include "drivers/GDI/Fl_GDI_Graphics_Driver.h" - -Fl_GDI_Surface_::Fl_GDI_Surface_() : Fl_Paged_Device() { - driver(new Fl_GDI_Graphics_Driver); - depth = 0; -} - -Fl_GDI_Surface_::~Fl_GDI_Surface_() { - delete driver(); -} - -void Fl_GDI_Surface_::translate(int x, int y) { - GetWindowOrgEx((HDC)driver()->gc(), origins+depth); - SetWindowOrgEx((HDC)driver()->gc(), origins[depth].x - x, origins[depth].y - y, NULL); - if (depth < sizeof(origins)/sizeof(POINT)) depth++; - else Fl::warning("Fl_GDI_Surface_: translate stack overflow!"); -} -void Fl_GDI_Surface_::untranslate() { - if (depth > 0) depth--; - SetWindowOrgEx((HDC)driver()->gc(), origins[depth].x, origins[depth].y, NULL); -} +#else #endif @@ -66,17 +44,15 @@ void Fl_GDI_Surface_::untranslate() { \param w and \param h are the width and height of the clipboard surface in pixels where drawing will occur. */ -Fl_Copy_Surface::Fl_Copy_Surface(int w, int h) : Fl_Surface_Device(NULL) +Fl_Copy_Surface::Fl_Copy_Surface(int w, int h) : Fl_Widget_Surface(NULL) { width = w; height = h; #ifdef __APPLE__ // PORTME: Fl_Surface_Driver - platform copy surface - helper = new Fl_Quartz_Surface_(width, height); - driver(helper->driver()); + driver(new Fl_Quartz_Graphics_Driver); prepare_copy_pdf_and_tiff(w, h); #elif defined(WIN32) - helper = new Fl_GDI_Surface_(); - driver(helper->driver()); + driver(new Fl_Translated_GDI_Graphics_Driver); oldgc = (HDC)Fl_Surface_Device::surface()->driver()->gc(); // exact computation of factor from screen units to EnhMetaFile units (0.01 mm) HDC hdc = GetDC(NULL); @@ -97,8 +73,7 @@ Fl_Copy_Surface::Fl_Copy_Surface(int w, int h) : Fl_Surface_Device(NULL) #elif defined(FL_PORTING) # pragma message "FL_PORTING: initialize members of Fl_Copy_Surface" #else // Xlib - helper = new Fl_Xlib_Surface_(); - driver(helper->driver()); + driver(new Fl_Translated_Xlib_Graphics_Driver()); Fl::first_window()->make_current(); oldwindow = fl_xid(Fl::first_window()); xid = fl_create_offscreen(w,h); @@ -116,7 +91,6 @@ Fl_Copy_Surface::~Fl_Copy_Surface() { #ifdef __APPLE__ // PORTME: Fl_Surface_Driver - platform copy surface complete_copy_pdf_and_tiff(); - delete (Fl_Quartz_Surface_*)helper; #elif defined(WIN32) if (oldgc == (HDC)Fl_Surface_Device::surface()->driver()->gc()) oldgc = NULL; HENHMETAFILE hmf = CloseEnhMetaFile (gc); @@ -130,7 +104,6 @@ Fl_Copy_Surface::~Fl_Copy_Surface() } DeleteDC(gc); Fl_Surface_Device::surface()->driver()->gc(oldgc); - delete (Fl_GDI_Surface_*)helper; #elif defined(FL_PORTING) # pragma message "FL_PORTING: free resources in destructor of Fl_Copy_Surface" #else // Xlib @@ -141,20 +114,9 @@ Fl_Copy_Surface::~Fl_Copy_Surface() Fl::copy_image(data,width,height,1); delete[] data; fl_delete_offscreen(xid); - delete (Fl_Xlib_Surface_*)helper; #endif } -/** Copies a widget in the clipboard - - \param widget any FLTK widget (e.g., standard, custom, window, GL view) to copy - \param delta_x and \param delta_y give - the position in the clipboard of the top-left corner of the widget - */ -void Fl_Copy_Surface::draw(Fl_Widget* widget, int delta_x, int delta_y) -{ - helper->print_widget(widget, delta_x, delta_y); -} void Fl_Copy_Surface::set_current() { @@ -211,157 +173,38 @@ void Fl_Copy_Surface::prepare_copy_pdf_and_tiff(int w, int h) CGContextSaveGState(gc); } -#endif // __APPLE__ // PORTME: Fl_Surface_Driver - platform copy surface - - -/** Copies a window and its borders and title bar to the clipboard. - \param win an FLTK window to copy - \param delta_x and \param delta_y give - the position in the clipboard of the top-left corner of the window's title bar -*/ -void Fl_Copy_Surface::draw_decorated_window(Fl_Window* win, int delta_x, int delta_y) -{ - helper->draw_decorated_window(win, delta_x, delta_y); +void Fl_Copy_Surface::translate(int x, int y) { + CGContextRef gc = (CGContextRef)driver()->gc(); + CGContextRestoreGState(gc); + CGContextSaveGState(gc); + CGContextTranslateCTM(gc, x, y); + CGContextSaveGState(gc); } -#if defined(WIN32) -#elif defined(__APPLE__) // PORTME: Fl_Graphics_Driver - platform copy surface -#elif defined(FL_PORTING) -# pragma message "FL_PORTING: do you need a helper class for your graphics driver" -#elif !defined(FL_DOXYGEN) - -#include "drivers/Xlib/Fl_Xlib_Graphics_Driver.h" - -/* graphics driver that translates all graphics coordinates before calling Xlib */ -class Fl_translated_Xlib_Graphics_Driver_ : public Fl_Xlib_Graphics_Driver { - int offset_x, offset_y; // translation between user and graphical coordinates: graphical = user + offset - unsigned depth; // depth of translation stack - int stack_x[20], stack_y[20]; // translation stack allowing cumulative translations -public: - Fl_translated_Xlib_Graphics_Driver_() { - offset_x = 0; offset_y = 0; - depth = 0; - } - virtual ~Fl_translated_Xlib_Graphics_Driver_() {}; - void translate_all(int dx, int dy) { // reversibly adds dx,dy to the offset between user and graphical coordinates - stack_x[depth] = offset_x; - stack_y[depth] = offset_y; - offset_x = stack_x[depth] + dx; - offset_y = stack_y[depth] + dy; - push_matrix(); - translate(dx, dy); - if (depth < sizeof(stack_x)/sizeof(int)) depth++; - else Fl::warning("%s: translate stack overflow!", "Fl_translated_Xlib_Graphics_Driver_"); - } - void untranslate_all() { // undoes previous translate_all() - if (depth > 0) depth--; - offset_x = stack_x[depth]; - offset_y = stack_y[depth]; - pop_matrix(); - } - void rect(int x, int y, int w, int h) { Fl_Xlib_Graphics_Driver::rect(x+offset_x, y+offset_y, w, h); } - void rectf(int x, int y, int w, int h) { Fl_Xlib_Graphics_Driver::rectf(x+offset_x, y+offset_y, w, h); } - void xyline(int x, int y, int x1) { Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x); } - void xyline(int x, int y, int x1, int y2) { Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x, y2+offset_y); } - void xyline(int x, int y, int x1, int y2, int x3) { Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x, y2+offset_y, x3+offset_x); } - void yxline(int x, int y, int y1) { Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y); } - void yxline(int x, int y, int y1, int x2) { Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y, x2+offset_x); } - void yxline(int x, int y, int y1, int x2, int y3) { Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y, x2+offset_x, y3+offset_y); } - void line(int x, int y, int x1, int y1) { Fl_Xlib_Graphics_Driver::line(x+offset_x, y+offset_y, x1+offset_x, y1+offset_y); } - void line(int x, int y, int x1, int y1, int x2, int y2) { Fl_Xlib_Graphics_Driver::line(x+offset_x, y+offset_y, x1+offset_x, y1+offset_y, x2+offset_x, y2+offset_y); } - void draw(const char* str, int n, int x, int y) { - Fl_Xlib_Graphics_Driver::draw(str, n, x+offset_x, y+offset_y); - } - void draw(int angle, const char *str, int n, int x, int y) { - Fl_Xlib_Graphics_Driver::draw(angle, str, n, x+offset_x, y+offset_y); - } - void rtl_draw(const char* str, int n, int x, int y) { - Fl_Xlib_Graphics_Driver::rtl_draw(str, n, x+offset_x, y+offset_y); - } - void draw(Fl_Pixmap *pxm, int XP, int YP, int WP, int HP, int cx, int cy) { - XP += offset_x; YP += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw(pxm, XP, YP, WP,HP,cx,cy); - untranslate_all(); - } - void draw(Fl_Bitmap *bm, int XP, int YP, int WP, int HP, int cx, int cy) { - XP += offset_x; YP += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw(bm, XP, YP, WP,HP,cx,cy); - untranslate_all(); - } - void draw(Fl_RGB_Image *img, int XP, int YP, int WP, int HP, int cx, int cy) { - XP += offset_x; YP += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw(img, XP, YP, WP,HP,cx,cy); - untranslate_all(); - } - void draw_image(const uchar* buf, int X,int Y,int W,int H, int D=3, int L=0) { - X += offset_x; Y += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw_image(buf, X, Y, W,H,D,L); - untranslate_all(); - } - void draw_image(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D=3) { - X += offset_x; Y += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw_image(cb, data, X, Y, W,H,D); - untranslate_all(); - } - void draw_image_mono(const uchar* buf, int X,int Y,int W,int H, int D=1, int L=0) { - X += offset_x; Y += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw_image_mono(buf, X, Y, W,H,D,L); - untranslate_all(); - } - void draw_image_mono(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D=1) { - X += offset_x; Y += offset_y; - translate_all(-offset_x, -offset_y); - Fl_Xlib_Graphics_Driver::draw_image_mono(cb, data, X, Y, W,H,D); - untranslate_all(); - } - void copy_offscreen(int x, int y, int w, int h, Fl_Offscreen pixmap, int srcx, int srcy) { - Fl_Xlib_Graphics_Driver::copy_offscreen(x+offset_x, y+offset_y, w, h,pixmap,srcx,srcy); - } - void push_clip(int x, int y, int w, int h) { - Fl_Xlib_Graphics_Driver::push_clip(x+offset_x, y+offset_y, w, h); - } - int not_clipped(int x, int y, int w, int h) { return Fl_Xlib_Graphics_Driver::not_clipped(x + offset_x, y + offset_y, w, h); }; - int clip_box(int x, int y, int w, int h, int& X, int& Y, int& W, int& H) { - int retval = Fl_Xlib_Graphics_Driver::clip_box(x + offset_x, y + offset_y, w,h,X,Y,W,H); - X -= offset_x; - Y -= offset_y; - return retval; - } - void pie(int x, int y, int w, int h, double a1, double a2) { Fl_Xlib_Graphics_Driver::pie(x+offset_x,y+offset_y,w,h,a1,a2); } - void arc(int x, int y, int w, int h, double a1, double a2) { Fl_Xlib_Graphics_Driver::arc(x+offset_x,y+offset_y,w,h,a1,a2); } - void polygon(int x0, int y0, int x1, int y1, int x2, int y2) { Fl_Xlib_Graphics_Driver::polygon(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y);} - void polygon(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3) { - Fl_Xlib_Graphics_Driver::polygon(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y,x3+offset_x,y3+offset_y); - } - void loop(int x0, int y0, int x1, int y1, int x2, int y2) {Fl_Xlib_Graphics_Driver::loop(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y);} - void loop(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3) { - Fl_Xlib_Graphics_Driver::loop(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y,x3+offset_x,y3+offset_y); - } - void point(int x, int y) { Fl_Xlib_Graphics_Driver::point(x+offset_x, y+offset_y); } -}; +void Fl_Copy_Surface::untranslate() { + CGContextRestoreGState((CGContextRef)driver()->gc()); +} +#elif defined(WIN32) -void Fl_Xlib_Surface_::translate(int x, int y) { - ((Fl_translated_Xlib_Graphics_Driver_*)driver())->translate_all(x, y); +void Fl_Copy_Surface::translate(int x, int y) { + ((Fl_Translated_GDI_Graphics_Driver*)driver())->translate_all(x, y); } -void Fl_Xlib_Surface_::untranslate() { - ((Fl_translated_Xlib_Graphics_Driver_*)driver())->untranslate_all(); + +void Fl_Copy_Surface::untranslate() { + ((Fl_Translated_GDI_Graphics_Driver*)driver())->untranslate_all(); } -Fl_Xlib_Surface_::Fl_Xlib_Surface_() : Fl_Paged_Device() { - driver(new Fl_translated_Xlib_Graphics_Driver_()); +#else +void Fl_Copy_Surface::translate(int x, int y) { + ((Fl_Translated_Xlib_Graphics_Driver*)driver())->translate_all(x, y); } -Fl_Xlib_Surface_::~Fl_Xlib_Surface_() { - delete driver(); + +void Fl_Copy_Surface::untranslate() { + ((Fl_Translated_Xlib_Graphics_Driver*)driver())->untranslate_all(); } -#endif +#endif // __APPLE__ // PORTME: Fl_Surface_Driver - platform copy surface // // End of "$Id$". diff --git a/src/Fl_Image_Surface.cxx b/src/Fl_Image_Surface.cxx index ea1d372e8..5aee95991 100644 --- a/src/Fl_Image_Surface.cxx +++ b/src/Fl_Image_Surface.cxx @@ -24,6 +24,12 @@ #ifdef FL_CFG_GFX_QUARTZ #include "drivers/Quartz/Fl_Quartz_Graphics_Driver.h" #endif +#ifdef FL_CFG_GFX_GDI +#include "drivers/GDI/Fl_GDI_Graphics_Driver.h" +#endif +#ifdef FL_CFG_GFX_XLIB +#include "drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H" +#endif #if defined(WIN32) #elif defined(__APPLE__) // PORTME: Fl_Surface_Driver - platform image surface @@ -40,16 +46,15 @@ If \p highres is non-zero, use Fl_Image_Surface::highres_image() to get the image data. \version 1.3.4 (1.3.3 without the highres parameter) */ -Fl_Image_Surface::Fl_Image_Surface(int w, int h, int highres) : Fl_Surface_Device(NULL) { +Fl_Image_Surface::Fl_Image_Surface(int w, int h, int highres) : Fl_Widget_Surface(NULL) { width = w; height = h; #ifdef __APPLE__ // PORTME: platform image surface offscreen = fl_create_offscreen(highres ? 2*w : w, highres ? 2*h : h); - helper = new Fl_Quartz_Flipped_Surface_(width, height); + driver(new Fl_Quartz_Graphics_Driver); if (highres) { CGContextScaleCTM(offscreen, 2, 2); } - driver(helper->driver()); CGContextSetShouldAntialias(offscreen, false); CGContextSaveGState(offscreen); CGContextTranslateCTM(offscreen, 0, height); @@ -58,14 +63,12 @@ Fl_Image_Surface::Fl_Image_Surface(int w, int h, int highres) : Fl_Surface_Devic CGContextFillRect(offscreen, CGRectMake(0,0,w,h)); #elif defined(WIN32) offscreen = fl_create_offscreen(w, h); - helper = new Fl_GDI_Surface_(); - driver(helper->driver()); + driver(new Fl_Translated_GDI_Graphics_Driver); #elif defined(FL_PORTING) # pragma message "FL_PORTING: implement Fl_Image_Surface" #else offscreen = fl_create_offscreen(w, h); - helper = new Fl_Xlib_Surface_(); - driver(helper->driver()); + driver(new Fl_Translated_Xlib_Graphics_Driver()); #endif } @@ -76,15 +79,12 @@ Fl_Image_Surface::~Fl_Image_Surface() { void *data = CGBitmapContextGetData((CGContextRef)offscreen); free(data); CGContextRelease((CGContextRef)offscreen); - delete (Fl_Quartz_Flipped_Surface_*)helper; #elif defined(WIN32) fl_delete_offscreen(offscreen); - delete (Fl_GDI_Surface_*)helper; #elif defined(FL_PORTING) # pragma message "FL_PORTING: implement Fl_Image_Surface" #else fl_delete_offscreen(offscreen); - delete (Fl_Xlib_Surface_*)helper; #endif } @@ -139,18 +139,6 @@ Fl_Shared_Image* Fl_Image_Surface::highres_image() } -/** Draws a widget in the image surface - - \param widget any FLTK widget (e.g., standard, custom, window, GL view) to draw in the image - \param delta_x and \param delta_y give - the position in the image of the top-left corner of the widget - */ -void Fl_Image_Surface::draw(Fl_Widget *widget, int delta_x, int delta_y) -{ - helper->print_widget(widget, delta_x, delta_y); -} - - void Fl_Image_Surface::set_current() { #if defined(__APPLE__) // PORTME: Fl_Surface_Driver - platform image surface @@ -181,10 +169,7 @@ void Fl_Image_Surface::set_current() #if defined(__APPLE__) // PORTME: Fl_Surface_Driver - platform image surface -Fl_Quartz_Flipped_Surface_::Fl_Quartz_Flipped_Surface_(int w, int h) : Fl_Quartz_Surface_(w, h) { -} - -void Fl_Quartz_Flipped_Surface_::translate(int x, int y) { +void Fl_Image_Surface::translate(int x, int y) { CGContextRef gc = (CGContextRef)driver()->gc(); CGContextRestoreGState(gc); CGContextSaveGState(gc); @@ -194,22 +179,33 @@ void Fl_Quartz_Flipped_Surface_::translate(int x, int y) { CGContextScaleCTM(gc, 1.0f, -1.0f); } -void Fl_Quartz_Flipped_Surface_::untranslate() { +void Fl_Image_Surface::untranslate() { CGContextRestoreGState((CGContextRef)driver()->gc()); } -#endif +#elif defined(WIN32) -/** Draws a window and its borders and title bar to the image drawing surface. - \param win an FLTK window to draw in the image - \param delta_x and \param delta_y give - the position in the image of the top-left corner of the window's title bar -*/ -void Fl_Image_Surface::draw_decorated_window(Fl_Window* win, int delta_x, int delta_y) -{ - helper->draw_decorated_window(win, delta_x, delta_y); +void Fl_Image_Surface::translate(int x, int y) { + ((Fl_Translated_GDI_Graphics_Driver*)driver())->translate_all(x, y); } +void Fl_Image_Surface::untranslate() { + ((Fl_Translated_GDI_Graphics_Driver*)driver())->untranslate_all(); +} + +#else + +void Fl_Image_Surface::translate(int x, int y) { + ((Fl_Translated_Xlib_Graphics_Driver*)driver())->translate_all(x, y); +} + +void Fl_Image_Surface::untranslate() { + ((Fl_Translated_Xlib_Graphics_Driver*)driver())->untranslate_all(); +} + +#endif + + // // End of "$Id$". diff --git a/src/Fl_Paged_Device.cxx b/src/Fl_Paged_Device.cxx index 51bedc127..2976d4a55 100644 --- a/src/Fl_Paged_Device.cxx +++ b/src/Fl_Paged_Device.cxx @@ -24,134 +24,7 @@ #include #include -#include "config_lib.h" -#ifdef FL_CFG_GFX_QUARTZ -#include "drivers/Quartz/Fl_Quartz_Graphics_Driver.h" -#endif -/** - @brief Draws the widget on the printed page. - * - The widget's position on the printed page is determined by the last call to origin() - and by the optional delta_x and delta_y arguments. - Its dimensions are in points unless there was a previous call to scale(). - @param[in] widget Any FLTK widget (e.g., standard, custom, window). - @param[in] delta_x Optional horizontal offset for positioning the widget relatively - to the current origin of graphics functions. - @param[in] delta_y Same as above, vertically. - */ -void Fl_Paged_Device::print_widget(Fl_Widget* widget, int delta_x, int delta_y) -{ - int old_x, old_y, new_x, new_y, is_window; - if ( ! widget->visible() ) return; - is_window = (widget->as_window() != NULL); - uchar old_damage = widget->damage(); - widget->damage(FL_DAMAGE_ALL); - // set origin to the desired top-left position of the widget - origin(&old_x, &old_y); - new_x = old_x + delta_x; - new_y = old_y + delta_y; - if (!is_window) { - new_x -= widget->x(); - new_y -= widget->y(); - } - if (new_x != old_x || new_y != old_y) { - translate(new_x - old_x, new_y - old_y ); - } - // if widget is a main window, clip all drawings to the window area - if (is_window && !widget->window()) { - fl_push_clip(0, 0, widget->w(), widget->h() ); -#ifdef __APPLE__ // for Mac OS X 10.6 and above, make window with rounded bottom corners - if ( fl_mac_os_version >= 100600 && driver()->has_feature(Fl_Graphics_Driver::NATIVE) ) { - Fl_X::clip_to_rounded_corners((CGContextRef)driver()->gc(), widget->w(), widget->h()); - } -#endif - } - // we do some trickery to recognize OpenGL windows and draw them via a plugin - int drawn_by_plugin = 0; - if (widget->as_gl_window()) { - Fl_Plugin_Manager pm("fltk:device"); - Fl_Device_Plugin *pi = (Fl_Device_Plugin*)pm.plugin("opengl.device.fltk.org"); - if (pi) { - drawn_by_plugin = pi->print(widget, 0, 0, 0); - } - } - if (!drawn_by_plugin) { - widget->draw(); - } - if (is_window && !widget->window()) fl_pop_clip(); - // find subwindows of widget and print them - traverse(widget); - // reset origin to where it was - if (new_x != old_x || new_y != old_y) { - untranslate(); - } - if ((old_damage & FL_DAMAGE_CHILD) == 0) widget->clear_damage(old_damage); - else widget->damage(FL_DAMAGE_ALL); -} - - -void Fl_Paged_Device::traverse(Fl_Widget *widget) -{ - Fl_Group *g = widget->as_group(); - if (!g) return; - int n = g->children(); - for (int i = 0; i < n; i++) { - Fl_Widget *c = g->child(i); - if ( !c->visible() ) continue; - if ( c->as_window() ) { - print_widget(c, c->x(), c->y()); - } - else traverse(c); - } -} - -/** - @brief Computes the page coordinates of the current origin of graphics functions. - * - @param[out] x If non-null, *x is set to the horizontal page offset of graphics origin. - @param[out] y Same as above, vertically. - */ -void Fl_Paged_Device::origin(int *x, int *y) -{ - if (x) *x = x_offset; - if (y) *y = y_offset; -} - -/** - @brief Prints a rectangular part of an on-screen window. - - @param win The window from where to capture. - @param x The rectangle left - @param y The rectangle top - @param w The rectangle width - @param h The rectangle height - @param delta_x Optional horizontal offset from current graphics origin where to print the captured rectangle. - @param delta_y As above, vertically. - */ -void Fl_Paged_Device::print_window_part(Fl_Window *win, int x, int y, int w, int h, int delta_x, int delta_y) -{ - Fl_Surface_Device *current = Fl_Surface_Device::surface(); - Fl_Display_Device::display_device()->set_current(); - Fl_Window *save_front = Fl::first_window(); - win->show(); - Fl::check(); - win->make_current(); - uchar *image_data; - image_data = fl_read_image(NULL, x, y, w, h); -#ifdef __APPLE__ // PORTME: Fl_Surface_Driver - platform paged device - Fl_X::q_release_context(); // matches make_current() call above -#endif - if (save_front != win) save_front->show(); - current->set_current(); - fl_draw_image(image_data, delta_x, delta_y, w, h, 3); - delete[] image_data; -#ifdef WIN32 - HDC gc = GetDC(fl_xid(win)); - fl_graphics_driver->gc(gc); - ReleaseDC(fl_xid(win), gc); -#endif -} /** @brief Starts a print job. @@ -172,16 +45,6 @@ int Fl_Paged_Device::start_job(int pagecount, int *frompage, int *topage) {retur */ int Fl_Paged_Device::start_page (void) {return 1;} -/** - @brief Computes the width and height of the printable area of the page. - - Values are in the same unit as that used by FLTK drawing functions, - are unchanged by calls to origin(), but are changed by scale() calls. - Values account for the user-selected paper type and print orientation. - @return 0 if OK, non-zero if any error - */ -int Fl_Paged_Device::printable_rect(int *w, int *h) {return 1;} - /** @brief Computes the dimensions of margins that lie between the printable page area and the full page. @@ -195,18 +58,6 @@ int Fl_Paged_Device::printable_rect(int *w, int *h) {return 1;} */ void Fl_Paged_Device::margins(int *left, int *top, int *right, int *bottom) {} -/** - @brief Sets the position in page coordinates of the origin of graphics functions. - - Arguments should be expressed relatively to the result of a previous printable_rect() call. - That is, printable_rect(&w, &h); origin(w/2, 0); sets the graphics origin at the - top center of the page printable area. - Origin() calls are not affected by rotate() calls. - Successive origin() calls don't combine their effects. - @param[in] x Horizontal position in page coordinates of the desired origin of graphics functions. - @param[in] y Same as above, vertically. - */ -void Fl_Paged_Device::origin(int x, int y) {} /** @brief Changes the scaling of page coordinates. @@ -242,19 +93,6 @@ int Fl_Paged_Device::end_page (void) {return 1;} */ void Fl_Paged_Device::end_job (void) {} -/** - @brief Translates the current graphics origin accounting for the current rotation. - - This function is only useful after a rotate() call. - Each translate() call must be matched by an untranslate() call. - Successive translate() calls add up their effects. - */ -void Fl_Paged_Device::translate(int x, int y) {} - -/** - @brief Undoes the effect of a previous translate() call. - */ -void Fl_Paged_Device::untranslate(void) {} const Fl_Paged_Device::page_format Fl_Paged_Device::page_formats[NO_PAGE_FORMATS] = { // order of enum Page_Format @@ -297,38 +135,6 @@ const Fl_Paged_Device::page_format Fl_Paged_Device::page_formats[NO_PAGE_FORMATS { 297, 684, "Env10"} // envelope }; -void Fl_Paged_Device::draw_decorated_window(Fl_Window *win, int x_offset, int y_offset) -{ - Fl_Shared_Image *top, *left, *bottom, *right; - win->capture_titlebar_and_borders(top, left, bottom, right); - int wsides = left ? left->w() : 0; - int toph = top ? top->h() : 0; - if (top) { - top->draw(x_offset, y_offset); - top->release(); - } - if (left) { - left->draw(x_offset, y_offset + toph); - left->release(); - } - if (right) { - right->draw(x_offset + wsides + win->w(), y_offset + toph); - right->release(); - } - if (bottom) { - bottom->draw(x_offset, y_offset + toph + win->h()); - bottom->release(); - } - this->print_widget(win, x_offset + wsides, y_offset + toph); -} - -#if !defined(__APPLE__) // PORTME: Fl_Surface_Driver - platform paged device // Mac OS version in Fl_Cocoa.mm -void Fl_Paged_Device::print_window(Fl_Window *win, int x_offset, int y_offset) -{ - draw_decorated_window(win, x_offset, y_offset); -} -#endif - // // End of "$Id$". // diff --git a/src/Fl_Printer.cxx b/src/Fl_Printer.cxx index 4b559a2d2..bd3ceb05b 100644 --- a/src/Fl_Printer.cxx +++ b/src/Fl_Printer.cxx @@ -209,9 +209,15 @@ void Fl_Printer::end_job (void) void Fl_Printer::print_widget(Fl_Widget* widget, int delta_x, int delta_y) { - printer->print_widget(widget, delta_x, delta_y); + printer->draw(widget, delta_x, delta_y); } +void Fl_Printer::draw_decorated_window(Fl_Window* win, int delta_x, int delta_y) +{ + printer->draw_decorated_window(win, delta_x, delta_y); +} + + void Fl_Printer::print_window_part(Fl_Window *win, int x, int y, int w, int h, int delta_x, int delta_y) { printer->print_window_part(win, x, y, w, h, delta_x, delta_y); diff --git a/src/Fl_Widget_Surface.cxx b/src/Fl_Widget_Surface.cxx new file mode 100644 index 000000000..f99a333fb --- /dev/null +++ b/src/Fl_Widget_Surface.cxx @@ -0,0 +1,210 @@ +// +// "$Id: Fl_Widget_Surface.cxx 11217 2016-02-25 17:56:48Z manolo $" +// +// Drivers code for the Fast Light Tool Kit (FLTK). +// +// Copyright 1998-2016 by Bill Spitzak and others. +// +// This library is free software. Distribution and use rights are outlined in +// the file "COPYING" which should have been included with this file. If this +// file is missing or damaged, see the license at: +// +// http://www.fltk.org/COPYING.php +// +// Please report all bugs and problems on the following page: +// +// http://www.fltk.org/str.php +// + +#include +#include +#include +#include + + +Fl_Widget_Surface::Fl_Widget_Surface(Fl_Graphics_Driver *d) : Fl_Surface_Device(d) { + x_offset = 0; + y_offset = 0; +} + +/** + @brief Draws the widget on the printed page. + * + The widget's position on the printed page is determined by the last call to origin() + and by the optional delta_x and delta_y arguments. + Its dimensions are in points unless there was a previous call to scale(). + @param[in] widget Any FLTK widget (e.g., standard, custom, window). + @param[in] delta_x Optional horizontal offset for positioning the widget relatively + to the current origin of graphics functions. + @param[in] delta_y Same as above, vertically. + */ +void Fl_Widget_Surface::draw(Fl_Widget* widget, int delta_x, int delta_y) +{ + int old_x, old_y, new_x, new_y, is_window; + if ( ! widget->visible() ) return; + is_window = (widget->as_window() != NULL); + uchar old_damage = widget->damage(); + widget->damage(FL_DAMAGE_ALL); + // set origin to the desired top-left position of the widget + origin(&old_x, &old_y); + new_x = old_x + delta_x; + new_y = old_y + delta_y; + if (!is_window) { + new_x -= widget->x(); + new_y -= widget->y(); + } + if (new_x != old_x || new_y != old_y) { + translate(new_x - old_x, new_y - old_y ); + } + // if widget is a main window, clip all drawings to the window area + if (is_window && !widget->window()) { + fl_push_clip(0, 0, widget->w(), widget->h() ); +#ifdef __APPLE__ // for Mac OS X 10.6 and above, make window with rounded bottom corners + if ( fl_mac_os_version >= 100600 && driver()->has_feature(Fl_Graphics_Driver::NATIVE) ) { + Fl_X::clip_to_rounded_corners((CGContextRef)driver()->gc(), widget->w(), widget->h()); + } +#endif + } + // we do some trickery to recognize OpenGL windows and draw them via a plugin + int drawn_by_plugin = 0; + if (widget->as_gl_window()) { + Fl_Plugin_Manager pm("fltk:device"); + Fl_Device_Plugin *pi = (Fl_Device_Plugin*)pm.plugin("opengl.device.fltk.org"); + if (pi) { + drawn_by_plugin = pi->print(widget, 0, 0, 0); + } + } + if (!drawn_by_plugin) { + widget->draw(); + } + if (is_window && !widget->window()) fl_pop_clip(); + // find subwindows of widget and print them + traverse(widget); + // reset origin to where it was + if (new_x != old_x || new_y != old_y) { + untranslate(); + } + if ((old_damage & FL_DAMAGE_CHILD) == 0) widget->clear_damage(old_damage); + else widget->damage(FL_DAMAGE_ALL); +} + + +void Fl_Widget_Surface::traverse(Fl_Widget *widget) +{ + Fl_Group *g = widget->as_group(); + if (!g) return; + int n = g->children(); + for (int i = 0; i < n; i++) { + Fl_Widget *c = g->child(i); + if ( !c->visible() ) continue; + if ( c->as_window() ) { + draw(c, c->x(), c->y()); + } + else traverse(c); + } +} + +/** + @brief Computes the page coordinates of the current origin of graphics functions. + * + @param[out] x If non-null, *x is set to the horizontal page offset of graphics origin. + @param[out] y Same as above, vertically. + */ +void Fl_Widget_Surface::origin(int *x, int *y) +{ + if (x) *x = x_offset; + if (y) *y = y_offset; +} + +/** + @brief Sets the position in page coordinates of the origin of graphics functions. + + Arguments should be expressed relatively to the result of a previous printable_rect() call. + That is, printable_rect(&w, &h); origin(w/2, 0); sets the graphics origin at the + top center of the page printable area. + Origin() calls are not affected by rotate() calls. + Successive origin() calls don't combine their effects. + @param[in] x Horizontal position in page coordinates of the desired origin of graphics functions. + @param[in] y Same as above, vertically. + */ +void Fl_Widget_Surface::origin(int x, int y) {} + +/** + @brief Prints a rectangular part of an on-screen window. + + @param win The window from where to capture. + @param x The rectangle left + @param y The rectangle top + @param w The rectangle width + @param h The rectangle height + @param delta_x Optional horizontal offset from current graphics origin where to print the captured rectangle. + @param delta_y As above, vertically. + */ +void Fl_Widget_Surface::print_window_part(Fl_Window *win, int x, int y, int w, int h, int delta_x, int delta_y) +{ + Fl_Surface_Device *current = Fl_Surface_Device::surface(); + Fl_Display_Device::display_device()->set_current(); + Fl_Window *save_front = Fl::first_window(); + win->show(); + Fl::check(); + win->make_current(); + uchar *image_data; + image_data = fl_read_image(NULL, x, y, w, h); +#ifdef __APPLE__ // PORTME: Fl_Surface_Driver - platform paged device + Fl_X::q_release_context(); // matches make_current() call above +#endif + if (save_front != win) save_front->show(); + current->set_current(); + fl_draw_image(image_data, delta_x, delta_y, w, h, 3); + delete[] image_data; +#ifdef WIN32 + HDC gc = GetDC(fl_xid(win)); + fl_graphics_driver->gc(gc); + ReleaseDC(fl_xid(win), gc); +#endif +} + +/** + @brief Computes the width and height of the printable area of the page. + + Values are in the same unit as that used by FLTK drawing functions, + are unchanged by calls to origin(), but are changed by scale() calls. + Values account for the user-selected paper type and print orientation. + @return 0 if OK, non-zero if any error + */ +int Fl_Widget_Surface::printable_rect(int *w, int *h) {return 1;} + +/** Draws a window with its title bar and frame if any. + + \p x_offset and \p y_offset are optional coordinates of where to position the window top left. + Equivalent to draw() if \p win is a subwindow or has no border. + Use Fl_Window::decorated_w() and Fl_Window::decorated_h() to get the size of the window. + */ +void Fl_Widget_Surface::draw_decorated_window(Fl_Window *win, int x_offset, int y_offset) +{ + Fl_Shared_Image *top, *left, *bottom, *right; + win->capture_titlebar_and_borders(top, left, bottom, right); + int wsides = left ? left->w() : 0; + int toph = top ? top->h() : 0; + if (top) { + top->draw(x_offset, y_offset); + top->release(); + } + if (left) { + left->draw(x_offset, y_offset + toph); + left->release(); + } + if (right) { + right->draw(x_offset + wsides + win->w(), y_offset + toph); + right->release(); + } + if (bottom) { + bottom->draw(x_offset, y_offset + toph + win->h()); + bottom->release(); + } + this->draw(win, x_offset + wsides, y_offset + toph); +} + +// +// End of "$Id: Fl_Widget_Surface.cxx 11217 2016-02-25 17:56:48Z manolo $". +// diff --git a/src/Fl_cocoa.mm b/src/Fl_cocoa.mm index 02d67a11b..898c68136 100644 --- a/src/Fl_cocoa.mm +++ b/src/Fl_cocoa.mm @@ -4366,7 +4366,7 @@ void Fl_Window::capture_titlebar_and_borders(Fl_Shared_Image*& top, Fl_Shared_Im } -void Fl_Paged_Device::print_window(Fl_Window *win, int x_offset, int y_offset) +void Fl_System_Printer::draw_decorated_window(Fl_Window *win, int x_offset, int y_offset) { if (!win->shown() || win->parent() || !win->border() || !win->visible()) { this->print_widget(win, x_offset, y_offset); diff --git a/src/Makefile b/src/Makefile index 4842bb0b6..e03e29bcf 100644 --- a/src/Makefile +++ b/src/Makefile @@ -98,6 +98,7 @@ CPPFILES = \ Fl_Value_Output.cxx \ Fl_Value_Slider.cxx \ Fl_Widget.cxx \ + Fl_Widget_Surface.cxx \ Fl_Window.cxx \ Fl_Window_Driver.cxx \ Fl_Window_fullscreen.cxx \ @@ -246,6 +247,7 @@ XLIBCPPFILES = \ drivers/Xlib/Fl_Xlib_Graphics_Driver_line_style.cxx \ drivers/Xlib/Fl_Xlib_Graphics_Driver_rect.cxx \ drivers/Xlib/Fl_Xlib_Graphics_Driver_vertex.cxx \ + drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx \ drivers/X11/Fl_X11_Window_Driver.cxx \ drivers/X11/Fl_X11_Screen_Driver.cxx \ drivers/Posix/Fl_Posix_System_Driver.cxx diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx index 175a48e7e..1230290c6 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx @@ -20,6 +20,7 @@ #include #include "../../config_lib.h" #include "Fl_GDI_Graphics_Driver.h" +#include /* Reference to the current device context @@ -129,6 +130,18 @@ void Fl_GDI_Graphics_Driver::copy_offscreen_with_alpha(int x,int y,int w,int h,H DeleteDC(new_gc); } +void Fl_Translated_GDI_Graphics_Driver::translate_all(int x, int y) { + GetWindowOrgEx((HDC)gc(), origins+depth); + SetWindowOrgEx((HDC)gc(), origins[depth].x - x, origins[depth].y - y, NULL); + if (depth < sizeof(origins)/sizeof(POINT)) depth++; + else Fl::warning("Fl_Copy_Surface: translate stack overflow!"); +} + +void Fl_Translated_GDI_Graphics_Driver::untranslate_all() { + if (depth > 0) depth--; + SetWindowOrgEx((HDC)gc(), origins[depth].x, origins[depth].y, NULL); +} + // // End of "$Id$". // diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.h b/src/drivers/GDI/Fl_GDI_Graphics_Driver.h index 6852b4beb..a4b2730aa 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.h +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.h @@ -26,6 +26,7 @@ #define FL_GDI_GRAPHICS_DRIVER_H #include +#include /** @@ -136,6 +137,14 @@ public: int draw_scaled(Fl_Image *img, int XP, int YP, int WP, int HP); }; +class Fl_Translated_GDI_Graphics_Driver : public Fl_GDI_Graphics_Driver { + unsigned depth; + POINT origins[10]; +public: + Fl_Translated_GDI_Graphics_Driver() {depth = 0;} + virtual void translate_all(int x, int y); + virtual void untranslate_all(void); +}; #endif // FL_GDI_GRAPHICS_DRIVER_H diff --git a/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H b/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H new file mode 100644 index 000000000..b90b1c47f --- /dev/null +++ b/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.H @@ -0,0 +1,75 @@ +// +// "$Id: Fl_Translated_Xlib_Graphics_Driver.H 11217 2016-02-25 17:56:48Z manolo $" +// +// Draw-to-image code for the Fast Light Tool Kit (FLTK). +// +// Copyright 1998-2016 by Bill Spitzak and others. +// +// This library is free software. Distribution and use rights are outlined in +// the file "COPYING" which should have been included with this file. If this +// file is missing or damaged, see the license at: +// +// http://www.fltk.org/COPYING.php +// +// Please report all bugs and problems on the following page: +// +// http://www.fltk.org/str.php +// + +#ifndef Fl_Translated_Xlib_Graphics_Driver_h +#define Fl_Translated_Xlib_Graphics_Driver_h + +#ifndef FL_DOXYGEN + +#include + +/* graphics driver that translates all graphics coordinates before calling Xlib */ +class Fl_Translated_Xlib_Graphics_Driver : public Fl_Xlib_Graphics_Driver { + int offset_x, offset_y; // translation between user and graphical coordinates: graphical = user + offset + unsigned depth; // depth of translation stack + int stack_x[20], stack_y[20]; // translation stack allowing cumulative translations +public: + Fl_Translated_Xlib_Graphics_Driver(); + virtual ~Fl_Translated_Xlib_Graphics_Driver(); + void translate_all(int dx, int dy); + void untranslate_all(); + void rect(int x, int y, int w, int h); + void rectf(int x, int y, int w, int h); + void xyline(int x, int y, int x1); + void xyline(int x, int y, int x1, int y2); + void xyline(int x, int y, int x1, int y2, int x3); + void yxline(int x, int y, int y1); + void yxline(int x, int y, int y1, int x2); + void yxline(int x, int y, int y1, int x2, int y3); + void line(int x, int y, int x1, int y1); + void line(int x, int y, int x1, int y1, int x2, int y2); + void draw(const char* str, int n, int x, int y); + void draw(int angle, const char *str, int n, int x, int y); + void rtl_draw(const char* str, int n, int x, int y); + void draw(Fl_Pixmap *pxm, int XP, int YP, int WP, int HP, int cx, int cy); + void draw(Fl_Bitmap *bm, int XP, int YP, int WP, int HP, int cx, int cy); + void draw(Fl_RGB_Image *img, int XP, int YP, int WP, int HP, int cx, int cy); + void draw_image(const uchar* buf, int X,int Y,int W,int H, int D=3, int L=0); + void draw_image(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D=3); + void draw_image_mono(const uchar* buf, int X,int Y,int W,int H, int D=1, int L=0) ; + void draw_image_mono(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D=1); + void copy_offscreen(int x, int y, int w, int h, Fl_Offscreen pixmap, int srcx, int srcy); + void push_clip(int x, int y, int w, int h); + int not_clipped(int x, int y, int w, int h); + int clip_box(int x, int y, int w, int h, int& X, int& Y, int& W, int& H); + void pie(int x, int y, int w, int h, double a1, double a2); + void arc(int x, int y, int w, int h, double a1, double a2); + void polygon(int x0, int y0, int x1, int y1, int x2, int y2); + void polygon(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3); + void loop(int x0, int y0, int x1, int y1, int x2, int y2); + void loop(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3); + void point(int x, int y); +}; + +#endif // FL_DOXYGEN + +#endif /* Fl_Translated_Xlib_Graphics_Driver_h */ + +// +// End of "$Id: Fl_Translated_Xlib_Graphics_Driver.H 11217 2016-02-25 17:56:48Z manolo $". +// diff --git a/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx b/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx new file mode 100644 index 000000000..89871f9b4 --- /dev/null +++ b/src/drivers/Xlib/Fl_Translated_Xlib_Graphics_Driver.cxx @@ -0,0 +1,202 @@ +// +// "$Id: Fl_Translated_Xlib_Graphics_Driver.cxx 11217 2016-02-25 17:56:48Z manolo $" +// +// Draw-to-image code for the Fast Light Tool Kit (FLTK). +// +// Copyright 1998-2016 by Bill Spitzak and others. +// +// This library is free software. Distribution and use rights are outlined in +// the file "COPYING" which should have been included with this file. If this +// file is missing or damaged, see the license at: +// +// http://www.fltk.org/COPYING.php +// +// Please report all bugs and problems on the following page: +// +// http://www.fltk.org/str.php +// + +#include "Fl_Translated_Xlib_Graphics_Driver.H" +#include + +#ifndef FL_DOXYGEN + +Fl_Translated_Xlib_Graphics_Driver::Fl_Translated_Xlib_Graphics_Driver() { + offset_x = 0; offset_y = 0; + depth = 0; +} + +Fl_Translated_Xlib_Graphics_Driver::~Fl_Translated_Xlib_Graphics_Driver() {} + +void Fl_Translated_Xlib_Graphics_Driver::translate_all(int dx, int dy) { // reversibly adds dx,dy to the offset between user and graphical coordinates + stack_x[depth] = offset_x; + stack_y[depth] = offset_y; + offset_x = stack_x[depth] + dx; + offset_y = stack_y[depth] + dy; + push_matrix(); + translate(dx, dy); + if (depth < sizeof(stack_x)/sizeof(int)) depth++; + else Fl::warning("%s: translate stack overflow!", "Fl_Translated_Xlib_Graphics_Driver"); +} + +void Fl_Translated_Xlib_Graphics_Driver::untranslate_all() { // undoes previous translate_all() + if (depth > 0) depth--; + offset_x = stack_x[depth]; + offset_y = stack_y[depth]; + pop_matrix(); +} + +void Fl_Translated_Xlib_Graphics_Driver::rect(int x, int y, int w, int h) { + Fl_Xlib_Graphics_Driver::rect(x+offset_x, y+offset_y, w, h); +} + +void Fl_Translated_Xlib_Graphics_Driver::rectf(int x, int y, int w, int h) { + Fl_Xlib_Graphics_Driver::rectf(x+offset_x, y+offset_y, w, h); +} + +void Fl_Translated_Xlib_Graphics_Driver::xyline(int x, int y, int x1) { + Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x); +} + +void Fl_Translated_Xlib_Graphics_Driver::xyline(int x, int y, int x1, int y2) { + Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x, y2+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::xyline(int x, int y, int x1, int y2, int x3) { + Fl_Xlib_Graphics_Driver::xyline(x+offset_x, y+offset_y, x1+offset_x, y2+offset_y, x3+offset_x); +} + +void Fl_Translated_Xlib_Graphics_Driver::yxline(int x, int y, int y1) { + Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::yxline(int x, int y, int y1, int x2) { + Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y, x2+offset_x); +} + +void Fl_Translated_Xlib_Graphics_Driver::yxline(int x, int y, int y1, int x2, int y3) { + Fl_Xlib_Graphics_Driver::yxline(x+offset_x, y+offset_y, y1+offset_y, x2+offset_x, y3+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::line(int x, int y, int x1, int y1) { + Fl_Xlib_Graphics_Driver::line(x+offset_x, y+offset_y, x1+offset_x, y1+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::line(int x, int y, int x1, int y1, int x2, int y2) { + Fl_Xlib_Graphics_Driver::line(x+offset_x, y+offset_y, x1+offset_x, y1+offset_y, x2+offset_x, y2+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw(const char* str, int n, int x, int y) { + Fl_Xlib_Graphics_Driver::draw(str, n, x+offset_x, y+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw(int angle, const char *str, int n, int x, int y) { + Fl_Xlib_Graphics_Driver::draw(angle, str, n, x+offset_x, y+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::rtl_draw(const char* str, int n, int x, int y) { + Fl_Xlib_Graphics_Driver::rtl_draw(str, n, x+offset_x, y+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw(Fl_Pixmap *pxm, int XP, int YP, int WP, int HP, int cx, int cy) { + XP += offset_x; YP += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw(pxm, XP, YP, WP,HP,cx,cy); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw(Fl_Bitmap *bm, int XP, int YP, int WP, int HP, int cx, int cy) { + XP += offset_x; YP += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw(bm, XP, YP, WP,HP,cx,cy); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw(Fl_RGB_Image *img, int XP, int YP, int WP, int HP, int cx, int cy) { + XP += offset_x; YP += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw(img, XP, YP, WP,HP,cx,cy); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw_image(const uchar* buf, int X,int Y,int W,int H, int D, int L) { + X += offset_x; Y += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw_image(buf, X, Y, W,H,D,L); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw_image(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D) { + X += offset_x; Y += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw_image(cb, data, X, Y, W,H,D); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw_image_mono(const uchar* buf, int X,int Y,int W,int H, int D, int L) { + X += offset_x; Y += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw_image_mono(buf, X, Y, W,H,D,L); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::draw_image_mono(Fl_Draw_Image_Cb cb, void* data, int X,int Y,int W,int H, int D) { + X += offset_x; Y += offset_y; + translate_all(-offset_x, -offset_y); + Fl_Xlib_Graphics_Driver::draw_image_mono(cb, data, X, Y, W,H,D); + untranslate_all(); +} + +void Fl_Translated_Xlib_Graphics_Driver::copy_offscreen(int x, int y, int w, int h, Fl_Offscreen pixmap, int srcx, int srcy) { + Fl_Xlib_Graphics_Driver::copy_offscreen(x+offset_x, y+offset_y, w, h,pixmap,srcx,srcy); +} + +void Fl_Translated_Xlib_Graphics_Driver::push_clip(int x, int y, int w, int h) { + Fl_Xlib_Graphics_Driver::push_clip(x+offset_x, y+offset_y, w, h); +} + +int Fl_Translated_Xlib_Graphics_Driver::not_clipped(int x, int y, int w, int h) { + return Fl_Xlib_Graphics_Driver::not_clipped(x + offset_x, y + offset_y, w, h); +} + +int Fl_Translated_Xlib_Graphics_Driver::clip_box(int x, int y, int w, int h, int& X, int& Y, int& W, int& H) { + int retval = Fl_Xlib_Graphics_Driver::clip_box(x + offset_x, y + offset_y, w,h,X,Y,W,H); + X -= offset_x; + Y -= offset_y; + return retval; +} + +void Fl_Translated_Xlib_Graphics_Driver::pie(int x, int y, int w, int h, double a1, double a2) { + Fl_Xlib_Graphics_Driver::pie(x+offset_x,y+offset_y,w,h,a1,a2); +} + +void Fl_Translated_Xlib_Graphics_Driver::arc(int x, int y, int w, int h, double a1, double a2) { + Fl_Xlib_Graphics_Driver::arc(x+offset_x,y+offset_y,w,h,a1,a2); +} + +void Fl_Translated_Xlib_Graphics_Driver::polygon(int x0, int y0, int x1, int y1, int x2, int y2) { + Fl_Xlib_Graphics_Driver::polygon(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::polygon(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3) { + Fl_Xlib_Graphics_Driver::polygon(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y,x3+offset_x,y3+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::loop(int x0, int y0, int x1, int y1, int x2, int y2) { + Fl_Xlib_Graphics_Driver::loop(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::loop(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3) { + Fl_Xlib_Graphics_Driver::loop(x0+offset_x,y0+offset_y,x1+offset_x,y1+offset_y,x2+offset_x,y2+offset_y,x3+offset_x,y3+offset_y); +} + +void Fl_Translated_Xlib_Graphics_Driver::point(int x, int y) { + Fl_Xlib_Graphics_Driver::point(x+offset_x, y+offset_y); +} + +#endif // FL_DOXYGEN + +// +// End of "$Id: Fl_Translated_Xlib_Graphics_Driver.cxx 11217 2016-02-25 17:56:48Z manolo $". +// + -- cgit v1.2.3