Using Fl_Window (Fl_Double_Window) + set_non_modal() is definitely easier, and
does not hog input. Thanks for mentioning that, Ian.
New problem, though. Test code is below.
Regardless of what group/win type I use, mouse input will pass through the
popup to the window/widgets below. This acts like an insertion-order thing. So,
widget is drawn z-top, but it is z-below for input. I can "fix" the input order
by making sure the other widget additions occur before the suggestion box.
In my project, though, I can't control/guarantee the insertion order of the
widget into the parent group ... so I'm a bit stumped.
Ideas? I'll keep reading docs/threads ...
Denton
---
/** \file main.cpp
creating a "suggestions" drop-down box
CHANGES
- dentonlt, jan 2013: original version
*/
#include <FL/Fl.H>
#include <FL/Fl_Window.H>
#include <FL/Fl_Group.H>
#include <FL/Fl_Input.H>
#include <FL/Fl_Button.H>
#include <FL/Fl_Select_Browser.H>
#include <FL/names.h>
class SuggestionBox : public Fl_Window {
Fl_Widget *anchor_;
Fl_Select_Browser *browser_;
static void static_browser_cb_(Fl_Widget *src, void *dat) {
if(!src || !dat) printf("SuggestionBox::browser_cb_ rec'd NULL arg.\n");
else ((SuggestionBox *)dat)->browser_cb_(src, dat);
}
void browser_cb_(Fl_Widget *src, void *dat) {
// hack!
printf("SuggestionBox::browser_cb_ runs\n"); fflush(stdout);
set_changed();
hide();
}
int handle(int event) {
//printf("SuggestionBox::handle() ran with event %s\n",
fl_eventnames[event]);
int ret = Fl_Window::handle(event);
if(changed()) {
clear_changed();
if(callback()) do_callback();
}
return ret;
}
public:
SuggestionBox(int X, int Y, int W, int H, const char *n = NULL) :
Fl_Window(X, Y, W, H, n) {
anchor_ = NULL;
browser_ = new Fl_Select_Browser(0, 0, W, H);
browser_->callback(static_browser_cb_, this);
// mock 'selection' data
browser_->add("red");
browser_->add("read");
browser_->add("reed");
browser_->add("regurgitate");
Fl_Window::end();
//clear_border();
//set_non_modal(); // stay on top, do not capture events
}
Fl_Select_Browser *browser() { return browser_; }
void anchor(Fl_Widget *a) { anchor_ = a; }
};
class SuggestionInput : public Fl_Input {
SuggestionBox *browser_;
static void static_browser_cb_(Fl_Widget *src, void *dat) {
if(!src || !dat) printf("SuggestionInput::browser_cb_ rec'd NULL arg.\n");
else ((SuggestionInput *)dat)->browser_cb_(src, dat);
}
void browser_cb_(Fl_Widget *src, void *dat) {
// hack!
printf("SuggestionInput::browser_cb_ runs\n"); fflush(stdout);
value(browser_->browser()->text(browser_->browser()->value()));
browser_->hide();
}
void post_suggestions_() {
printf("SuggestionInput::post_suggestions_() runs\n"); fflush(stdout);
if(browser_->parent()) browser_->position(x(), y() + h());
//else browser_->position(Fl::first_window()->x() + x(),
Fl::first_window()->y() + y() + h());
browser_->show();
browser_->redraw();
}
int handle(int event) {
int ret = Fl_Input::handle(event);
if(changed()) {
clear_changed();
if(value()) post_suggestions_();
if(callback()) do_callback();
}
return ret;
}
public:
SuggestionInput(int X, int Y, int W, int H, const char *n = NULL) :
Fl_Input(X, Y, W, H, n) {
browser_ = new SuggestionBox(0, 0, W, 80);
browser_->callback(static_browser_cb_, this);
browser_->hide();
browser_->anchor(this);
// try both with & without ...
//if(browser_->parent()) browser_->parent(NULL);
}
~SuggestionInput() {
printf("SuggestionInput::dtor runs\n"); fflush(stdout);
delete browser_;
}
};
void button_cb_(Fl_Widget *, void *) {
printf("button_cb_ ran.\n"); fflush(stdout);
}
int main (int argc, char ** argv)
{
Fl_Window *window;
Fl_Input *input;
Fl_Button *button;
window = new Fl_Window (600, 300);
// if I create 'button' here, then it is 'under' the popup.
input = new SuggestionInput(10, 10, 200, 35);
// creating button here hides input from previously inserted widgets
button = new Fl_Button(10, 45, 200, 35, "nothing"); // this masks input
into the popup ...
button->callback(button_cb_, NULL);
window->resizable(NULL);
window->end ();
window->show (argc, argv);
return(Fl::run());
}
_______________________________________________
fltk mailing list
[email protected]
http://lists.easysw.com/mailman/listinfo/fltk