handstatebase.c 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. /**@class HandStateBase
  2. * @brief represent hand state base
  3. *
  4. * Class comes with entry/update/exit hooks that can be overriden in custom states
  5. **/
  6. class HandStateBase
  7. {
  8. Man m_Player; /// entity that this state relates to
  9. HandStateBase m_parentState; /// hierarchical parent state of this state (or null)
  10. ref HandFSM m_FSM; /// nested state machine (or null)
  11. void HandStateBase (Man player = NULL, HandStateBase parent = NULL) { m_Player = player; m_parentState = parent; }
  12. /**@fn SetParentState
  13. * @brief allows construction of hierarchical state machine
  14. **/
  15. void SetParentState (HandStateBase parent) { m_parentState = parent; }
  16. /**@fn GetParentState
  17. * @return state that owns this sub-state (or null if plain state)
  18. **/
  19. HandStateBase GetParentState () { return m_parentState; }
  20. bool HasFSM () { return m_FSM != NULL; }
  21. HandFSM GetFSM () { return m_FSM; }
  22. bool ProcessEvent (HandEventBase e)
  23. {
  24. if (HasFSM())
  25. return m_FSM.ProcessEvent(e);
  26. return false;
  27. }
  28. /**@fn AddTransition
  29. * @brief adds transition into m_FSM transition table
  30. **/
  31. void AddTransition (HandTransition t)
  32. {
  33. if (HasFSM())
  34. m_FSM.AddTransition(t);
  35. else
  36. Error("[hndfsm] adding transition to state without FSM. Configure FSM first.");
  37. }
  38. /**@fn OnEntry
  39. * @brief called upon entry to state
  40. * @NOTE if state has (non-running) sub-machine, it's started on entry
  41. * @param[in] e the event that triggered transition to this state
  42. **/
  43. void OnEntry (HandEventBase e)
  44. {
  45. if (HasFSM() && !m_FSM.IsRunning())
  46. {
  47. if (e)
  48. {
  49. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] { " + Object.GetDebugName(e.m_Player) + " STS = " + e.m_Player.GetSimulationTimeStamp() + " " + this.Type().ToString() + " Has Sub-FSM! Starting submachine...");
  50. }
  51. else
  52. {
  53. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] { " + this.Type().ToString() + " Has Sub-FSM! Starting submachine...");
  54. }
  55. m_FSM.Start(e);
  56. }
  57. else
  58. {
  59. if (e)
  60. {
  61. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] { " + Object.GetDebugName(e.m_Player) + " STS = " + e.m_Player.GetSimulationTimeStamp() + " " + this.Type().ToString());
  62. }
  63. else
  64. {
  65. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] { " + this.Type().ToString());
  66. }
  67. }
  68. }
  69. /**@fn OnUpdate
  70. * @brief ongoing behavior, performed while being in the state
  71. *
  72. * @NOTE: this is supposed to be the Do() operation in UML speak
  73. **/
  74. void OnUpdate (float dt)
  75. {
  76. if (HasFSM() && m_FSM.IsRunning())
  77. m_FSM.GetCurrentState().OnUpdate(dt);
  78. }
  79. /**@fn OnAbort
  80. * @brief called when abort signal arrives
  81. * @param[in] e the event that triggered abort from this state
  82. **/
  83. void OnAbort (HandEventBase e)
  84. {
  85. if (HasFSM() && m_FSM.IsRunning())
  86. {
  87. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] OnAbort " + this.Type().ToString() + " Has Sub-FSM! Aborting submachine...");
  88. m_FSM.Abort(e);
  89. }
  90. //Debug.InventoryHFSMLog("ABORTED " + e.m_Player.GetSimulationTimeStamp(), ""/*typename.EnumToString(HandEventID, GetEventID()) */, "n/a", "OnAbort", m_Player.ToString() );
  91. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] } " + Object.GetDebugName(e.m_Player) + " STS = " + e.m_Player.GetSimulationTimeStamp() + " ABORTED " + this.Type().ToString());
  92. }
  93. /**@fn OnExit
  94. * @brief called on exit from state
  95. * @param[in] e the event that triggered transition from this state
  96. **/
  97. void OnExit (HandEventBase e)
  98. {
  99. if (LogManager.IsInventoryHFSMLogEnable()) hndDebugPrint("[hndfsm] } " + Object.GetDebugName(e.m_Player) + " STS = " + e.m_Player.GetSimulationTimeStamp() + " " + this.Type().ToString());
  100. }
  101. /**@fn IsWaitingForActionFinish
  102. * @brief waiting for active animation action/actionType finish
  103. * @return true if this state is waiting for finish signal
  104. **/
  105. bool IsWaitingForActionFinish () { return HasFSM() && m_FSM.IsRunning() && m_FSM.GetCurrentState().IsWaitingForActionFinish(); }
  106. /**@fn IsIdle
  107. * @brief idle state does not expect any animation events
  108. * @return true if this state is idle
  109. **/
  110. bool IsIdle () { return false; }
  111. /**@fn OnSubMachineChanged
  112. * @brief called when sub-machine has changed its state
  113. * @param[in] src from state (previous)
  114. * @param[in] dst to state (current)
  115. **/
  116. void OnSubMachineChanged (HandStateBase src, HandStateBase dst) { }
  117. /**@fn OnStateChanged
  118. * @brief called on current state when state machine has changed its state
  119. * @param[in] src from state (previous)
  120. * @param[in] dst to state (current)
  121. **/
  122. void OnStateChanged (HandStateBase src, HandStateBase dst)
  123. {
  124. m_Player.GetHumanInventory().OnHandsStateChanged(src, dst);
  125. }
  126. };