ImGuiProgressList.cpp 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. /*
  2. * Copyright (c) Contributors to the Open 3D Engine Project.
  3. * For complete copyright and license terms please see the LICENSE at the root of this distribution.
  4. *
  5. * SPDX-License-Identifier: Apache-2.0 OR MIT
  6. *
  7. */
  8. #include <Utils/ImGuiProgressList.h>
  9. #include <Automation/ScriptableImGui.h>
  10. namespace AtomSampleViewer
  11. {
  12. void ImGuiProgressList::OpenPopup(AZStd::string_view title, AZStd::string_view description, const AZStd::vector<AZStd::string>& itemsList,
  13. AZStd::function<void()> onUserAction, bool automaticallyCloseOnAction, AZStd::string_view actionButtonLabel)
  14. {
  15. AZ_Assert(m_state == State::Closed, "Popup is already open");
  16. m_title = title;
  17. m_description = description;
  18. m_itemsList = itemsList;
  19. m_onUserAction = onUserAction;
  20. m_automaticallyCloseOnAction = automaticallyCloseOnAction;
  21. m_actionButtonLabel = actionButtonLabel;
  22. m_state = State::Opening;
  23. AZ::TickBus::Handler::BusConnect();
  24. }
  25. void ImGuiProgressList::ClosePopup()
  26. {
  27. if (m_state == State::Closed)
  28. {
  29. return;
  30. }
  31. AZ::TickBus::Handler::BusDisconnect();
  32. m_onUserAction = nullptr;
  33. m_state = State::Closed;
  34. }
  35. void ImGuiProgressList::AddItem(AZStd::string_view item)
  36. {
  37. AZ_Assert(m_state != State::Closed, "Can't add item while this widget is closed.");
  38. m_itemsList.push_back(item);
  39. }
  40. void ImGuiProgressList::RemoveItem(AZStd::string_view item)
  41. {
  42. AZ_Assert(m_state != State::Closed, "Can't remove item while this widget is closed.");
  43. m_itemsList.erase(AZStd::remove(m_itemsList.begin(), m_itemsList.end(), item), m_itemsList.end());
  44. }
  45. void ImGuiProgressList::TickPopup()
  46. {
  47. if (m_state == State::Opening)
  48. {
  49. ImGui::OpenPopup(m_title.c_str());
  50. m_state = State::Open;
  51. }
  52. if (ImGui::IsPopupOpen(m_title.c_str()))
  53. {
  54. if (m_itemsList.size() == 0)
  55. {
  56. ClosePopup();
  57. return;
  58. }
  59. const ImGuiWindowFlags windowFlags =
  60. ImGuiWindowFlags_NoCollapse |
  61. ImGuiWindowFlags_HorizontalScrollbar;
  62. if (ImGui::BeginPopupModal(m_title.c_str(), nullptr, windowFlags))
  63. {
  64. ImGui::Text("%s", m_description.c_str());
  65. ScriptableImGui::PushNameContext(m_title.c_str());
  66. auto listBoxGetter = +[](void* data, int idx, const char** out_text)
  67. {
  68. const auto* itemsList = reinterpret_cast<const AZStd::vector<AZStd::string>*>(data);
  69. *out_text = (*itemsList)[idx].c_str();
  70. return true;
  71. };
  72. ImGui::PushItemWidth(-1.0f);
  73. ScriptableImGui::ListBox("", &m_selectedItemIndex, listBoxGetter, &m_itemsList, static_cast<int>(m_itemsList.size()));
  74. ImGui::PopItemWidth();
  75. if (ScriptableImGui::Button(m_actionButtonLabel.c_str()))
  76. {
  77. if (m_onUserAction)
  78. {
  79. m_onUserAction();
  80. }
  81. if (m_automaticallyCloseOnAction)
  82. {
  83. ImGui::CloseCurrentPopup();
  84. ClosePopup();
  85. }
  86. }
  87. ScriptableImGui::PopNameContext();
  88. ImGui::EndPopup();
  89. }
  90. }
  91. else if(m_state == State::Open)
  92. {
  93. // If another ImGui window is opened while a modal popup is open, it kills the modal popup. So open it again.
  94. m_state = State::Opening;
  95. }
  96. }
  97. void ImGuiProgressList::OnTick([[maybe_unused]] float deltaTime, [[maybe_unused]] AZ::ScriptTimePoint time)
  98. {
  99. TickPopup();
  100. }
  101. } // namespace AtomSampleViewer