Fixed textbox

This commit is contained in:
Yousef Khadadeh 2026-04-01 18:40:52 +03:00
parent b50cab2d33
commit b95adcf0f0
2 changed files with 24 additions and 16 deletions

View file

@ -31,9 +31,10 @@ template <typename T> class TextBox : public Element {
virtual void input_key_callback(const InputManager::KeyCallbackArgs& key) override;
~TextBox();
private:
void init_textbox(UpdateInputData& io);
void init_textbox(UpdateInputData& io, bool forceTextUpdate);
bool update_data();
std::optional<T> oldData;
bool isSelected = false;
TextBoxData<T> userInfo;
std::shared_ptr<RichText::TextBox> textbox;

View file

@ -8,7 +8,7 @@ template <typename T> TextBox<T>::TextBox(GUIManager& gui): Element(gui) {}
template <typename T> void TextBox<T>::layout(const Clay_ElementId& id, const TextBoxData<T>& userInfo) {
auto& io = gui.io;
this->userInfo = userInfo;
init_textbox(io);
init_textbox(io, false);
CLAY(id, {
.layout = {
.sizing = {.width = CLAY_SIZING_GROW(static_cast<float>(io.fontSize * 2)), .height = CLAY_SIZING_FIXED(static_cast<float>(io.fontSize * 1.25f))}
@ -72,8 +72,8 @@ template <typename T> bool TextBox<T>::input_mouse_button_callback(const InputMa
else if(isSelected) {
gui.io.input->remove_rich_text_box_input(textbox);
if(update_data())
gui.set_post_callback_func(userInfo.onEdit);
init_textbox(gui.io);
gui.set_post_callback_func_high_priority(userInfo.onEdit);
init_textbox(gui.io, true);
isSelected = false;
}
}
@ -91,31 +91,37 @@ template <typename T> bool TextBox<T>::input_mouse_motion_callback(const InputMa
}
template <typename T> void TextBox<T>::input_key_callback(const InputManager::KeyCallbackArgs& key) {
if(key.key == InputManager::KEY_TEXT_ENTER && key.down && userInfo.onEnter) {
if(key.key == InputManager::KEY_TEXT_ENTER && key.down && isSelected) {
bool success = update_data();
gui.set_post_callback_func([&, success] {
gui.set_post_callback_func_high_priority([&, success] {
if(success && userInfo.onEdit) userInfo.onEdit();
userInfo.onEnter();
if(userInfo.onEnter) userInfo.onEnter();
init_textbox(gui.io, true);
});
}
}
template <typename T> void TextBox<T>::init_textbox(UpdateInputData& io) {
textbox = std::make_shared<RichText::TextBox>();
textbox->set_width(std::numeric_limits<float>::max());
textbox->set_font_data(io.fonts);
textbox->set_allow_newlines(false);
template <typename T> void TextBox<T>::init_textbox(UpdateInputData& io, bool forceTextUpdate) {
if(!textbox) {
textbox = std::make_shared<RichText::TextBox>();
textbox->set_width(std::numeric_limits<float>::max());
textbox->set_font_data(io.fonts);
textbox->set_allow_newlines(false);
cur = std::make_shared<RichText::TextBox::Cursor>();
rect = std::make_shared<SCollision::AABB<float>>();
}
cur = std::make_shared<RichText::TextBox::Cursor>();
rect = std::make_shared<SCollision::AABB<float>>();
if(forceTextUpdate || !oldData.has_value() || oldData.value() != *userInfo.data) {
textbox->clear_text();
cur->pos = cur->selectionBeginPos = cur->selectionEndPos = textbox->insert({0, 0}, userInfo.toStr(*userInfo.data));
}
cur->pos = cur->selectionBeginPos = cur->selectionEndPos = textbox->insert({0, 0}, userInfo.toStr(*userInfo.data));
textbox->onUserTextEdit = [&] {
if(userInfo.immutable)
cur->pos = cur->selectionBeginPos = cur->selectionEndPos = textbox->insert({0, 0}, userInfo.toStr(*userInfo.data));
else {
if(update_data() && userInfo.onEdit)
gui.set_post_callback_func(userInfo.onEdit);
gui.set_post_callback_func_high_priority(userInfo.onEdit);
}
};
}
@ -124,6 +130,7 @@ template <typename T> bool TextBox<T>::update_data() {
std::optional<T> dataToAssign = userInfo.fromStr(textbox->get_string());
if(dataToAssign.has_value()) {
*userInfo.data = dataToAssign.value();
oldData = dataToAssign;
return true;
}
return false;