On 04.05.2012 08:14, Matthias Melcher wrote: > For composite widgets, I would like to propose something else though. It > should be possible to derive a new widget from any other widget, based on the > data that widget provides, not on the UI. For example, InputChoice is derived > from Group. That is silly, because Group does not normally handle text. It > should rather be derived from Input, right?
Absolutely. > But currently only a Group can have children. So what I would like to do is > keep the children in Group (no need to move them to Widget - that would be a > waste), but add something to Widgets that I call Nephew for lack of a better > word. That's exactly what I proposed a long time ago, and I had a somewhat working solution in a FLTK 1 branch. It was not ready, but I believe it could work. I called your Nephews "subwidgets". This branch is still there at: https://svn.easysw.com/public/fltk/fltk/branches/branch-1.3-composite (use svn to check it out). Although I believe it's not my latest dev. version, it shows some features (see also below). Some of them are now in FLTK 1.3 and later, but some would be new: $ svn log -r 6317 https://svn.easysw.com/public/fltk/fltk/branches/branch-1.3-composite ------------------------------------------------------------------------ r6317 | AlbrechtS | 2008-09-20 13:07:58 +0200 (Sa, 20. Sep 2008) | 12 Zeilen This is a test version. For a list of changes see the file CHANGES.branch. Short version: - Widgets remove themselves from their parents when destroyed. - parents can now be simple (non-Fl_Group) widgets. - composite widgets like Fl_Scroll can now have private children ("subwidgets"). - Fl_Scroll now doesn't use the Fl_Group to handle its subwidgets, the scrollbars (a similar change has been done in FLTK 2). ------------------------------------------------------------------------ See also: <http://svn.easysw.com/public/fltk/fltk/branches/branch-1.3-composite/CHANGES.branch> > Nephews are managed like children in that they occupy space in the widget, > can receive events, and are drawn by their "Uncle", but they differ in that > they are not some unknown sized array of any kind of widget, reducing all the > overhead associated with that. > > For example: > > class InputChoice : public Input { > Menu_ myPulldownMenu; > }; > > InputChoice::InputChoice(int x, int y, int w, int h) > : myPulldownMenu(w-20, 0, 20, h) // in Ffltk3, all coordinates are relative > to the parent > { > } > > void draw() { > Input::draw(0, 0, w-20, h); > myPulldownMenu::draw(); > } This would need public draw() methods or this strange "cast-to-widget- pointer-and-call-the-virtual-method" trick. But yes, I think this is the correct approach. > int handle(int ev) { > if (event_inside(0, 0, w-20, h) { > return Input::handle(ev, 0, 0, w-20, h); > else > return send(ev, myPulldownMenu); > } > You used the unqualified "event_inside()" method. In FLTK 1 we have Fl::event_inside(), and this checks the widget's boundaries only. To make this work with composite widgets that don't have a common area (like InputChoice) I used a virtual method Widget::event_inside() that delegates the decision whether an event is /inside/ a widget to the widget itself, so that it can check its subwidgets (nephews), like this: int InputChoice::event_inside() { return event_inside() // the parent Input widget || myPulldownMenu.event_inside(); // the nephew pulldown } -------------------- | Input ... | Menu | -------------------- That's necessary, because the Group widget wouldn't know that an event in the Menu area should be delivered to the Input widget in the first place, because it's outside the Input rect. The base (Widget) class would only check the Widget's area itself, just like Fl::event_inside() does now. That and some small other changes (e.g. making parent() return a Widget instead of a Group for some other reasons) made it work as far as I could test. I'd really like to have features like this in FLTK 3 ! Albrecht _______________________________________________ fltk-dev mailing list [email protected] http://lists.easysw.com/mailman/listinfo/fltk-dev
