/***************************************************************************************** * * * OpenSpace * * * * Copyright (c) 2014-2021 * * * * Permission is hereby granted, free of charge, to any person obtaining a copy of this * * software and associated documentation files (the "Software"), to deal in the Software * * without restriction, including without limitation the rights to use, copy, modify, * * merge, publish, distribute, sublicense, and/or sell copies of the Software, and to * * permit persons to whom the Software is furnished to do so, subject to the following * * conditions: * * * * The above copyright notice and this permission notice shall be included in all copies * * or substantial portions of the Software. * * * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, * * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A * * PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT * * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE * * OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. * ****************************************************************************************/ #include #include #include #include #include #include #include #include #include #include #include namespace { constexpr const char _loggerCat[] = "EventInfo"; } // namespace using namespace std::string_literals; namespace openspace::events { void log(int i, const EventSceneGraphNodeAdded& e) { ghoul_assert(e.type == EventSceneGraphNodeAdded::Type, "Wrong type"); LINFO(fmt::format("[{}] SceneGraphNodeAdded: {}", i, e.node)); } void log(int i, const EventSceneGraphNodeRemoved& e) { ghoul_assert(e.type == EventSceneGraphNodeRemoved::Type, "Wrong type"); LINFO(fmt::format("[{}] SceneGraphNodeRemoved: {}", i, e.node)); } void log(int i, const EventParallelConnection& e) { ghoul_assert(e.type == EventParallelConnection::Type, "Wrong type"); std::string_view state = [](EventParallelConnection::State s) { switch (s) { case EventParallelConnection::State::Established: return "Established"; case EventParallelConnection::State::Lost: return "Lost"; case EventParallelConnection::State::HostshipGained: return "HostshipGained"; case EventParallelConnection::State::HostshipLost: return "HostshipLost"; default: throw ghoul::MissingCaseException(); } }(e.state); LINFO(fmt::format("[{}] ParallelConnection ({})", i, state)); } void log(int i, [[ maybe_unused ]] const EventProfileLoadingFinished& e) { ghoul_assert(e.type == EventProfileLoadingFinished::Type, "Wrong type"); LINFO(fmt::format("[{}] ProfileLoadingFinished", i)); } void log(int i, const EventApplicationShutdown& e) { ghoul_assert(e.type == EventApplicationShutdown::Type, "Wrong type"); std::string t = [](EventApplicationShutdown::State state) { switch (state) { case EventApplicationShutdown::State::Started: return "started"; case EventApplicationShutdown::State::Aborted: return "aborted"; case EventApplicationShutdown::State::Finished: return "finished"; default: throw ghoul::MissingCaseException(); } }(e.state); LINFO(fmt::format("[{}] ApplicationShutdown", i)); } void log(int i, const EventScreenSpaceRenderableAdded& e) { ghoul_assert(e.type == EventScreenSpaceRenderableAdded::Type, "Wrong type"); LINFO(fmt::format("[{}] ScreenSpaceRenderableAdded: {}", i, e.renderable)); } void log(int i, const EventScreenSpaceRenderableRemoved& e) { ghoul_assert(e.type == EventScreenSpaceRenderableRemoved::Type, "Wrong type"); LINFO(fmt::format("[{}] ScreenSpaceRenderableRemoved: {}", i, e.renderable)); } void log(int i, const EventCameraFocusTransition& e) { ghoul_assert(e.type == EventCameraFocusTransition::Type, "Wrong type"); std::string_view t = [](EventCameraFocusTransition::Transition transition) { switch (transition) { case EventCameraFocusTransition::Transition::Approaching: return "Approaching"; case EventCameraFocusTransition::Transition::Reaching: return "Reaching"; case EventCameraFocusTransition::Transition::Receding: return "Receding"; case EventCameraFocusTransition::Transition::Exiting: return "Exiting"; default: throw ghoul::MissingCaseException(); } }(e.transition); LINFO(fmt::format( "[{}] CameraTransition: {}, {} ({})", i, reinterpret_cast(e.camera), e.node, t )); } void log(int i, const EventTimeOfInterestReached& e) { ghoul_assert(e.type == EventTimeOfInterestReached::Type, "Wrong type"); LINFO(fmt::format( "[{}] TimeOfInterestReached: {}, {}", i, e.time->UTC(), reinterpret_cast(e.camera) )); } void log(int i, [[ maybe_unused ]] const EventMissionEventReached& e) { ghoul_assert(e.type == EventMissionEventReached::Type, "Wrong type"); LINFO(fmt::format("[{}] MissionEventReached", i)); } void log(int i, const EventPlanetEclipsed& e) { ghoul_assert(e.type == EventPlanetEclipsed::Type, "Wrong type"); LINFO(fmt::format("[{}] PlanetEclipsed: {} -> {}", i, e.eclipsee, e.eclipser)); } void log(int i, [[ maybe_unused ]] const EventInterpolationFinished& e) { ghoul_assert(e.type == EventInterpolationFinished::Type, "Wrong type"); LINFO(fmt::format("[{}] InterpolationFinished", i)); } void log(int i, const EventFocusNodeChanged& e) { ghoul_assert(e.type == EventFocusNodeChanged::Type, "Wrong type"); LINFO(fmt::format("[{}] FocusNodeChanged: {} -> {}", i, e.oldNode, e.newNode)); } void log(int i, const EventLayerAdded& e) { ghoul_assert(e.type == EventLayerAdded::Type, "Wrong type"); LINFO(fmt::format("[{}] LayerAdded: {}", i, e.layer)); } void log(int i, const EventLayerRemoved& e) { ghoul_assert(e.type == EventLayerRemoved::Type, "Wrong type"); LINFO(fmt::format("[{}] LayerRemoved: {}", i, e.layer)); } void log(int i, const EventSessionRecordingPlayback& e) { ghoul_assert(e.type == EventSessionRecordingPlayback::Type, "Wrong type"); std::string_view state = [](EventSessionRecordingPlayback::State s) { switch (s) { case EventSessionRecordingPlayback::State::Started: return "Started"; case EventSessionRecordingPlayback::State::Paused: return "Paused"; case EventSessionRecordingPlayback::State::Resumed: return "Resumed"; case EventSessionRecordingPlayback::State::Finished: return "Finished"; default: throw ghoul::MissingCaseException(); } }(e.state); LINFO(fmt::format("[{}] SessionRecordingPlayback: {}", i, state)); } void log(int i, const CustomEvent& e) { ghoul_assert(e.type == CustomEvent::Type, "Wrong type"); LINFO(fmt::format("[{}] CustomEvent: {} ({})", i, e.subtype, e.payload)); } std::string_view toString(Event::Type type) { switch (type) { case Event::Type::SceneGraphNodeAdded: return "SceneGraphNodeAdded"; case Event::Type::SceneGraphNodeRemoved: return "SceneGraphNodeRemoved"; case Event::Type::ParallelConnection: return "ParallelConnection"; case Event::Type::ProfileLoadingFinished: return "ProfileLoadingFinished"; case Event::Type::ApplicationShutdown: return "ApplicationShutdown"; case Event::Type::ScreenSpaceRenderableAdded: return "ScreenSpaceRenderableAdded"; case Event::Type::ScreenSpaceRenderableRemoved: return "ScreenSpaceRenderableRemoved"; case Event::Type::CameraFocusTransition: return "CameraFocusTransition"; case Event::Type::TimeOfInterestReached: return "TimeOfInterestReached"; case Event::Type::MissionEventReached: return "MissionEventReached"; case Event::Type::PlanetEclipsed: return "PlanetEclipsed"; case Event::Type::InterpolationFinished: return "InterpolationFinished"; case Event::Type::FocusNodeChanged: return "FocusNodeChanged"; case Event::Type::LayerAdded: return "LayerAdded"; case Event::Type::LayerRemoved: return "LayerRemoved"; case Event::Type::SessionRecordingPlayback: return "SessionRecordingPlayback"; case Event::Type::Custom: return "Custom"; default: throw ghoul::MissingCaseException(); } } Event::Type fromString(std::string_view str) { if (str == "SceneGraphNodeAdded") { return Event::Type::SceneGraphNodeAdded; } else if (str == "SceneGraphNodeRemoved") { return Event::Type::SceneGraphNodeRemoved; } else if (str == "ParallelConnection") { return Event::Type::ParallelConnection; } else if (str == "ProfileLoadingFinished") { return Event::Type::ProfileLoadingFinished; } else if (str == "ApplicationShutdown") { return Event::Type::ApplicationShutdown; } else if (str == "ScreenSpaceRenderableAdded") { return Event::Type::ScreenSpaceRenderableAdded; } else if (str == "ScreenSpaceRenderableRemoved") { return Event::Type::ScreenSpaceRenderableRemoved; } else if (str == "CameraFocusTransition") { return Event::Type::CameraFocusTransition; } else if (str == "TimeOfInterestReached") { return Event::Type::TimeOfInterestReached; } else if (str == "MissionEventReached") { return Event::Type::MissionEventReached; } else if (str == "PlanetEclipsed") { return Event::Type::PlanetEclipsed; } else if (str == "InterpolationFinished") { return Event::Type::InterpolationFinished; } else if (str == "FocusNodeChanged") { return Event::Type::FocusNodeChanged; } else if (str == "LayerAdded") { return Event::Type::LayerAdded; } else if (str == "LayerRemoved") { return Event::Type::LayerRemoved; } else if (str == "SessionRecordingPlayback") { return Event::Type::SessionRecordingPlayback; } else if (str == "Custom") { return Event::Type::Custom; } throw ghoul::RuntimeError(fmt::format("Unknown event type '{}'", str)); } ghoul::Dictionary toParameter(const Event& e) { ghoul::Dictionary d; switch (e.type) { case Event::Type::SceneGraphNodeAdded: d.setValue( "Node", std::string(static_cast(e).node) ); break; case Event::Type::SceneGraphNodeRemoved: d.setValue( "Node", std::string(static_cast(e).node) ); break; case Event::Type::ParallelConnection: switch (static_cast(e).state) { case EventParallelConnection::State::Established: d.setValue("State", "Established"s); break; case EventParallelConnection::State::Lost: d.setValue("State", "Lost"s); break; case EventParallelConnection::State::HostshipGained: d.setValue("State", "HostshipGained"s); break; case EventParallelConnection::State::HostshipLost: d.setValue("State", "HostshipLost"s); break; default: throw ghoul::MissingCaseException(); } break; case Event::Type::ApplicationShutdown: switch (static_cast(e).state) { case EventApplicationShutdown::State::Started: d.setValue("State", "Started"s); break; case EventApplicationShutdown::State::Aborted: d.setValue("State", "Aborted"s); break; case EventApplicationShutdown::State::Finished: d.setValue("State", "Finished"s); break; } break; case Event::Type::ScreenSpaceRenderableAdded: d.setValue( "Renderable", std::string( static_cast(e).renderable ) ); break; case Event::Type::ScreenSpaceRenderableRemoved: d.setValue( "Renderable", std::string( static_cast(e).renderable ) ); break; case Event::Type::CameraFocusTransition: d.setValue( "Node", std::string(static_cast(e).node) ); switch (static_cast(e).transition) { case EventCameraFocusTransition::Transition::Approaching: d.setValue("Transition", "Approaching"s); break; case EventCameraFocusTransition::Transition::Reaching: d.setValue("Transition", "Reaching"s); break; case EventCameraFocusTransition::Transition::Receding: d.setValue("Transition", "Receding"s); break; case EventCameraFocusTransition::Transition::Exiting: d.setValue("Transition", "Exiting"s); break; default: throw ghoul::MissingCaseException(); } break; case Event::Type::PlanetEclipsed: d.setValue( "Eclipsee", std::string(static_cast(e).eclipsee) ); d.setValue( "Eclipser", std::string(static_cast(e).eclipser) ); break; case Event::Type::InterpolationFinished: d.setValue( "Property", std::string(static_cast(e).property) ); break; case Event::Type::FocusNodeChanged: d.setValue( "OldNode", std::string(static_cast(e).oldNode) ); d.setValue( "NewNode", std::string(static_cast(e).newNode) ); break; case Event::Type::LayerAdded: d.setValue( "Globe", std::string(static_cast(e).node) ); d.setValue( "Group", std::string(static_cast(e).layerGroup) ); d.setValue( "Layer", std::string(static_cast(e).layer) ); break; case Event::Type::LayerRemoved: d.setValue( "Globe", std::string(static_cast(e).node) ); d.setValue( "Group", std::string(static_cast(e).layerGroup) ); d.setValue( "Layer", std::string(static_cast(e).layer) ); break; case Event::Type::SessionRecordingPlayback: switch (static_cast(e).state) { case EventSessionRecordingPlayback::State::Started: d.setValue("State", "Started"s); break; case EventSessionRecordingPlayback::State::Paused: d.setValue("State", "Paused"s); break; case EventSessionRecordingPlayback::State::Resumed: d.setValue("State", "Resumed"s); break; case EventSessionRecordingPlayback::State::Finished: d.setValue("State", "Finished"s); break; } break; case Event::Type::Custom: d.setValue( "Subtype", std::string(static_cast(e).subtype) ); break; default: break; } return d; } void logAllEvents(const Event* e) { int i = 0; while (e) { switch (e->type) { case Event::Type::SceneGraphNodeAdded: log(i, *static_cast(e)); break; case Event::Type::SceneGraphNodeRemoved: log(i, *static_cast(e)); break; case Event::Type::ParallelConnection: log(i, *static_cast(e)); break; case Event::Type::ProfileLoadingFinished: log(i, *static_cast(e)); break; case Event::Type::ApplicationShutdown: log(i, *static_cast(e)); break; case Event::Type::ScreenSpaceRenderableAdded: log(i, *static_cast(e)); break; case Event::Type::ScreenSpaceRenderableRemoved: log(i, *static_cast(e)); break; case Event::Type::CameraFocusTransition: log(i, *static_cast(e)); break; case Event::Type::TimeOfInterestReached: log(i, *static_cast(e)); break; case Event::Type::MissionEventReached: log(i, *static_cast(e)); break; case Event::Type::PlanetEclipsed: log(i, *static_cast(e)); break; case Event::Type::InterpolationFinished: log(i, *static_cast(e)); break; case Event::Type::FocusNodeChanged: log(i, *static_cast(e)); break; case Event::Type::LayerAdded: log(i, *static_cast(e)); break; case Event::Type::LayerRemoved: log(i, *static_cast(e)); break; case Event::Type::SessionRecordingPlayback: log(i, *static_cast(e)); break; case Event::Type::Custom: log(i, *static_cast(e)); break; default: LINFO(fmt::format("[{}]: Unknown {}", typeid(e).name())); break; } i++; e = e->next; } } EventSceneGraphNodeAdded::EventSceneGraphNodeAdded(const SceneGraphNode* node_) : Event(Type) , node(temporaryString(node_->identifier())) {} EventSceneGraphNodeRemoved::EventSceneGraphNodeRemoved(const SceneGraphNode* node_) : Event(Type) , node(temporaryString(node_->identifier())) {} EventParallelConnection::EventParallelConnection(State state_) : Event(Type) , state(state_) {} EventProfileLoadingFinished::EventProfileLoadingFinished() : Event(Type) {} EventApplicationShutdown::EventApplicationShutdown(State state_) : Event(Type) , state(state_) {} EventScreenSpaceRenderableAdded::EventScreenSpaceRenderableAdded( const ScreenSpaceRenderable* renderable_) : Event(Type) , renderable(temporaryString(renderable_->identifier())) {} EventScreenSpaceRenderableRemoved::EventScreenSpaceRenderableRemoved( const ScreenSpaceRenderable* renderable_) : Event(Type) , renderable(temporaryString(renderable_->identifier())) {} EventCameraFocusTransition::EventCameraFocusTransition(const Camera* camera_, const SceneGraphNode* node_, Transition transition_) : Event(Type) , camera(camera_) , node(temporaryString(node_->identifier())) , transition(transition_) {} EventTimeOfInterestReached::EventTimeOfInterestReached(const Time* time_, const Camera* camera_) : Event(Type) , time(time_) , camera(camera_) {} EventMissionEventReached::EventMissionEventReached() : Event(Type) {} EventPlanetEclipsed::EventPlanetEclipsed(const SceneGraphNode* eclipsee_, const SceneGraphNode* eclipser_) : Event(Type) , eclipsee(temporaryString(eclipsee_->identifier())) , eclipser(temporaryString(eclipser_->identifier())) {} EventInterpolationFinished::EventInterpolationFinished( const properties::Property* property_) : Event(Type) , property(temporaryString(property_->fullyQualifiedIdentifier())) {} EventFocusNodeChanged::EventFocusNodeChanged(const SceneGraphNode* oldNode_, const SceneGraphNode* newNode_) : Event(Type) , oldNode(oldNode_ ? temporaryString(oldNode_->identifier()) : "") , newNode(temporaryString(newNode_->identifier())) { ghoul_assert(newNode_, "There must be a new node"); } EventLayerAdded::EventLayerAdded(std::string_view node_, std::string_view layerGroup_, std::string_view layer_) : Event(Type) , node(temporaryString(node_)) , layerGroup(temporaryString(layerGroup_)) , layer(temporaryString(layer_)) {} EventLayerRemoved::EventLayerRemoved(std::string_view node_, std::string_view layerGroup_, std::string_view layer_) : Event(Type) , node(temporaryString(node_)) , layerGroup(temporaryString(layerGroup_)) , layer(temporaryString(layer_)) {} EventSessionRecordingPlayback::EventSessionRecordingPlayback(State state_) : Event(Type) , state(state_) {} CustomEvent::CustomEvent(std::string_view subtype_, const void* payload_) : Event(Type) , subtype(subtype_) , payload(payload_) {} } // namespace openspace::events