Example: gui_windows_events

See: Tutorial: 3D scenes

C++ example source code:

/* +------------------------------------------------------------------------+
   |                     Mobile Robot Programming Toolkit (MRPT)            |
   |                          https://www.mrpt.org/                         |
   |                                                                        |
   | Copyright (c) 2005-2023, Individual contributors, see AUTHORS file     |
   | See: https://www.mrpt.org/Authors - All rights reserved.               |
   | Released under BSD License. See: https://www.mrpt.org/License          |
   +------------------------------------------------------------------------+ */

#include <mrpt/gui/CDisplayWindow.h>
#include <mrpt/gui/CDisplayWindow3D.h>
#include <mrpt/gui/CDisplayWindowPlots.h>
#include <mrpt/opengl/CGridPlaneXY.h>
#include <mrpt/system/CObserver.h>

#include <chrono>
#include <iostream>
#include <thread>

using namespace mrpt;
using namespace mrpt::gui;
using namespace mrpt::math;
using namespace mrpt::system;
using namespace mrpt::img;
using namespace std;

#include <mrpt/examples_config.h>
string myExampleImage(
    MRPT_EXAMPLES_BASE_DIRECTORY + string("img_basic_example/frame_color.jpg"));

class MyObserver : public mrpt::system::CObserver
{
   protected:
    void OnEvent(const mrptEvent& e) override
    {
        if (e.isOfType<mrptEventOnDestroy>())
            cout << "[MyObserver] Event received: mrptEventOnDestroy\n";
        else if (e.isOfType<mrptEventWindowResize>())
        {
            const mrptEventWindowResize& ee =
                static_cast<const mrptEventWindowResize&>(e);
            cout << "[MyObserver] Resize event received from: "
                 << ee.source_object << ", new size: " << ee.new_width << " x "
                 << ee.new_height << "\n";
        }
        else if (e.isOfType<mrptEventWindowChar>())
        {
            const mrptEventWindowChar& ee =
                static_cast<const mrptEventWindowChar&>(e);
            cout << "[MyObserver] Char event received from: "
                 << ee.source_object << ". Char code: " << ee.char_code
                 << " modif: " << ee.key_modifiers << "\n";
        }
        else if (e.isOfType<mrptEventWindowClosed>())
        {
            const mrptEventWindowClosed& ee =
                static_cast<const mrptEventWindowClosed&>(e);
            cout << "[MyObserver] Window closed event received from: "
                 << ee.source_object << "\n";
        }
        else if (e.isOfType<mrptEventMouseDown>())
        {
            const mrptEventMouseDown& ee =
                static_cast<const mrptEventMouseDown&>(e);
            cout << "[MyObserver] Mouse down event received from: "
                 << ee.source_object << "pt: " << ee.coords.x << ","
                 << ee.coords.y << "\n";
        }
        else
            cout << "[MyObserver] Event received: Another mrptEvent \n";
    }
};

// Observe windows for events.
// Declared out of the scope of windows so we can observe their destructors
MyObserver observer;

void TestGuiWindowsEvents()
{
    // Create some windows:
    CDisplayWindow win2D("Bitmap window", 300, 300);

    {
        mrpt::img::CImage img(300, 300, CH_RGB);
        img.filledRectangle(0, 0, 300, 300, TColor(0, 0, 255));
        img.textOut(50, 50, "Hello world!", TColor(255, 255, 255));
        win2D.showImage(img);
    }

    CDisplayWindow3D win3D("3D window", 300, 300);

    {
        mrpt::opengl::Scene::Ptr& scene = win3D.get3DSceneAndLock();
        scene->insert(mrpt::opengl::CGridPlaneXY::Create());
        win3D.unlockAccess3DScene();
        win3D.repaint();
    }

    CDisplayWindowPlots winPlot("Plots window", 300, 300);

    // Tile windows nicely:
    win2D.setPos(10, 10);
    win3D.setPos(340, 10);
    winPlot.setPos(10, 340);

    observer.observeBegin(win2D);
    observer.observeBegin(win3D);
    observer.observeBegin(winPlot);

    // Wait until end:
    cout << "Waiting for window events...\n";
    cout << "** Close any window to end the program **\n";

    while (win2D.isOpen() && win3D.isOpen() && winPlot.isOpen())
    {
        std::this_thread::sleep_for(100ms);
    }
}

// ------------------------------------------------------
//                      MAIN
// ------------------------------------------------------
int main()
{
    try
    {
        TestGuiWindowsEvents();
        return 0;
    }
    catch (const std::exception& e)
    {
        std::cerr << "MRPT error: " << mrpt::exception_to_str(e) << std::endl;
        return -1;
    }
}