FLTK是基于回调的GUI系统,但有时我需要用户在Fl_Input小部件中输入可接受的答案,然后函数才能返回。
这似乎需要更新小部件,收集答案,然后返回答案(如果有效)。
因此,从本质上讲,我有一个名为int get_int(Fl_Input i)的函数。此函数需要不断更新Fl_Input,通过尝试将value()强制转换为int来验证内容,如果验证失败则清除Fl_Input,最后从函数返回强制转换的int。该确认应在按Enter键时进行。 (我计划还具有返回转换字符串和浮点数的函数,但它们将以相同的方式工作)
这实际上是脚本系统的一部分,FLTK是GUI。嵌入式语言正在等待从我的Fl_Input获取适当的int,但是FLTK无法更新和处理事件,因为它尚未完成主循环。我似乎无法通过普通的FLTK回调轻松完成此操作,因为它们必须返回void,并且根据从其读取的对象的上下文,我将在单一输入上进行多种类型的转换和验证。
感谢任何可以帮助我的人!
这里的编辑是我需要的一些粗略示例代码。
Embeddable Common Lisp需要包装get_int函数,但是我不确定如何使用中断更新所有小部件,以及如何通过不会直接影响循环的回调中断循环。 (也许是 bool(boolean) 型标志?)
#include <iostream>
#include <FL/Fl.H>
#include <FL/Fl_Window.H>
#include <Fl/Fl_Input.H>
#include <Fl/Fl_Button.H>
#include <stdexcept>
int get_int(Fl_Input* i)
{
int temp = 0;
while(True)
{
// not sure how to update here
// at this point, button and field need to update
// also somehow validate needs to be done on Enter button press
// but callbacks can't interact with this part of the code directly
// to validate and end the loop here
try
{
temp = std::stoi(i->value());
}
catch(...)
{
std::cout << "Invalid conversion to int" << i->value() << std::endl;
i->value("");
}
}
return temp;
}
void field_callback(Fl_Widget * w, void *d)
{
// This callback simulates Embeddable Common Lisp calling wrapped get_int
// Once a number is valid, it is converted and passed to back to Lisp
int something = get_int((Fl_Input*)w);
std::cout << something << std::endl;
}
int main()
{
Fl_Window *w = new Fl_Window(200, 32);
Fl_Input *i = new Fl_Input(0, 0, 128, 24, "");
Fl_Button *b = new Fl_Button(128, 0, 32, 24, "Simulate Request");
b->callback(field_callback);
w->show();
return(Fl::run());
}
最佳答案
在获得FLTK邮件列表的帮助后,我为那些希望做类似事情的人提供了一个示例。这只是袖手旁观,可能会在生产中使用。确保进行调试,而不是直接复制/粘贴。
#include <FL/Fl.H>
#include <FL/Fl_Box.H>
#include <FL/Fl_Input.H>
#include <FL/Fl_Window.H>
#include <FL/Fl_Button.H>
#include <string>
#include <iostream>
Fl_Window* win = new Fl_Window(240, 128, "Loop n Prompt");
Fl_Button* button = new Fl_Button(5, 5, 128, 24, "Simulate Prompt");
Fl_Input* input = new Fl_Input(5, 96, 230, 24, "");
Fl_Box* prompt_msg = new Fl_Box(5, 48, 230, 24, "");
std::string get_input(const char* prompt, Fl_Input *input)
{
// Lock all widgets not pertaining to field here
button->deactivate();
prompt_msg->label(prompt);
// Open up the input for value entry
input->readonly(false);
input->activate();
while(! input->readonly())
{
Fl::wait();
}
// other groups activate here
button->activate();
// Have a funny feeling about c -> std::string conversion double check...
std::string return_string = input->value();
// Reset input and prompt to ""
input->value("");
prompt_msg->label("");
return return_string;
}
void input_CB(Fl_Widget *w, void* data)
{
Fl_Input* ptr = (Fl_Input*)w;
ptr->readonly(true);
}
void button_CB(Fl_Widget *w, void* data)
{
// Simulate something needing these values RIGHT NOW
std::cout << "Got " << get_input("Please enter name", input) << std::endl;
std::cout << "Got " << get_input("Please enter mother's name", input) << std::endl;
std::cout << "Got " << get_input("Please enter father's name", input) << std::endl;
// Now try a standard loop until thing
std::string password = "";
while(password != "password")
{
password = get_input("You must enter 'password'", input);
}
std::cout << "Nice job you answered correctly to exit the loop!" << std::endl;
}
int main()
{
// Callback setup
input->callback((Fl_Callback*)input_CB);
button->callback((Fl_Callback*)button_CB);
// Entry field does callback when enter key pressed
input->when(FL_WHEN_ENTER_KEY_ALWAYS);
// Show the window and all children
win->show();
return(Fl::run());
}
关于c++ - 具有更新/验证循环的C++ FLTK的Fl_Input数据,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/36733529/