diff --git a/samples/main.cpp b/samples/main.cpp index 3a7f42e..bfb60bc 100644 --- a/samples/main.cpp +++ b/samples/main.cpp @@ -95,13 +95,14 @@ int main(int argc, char *argv[]) { Widgets::button(5, RootPanelId, "Test 3", Rect(100, 150, 100, 40), nullptr); Widgets::imageButton(6, RootPanelId, "button_test.png", Rect(100, 200, 100, 40), nullptr); - auto &ctx = TinyUi::getContext(); - CallbackI quitCallback(quit, (void*) &ctx); - Widgets::button(7, RootPanelId, "Quit", Rect(100, 250, 100, 40), &quitCallback); - CallbackI updateProgressBarCallback(updateProgressbar, nullptr, Events::UpdateEvent); - Widgets::progressBar(8, RootPanelId, Rect(100, 300, 100, 40), 50, &updateProgressBarCallback); + // Allocate callbacks dynamically to ensure they persist during event handling + CallbackI *dynamicQuitCallback = new CallbackI(quit, (void*) &ctx); + CallbackI *dynamicUpdateProgressBarCallback = new CallbackI(updateProgressbar, nullptr, Events::UpdateEvent); + + Widgets::button(7, RootPanelId, "Quit", Rect(100, 250, 100, 40), dynamicQuitCallback); + Widgets::progressBar(8, RootPanelId, Rect(100, 300, 100, 40), 50, dynamicUpdateProgressBarCallback); Widgets::inputText(9, RootPanelId, Rect(100, 350, 100, 40), Alignment::Left); @@ -110,7 +111,7 @@ int main(int argc, char *argv[]) { //Widgets::treeItem(12, 11, "Item 1.1"); Widgets::treeItem(13, 10, "Item 2"); Widgets::treeItem(14, 13, "Item 2.1"); - + while (TinyUi::run()) { TinyUi::render(); } diff --git a/src/tinyui.h b/src/tinyui.h index b0fed8d..103119b 100644 --- a/src/tinyui.h +++ b/src/tinyui.h @@ -314,6 +314,8 @@ struct CallbackI { funcCallback mfuncCallback[Events::NumEvents]; /// The data instance. void *mInstance{nullptr}; + /// The reference count for the callback interface, used for memory management. + uint32_t mNumRefs{ 0 }; /// @brief The default class constructor. CallbackI() : mfuncCallback{ nullptr } { @@ -339,6 +341,21 @@ struct CallbackI { mfuncCallback[i] = nullptr; } } + + /// @brief Increment the reference count. + void incRef() { + ++mNumRefs; + } + + /// @brief Decrement the reference count. + void decRef() { + if (mNumRefs > 0) { + --mNumRefs; + if (mNumRefs == 0) { + delete this; + } + } + } }; /// @brief The event callback array. diff --git a/src/widgets.cpp b/src/widgets.cpp index 0c131df..7dce1b0 100644 --- a/src/widgets.cpp +++ b/src/widgets.cpp @@ -271,6 +271,9 @@ ret_code Widgets::button(Id id, Id parentId, const char *text, const Rect &rect, } child->mCallback = callback; + if (callback != nullptr) { + callback->incRef(); + } if (text != nullptr) { child->mText.assign(text); } @@ -294,6 +297,10 @@ ret_code Widgets::imageButton(Id id, Id parentId, const char *image, const Rect } child->mCallback = callback; + if (callback != nullptr) { + callback->incRef(); + } + if (image != nullptr) { child->mImage = loadIntoImageCache(ctx, image); } @@ -395,6 +402,9 @@ ret_code Widgets::treeView(Id id, Id parentId, const char *title, const Rect &re CallbackI *callback = new CallbackI(onTreeViewItemClicked, nullptr, Events::MouseButtonDownEvent); widget->mCallback = callback; + if (callback != nullptr) { + callback->incRef(); + } return ResultOk; } diff --git a/src/widgets.h b/src/widgets.h index 0fbae5c..4e897a1 100644 --- a/src/widgets.h +++ b/src/widgets.h @@ -94,6 +94,10 @@ struct Widget { if (mContent != nullptr) { delete [] mContent; } + + if (mCallback != nullptr) { + mCallback->decRef(); + } } /// @brief Check if the widget has a specific style.