Replies: 10 comments 20 replies
-
I think this should be in UppHub. |
Beta Was this translation helpful? Give feedback.
-
Yes, I agree with Mirek, it should be part of UppHub. We should carefully add new libraries to the main branch. Also, adding new lirbaries to UppHub is easy. If you will have any troubles, please let me know. I will help. |
Beta Was this translation helpful? Give feedback.
-
Hi Trilec Nice!, your library can be very useful for people who are interested in process modelling. Best regards |
Beta Was this translation helpful? Give feedback.
-
Hi Trilec, Nice stuff. If you need any help preparing this for UppHub, let me or Kluiger know. Best, |
Beta Was this translation helpful? Give feedback.
-
Good point, and normally I'd agree 100% on My thinking here is a little different, and it's really a two-part argument. The first part is my specific plan, and the second, more important part is about the fundamental nature of a state machine in a modern framework. First, this is step one of a two-step project for me. The next step is to build a But more broadly, I believe providing a state machine as a core component is a powerful way to empower developers. For context, here's how some other major ecosystems approach this:
My goal is to provide a tool that makes U++ more powerful and aligns it with other leading platforms. It's a strategic dependency the future, and hopefully attract more developers with its core features. (I feel I'm in this boat, as I now try to shift my development to U++, and see it with fairly fresh eyes) I hope that provides a clearer and more compelling case for its inclusion in the main library. |
Beta Was this translation helpful? Give feedback.
-
Just my two cents: I believe that, if implemented well, U++ could really benefit from an asynchronous state machine. While animations aren't my main concern, I'm especially interested in the socket and networking side of things. Take a look at the Moreover, it would help establish a uniform and structured approach to asynchronous code across the framework, reducing duplication in future developments, whatever they may be. |
Beta Was this translation helpful? Give feedback.
-
Just to make things clear, we are more concerned about the amount of source code that is considered "canonical" (like core U++). It is maintainance concerns basically. |
Beta Was this translation helpful? Give feedback.
-
Thanks all for the feedback. Just to clarify — while this state machine is designed with UI and animation flows in mind, it's a general-purpose asynchronous tool. It works well for task orchestration, background logic, lifecycles, stateful APIs and anywhere structured state transitions help manage complexity. The goal is clean, non-blocking flow, tied into the U++ main loop — not just for look-and-feel, but for clarity and maintainability across app types. I understand the concern about keeping upp lean. At the same time, I’d argue this FSM fills a foundational role — much like what .NET/ Qt /Redux/Swift and other modern frameworks — especially if we want to support animation and richer UI behavior natively. My intention is to build a View or Animation Manager on top of this. Splitting them into UppHub and core would fragment the architecture and create unnecessary overhead for anyone using both. As for async interface styles — I see @kov-serg’s loop-based model is valid for service-like use cases. While the FSM here isn’t based on polling, it wouldn’t be hard to add a wrapper (e.g., monitorAdapter) for that style, if needed — without changing the core design. // possible minimal “monitor” adapter ( rough concept)
// Lets a polling scheduler *observe* when the FSM is done.
// however It does **not** drive transitions or advance time.
enum { se_Init, se_Done };
struct FsmMonitorAdapter {
StateMachine* fsm; // proposed StateMachine
static int Setup(void* ctx, int cmd) {
auto* self = static_cast<FsmMonitorAdapter*>(ctx);
switch(cmd) {
case se_Init: return self->fsm->Start() ? 0 : -1;
case se_Done: return self->fsm->Stop() ? 0 : -1;
default: return -1; // unsupported command
}
}
// 1 = still busy, 0 = reached a terminal state
static int Loop(void* ctx) {
auto* self = static_cast<FsmMonitorAdapter*>(ctx);
return self->fsm->IsBusy() ? 1 : 0;
}
}; Caveats of this approach
In short, the adapter can integrate with a polling framework, but it’s a monitor, not a driver. I’m happy to release this to UppHub if that’s the consensus, but feel there's a strong case for treating it as a small but strategic addition to core — especially if we want U++ to evolve toward more responsive / swipe / mobile-like GUIs. Cheers, |
Beta Was this translation helpful? Give feedback.
-
Hi all — just checking in. I’d like to move forward on this now. From my side the design’s settled and seems stable enough for a PR — unless anyone has strong objections, happy to prep it for submission. Let me know if that sounds okay. Cheers, |
Beta Was this translation helpful? Give feedback.
-
Thanks for the support @klugier.
Next steps:
Feel free to review here [ github.com/Trilec/upp_statemachine ] Cheers, |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
-
Hello U++ peoples,
I would like to propose the inclusion of a new library,
upp-statemachine
, into the U++ framework. This is a general-purpose, asynchronous state machine designed to manage complex application logic in a clean, robust, and maintainable way. It is implemented as a traditional.h
and.cpp
pair.The complete source code, along with a comprehensive GUI test harness, is available for review here:
https://github.com/Trilec/upp_statemachine
Why a State Machine for U++?
Many applications, from complex user interfaces to background services, are fundamentally stateful. Managing this state often involves complex chains of
if/else
statements, boolean flags, and scattered logic, which can be difficult to debug and extend.A formal state machine provides a proven pattern for solving this problem. This library is designed to:
While it is a perfect companion for
CtrlLib
to manage window or dialog states, it has no dependency on GUI components and is equally powerful for console applications, server-side logic, or any long-running process.Key Features & Design Philosophy
The design was guided by the U++ philosophy of creating efficient, powerful, and easy-to-use tools.
One<>
smart pointers for managing the lifecycle of states and transitions, integrating cleanly with U++'s memory model.OnEnter
) and exit (OnExit
) handlers are asynchronous. They receive adone
callback which they must invoke to signal completion, allowing for non-blocking, long-running operations.Guard
: A function that can conditionally block a transition from occurring.OnBefore
/OnAfter
: Callbacks that fire just before and after a transition, allowing for side effects and logging.GoBack()
method to revert to the previous state—ideal for "Cancel" or "Back" button functionality.Core
, making it lightweight and truly general-purpose.State
andTransition
structs, configured cleanly with lambdas for callbacks and guards.Robustness and Testing
A key goal was to ensure the library is stable and production-ready. To that end, it includes a comprehensive GUI test harness (
main.cpp
) that validates every aspect of its functionality, including:GoBack()
operations.This test suite serves as both a guarantee of correctness and as a rich source of usage examples.
Proposed Placement
Given its minimal dependency on
Core
and its general-purpose nature, I believe it could be a good fit within theuppsrc
directory, perhaps asuppsrc/Core/StateMachine.h
and.cpp
. However, I am completely open to suggestions on where it would best reside within the framework's structure.I believe this library would be a valuable addition to the U++ ecosystem.
I look forward to hearing your thoughts and feedback.
Cheers Curt
Beta Was this translation helpful? Give feedback.
All reactions