From a6163888f3c56123b1db313743c6147ba498732c Mon Sep 17 00:00:00 2001 From: Yuval Adam Date: Fri, 8 Aug 2014 14:42:07 +0300 Subject: Add third_party libs --- third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx | 318 ++++++++++++++++++++++ 1 file changed, 318 insertions(+) create mode 100644 third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx (limited to 'third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx') diff --git a/third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx b/third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx new file mode 100644 index 0000000..f3713a9 --- /dev/null +++ b/third_party/windows/fltk-1.1.10/src/Fl_Widget.cxx @@ -0,0 +1,318 @@ +// +// "$Id: Fl_Widget.cxx 6978 2009-12-23 12:54:41Z AlbrechtS $" +// +// Base widget class for the Fast Light Tool Kit (FLTK). +// +// Copyright 1998-2005 by Bill Spitzak and others. +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Library General Public +// License as published by the Free Software Foundation; either +// version 2 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Library General Public License for more details. +// +// You should have received a copy of the GNU Library General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 +// USA. +// +// Please report all bugs and problems on the following page: +// +// http://www.fltk.org/str.php +// + +#include +#include +#include +#include +#include +#include +#include "flstring.h" + + +//////////////////////////////////////////////////////////////// +// for compatability with Forms, all widgets without callbacks are +// inserted into a "queue" when they are activated, and the forms +// compatability interaction functions (fl_do_events, etc) will +// read one widget at a time from this queue and return it: + +const int QUEUE_SIZE = 20; + +static Fl_Widget *obj_queue[QUEUE_SIZE]; +static int obj_head, obj_tail; + +void Fl_Widget::default_callback(Fl_Widget *o, void * /*v*/) { +#if 0 + // This is necessary for strict forms compatibility but is confusing. + // Use the parent's callback if this widget does not have one. + for (Fl_Widget *p = o->parent(); p; p = p->parent()) + if (p->callback() != default_callback) { + p->do_callback(o,v); + return; + } +#endif + obj_queue[obj_head++] = o; + if (obj_head >= QUEUE_SIZE) obj_head = 0; + if (obj_head == obj_tail) { + obj_tail++; + if (obj_tail >= QUEUE_SIZE) obj_tail = 0; + } +} +/* + All Fl_Widgets that don't have a callback defined use a + default callback that puts a pointer to the widget in this queue, + and this method reads the oldest widget out of this queue. +*/ +Fl_Widget *Fl::readqueue() { + if (obj_tail==obj_head) return 0; + Fl_Widget *o = obj_queue[obj_tail++]; + if (obj_tail >= QUEUE_SIZE) obj_tail = 0; + return o; +} +/* + This static internal function removes all pending callbacks for a + specific widget from the default callback queue (Fl::readqueue()). + It is only called from Fl_Widget's destructor if the widget + doesn't have an own callback. + Note: There's no need to have this in the Fl:: namespace. +*/ +static void cleanup_readqueue(Fl_Widget *w) { + + if (obj_tail==obj_head) return; + + // Read the entire queue and copy over all valid entries. + // The new head will be determined after the last copied entry. + + int old_head = obj_head; // save newest entry + int entry = obj_tail; // oldest entry + obj_head = obj_tail; // new queue start + for (;;) { + Fl_Widget *o = obj_queue[entry++]; + if (entry >= QUEUE_SIZE) entry = 0; + if (o != w) { // valid entry + obj_queue[obj_head++] = o; + if (obj_head >= QUEUE_SIZE) obj_head = 0; + } // valid entry + if (entry == old_head) break; + } + return; +} + +//////////////////////////////////////////////////////////////// + +int Fl_Widget::handle(int) { + return 0; +} + +int FL_NORMAL_SIZE = 14; + +Fl_Widget::Fl_Widget(int X, int Y, int W, int H, const char* L) { + + x_ = X; y_ = Y; w_ = W; h_ = H; + + label_.value = L; + label_.image = 0; + label_.deimage = 0; + label_.type = FL_NORMAL_LABEL; + label_.font = FL_HELVETICA; + label_.size = (uchar)FL_NORMAL_SIZE; + label_.color = FL_FOREGROUND_COLOR; + tooltip_ = 0; + callback_ = default_callback; + user_data_ = 0; + type_ = 0; + flags_ = VISIBLE_FOCUS; + damage_ = 0; + box_ = FL_NO_BOX; + color_ = FL_GRAY; + color2_ = FL_GRAY; + align_ = FL_ALIGN_CENTER; + when_ = FL_WHEN_RELEASE; + + parent_ = 0; + if (Fl_Group::current()) Fl_Group::current()->add(this); +} + +void Fl_Widget::resize(int X, int Y, int W, int H) { + x_ = X; y_ = Y; w_ = W; h_ = H; +} + +// this is useful for parent widgets to call to resize children: +int Fl_Widget::damage_resize(int X, int Y, int W, int H) { + if (x() == X && y() == Y && w() == W && h() == H) return 0; + resize(X, Y, W, H); + redraw(); + return 1; +} + +int Fl_Widget::take_focus() { + if (!takesevents()) return 0; + if (!visible_focus()) return 0; + if (!handle(FL_FOCUS)) return 0; // see if it wants it + if (contains(Fl::focus())) return 1; // it called Fl::focus for us + Fl::focus(this); + return 1; +} + +extern void fl_throw_focus(Fl_Widget*); // in Fl_x.cxx + +// Destruction does not remove from any parent group! And groups when +// destroyed destroy all their children. This is convienent and fast. +// However, it is only legal to destroy a "root" such as an Fl_Window, +// and automatic destructors may be called. +Fl_Widget::~Fl_Widget() { + Fl::clear_widget_pointer(this); + if (flags() & COPIED_LABEL) free((void *)(label_.value)); + parent_ = 0; // Don't throw focus to a parent widget. + fl_throw_focus(this); + // remove stale entries from default callback queue (Fl::readqueue()) + if (callback_ == default_callback) cleanup_readqueue(this); +} + +// draw a focus box for the widget... +void +Fl_Widget::draw_focus(Fl_Boxtype B, int X, int Y, int W, int H) const { + if (!Fl::visible_focus()) return; + switch (B) { + case FL_DOWN_BOX: + case FL_DOWN_FRAME: + case FL_THIN_DOWN_BOX: + case FL_THIN_DOWN_FRAME: + X ++; + Y ++; + default: + break; + } + + fl_color(fl_contrast(FL_BLACK, color())); + +#if defined(WIN32) || defined(__APPLE_QD__) + // Windows 95/98/ME do not implement the dotted line style, so draw + // every other pixel around the focus area... + // + // Also, QuickDraw (MacOS) does not support line styles specifically, + // and the hack we use in fl_line_style() will not draw horizontal lines + // on odd-numbered rows... + int i, xx, yy; + + X += Fl::box_dx(B); + Y += Fl::box_dy(B); + W -= Fl::box_dw(B) + 2; + H -= Fl::box_dh(B) + 2; + + for (xx = 0, i = 1; xx < W; xx ++, i ++) if (i & 1) fl_point(X + xx, Y); + for (yy = 0; yy < H; yy ++, i ++) if (i & 1) fl_point(X + W, Y + yy); + for (xx = W; xx > 0; xx --, i ++) if (i & 1) fl_point(X + xx, Y + H); + for (yy = H; yy > 0; yy --, i ++) if (i & 1) fl_point(X, Y + yy); +#else + fl_line_style(FL_DOT); + fl_rect(X + Fl::box_dx(B), Y + Fl::box_dy(B), + W - Fl::box_dw(B) - 1, H - Fl::box_dh(B) - 1); + fl_line_style(FL_SOLID); +#endif // WIN32 +} + + +void Fl_Widget::activate() { + if (!active()) { + clear_flag(INACTIVE); + if (active_r()) { + redraw(); + redraw_label(); + handle(FL_ACTIVATE); + if (inside(Fl::focus())) Fl::focus()->take_focus(); + } + } +} + +void Fl_Widget::deactivate() { + if (active_r()) { + set_flag(INACTIVE); + redraw(); + redraw_label(); + handle(FL_DEACTIVATE); + fl_throw_focus(this); + } else { + set_flag(INACTIVE); + } +} + +int Fl_Widget::active_r() const { + for (const Fl_Widget* o = this; o; o = o->parent()) + if (!o->active()) return 0; + return 1; +} + +void Fl_Widget::show() { + if (!visible()) { + clear_flag(INVISIBLE); + if (visible_r()) { + redraw(); + redraw_label(); + handle(FL_SHOW); + if (inside(Fl::focus())) Fl::focus()->take_focus(); + } + } +} + +void Fl_Widget::hide() { + if (visible_r()) { + set_flag(INVISIBLE); + for (Fl_Widget *p = parent(); p; p = p->parent()) + if (p->box() || !p->parent()) {p->redraw(); break;} + handle(FL_HIDE); + fl_throw_focus(this); + } else { + set_flag(INVISIBLE); + } +} + +int Fl_Widget::visible_r() const { + for (const Fl_Widget* o = this; o; o = o->parent()) + if (!o->visible()) return 0; + return 1; +} + +// return true if widget is inside (or equal to) this: +// Returns false for null widgets. +int Fl_Widget::contains(const Fl_Widget *o) const { + for (; o; o = o->parent_) if (o == this) return 1; + return 0; +} + + +void +Fl_Widget::label(const char *a) { + if (flags() & COPIED_LABEL) { + // reassigning a copied label remains the same copied label + if (label_.value == a) + return; + free((void *)(label_.value)); + clear_flag(COPIED_LABEL); + } + label_.value=a; + redraw_label(); +} + + +void +Fl_Widget::copy_label(const char *a) { + if (flags() & COPIED_LABEL) free((void *)(label_.value)); + if (a) { + set_flag(COPIED_LABEL); + label_.value=strdup(a); + } else { + clear_flag(COPIED_LABEL); + label_.value=(char *)0; + } + redraw_label(); +} + + +// +// End of "$Id: Fl_Widget.cxx 6978 2009-12-23 12:54:41Z AlbrechtS $". +// -- cgit v1.3.1