summaryrefslogtreecommitdiff
path: root/src/Fl_Window_Driver.cxx
diff options
context:
space:
mode:
authorManolo Gouy <Manolo>2016-03-10 17:19:34 +0000
committerManolo Gouy <Manolo>2016-03-10 17:19:34 +0000
commitd4768073fa67e7f78872bc80f4dff1dd8aa32f69 (patch)
treee49adba4ced816e851cbb74e5cac4f9a995f4189 /src/Fl_Window_Driver.cxx
parent79f79d292c8ffe7a172237c614345a7bc667de80 (diff)
Implement non-rectangular windows using the Window Driver mechanism.
git-svn-id: file:///fltk/svn/fltk/branches/branch-1.3-porting@11336 ea41ed52-d2ee-0310-a9c1-e6b18d33e121
Diffstat (limited to 'src/Fl_Window_Driver.cxx')
-rw-r--r--src/Fl_Window_Driver.cxx123
1 files changed, 122 insertions, 1 deletions
diff --git a/src/Fl_Window_Driver.cxx b/src/Fl_Window_Driver.cxx
index 37ce9637f..de8760f90 100644
--- a/src/Fl_Window_Driver.cxx
+++ b/src/Fl_Window_Driver.cxx
@@ -22,11 +22,13 @@
#include "config_lib.h"
#include <FL/Fl_Window_Driver.H>
#include <FL/Fl.H>
+#include <FL/fl_draw.H>
Fl_Window_Driver::Fl_Window_Driver(Fl_Window *win) :
pWindow(win)
{
+ shape_data_ = NULL;
}
@@ -34,10 +36,129 @@ Fl_Window_Driver::~Fl_Window_Driver()
{
}
+int Fl_Window_Driver::double_flush(int eraseoverlay) {
+ /* This is a working, platform-independent implementation.
+ Some platforms may re-implement it for their own logic:
+ - on Mac OS, the system double buffers all windows, so it is
+ reimplemented to do the same as Fl_Window::flush(), except for
+ Fl_Overlay_Window's which fall back on this implementation.
+ - on Xlib, it is reimplemented if the Xdbe extension is available.
+ */
+ Fl_X *i = Fl_X::i(pWindow);
+
+ if (!i->other_xid) {
+ i->other_xid = fl_create_offscreen(pWindow->w(), pWindow->h());
+ pWindow->clear_damage(FL_DAMAGE_ALL);
+ }
+ if (pWindow->damage() & ~FL_DAMAGE_EXPOSE) {
+ fl_clip_region(i->region); i->region = 0;
+ fl_begin_offscreen(i->other_xid);
+ fl_graphics_driver->clip_region( 0 );
+ draw();
+ fl_end_offscreen();
+ }
+ return 0;
+}
+
+void Fl_Window_Driver::destroy_double_buffer() {
+ Fl_X *i = Fl_X::i(pWindow);
+ /* This is a working, platform-independent implementation.
+ Some platforms may re-implement it for their own logic:
+ - on Xlib, it is reimplemented if the Xdbe extension is available.
+ */
+ fl_delete_offscreen(i->other_xid);
+ i->other_xid = 0;
+}
+
void Fl_Window_Driver::draw() {
- pWindow->draw();
+ // The following is similar to Fl_Group::draw(), but ...
+ //
+ // - draws the box at (0,0), i.e. with x=0 and y=0 instead of x() and y()
+ // - does NOT draw the label (text)
+ // - draws the image only if FL_ALIGN_INSIDE is set
+ //
+ // Note: The label (text) of top level windows is drawn in the title bar.
+ // Other windows do not draw their labels at all, unless drawn by their
+ // parent widgets or by special draw() methods (derived classes).
+
+ if (pWindow->damage() & ~FL_DAMAGE_CHILD) { // draw the entire thing
+ pWindow->draw_box(pWindow->box(),0,0,pWindow->w(),pWindow->h(),pWindow->color()); // draw box with x/y = 0
+
+ if (pWindow->image() && (pWindow->align() & FL_ALIGN_INSIDE)) { // draw the image only
+ Fl_Label l1;
+ memset(&l1,0,sizeof(l1));
+ l1.align_ = pWindow->align();
+ l1.image = pWindow->image();
+ if (!pWindow->active_r() && l1.image && l1.deimage) l1.image = l1.deimage;
+ l1.type = pWindow->labeltype();
+ l1.draw(0,0,pWindow->w(),pWindow->h(),pWindow->align());
+ }
+ }
+ pWindow->draw_children();
+
+# if defined(FLTK_USE_CAIRO)
+ Fl::cairo_make_current(this); // checkout if an update is necessary
+# endif
+}
+
+void Fl_Window::draw() {pWindowDriver->draw();}
+
+/** Assigns a non-rectangular shape to the window.
+ This function gives an arbitrary shape (not just a rectangular region) to an Fl_Window.
+ An Fl_Image of any dimension can be used as mask; it is rescaled to the window's dimension as needed.
+
+ The layout and widgets inside are unaware of the mask shape, and most will act as though the window's
+ rectangular bounding box is available
+ to them. It is up to you to make sure they adhere to the bounds of their masking shape.
+
+ The \p img argument can be an Fl_Bitmap, Fl_Pixmap, Fl_RGB_Image or Fl_Shared_Image:
+ \li With Fl_Bitmap or Fl_Pixmap, the shaped window covers the image part where bitmap bits equal one,
+ or where the pixmap is not fully transparent.
+ \li With an Fl_RGB_Image with an alpha channel (depths 2 or 4), the shaped window covers the image part
+ that is not fully transparent.
+ \li With an Fl_RGB_Image of depth 1 (gray-scale) or 3 (RGB), the shaped window covers the non-black image part.
+ \li With an Fl_Shared_Image, the shape is determined by rules above applied to the underlying image.
+ The shared image should not have been scaled through Fl_Shared_Image::scale().
+
+ Platform details:
+ \li On the unix/linux platform, the SHAPE extension of the X server is required.
+ This function does control the shape of Fl_Gl_Window instances.
+ \li On the MSWindows platform, this function does nothing with class Fl_Gl_Window.
+ \li On the Mac platform, OS version 10.4 or above is required.
+ An 8-bit shape-mask is used when \p img is an Fl_RGB_Image:
+ with depths 2 or 4, the image alpha channel becomes the shape mask such that areas with alpha = 0
+ are out of the shaped window;
+ with depths 1 or 3, white and black are in and out of the
+ shaped window, respectively, and other colors give intermediate masking scores.
+ This function does nothing with class Fl_Gl_Window.
+
+ The window borders and caption created by the window system are turned off by default. They
+ can be re-enabled by calling Fl_Window::border(1).
+
+ A usage example is found at example/shapedwindow.cxx.
+
+ \version 1.3.3 (and requires compilation with FL_ABI_VERSION >= 10303)
+ */
+void Fl_Window::shape(const Fl_Image* img) {pWindowDriver->shape(img);}
+
+
+/** Set the window's shape with an Fl_Image.
+ \see void shape(const Fl_Image* img)
+ */
+void Fl_Window::shape(const Fl_Image& img) {pWindowDriver->shape(&img);}
+
+/** Returns non NULL when the window has been assigned a non-rectangular shape */
+int Fl_Window::is_shaped() {return pWindowDriver->shape_data_ != NULL;}
+
+void Fl_Window_Driver::shape_pixmap_(Fl_Image* pixmap) {
+ Fl_RGB_Image* rgba = new Fl_RGB_Image((Fl_Pixmap*)pixmap);
+ shape_alpha_(rgba, 3);
+ delete rgba;
}
+
+
+
//
// End of "$Id$".
//