diff --git a/common/tier4_system_rviz_plugin/CMakeLists.txt b/common/tier4_system_rviz_plugin/CMakeLists.txt
new file mode 100644
index 0000000000000..a65379c553131
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/CMakeLists.txt
@@ -0,0 +1,36 @@
+cmake_minimum_required(VERSION 3.14)
+project(tier4_system_rviz_plugin)
+
+find_package(autoware_cmake REQUIRED)
+autoware_package()
+
+find_package(Qt5 REQUIRED Core Widgets)
+set(QT_LIBRARIES Qt5::Widgets)
+
+set(CMAKE_AUTOMOC ON)
+set(CMAKE_INCLUDE_CURRENT_DIR ON)
+add_definitions(-DQT_NO_KEYWORDS)
+
+set(HEADERS
+ src/mrm_summary_overlay_display.hpp
+ src/jsk_overlay_utils.hpp
+)
+
+## Declare a C++ library
+ament_auto_add_library(tier4_system_rviz_plugin SHARED
+ src/mrm_summary_overlay_display.cpp
+ src/jsk_overlay_utils.cpp
+ ${HEADERS}
+)
+
+target_link_libraries(tier4_system_rviz_plugin
+ ${QT_LIBRARIES}
+)
+
+# Export the plugin to be imported by rviz2
+pluginlib_export_plugin_description_file(rviz_common plugins/plugin_description.xml)
+
+ament_auto_package(
+ INSTALL_TO_SHARE
+ plugins
+)
diff --git a/common/tier4_system_rviz_plugin/README.md b/common/tier4_system_rviz_plugin/README.md
new file mode 100644
index 0000000000000..098844c8b4091
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/README.md
@@ -0,0 +1 @@
+# tier4_system_rviz_plugin
diff --git a/common/tier4_system_rviz_plugin/package.xml b/common/tier4_system_rviz_plugin/package.xml
new file mode 100644
index 0000000000000..adae997ea07aa
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/package.xml
@@ -0,0 +1,30 @@
+
+
+
+ tier4_system_rviz_plugin
+ 0.1.0
+ The tier4_vehicle_rviz_plugin package
+ Koji Minoda
+ Apache License 2.0
+
+ ament_cmake_auto
+ autoware_cmake
+
+ autoware_auto_system_msgs
+ diagnostic_msgs
+ libqt5-core
+ libqt5-gui
+ libqt5-widgets
+ qtbase5-dev
+ rviz_common
+ rviz_default_plugins
+ rviz_ogre_vendor
+ tier4_autoware_utils
+
+ ament_lint_auto
+ autoware_lint_common
+
+
+ ament_cmake
+
+
diff --git a/common/tier4_system_rviz_plugin/plugins/plugin_description.xml b/common/tier4_system_rviz_plugin/plugins/plugin_description.xml
new file mode 100644
index 0000000000000..a3ac26d1a304d
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/plugins/plugin_description.xml
@@ -0,0 +1,6 @@
+
+
+
+
diff --git a/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.cpp b/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.cpp
new file mode 100644
index 0000000000000..36c5d1ce82693
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.cpp
@@ -0,0 +1,222 @@
+// Copyright 2022 Tier IV, Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Copyright (c) 2014, JSK Lab
+// All rights reserved.
+//
+// Software License Agreement (BSD License)
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following
+// disclaimer in the documentation and/or other materials provided
+// with the distribution.
+// * Neither the name of {copyright_holder} nor the names of its
+// contributors may be used to endorse or promote products derived
+// from this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+// COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+// ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.S SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.
+
+#include "jsk_overlay_utils.hpp"
+
+#include
+
+namespace jsk_rviz_plugins
+{
+ScopedPixelBuffer::ScopedPixelBuffer(Ogre::HardwarePixelBufferSharedPtr pixel_buffer)
+: pixel_buffer_(pixel_buffer)
+{
+ pixel_buffer_->lock(Ogre::HardwareBuffer::HBL_NORMAL);
+}
+
+ScopedPixelBuffer::~ScopedPixelBuffer()
+{
+ pixel_buffer_->unlock();
+}
+
+Ogre::HardwarePixelBufferSharedPtr ScopedPixelBuffer::getPixelBuffer()
+{
+ return pixel_buffer_;
+}
+
+QImage ScopedPixelBuffer::getQImage(unsigned int width, unsigned int height)
+{
+ const Ogre::PixelBox & pixelBox = pixel_buffer_->getCurrentLock();
+ Ogre::uint8 * pDest = static_cast(pixelBox.data);
+ memset(pDest, 0, width * height);
+ return QImage(pDest, width, height, QImage::Format_ARGB32);
+}
+
+QImage ScopedPixelBuffer::getQImage(unsigned int width, unsigned int height, QColor & bg_color)
+{
+ QImage Hud = getQImage(width, height);
+ for (unsigned int i = 0; i < width; i++) {
+ for (unsigned int j = 0; j < height; j++) {
+ Hud.setPixel(i, j, bg_color.rgba());
+ }
+ }
+ return Hud;
+}
+
+QImage ScopedPixelBuffer::getQImage(OverlayObject & overlay)
+{
+ return getQImage(overlay.getTextureWidth(), overlay.getTextureHeight());
+}
+
+QImage ScopedPixelBuffer::getQImage(OverlayObject & overlay, QColor & bg_color)
+{
+ return getQImage(overlay.getTextureWidth(), overlay.getTextureHeight(), bg_color);
+}
+
+OverlayObject::OverlayObject(const std::string & name) : name_(name)
+{
+ std::string material_name = name_ + "Material";
+ Ogre::OverlayManager * mOverlayMgr = Ogre::OverlayManager::getSingletonPtr();
+ overlay_ = mOverlayMgr->create(name_);
+ panel_ = static_cast(
+ mOverlayMgr->createOverlayElement("Panel", name_ + "Panel"));
+ panel_->setMetricsMode(Ogre::GMM_PIXELS);
+
+ panel_material_ = Ogre::MaterialManager::getSingleton().create(
+ material_name, Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
+ panel_->setMaterialName(panel_material_->getName());
+ overlay_->add2D(panel_);
+}
+
+OverlayObject::~OverlayObject()
+{
+ hide();
+ panel_material_->unload();
+ Ogre::MaterialManager::getSingleton().remove(panel_material_->getName());
+ // Ogre::OverlayManager* mOverlayMgr = Ogre::OverlayManager::getSingletonPtr();
+ // mOverlayMgr->destroyOverlayElement(panel_);
+ // delete panel_;
+ // delete overlay_;
+}
+
+std::string OverlayObject::getName()
+{
+ return name_;
+}
+
+void OverlayObject::hide()
+{
+ if (overlay_->isVisible()) {
+ overlay_->hide();
+ }
+}
+
+void OverlayObject::show()
+{
+ if (!overlay_->isVisible()) {
+ overlay_->show();
+ }
+}
+
+bool OverlayObject::isTextureReady()
+{
+ return static_cast(texture_);
+}
+
+void OverlayObject::updateTextureSize(unsigned int width, unsigned int height)
+{
+ const std::string texture_name = name_ + "Texture";
+ if (width == 0) {
+ RCLCPP_WARN(rclcpp::get_logger("OverlayObject"), "width=0 is specified as texture size");
+ width = 1;
+ }
+ if (height == 0) {
+ RCLCPP_WARN(rclcpp::get_logger("OverlayObject"), "height=0 is specified as texture size");
+ height = 1;
+ }
+ if (!isTextureReady() || ((width != texture_->getWidth()) || (height != texture_->getHeight()))) {
+ if (isTextureReady()) {
+ Ogre::TextureManager::getSingleton().remove(texture_name);
+ panel_material_->getTechnique(0)->getPass(0)->removeAllTextureUnitStates();
+ }
+ texture_ = Ogre::TextureManager::getSingleton().createManual(
+ texture_name, // name
+ Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME,
+ Ogre::TEX_TYPE_2D, // type
+ width, height, // width & height of the render window
+ 0, // number of mipmaps
+ Ogre::PF_A8R8G8B8, // pixel format chosen to match a format Qt can use
+ Ogre::TU_DEFAULT // usage
+ );
+ panel_material_->getTechnique(0)->getPass(0)->createTextureUnitState(texture_name);
+
+ panel_material_->getTechnique(0)->getPass(0)->setSceneBlending(Ogre::SBT_TRANSPARENT_ALPHA);
+ }
+}
+
+ScopedPixelBuffer OverlayObject::getBuffer()
+{
+ if (isTextureReady()) {
+ return ScopedPixelBuffer(texture_->getBuffer());
+ } else {
+ return ScopedPixelBuffer(Ogre::HardwarePixelBufferSharedPtr());
+ }
+}
+
+void OverlayObject::setPosition(double left, double top)
+{
+ panel_->setPosition(left, top);
+}
+
+void OverlayObject::setDimensions(double width, double height)
+{
+ panel_->setDimensions(width, height);
+}
+
+bool OverlayObject::isVisible()
+{
+ return overlay_->isVisible();
+}
+
+unsigned int OverlayObject::getTextureWidth()
+{
+ if (isTextureReady()) {
+ return texture_->getWidth();
+ } else {
+ return 0;
+ }
+}
+
+unsigned int OverlayObject::getTextureHeight()
+{
+ if (isTextureReady()) {
+ return texture_->getHeight();
+ } else {
+ return 0;
+ }
+}
+
+} // namespace jsk_rviz_plugins
diff --git a/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.hpp b/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.hpp
new file mode 100644
index 0000000000000..568111f241a28
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/src/jsk_overlay_utils.hpp
@@ -0,0 +1,138 @@
+// Copyright 2022 Tier IV, Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Copyright (c) 2014, JSK Lab
+// All rights reserved.
+//
+// Software License Agreement (BSD License)
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following
+// disclaimer in the documentation and/or other materials provided
+// with the distribution.
+// * Neither the name of {copyright_holder} nor the names of its
+// contributors may be used to endorse or promote products derived
+// from this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+// COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+// ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.S SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.
+
+#ifndef JSK_OVERLAY_UTILS_HPP_
+#define JSK_OVERLAY_UTILS_HPP_
+
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+// see OGRE/OgrePrerequisites.h
+// #define OGRE_VERSION
+// ((OGRE_VERSION_MAJOR << 16) | (OGRE_VERSION_MINOR << 8) | OGRE_VERSION_PATCH)
+#if OGRE_VERSION < ((1 << 16) | (9 << 8) | 0)
+#include
+#include
+#include
+#include
+#else
+#include
+#include
+#include
+#include
+#include
+#endif
+
+#include
+#include
+#include
+
+namespace jsk_rviz_plugins
+{
+class OverlayObject;
+
+class ScopedPixelBuffer
+{
+public:
+ explicit ScopedPixelBuffer(Ogre::HardwarePixelBufferSharedPtr pixel_buffer);
+ virtual ~ScopedPixelBuffer();
+ virtual Ogre::HardwarePixelBufferSharedPtr getPixelBuffer();
+ virtual QImage getQImage(unsigned int width, unsigned int height);
+ virtual QImage getQImage(OverlayObject & overlay);
+ virtual QImage getQImage(unsigned int width, unsigned int height, QColor & bg_color);
+ virtual QImage getQImage(OverlayObject & overlay, QColor & bg_color);
+
+protected:
+ Ogre::HardwarePixelBufferSharedPtr pixel_buffer_;
+
+private:
+};
+
+// this is a class for put overlay object on rviz 3D panel.
+// This class suppose to be instantiated in onInitialize method
+// of rviz::Display class.
+class OverlayObject
+{
+public:
+ typedef std::shared_ptr Ptr;
+
+ explicit OverlayObject(const std::string & name);
+ virtual ~OverlayObject();
+
+ virtual std::string getName();
+ virtual void hide();
+ virtual void show();
+ virtual bool isTextureReady();
+ virtual void updateTextureSize(unsigned int width, unsigned int height);
+ virtual ScopedPixelBuffer getBuffer();
+ virtual void setPosition(double left, double top);
+ virtual void setDimensions(double width, double height);
+ virtual bool isVisible();
+ virtual unsigned int getTextureWidth();
+ virtual unsigned int getTextureHeight();
+
+protected:
+ const std::string name_;
+ Ogre::Overlay * overlay_;
+ Ogre::PanelOverlayElement * panel_;
+ Ogre::MaterialPtr panel_material_;
+ Ogre::TexturePtr texture_;
+
+private:
+};
+
+// Ogre::Overlay* createOverlay(std::string name);
+// Ogre::PanelOverlayElement* createOverlayPanel(Ogre::Overlay* overlay);
+// Ogre::MaterialPtr createOverlayMaterial(Ogre::Overlay* overlay);
+} // namespace jsk_rviz_plugins
+
+#endif // JSK_OVERLAY_UTILS_HPP_
diff --git a/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.cpp b/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.cpp
new file mode 100644
index 0000000000000..b80f06f645632
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.cpp
@@ -0,0 +1,251 @@
+// Copyright 2023 Tier IV, Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Copyright (c) 2014, JSK Lab
+// All rights reserved.
+//
+// Software License Agreement (BSD License)
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following
+// disclaimer in the documentation and/or other materials provided
+// with the distribution.
+// * Neither the name of {copyright_holder} nor the names of its
+// contributors may be used to endorse or promote products derived
+// from this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+// COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+// ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.S SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.
+
+#include "mrm_summary_overlay_display.hpp"
+
+#include
+#include
+
+#include
+
+#include
+
+#include
+#include
+#include
+#include
+
+namespace rviz_plugins
+{
+void insertNewlines(std::string & str, const size_t max_line_length)
+{
+ size_t index = max_line_length;
+
+ while (index < str.size()) {
+ str.insert(index, "\n");
+ index = index + max_line_length + 1;
+ }
+}
+
+std::optional generateMrmMessage(diagnostic_msgs::msg::DiagnosticStatus diag_status)
+{
+ if (diag_status.hardware_id == "" || diag_status.hardware_id == "system_error_monitor") {
+ return std::nullopt;
+ } else if (diag_status.level == diagnostic_msgs::msg::DiagnosticStatus::ERROR) {
+ std::string msg = "- ERROR: " + diag_status.name + " (" + diag_status.message + ")";
+ insertNewlines(msg, 100);
+ return msg;
+ } else if (diag_status.level == diagnostic_msgs::msg::DiagnosticStatus::WARN) {
+ std::string msg = "- WARN: " + diag_status.name + " (" + diag_status.message + ")";
+ insertNewlines(msg, 100);
+ return msg;
+ }
+ return std::nullopt;
+}
+
+MrmSummaryOverlayDisplay::MrmSummaryOverlayDisplay()
+{
+ const Screen * screen_info = DefaultScreenOfDisplay(XOpenDisplay(NULL));
+
+ constexpr float hight_4k = 2160.0;
+ const float scale = static_cast(screen_info->height) / hight_4k;
+ const auto left = static_cast(std::round(1024 * scale));
+ const auto top = static_cast(std::round(128 * scale));
+
+ property_text_color_ = new rviz_common::properties::ColorProperty(
+ "Text Color", QColor(25, 255, 240), "text color", this, SLOT(updateVisualization()), this);
+ property_left_ = new rviz_common::properties::IntProperty(
+ "Left", left, "Left of the plotter window", this, SLOT(updateVisualization()), this);
+ property_left_->setMin(0);
+ property_top_ = new rviz_common::properties::IntProperty(
+ "Top", top, "Top of the plotter window", this, SLOT(updateVisualization()));
+ property_top_->setMin(0);
+
+ property_value_height_offset_ = new rviz_common::properties::IntProperty(
+ "Value height offset", 0, "Height offset of the plotter window", this,
+ SLOT(updateVisualization()));
+ property_font_size_ = new rviz_common::properties::IntProperty(
+ "Font Size", 10, "Font Size", this, SLOT(updateVisualization()), this);
+ property_font_size_->setMin(1);
+ property_max_letter_num_ = new rviz_common::properties::IntProperty(
+ "Max Letter Num", 100, "Max Letter Num", this, SLOT(updateVisualization()), this);
+ property_max_letter_num_->setMin(10);
+}
+
+MrmSummaryOverlayDisplay::~MrmSummaryOverlayDisplay()
+{
+ if (initialized()) {
+ overlay_->hide();
+ }
+}
+
+void MrmSummaryOverlayDisplay::onInitialize()
+{
+ RTDClass::onInitialize();
+ static int count = 0;
+ rviz_common::UniformStringStream ss;
+ ss << "MrmSummaryOverlayDisplayObject" << count++;
+ overlay_.reset(new jsk_rviz_plugins::OverlayObject(ss.str()));
+
+ overlay_->show();
+
+ const int texture_size = property_font_size_->getInt() * property_max_letter_num_->getInt();
+ overlay_->updateTextureSize(texture_size, texture_size);
+ overlay_->setPosition(property_left_->getInt(), property_top_->getInt());
+ overlay_->setDimensions(overlay_->getTextureWidth(), overlay_->getTextureHeight());
+}
+
+void MrmSummaryOverlayDisplay::onEnable()
+{
+ subscribe();
+ overlay_->show();
+}
+
+void MrmSummaryOverlayDisplay::onDisable()
+{
+ unsubscribe();
+ reset();
+ overlay_->hide();
+}
+
+void MrmSummaryOverlayDisplay::update(float wall_dt, float ros_dt)
+{
+ (void)wall_dt;
+ (void)ros_dt;
+
+ // MRM summary
+ std::vector mrm_comfortable_stop_summary_list = {};
+ std::vector mrm_emergency_stop_summary_list = {};
+ {
+ std::lock_guard message_lock(mutex_);
+ if (last_msg_ptr_) {
+ for (const auto & diag_status : last_msg_ptr_->status.diag_latent_fault) {
+ const std::optional msg = generateMrmMessage(diag_status);
+ if (msg != std::nullopt) {
+ mrm_comfortable_stop_summary_list.push_back(msg.value());
+ }
+ }
+ for (const auto & diag_status : last_msg_ptr_->status.diag_single_point_fault) {
+ const std::optional msg = generateMrmMessage(diag_status);
+ if (msg != std::nullopt) {
+ mrm_emergency_stop_summary_list.push_back(msg.value());
+ }
+ }
+ }
+ }
+
+ // Display
+ QColor background_color;
+ background_color.setAlpha(0);
+ jsk_rviz_plugins::ScopedPixelBuffer buffer = overlay_->getBuffer();
+ QImage hud = buffer.getQImage(*overlay_);
+ hud.fill(background_color);
+
+ QPainter painter(&hud);
+ painter.setRenderHint(QPainter::Antialiasing, true);
+
+ const int w = overlay_->getTextureWidth() - line_width_;
+ const int h = overlay_->getTextureHeight() - line_width_;
+
+ // text
+ QColor text_color(property_text_color_->getColor());
+ text_color.setAlpha(255);
+ painter.setPen(QPen(text_color, static_cast(2), Qt::SolidLine));
+ QFont font = painter.font();
+ font.setPixelSize(property_font_size_->getInt());
+ font.setBold(true);
+ painter.setFont(font);
+
+ std::ostringstream output_text;
+ output_text << std::fixed
+ << "Comfortable Stop MRM Summary: " << int(mrm_comfortable_stop_summary_list.size())
+ << std::endl;
+ for (const auto & mrm_element : mrm_comfortable_stop_summary_list) {
+ output_text << mrm_element << std::endl;
+ }
+ output_text << "Emergency Stop MRM Summary: " << int(mrm_emergency_stop_summary_list.size())
+ << std::endl;
+ for (const auto & mrm_element : mrm_emergency_stop_summary_list) {
+ output_text << mrm_element << std::endl;
+ }
+
+ // same as above, but align on right side
+ painter.drawText(
+ 0, std::min(property_value_height_offset_->getInt(), h - 1), w,
+ std::max(h - property_value_height_offset_->getInt(), 1), Qt::AlignLeft | Qt::AlignTop,
+ output_text.str().c_str());
+ painter.end();
+ updateVisualization();
+}
+
+void MrmSummaryOverlayDisplay::processMessage(
+ const autoware_auto_system_msgs::msg::HazardStatusStamped::ConstSharedPtr msg_ptr)
+{
+ if (!isEnabled()) {
+ return;
+ }
+
+ {
+ std::lock_guard message_lock(mutex_);
+ last_msg_ptr_ = msg_ptr;
+ }
+
+ queueRender();
+}
+
+void MrmSummaryOverlayDisplay::updateVisualization()
+{
+ const int texture_size = property_font_size_->getInt() * property_max_letter_num_->getInt();
+ overlay_->updateTextureSize(texture_size, texture_size);
+ overlay_->setPosition(property_left_->getInt(), property_top_->getInt());
+ overlay_->setDimensions(overlay_->getTextureWidth(), overlay_->getTextureHeight());
+}
+
+} // namespace rviz_plugins
+
+#include
+PLUGINLIB_EXPORT_CLASS(rviz_plugins::MrmSummaryOverlayDisplay, rviz_common::Display)
diff --git a/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.hpp b/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.hpp
new file mode 100644
index 0000000000000..2ca0364e35d83
--- /dev/null
+++ b/common/tier4_system_rviz_plugin/src/mrm_summary_overlay_display.hpp
@@ -0,0 +1,109 @@
+// Copyright 2023 Tier IV, Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Copyright (c) 2014, JSK Lab
+// All rights reserved.
+//
+// Software License Agreement (BSD License)
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following
+// disclaimer in the documentation and/or other materials provided
+// with the distribution.
+// * Neither the name of {copyright_holder} nor the names of its
+// contributors may be used to endorse or promote products derived
+// from this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+// COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+// ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.S SOFTWARE, EVEN IF ADVISED OF THE
+// POSSIBILITY OF SUCH DAMAGE.
+
+#ifndef MRM_SUMMARY_OVERLAY_DISPLAY_HPP_
+#define MRM_SUMMARY_OVERLAY_DISPLAY_HPP_
+
+#include
+#include
+
+#ifndef Q_MOC_RUN
+#include "jsk_overlay_utils.hpp"
+
+#include
+#include
+#include
+#include
+#include
+
+#include
+
+#endif
+
+namespace rviz_plugins
+{
+class MrmSummaryOverlayDisplay
+: public rviz_common::RosTopicDisplay
+
+{
+ Q_OBJECT
+
+public:
+ MrmSummaryOverlayDisplay();
+ ~MrmSummaryOverlayDisplay() override;
+
+ void onInitialize() override;
+ void onEnable() override;
+ void onDisable() override;
+
+private Q_SLOTS:
+ void updateVisualization();
+
+protected:
+ void update(float wall_dt, float ros_dt) override;
+ void processMessage(
+ const autoware_auto_system_msgs::msg::HazardStatusStamped::ConstSharedPtr msg_ptr) override;
+ jsk_rviz_plugins::OverlayObject::Ptr overlay_;
+ rviz_common::properties::ColorProperty * property_text_color_;
+ rviz_common::properties::IntProperty * property_left_;
+ rviz_common::properties::IntProperty * property_top_;
+ rviz_common::properties::IntProperty * property_value_height_offset_;
+ rviz_common::properties::FloatProperty * property_value_scale_;
+ rviz_common::properties::IntProperty * property_font_size_;
+ rviz_common::properties::IntProperty * property_max_letter_num_;
+ // QImage hud_;
+
+private:
+ static constexpr int line_width_ = 2;
+ static constexpr int hand_width_ = 4;
+
+ std::mutex mutex_;
+ autoware_auto_system_msgs::msg::HazardStatusStamped::ConstSharedPtr last_msg_ptr_;
+};
+} // namespace rviz_plugins
+
+#endif // MRM_SUMMARY_OVERLAY_DISPLAY_HPP_