Initial commit

This commit is contained in:
torsten committed 2026-08-13 18:33:10 +02:00
commit b7d90b9afe
16245 files changed
+3396666

No files matched your search

@@ -0,0 +1,58 @@
#
# $Id$
# $HeadURL$
# $Author$
# Created by Patric Karwat, SLSE, 2018-01-17
#
SET(osc_terminal_gui_SRCS
osc_terminal_gui_plugin.cpp
osc_terminal_gui_plugin.h
osc_demand_situation.cpp
osc_demand_situation.h
osc_fault_message.h
osc_fault_message.cpp
osc_equip_player.h
osc_equip_player.cpp
osc_edit_folder_content.cpp
osc_edit_folder_content.h
osc_demand_situation_filter.cpp
osc_demand_situation_filter.h
)
NGL_WRAP_UI(osc_terminal_gui_SRCS
osc_demand_situation.ui
osc_fault_message.ui
osc_equip_player.ui
osc_edit_folder_content.ui
osc_demand_situation_filter.ui
)
NGL_ADD_LIBRARY(WS OscTerminalGuiPlugin MODULE ${osc_terminal_gui_SRCS})
NGL_TARGET_LINK_LIBRARIES(OscTerminalGuiPlugin
AsbDataPluginInterface
LtsPrinting
NGLLogger
LtsNotification
LtsSession
LtsSessionData
LtsDataView
LtsUtilsSettings
PpmCommon
PpmDataPluginInterface
TabocDataPluginInterface
ObdDataPluginInterface
SituationMapGuiPluginInterface
OscTerminalGuiPluginInterface
svcOscClient
LtsWidgets
ngltools
nglsettings
ltsCoordWidget
LtsUtilsSettings
LtsUtilsGuiDds
Qt5::Widgets
)
NGL_INSTALL_TARGET(OscTerminalGuiPlugin)
@@ -0,0 +1,315 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - DemandSituation Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#include "osc_demand_situation.h"
#include "ui_osc_demand_situation.h"
#include <AdvancedSymbology/asb_data_plugin_interface.h>
#include <Plugins/SituationMapPlugin/situation_map_gui_plugin_interface.h>
#include <PluginInterfaces/gui_plugin_interface.h>
#include <LtsUtilsSettings/settings.h>
#include <Map/map.h> // Interface
#include <QTreeView>
namespace OcSituationClient
{
DemandSituation::DemandSituation(LtsSession::LtsSession *session, QWidget *parent)
: LtsWidgets::LtsDialog(parent, LtsWidgets::ButtonCombination::OkApplyCancel)
, m_session(session)
, m_requestHelper(new LtsUtils::RequestHelper(this))
, m_selectedEqNr(0)
, m_ocDemandGroupString(QStringLiteral("ObserverControllerDemand"))
, m_ocDemandFilterGroupString(QStringLiteral("ObserverControllerDemandFilter"))
, m_opSettings(LtsUtils::OperatorSettings::getInstance())
, m_model(nullptr)
, m_proxyModel(nullptr)
, m_ui(new Ui::DemandSituation)
, m_logger(getLogger("DemandSituationDialog"))
{
m_ui->setupUi(this);
setOnlineHelpFilename(QStringLiteral("OC-Demand_Situation"));
}
DemandSituation::~DemandSituation()
{
delete m_ui;
}
bool DemandSituation::init(const std::shared_ptr<Interface::Ftc> &ftc)
{
if (!ftc)
return false;
m_ftc = ftc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> dtcPpm;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(dtcPpm))
return false;
if (!m_session->getForeignGuiInterface<ParticipantManagement::ForeignGuiComboboxInterface>(m_ppmCbxGui))
return false;
if (!m_session->getForeignGuiInterface<SituationMap::ForeignGuiInterface>(m_sitMapGuiIfc))
return false;
//optional
m_session->getForeignGuiInterface<SituationMap::ForeignGuiInterface>(m_sitMapGuiIfc);
std::shared_ptr<AdvancedSymbology::ForeignDataInterface> asb;
m_session->getForeignDataInterface<AdvancedSymbology::DataInterface>(asb);
m_model = new ParticipantManagement::ParticipantEditModel(this, dtcPpm, asb);
// only needed to set recursiveFilteringEnabled
m_proxyModel = new ParticipantManagement::ParticipantTreeFilterProxyModel(this);
m_proxyModel->setSourceModel(m_model);
m_proxyModel->setRecursiveFilteringEnabled(true);
m_ui->dvParticipants->setModel(m_proxyModel);
m_ppmCbxGui->fillPartyComboBox(m_ui->cbParty, ParticipantManagement::ForeignGuiComboboxInterface::CbxPartyFilter::NormalOc);
connect(m_ui->dvParticipants, &LtsDataView::LtsDataView::signalSelectionChanged,
this, &DemandSituation::onSlotSelectionChanged);
if (m_sitMapGuiIfc)
{
connect(m_ui->pbClear, &QPushButton::clicked, this, &DemandSituation::onClearCoordinate);
connect(m_ui->pbPos, &QPushButton::clicked, this, &DemandSituation::onGetPosition);
}
else
{
m_ui->pbPos->setEnabled(false);
}
connect(m_ui->cbParty, &LtsWidgets::LtsComboBox::currentTextChanged, this, [this]
{
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->dvParticipants->expandAll();
});
connect(m_ui->slRange, &QSlider::valueChanged, this, [this](int range)
{
m_ui->lblRange->setText(QString::number(range));
repaintSitmapCircle();
});
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->slRange->setValue(10);
m_ui->dvParticipants->expandAll();
m_ui->dvParticipants->setSortIndicator(0, Qt::AscendingOrder);
//load old settings
m_ui->slRange->setValue(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("Range"), 100).toInt());
m_ui->cbParty->setCurrentIndex(m_ui->cbParty->findData(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("Party"), 1).toInt()));
if (m_opSettings->value(m_ocDemandGroupString, QStringLiteral("ParticipantId"), 0).toInt() > 0)
{
const auto idx = m_model->indexFromParticipantId(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("ParticipantId"), -1).toInt());
m_ui->dvParticipants->treeView()->setCurrentIndex(m_proxyModel->mapFromSource(idx));
m_ui->dtePos->clear();
}
else if (m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLon"), -1).toDouble() > 0)
{
m_ui->dtePos->setCoordinate(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLon"), -1).toDouble(),
m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLat"), -1).toDouble());
}
m_ui->cbFilter->setChecked(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("FilterActive"), false).toBool());
connect(m_ui->pbClear, &QPushButton::clicked,
m_ui->dvParticipants->selectionModel(), &QItemSelectionModel::clearSelection);
__unchange__();
return true;
}
void DemandSituation::onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject)
{
if (replyObject.str().empty())
{
// save new settings
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("Range"), m_ui->slRange->value());
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("Party"), m_ui->cbParty->currentData().toInt());
const auto selIndexes = m_ui->dvParticipants->selectedRows();
if (!selIndexes.isEmpty())
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("ParticipantId"), m_model->getParticipantData(selIndexes.first()).id());
else
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("ParticipantId"), 0);
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("PosLon"), m_ui->dtePos->coordinate().x());
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("PosLat"), m_ui->dtePos->coordinate().y());
m_opSettings->setValue(m_ocDemandGroupString, QStringLiteral("FilterActive"),m_ui->cbFilter->isChecked());
}
else
{
// reset to old settings
discardSitmapCircle();
}
m_requestHelper->requestReply(replyObject);
}
void DemandSituation::onSlotSelectionChanged()
{
m_selectedEqNr = 0;
const auto selIndexes = m_ui->dvParticipants->selectedRows();
if (!selIndexes.isEmpty())
{
ParticipantManagement::ParticipantData part = m_model->getParticipantData(selIndexes.first());
if (part.equipmentNumber().is_set())
{
//clear pos
onClearCoordinate();
m_selectedEqNr = part.equipmentNumber().get();
}
else
m_selectedEqNr = 0;
}
repaintSitmapCircle();
slotChangesMade();
}
void DemandSituation::onGetPosition()
{
//clear selection
m_ui->dvParticipants->selectionModel()->clearSelection();
m_sitMapGuiIfc->getCircle(this,
SLOT(onCoordinate(QPointF, double)),
nullptr,
m_ui->slRange->minimum(),
m_ui->slRange->maximum());
}
void DemandSituation::onCoordinate(const QPointF &coord, double radius)
{
m_ui->dtePos->setCoordinate(coord);
m_ui->slRange->setValue(static_cast<int>(radius));
repaintSitmapCircle();
slotChangesMade();
}
void DemandSituation::onClearCoordinate()
{
m_ui->dtePos->clear();
slotChangesMade();
}
void DemandSituation::retranslate()
{
translate(m_ui, tr("Demand Situation") );
m_uiRequirements->clear();
m_uiRequirements->addRequirement({m_ui->lbRange, [this]() { return !!(m_selectedEqNr >= 0 || m_ui->dtePos->coordinate().x() > 0 ); },
tr("Select none or one participant with equipment number or a position.")});
}
bool DemandSituation::apply()
{
// set filter
m_partys.clear();
m_typesClass.clear();
if(m_ui->cbFilter->isChecked())
{
m_filterActive = true;
QStringList partyList = m_opSettings->value(m_ocDemandFilterGroupString, QStringLiteral("Partys"),-1).toStringList();
for(const auto &s : partyList)
m_partys.push_back(s.toInt());
QStringList typeClassList = m_opSettings->value(m_ocDemandFilterGroupString, QStringLiteral("TypeClass"),-1).toStringList();
for(const auto &s : typeClassList)
m_typesClass.push_back(s.toInt());
}
else
{
m_filterActive = false;
}
SendDemandSituationRequest req(m_selectedEqNr,
m_ui->slRange->value(),
dds::core::optional<Core::GeoPosition2D>(),
m_filterActive,
m_partys,
m_typesClass);
bool bret;
bool stopDemand = false;
if (m_ui->dtePos->coordinate().isNull() && m_selectedEqNr == 0)
{
req.radius() = 0;
const Core::GeoPosition2D pos(std::nan(""),std::nan(""));
req.position() = pos;
stopDemand = true;
}
else if (m_ui->dtePos->coordinate().x() > 0)
{
const Core::GeoPosition2D pos(m_ui->dtePos->coordinate().x(), m_ui->dtePos->coordinate().y() );
req.position().set(pos);
}
bret = m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendDemandSituationRequest(req, this);
});
if (bret && stopDemand)
emit demandSituationStopped();
return bret;
}
void DemandSituation::dialogCanceled()
{
discardSitmapCircle();
}
void DemandSituation::repaintSitmapCircle()
{
double range = static_cast<double>(m_ui->slRange->value());
const auto selIndexes = m_ui->dvParticipants->selectedRows();
if (!selIndexes.isEmpty())
{
m_sitMapGuiIfc->ocSituationRange_create(m_model->getParticipantData(selIndexes.first()).id(), range);
}
else if (!m_ui->dtePos->coordinate().isNull())
{
QPointF pos(m_ui->dtePos->coordinate().x(),
m_ui->dtePos->coordinate().y());
m_sitMapGuiIfc->ocSituationRange_create(pos, range);
}
else
{
m_sitMapGuiIfc->ocSituationRange_remove();
}
}
void DemandSituation::discardSitmapCircle()
{
//load old settings
double range = static_cast<double>(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("Range"), 100).toInt());
int participantId = m_opSettings->value(m_ocDemandGroupString, QStringLiteral("ParticipantId"), 0).toInt();
if (participantId > 0)
{
m_sitMapGuiIfc->ocSituationRange_create(participantId, range);
}
else if (m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLon"), -1).toDouble() > 0)
{
QPointF pos(m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLon"), -1).toDouble(),
m_opSettings->value(m_ocDemandGroupString, QStringLiteral("PosLat"), -1).toDouble());
m_sitMapGuiIfc->ocSituationRange_create(pos, range);
}
else // no oc sitmap selected
{
m_sitMapGuiIfc->ocSituationRange_remove();
}
}
} // namespace OcSituationClient
@@ -0,0 +1,95 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - Demand Situation Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#pragma once
#include <LtsWidgets/lts_dialog.h>
#include <LtsSession/lts_session.h>
#include <OcSituationClient/logger.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsUtilsGuiDds/request_helper.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <ParticipantManagement/Gui/Common/participant_edit_model.h>
#include <Plugins/ParticipantManagement/ppm_gui_combobox_plugin_interface.h>
#include <Plugins/SituationMapPlugin/situation_map_gui_plugin_interface.h>
namespace Ui
{
class DemandSituation;
}
namespace SituationMap
{
class ForeignGuiInterface;
}
namespace LtsUtils
{
class OperatorSettings;
}
namespace LtsWidgets
{
class LtsColumnFilterProxyModel;
}
namespace OcSituationClient
{
class DemandSituation : public LtsWidgets::LtsDialog,
private OcSituationClient::Interface::Ftc::SendDemandSituationReplyHandler
{
Q_OBJECT
public:
explicit DemandSituation(LtsSession::LtsSession *session, QWidget *parent = nullptr);
~DemandSituation();
bool init(const std::shared_ptr<Interface::Ftc> &ftc);
void onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject) override;
Q_SIGNALS:
void demandSituationStopped();
private Q_SLOTS:
void onSlotSelectionChanged();
void onGetPosition();
void onCoordinate(const QPointF &coord, double radius);
void onClearCoordinate();
private:
void retranslate() override;
bool apply() override;
void dialogCanceled () override;
void repaintSitmapCircle();
void discardSitmapCircle();
private:
LtsSession::LtsSession *m_session;
LtsUtils::RequestHelper *m_requestHelper;
int m_selectedEqNr;
bool m_filterActive{false};
std::vector<int> m_partys;
std::vector<int> m_typesClass;
QString m_ocDemandGroupString;
QString m_ocDemandFilterGroupString;
LtsUtils::OperatorSettings *m_opSettings;
ParticipantManagement::ParticipantEditModel *m_model;
LtsWidgets::LtsColumnFilterProxyModel *m_proxyModel;
std::shared_ptr<OcSituationClient::Interface::Ftc> m_ftc;
std::shared_ptr<ParticipantManagement::ForeignGuiComboboxInterface> m_ppmCbxGui;
std::shared_ptr<SituationMap::ForeignGuiInterface> m_sitMapGuiIfc;
Ui::DemandSituation *m_ui;
LOGGER_T m_logger;
};
} // namespace OcSituationClient
@@ -0,0 +1,182 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>DemandSituation</class>
<widget class="QWidget" name="DemandSituation">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>438</width>
<height>82</height>
</rect>
</property>
<property name="windowTitle">
<string notr="true">MessagingView</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0">
<layout class="QHBoxLayout" name="horizontalLayout_2">
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>Party:</string>
</property>
</widget>
</item>
<item>
<widget class="LtsWidgets::LtsComboBox" name="cbParty"/>
</item>
<item>
<spacer name="horizontalSpacer">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QLabel" name="label2">
<property name="text">
<string>Position</string>
</property>
</widget>
</item>
<item>
<widget class="LtsCoordWidget::LtsCoordWidget" name="dtePos" native="true"/>
</item>
<item>
<widget class="QPushButton" name="pbPos">
<property name="text">
<string/>
</property>
<property name="icon">
<iconset>
<normaloff>:/style/position.svg</normaloff>:/style/position.svg</iconset>
</property>
</widget>
</item>
<item>
<widget class="QPushButton" name="pbClear">
<property name="text">
<string/>
</property>
<property name="icon">
<iconset>
<normaloff>:/style/remove.svg</normaloff>:/style/remove.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QLabel" name="label_2">
<property name="text">
<string>Use Filter:</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="cbFilter">
<property name="text">
<string/>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer_3">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item row="1" column="0">
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<widget class="QLabel" name="lbRange">
<property name="text">
<string>Range: [m]</string>
</property>
</widget>
</item>
<item>
<widget class="QSlider" name="slRange">
<property name="minimum">
<number>1</number>
</property>
<property name="maximum">
<number>5000</number>
</property>
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="lblRange">
<property name="text">
<string notr="true">&lt;RANGE&gt;</string>
</property>
</widget>
</item>
</layout>
</item>
<item row="2" column="0">
<widget class="LtsDataView::LtsDataView" name="dvParticipants" native="true">
<property name="rootIsDecorated" stdset="0">
<bool>true</bool>
</property>
<property name="showColumnCount" stdset="0">
<bool>false</bool>
</property>
<property name="toolButtonsVisible" stdset="0">
<bool>false</bool>
</property>
</widget>
</item>
</layout>
</widget>
<customwidgets>
<customwidget>
<class>LtsCoordWidget::LtsCoordWidget</class>
<extends>QWidget</extends>
<header>LtsCoordTrans/lts_coord_widget.h</header>
</customwidget>
<customwidget>
<class>LtsWidgets::LtsComboBox</class>
<extends>QComboBox</extends>
<header>LtsWidgets/lts_combo_box.h</header>
</customwidget>
<customwidget>
<class>LtsDataView::LtsDataView</class>
<extends>QWidget</extends>
<header>LtsDataView/lts_data_view.h</header>
<container>1</container>
</customwidget>
</customwidgets>
<resources/>
<connections/>
</ui>
@@ -0,0 +1,245 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - OC Situation Filter
* $Id$
* $HeadURL$
* $Author$
* Created by Steve Kemayou, SLSE, 2022-07-07
*/
#include "osc_demand_situation_filter.h"
#include "ui_osc_demand_situation_filter.h"
#include <PluginInterfaces/gui_plugin_interface.h>
#include <LtsUtilsSettings/settings.h>
#include <QVBoxLayout>
#include <QLayout>
#include <QCheckBox>
#include <QLabel>
namespace OcSituationClient
{
DemandSituationFilter::DemandSituationFilter(LtsSession::LtsSession *session, QWidget *parent)
: LtsWidgets::LtsDialog(parent, LtsWidgets::ButtonCombination::OkApplyCancel)
, m_ui(new Ui::DemandSituationFilter)
, m_session(session)
, m_requestHelper(new LtsUtils::RequestHelper(this))
, m_ftc(nullptr)
, m_ppmDtc(nullptr)
, m_opSettings(LtsUtils::OperatorSettings::getInstance())
, m_ocDemandFilterGroupString(QStringLiteral("ObserverControllerDemandFilter"))
{
m_ui->setupUi(this);
setOnlineHelpFilename(QStringLiteral("OC-Demand_Situation_Filter"));
}
DemandSituationFilter::~DemandSituationFilter()
{
delete m_ui;
}
void DemandSituationFilter::retranslate()
{
translate(m_ui, tr("Demand Situation Filter") );
m_uiRequirements->retranslate();
}
bool DemandSituationFilter::init(const std::shared_ptr<Interface::Ftc> &ftc)
{
if (!ftc)
return false;
m_ftc = ftc;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(m_ppmDtc))
return false;
m_ppmDtc->enableParticipant(true);
m_ppmDtc->enableEquipmentType(true);
m_partyList.clear();
m_typeClassList.clear();
/// build partys filter
// get settings
QStringList partys;
partys = m_opSettings->value(m_ocDemandFilterGroupString, QStringLiteral("Partys"),-1).toStringList();
for(const auto &s : partys)
{
if(s.compare(QStringLiteral("-1")) != 0)
m_partyList << s;
}
buildPartyTable(m_ppmDtc->partys());
/// build typeClass filter
// fill typClass
std::set<ParticipantManagement::TypeClass> ppmTypeClass;
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::SupportEntity);
//ppmTypeClass.insert(ParticipantManagement::TypeClass_def::Unit);
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::Human);
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::GroundVehicle);
//ppmTypeClass.insert(ParticipantManagement::TypeClass_def::Vessel);
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::VehicleWithGear);
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::WeaponSystem);
//ppmTypeClass.insert(ParticipantManagement::TypeClass_def::SupportUnit);
ppmTypeClass.insert(ParticipantManagement::TypeClass_def::Aircraft);
// get current settings
QStringList typeClassList;
typeClassList = m_opSettings->value(m_ocDemandFilterGroupString, QStringLiteral("TypeClass"),-1).toStringList();
for(const auto &s : typeClassList)
{
if(s.compare(QStringLiteral("-1")) != 0)
m_typeClassList << s;
}
buildTypeClassTable(ppmTypeClass);
m_ui->lblInfo->setText(tr("After saving Filter settings, the Demand Situation Request will be updated, if the filter in 'Demand Situation Dialog' is activated."));
return true;
}
bool DemandSituationFilter::apply()
{
// save typeClassList and partyList
m_opSettings->setValue(m_ocDemandFilterGroupString, QStringLiteral("Partys"),m_partyList);
m_opSettings->setValue(m_ocDemandFilterGroupString, QStringLiteral("TypeClass"),m_typeClassList);
bool ret;
const QString ocDemandGroup = QStringLiteral("ObserverControllerDemand");
const bool useFilter = m_opSettings->value(ocDemandGroup, QStringLiteral("FilterActive"), false).toBool();
const int ppId = m_opSettings->value(ocDemandGroup, QStringLiteral("ParticipantId"), 0).toInt();
if(useFilter == true && ppId > 0)
{
const int range = m_opSettings->value(ocDemandGroup, QStringLiteral("Range"), 100).toInt();
const double posLon = m_opSettings->value(ocDemandGroup, QStringLiteral("PosLon"), -1).toDouble();
const double posLat = m_opSettings->value(ocDemandGroup, QStringLiteral("PosLat"), -1).toDouble();
const ParticipantManagement::Participant participant = m_ppmDtc->participant(ppId);
int equipNumber = 0;
if(participant.equipmentNumber().is_set())
{
equipNumber= participant.equipmentNumber().get();
}
std::vector<int> partyList;
for(const auto & pl : m_partyList )
{
partyList.push_back(pl.toInt());
}
std::vector<int> typeClassList;
for(const auto &tl : m_typeClassList)
{
typeClassList.push_back(tl.toInt());
}
SendDemandSituationRequest req(equipNumber,
range,
dds::core::optional<Core::GeoPosition2D>(),
useFilter,
partyList,
typeClassList);
if (posLon > 0)
{
const Core::GeoPosition2D pos(posLon, posLat );
req.position().set(pos);
}
ret = m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendDemandSituationRequest(req, this);
});
if(ret == false)
{
LtsWidgets::LtsMessageDialog::showMessage(this, tr("Filter successfully Saved, but Couldn't send demand situation request."));
}
}
return true;
}
static void addSpacerItem(QVBoxLayout *gridLayout)
{
gridLayout->addItem(new QSpacerItem(0, 0, QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding));
}
void DemandSituationFilter::buildPartyTable(const QMap<int, ParticipantManagement::Party> &parties)
{
for (const ParticipantManagement::Party &party : parties)
{
if(party.id() == 0)
continue;
QCheckBox *cbParty = new QCheckBox(ParticipantManagement::trPartyName(party.name()), this);
cbParty->setObjectName(QStringLiteral("party_%1").arg(party.id()));
cbParty->setChecked(m_partyList.contains(QString::number(party.id())));
connect(cbParty, &QCheckBox::stateChanged, this, &DemandSituationFilter::onPartyBoxChecked);
m_ui->glParty->addWidget(cbParty);
// <spc>
}
addSpacerItem(m_ui->glParty);
}
void DemandSituationFilter::buildTypeClassTable(const std::set<ParticipantManagement::TypeClass> &typeClassList)
{
for (const ParticipantManagement::TypeClass &typeClass : typeClassList)
{
QCheckBox *cb = new QCheckBox(ParticipantManagement::toString(typeClass.underlying()), this);
cb->setObjectName(QStringLiteral("typeClass_%1").arg(typeClass.underlying()));
cb->setChecked(m_typeClassList.contains(QString::number(typeClass.underlying())));
connect(cb, &QCheckBox::stateChanged, this, &DemandSituationFilter::onTypeClassCBoxChecked);
m_ui->glTypeClass->addWidget(cb);
}
addSpacerItem(m_ui->glTypeClass);
}
void DemandSituationFilter::onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject)
{
DEBUG_LOG(m_logger)<< " update filter demand situationReply: "<<replyObject.str();
m_requestHelper->requestReply(replyObject);
}
void DemandSituationFilter::onPartyBoxChecked()
{
QCheckBox *cb = (QCheckBox*) sender();
if(cb!=nullptr)
{
QString partyId = cb->objectName().section(QStringLiteral("party_"),1,1);
DEBUG_LOG(m_logger)<<" onPartyBoxChecked(): partyId: "<<partyId;
if(cb->isChecked())
{
m_partyList << partyId;
}
else
{
m_partyList.removeOne(partyId);
}
}
}
void DemandSituationFilter::onTypeClassCBoxChecked()
{
QCheckBox *cb = (QCheckBox*) sender();
if(cb!=nullptr)
{
QString partyId = cb->objectName().section(QStringLiteral("typeClass_"),1,1);
DEBUG_LOG(m_logger)<<" onTypeClassCBoxChecked(): typClass: "<<partyId;
if(cb->isChecked())
{
if(m_typeClassList.contains(partyId) == false)
{
m_typeClassList << partyId;
}
}
else
{
m_typeClassList.removeOne(partyId);
}
}
}
} // namespace OcSituationClient
@@ -0,0 +1,72 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - OC Situation Filter
* $Id$
* $HeadURL$
* $Author$
* Created by Steve Kemayou, SLSE, 2022-07-07
*/
#pragma once
#include <LtsWidgets/lts_dialog.h>
#include <LtsSession/lts_session.h>
#include <OcSituationClient/logger.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsUtilsGuiDds/request_helper.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <ProjectDataManagement/pdm_enums.hpp>
#include <ParticipantManagement/ppm_translation.h>
#include <ParticipantManagement/ppm.hpp>
#include <set>
#include <QWidget>
namespace Ui {
class DemandSituationFilter;
}
namespace LtsUtils
{
class OperatorSettings;
}
namespace OcSituationClient
{
class DemandSituationFilter : public LtsWidgets::LtsDialog,
private OcSituationClient::Interface::Ftc::SendDemandSituationReplyHandler
{
Q_OBJECT
public:
explicit DemandSituationFilter(LtsSession::LtsSession *session, QWidget *parent = nullptr);
~DemandSituationFilter();
bool init(const std::shared_ptr<Interface::Ftc> &ftc);
void buildPartyTable(const QMap<int, ParticipantManagement::Party> &parties);
void buildTypeClassTable(const std::set<ParticipantManagement::TypeClass> &typeClassList);
void onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject) override;
protected slots:
void onPartyBoxChecked();
void onTypeClassCBoxChecked();
private:
bool apply() override;
void retranslate() override;
private:
Ui::DemandSituationFilter *m_ui;
LtsSession::LtsSession *m_session;
LtsUtils::RequestHelper *m_requestHelper;
std::shared_ptr<OcSituationClient::Interface::Ftc> m_ftc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> m_ppmDtc;
QStringList m_typeClassList;
QStringList m_partyList;
LtsUtils::OperatorSettings *m_opSettings;
QString m_ocDemandFilterGroupString;
};
} // namespace OcSituationClient
@@ -0,0 +1,113 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>DemandSituationFilter</class>
<widget class="QWidget" name="DemandSituationFilter">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>787</width>
<height>326</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="2" column="2">
<spacer name="verticalSpacer_2">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::MinimumExpanding</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>247</height>
</size>
</property>
</spacer>
</item>
<item row="0" column="1" rowspan="3">
<widget class="Line" name="line">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
</widget>
</item>
<item row="1" column="0">
<layout class="QVBoxLayout" name="glParty"/>
</item>
<item row="2" column="0">
<spacer name="verticalSpacer">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::MinimumExpanding</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>247</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="2">
<layout class="QVBoxLayout" name="glTypeClass"/>
</item>
<item row="3" column="0" colspan="3">
<widget class="QLabel" name="lblInfo">
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="text">
<string notr="true">&lt;INFO&gt;</string>
</property>
</widget>
</item>
<item row="0" column="2">
<widget class="QLabel" name="label_2">
<property name="font">
<font>
<pointsize>12</pointsize>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="text">
<string>Type Class</string>
</property>
<property name="alignment">
<set>Qt::AlignCenter</set>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QLabel" name="label">
<property name="font">
<font>
<pointsize>12</pointsize>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="text">
<string>Partys</string>
</property>
<property name="alignment">
<set>Qt::AlignCenter</set>
</property>
</widget>
</item>
</layout>
</widget>
<resources/>
<connections/>
</ui>
@@ -0,0 +1,362 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - PDF Folder Content
* $Id$
* $HeadURL$
* $Author$
* Created by Steve Kemayou, SLSE, 2022-07-07
*/
#include "osc_edit_folder_content.h"
#include "ui_osc_edit_folder_content.h"
#include <QDir>
#include <QTableView>
#include <LtsUtilsSettings/settings.h>
#include <LtsDataView/lts_data_view.h>
#include <LtsSession/lts_session_data.h>
namespace OcSituationClient
{
static Poppler::Page::Rotation getRotationFromValue(int rotation);
/*!
* \brief FolderContentEditDialog::FolderContentEditDialog
* \param parent
*/
FolderContentEditDialog::FolderContentEditDialog(QWidget *parent)
:LtsWidgets::LtsDialog(parent, LtsWidgets::ButtonCombination::CloseOnly)
, m_ui(new Ui::FolderContentEditDialog)
, m_session(nullptr)
, m_obdFtc(nullptr)
, m_requestHelper(new LtsUtils::RequestHelper(this))
, m_logger(getLogger("OscFolderContentEditDialog"))
{
m_ui->setupUi(this);
setOnlineHelpFilename(QStringLiteral("OSC-Edit_Folder_Content"));
m_ui->filesView->horizontalHeader()->setStretchLastSection(true);
m_ui->filesView->horizontalHeader()->setSectionResizeMode(QHeaderView::ResizeToContents); // resize view table to have the same column width
m_ui->filesView->setSelectionBehavior(QAbstractItemView::SelectRows);
m_ui->filesView->setEditTriggers(QAbstractItemView::NoEditTriggers); // can't be edited from user.
m_ui->filesView->verticalHeader()->hide();
m_buttonBox->connectButton(LtsWidgets::DialogButton::Remove, this, &FolderContentEditDialog::onDeleteFile);
m_buttonBox->connectButton(LtsWidgets::DialogButton::Show, this, &FolderContentEditDialog::onPreviewFile);
enaDisa();
const QString opName = LtsSessionData::LtsSessionData::getInstance()->getOperatorName();
const QString dir = QStringLiteral("%1/OcPdf/%2/").arg(QDir::tempPath()).arg(opName);
QDir directory(dir);
if(!directory.exists())
directory.mkdir(dir);
setDefaultFileSystemPath(dir);
}
FolderContentEditDialog::~FolderContentEditDialog()
{
if(m_pdfWidget != nullptr)
delete m_pdfWidget;
m_pdfWidget = nullptr;
delete m_ui;
}
/*!
* \brief FolderContentEditDialog::init
* \param session
* \return
*/
bool FolderContentEditDialog::init(LtsSession::LtsSessionDataDds *session)
{
m_session = session;
if (!m_session->getFtc<OcBaseDownload::DataInterface>(m_obdFtc))
{
ERROR_LOG(m_logger) << "Cant get Obd FTC can't download";
return false;
}
delete m_fileSystemModel;
m_fileSystemModel = new QFileSystemModel();
m_fileSystemModel->setFilter(QDir::Files|QDir::NoDotAndDotDot);
m_fileSystemModel->setReadOnly(true);
QStringList filters;
filters << QStringLiteral("*.pdf");
m_fileSystemModel->setNameFilters(filters);
m_fileSystemModel->setNameFilterDisables(false);
m_fileSystemModel->setReadOnly(true);
m_ui->filesView->setModel(m_fileSystemModel);
m_ui->filesView->setRootIndex(m_fileSystemModel->setRootPath(getFileSysPath()));
m_ui->filesView->hideColumn(1);
m_fileSystemModel->sort(3, Qt::DescendingOrder);
m_ui->filesView->horizontalHeader()->setStyleSheet(QStringLiteral("font-weight: bold;"));
connect(m_ui->filesView->selectionModel(), &QItemSelectionModel::selectionChanged, this, &FolderContentEditDialog::onSelectionChanged);
QPushButton *btn = m_buttonBox->getButton(LtsWidgets::DialogButton::Save);
btn->setText(tr("Pdf Download"));
m_buttonBox->connectButton(LtsWidgets::DialogButton::Save, this, &FolderContentEditDialog::onOcPdfDownloadClicked);
initPdfWidow();
return true;
}
/*!
* \brief FolderContentEditDialog::retranslate
*/
void FolderContentEditDialog::retranslate()
{
translate(m_ui, tr("Folder Content"));
}
/*!
* \brief FolderContentEditDialog::enaDisa
*/
void FolderContentEditDialog::enaDisa()
{
m_buttonBox->setButtonEnabled(LtsWidgets::DialogButton::Remove, false);
m_buttonBox->setButtonEnabled(LtsWidgets::DialogButton::Show, false);
QItemSelectionModel *select = m_ui->filesView->selectionModel();
if(select == nullptr)
return;
QModelIndexList indexList =select->selectedRows();
if(indexList.size() == 0)
return;
m_buttonBox->setButtonEnabled(LtsWidgets::DialogButton::Remove, indexList.size() > 0);
m_buttonBox->setButtonEnabled(LtsWidgets::DialogButton::Show, indexList.size()==1);
}
/*!
* \brief FolderContentEditDialog::onSelectionChanged
*/
void FolderContentEditDialog::onSelectionChanged()
{
enaDisa();
}
void FolderContentEditDialog::onOcPdfDownloadClicked()
{
LtsUtils::ProjectSettings *ps = LtsUtils::ProjectSettings::getInstance();
const int folderId = ps->value(QStringLiteral("obd"), QStringLiteral("ocPdfDownloadFolderId")).toInt();
if(folderId <= 0)
{
LtsWidgets::LtsMessageDialog::showMessage(this, tr("Couldn't download pdf files: Folder id invalid!"));
return;
}
const QString matrixOperator = LtsSessionData::LtsSessionData::getInstance()->getOperatorName();
DEBUG_LOG(m_logger)<<LOGFUNCTION<<" folderId:" <<folderId<<" operatorName: "<<matrixOperator;
OcBaseDownload::OcPdfDownloadRequest req(folderId,matrixOperator.toStdString());
m_requestHelper->startSingleRequest([req, this]()
{
return m_obdFtc->ocPdfDownloadRequest(req, this);
});
}
/*!
* \brief FolderContentEditDialog::onPreviewFile
*/
void FolderContentEditDialog::onPreviewFile()
{
QItemSelectionModel *select = m_ui->filesView->selectionModel();
if(select == nullptr)
return;
QModelIndexList indexList =select->selectedRows();
if(indexList.size() == 0)
return;
QModelIndex index = indexList.at(0);
m_currViewPath = m_fileSystemModel->filePath(index);
//const QUrl url = QUrl(QStringLiteral("file://") + m_currViewPath);
if(m_pdfWidget == nullptr)
{
WARNING_LOG(m_logger)<<" pdf widget not initialized. trying to init...";
initPdfWidow();
}
QFile f(m_currViewPath);
if(f.open(QIODevice::ReadOnly))
{
DEBUG_LOG(m_logger) << "Current File: " << m_currViewPath;
setPage(1);
setZoomFactor(ZOOM_DEFAULT);
setRotation(Poppler::Page::Rotate0);
m_pdfWidget->setWindowTitle(m_fileSystemModel->fileName(index));
m_pdfWidget->showPDF(f.readAll());
m_pdfWidget->setVisible(true);
m_pdfWidget->showMaximized();
}
}
/*!
* \brief FolderContentEditDialog::onDeleteFile
*/
void FolderContentEditDialog::onDeleteFile()
{
TRACE_LOG(m_logger)<<" delete file START ";
QItemSelectionModel *select = m_ui->filesView->selectionModel();
if(select == nullptr)
return;
QModelIndexList indexList =select->selectedRows();
m_pdfWidget->hide();
if(indexList.size() > 0)
{
QFileInfoList fileInfoList;
for(const auto index : qAsConst(indexList))
{
fileInfoList << m_fileSystemModel->fileInfo(index);
TRACE_LOG(m_logger)<< "file path:"<<fileInfoList.last().absoluteFilePath();
}
QDir dir;
dir.setPath(getFileSysPath());
for (auto fileInfo : fileInfoList)
{
bool success = dir.remove(fileInfo.fileName());
TRACE_LOG(m_logger)<< "remove file:"<<fileInfo.absoluteFilePath() << " | succeed? "<< success;
}
}
TRACE_LOG(m_logger) <<" delete file End ";
}
/*!
* \brief FolderContentEditDialog::setDefaultFileSystemPath
* \param path
*/
void FolderContentEditDialog::setDefaultFileSystemPath(QString path)
{
m_filesysPath = path.isEmpty() ? QDir::homePath() : path;
TRACE_LOG(m_logger)<<" set default filesystem path: "<< path;
}
/*!
* \brief FolderContentEditDialog::setPage
* \param pageNo
*/
void FolderContentEditDialog::setPage(int pageNo)
{
if (m_pageNo == pageNo)
return;
DEBUG_LOG(m_logger) << "setPage = " << pageNo;
m_pageNo = pageNo;
m_pdfWidget->setPage(pageNo);
emit currentPageChanged(m_pageNo);
}
/*!
* \brief FolderContentEditDialog::getCurPage
* \return
*/
int FolderContentEditDialog::getCurPage() const
{
return m_pdfWidget->curPage();
}
/*!
* \brief FolderContentEditDialog::getNumPages
* \return
*/
int FolderContentEditDialog::getNumPages() const
{
return m_pdfWidget->numPages();
}
/*!
* \brief FolderContentEditDialog::setZoomFactor
* \param zoomFactor
*/
void FolderContentEditDialog::setZoomFactor(double zoomFactor)
{
if (qFuzzyCompare(m_zoomFactor, zoomFactor))
return;
DEBUG_LOG(m_logger) << "setZoomFactor = " << zoomFactor;
m_zoomFactor = zoomFactor;
m_pdfWidget->setZoomFactor(zoomFactor);
}
/*!
* \brief FolderContentEditDialog::setRotation
* \param rotation
*/
void FolderContentEditDialog::setRotation(int rotation)
{
if (m_rotation == rotation)
return;
DEBUG_LOG(m_logger) << "setRotation = " << rotation;
m_rotation = rotation;
m_pdfWidget->setRotation(getRotationFromValue(m_rotation));
emit rotationChanged(rotation);
}
/*!
* \brief FolderContentEditDialog::initPdfWidow
*/
void FolderContentEditDialog::initPdfWidow()
{
if(m_pdfWidget!= nullptr)
delete m_pdfWidget;
m_pdfWidget = new NGL::PDFWidget();
m_pdfWidget->setObjectName(QStringLiteral("osc_pdfWidget"));
m_pdfWidget->setSizePolicy(QSizePolicy::Policy::MinimumExpanding, QSizePolicy::Policy::MinimumExpanding);
m_pdfWidget->setWindowFlags(windowFlags() | Qt::WindowStaysOnTopHint);
connect(m_pdfWidget, &NGL::PDFWidget::currentPageChanged, this, &FolderContentEditDialog::setPage);
connect(m_pdfWidget, &NGL::PDFWidget::rotationChanged, this, [this](Poppler::Page::Rotation rot)
{
switch (rot)
{
case Poppler::Page::Rotate90:
setRotation(90);
break;
case Poppler::Page::Rotate180:
setRotation(180);
break;
case Poppler::Page::Rotate270:
setRotation(270);
break;
case Poppler::Page::Rotate0:
setRotation(0);
break;
}
});
}
void FolderContentEditDialog::onOcPdfDownloadReply(const Core::FunctionReplyObject & replyObject)
{
m_requestHelper->requestReply(replyObject);
m_fileSystemModel->setRootPath(getFileSysPath());
}
/*!
* \brief getRotationFromValue
* \param rotation
* \return
*/
Poppler::Page::Rotation getRotationFromValue(int rotation)
{
Poppler::Page::Rotation rot;
switch (rotation)
{
case 90:
rot = Poppler::Page::Rotate90;
break;
case 180:
rot = Poppler::Page::Rotate180;
break;
case 270:
rot = Poppler::Page::Rotate270;
break;
case 0:
default:
rot = Poppler::Page::Rotate0;
break;
}
return rot;
}
} // end namespace
@@ -0,0 +1,84 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - PDF Folder Content
* $Id$
* $HeadURL$
* $Author$
* Created by Steve Kemayou, SLSE, 2022-07-07
*/
#pragma once
#include <LtsWidgets/lts_dialog.h>
#include <OcSituationClient/logger.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsSession/lts_session.h>
#include <QFileSystemModel>
#include <nglwidgets/nglpdfwidget.h>
#include <QSortFilterProxyModel>
#include <LtsUtilsGuiDds/request_helper.h>
#include <Plugins/OcBaseDownload/obd_data_plugin_interface.h>
#define ZOOM_DEFAULT 1.0
namespace Ui {
class FolderContentEditDialog;
}
namespace OcSituationClient
{
class FolderContentEditDialog : public LtsWidgets::LtsDialog
, protected OcBaseDownload::Interface::Ftc::OcPdfDownloadReplyHandler
{
Q_OBJECT
public:
explicit FolderContentEditDialog(QWidget *parent = nullptr);
~FolderContentEditDialog();
bool init(LtsSession::LtsSessionDataDds *session);
void setDefaultFileSystemPath(QString path = QStringLiteral(""));
QString getFileSysPath(){return m_filesysPath;}
void initPdfWidow();
void onOcPdfDownloadReply(const Core::FunctionReplyObject &replyObject) override final;
private slots:
void onDeleteFile();
void onPreviewFile();
void setPage(int pageNo);
int getNumPages() const;
int getCurPage() const;
void setZoomFactor(double zoomFactor);
void setRotation(int rotation);
void onSelectionChanged();
void onOcPdfDownloadClicked();
signals:
void currentPageChanged(int curPage);
void rotationChanged(int rotation);
private:
void retranslate();
void enaDisa();
Ui::FolderContentEditDialog *m_ui;
LtsSession::LtsSessionDataDds *m_session;
std::shared_ptr<OcBaseDownload::Interface::Ftc> m_obdFtc;
QFileSystemModel *m_fileSystemModel{nullptr};
QString m_filesysPath{};
NGL::PDFWidget *m_pdfWidget{nullptr};
int m_pageNo{-1};
double m_zoomFactor{ZOOM_DEFAULT};
int m_rotation; // degree
QSortFilterProxyModel *m_proxymodel;
QString m_currViewPath;
QSortFilterProxyModel *m_sortProxyModel{nullptr};
LtsUtils::RequestHelper *m_requestHelper{nullptr};
LOGGER_T m_logger;
};
}// namespace FileManagement
@@ -0,0 +1,24 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>FolderContentEditDialog</class>
<widget class="QWidget" name="FolderContentEditDialog">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>490</width>
<height>300</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0">
<widget class="QTableView" name="filesView"/>
</item>
</layout>
</widget>
<resources/>
<connections/>
</ui>
@@ -0,0 +1,240 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - Fault Message Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#include "osc_equip_player.h"
#include "ui_osc_equip_player.h"
#include <AdvancedSymbology/asb_data_plugin_interface.h>
#include <PluginInterfaces/gui_plugin_interface.h>
#include <ParticipantManagement/ppm_ftc.h>
namespace OcSituationClient
{
EquipPlayer::EquipPlayer(LtsSession::LtsSession *session, QWidget *parent)
: LtsWidgets::LtsDialog(parent, LtsWidgets::ButtonCombination::OkApplyCancel)
, m_session(session)
, m_requestHelper(new LtsUtils::RequestHelper(this))
, m_selectedParticipantId(-1)
, m_maxChars(255)
, m_maxPartChars(35)
, m_isValid(false)
, m_model(nullptr)
, m_ftc(nullptr)
, m_ppmFtc(nullptr)
, m_tabocDtc(nullptr)
, m_ppmDtc(nullptr)
, m_ppmCbxGui(nullptr)
, m_ui(new Ui::EquipPlayer)
, m_logger(getLogger("EquipPlayerDialog"))
{
m_ui->setupUi(this);
setOnlineHelpFilename(QStringLiteral("OC-Equip_Player"));
}
EquipPlayer::~EquipPlayer()
{
delete m_ui;
}
bool EquipPlayer::init(const std::shared_ptr<Interface::Ftc> &ftc)
{
if (!ftc)
return false;
m_ftc = ftc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> dtcPpm;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(dtcPpm))
return false;
if (!m_session->getFtc<ParticipantManagement::DataInterface>(m_ppmFtc))
return false;
if (!m_session->getDtc<TrainingAreaBaseOC::DataInterface>(m_tabocDtc))
return false;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(m_ppmDtc))
return false;
if (!m_session->getForeignGuiInterface<ParticipantManagement::ForeignGuiComboboxInterface>(m_ppmCbxGui))
return false;
#ifdef TABLET_MODE
//css didn"t worked
m_ui->dvParticipants->setIconSize(QSize(50,50));
#endif
std::shared_ptr<AdvancedSymbology::ForeignDataInterface> asb;
m_session->getForeignDataInterface<AdvancedSymbology::DataInterface>(asb);
m_model = new ParticipantManagement::ParticipantEditModel(this, dtcPpm, asb);
// only needed to set recursiveFilteringEnabled
m_proxyModel = new ParticipantManagement::ParticipantTreeFilterProxyModel(this);
m_proxyModel->setSourceModel(m_model);
m_proxyModel->setRecursiveFilteringEnabled(true);
m_ui->dvParticipants->setModel(m_proxyModel);
m_ppmCbxGui->fillPartyComboBox(m_ui->cbParty);
connect(m_ui->dvParticipants, &LtsDataView::LtsDataView::signalSelectionChanged,
this, &EquipPlayer::onSlotSelectionChanged);
connect(m_ui->cbParty, &LtsWidgets::LtsComboBox::currentTextChanged, this, [this]
{
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->dvParticipants->expandAll();
});
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->dvParticipants->expandAll();
m_ui->dvParticipants->setSortIndicator(0, Qt::AscendingOrder);
m_ui->leParticipant->setValidator( new QIntValidator(0, 10000, this) );
m_ui->lblMaxEq->setText(QStringLiteral("-"));
m_ui->lblMinEq->setText(QStringLiteral("-"));
return true;
}
void EquipPlayer::onSlotSelectionChanged()
{
m_selectedParticipantId = 0;
const auto selIndexes = m_ui->dvParticipants->selectedRows();
ParticipantManagement::ParticipantData part;
ParticipantManagement::TypeClass tc;
if (!selIndexes.isEmpty())
{
part = m_model->getParticipantData(selIndexes.first());
ParticipantManagement::Type tp = m_ppmDtc->type(part.typeId());
ParticipantManagement::EquipmentType eq= m_ppmDtc->equipmentType(tp.equipmentTypeId());
m_ui->lblMinEq->setText(QString::number(eq.minEquipNo()));
m_ui->lblMaxEq->setText(QString::number(eq.maxEquipNo()));
tc = tp.typeClass();
if ( (tc == ParticipantManagement::TypeClass::Human)
|| (tc == ParticipantManagement::TypeClass::GroundVehicle)
|| (tc == ParticipantManagement::TypeClass::Aircraft)
|| (tc == ParticipantManagement::TypeClass::Vessel)
|| (tc == ParticipantManagement::TypeClass::WeaponSystem)
|| (tc == ParticipantManagement::TypeClass::VehicleWithGear) )
m_isValid = true;
else
m_isValid = false;
if (part.id())
m_selectedParticipantId = part.id();
else
m_selectedParticipantId = -1;
}
else
{
m_isValid = false;
m_selectedParticipantId = -1;
}
slotChangesMade();
if (m_selectedParticipantId > 0 && part.equipmentNumber().is_set())
m_ui->leParticipant->setText(QString::number(part.equipmentNumber().get()));
else
m_ui->leParticipant->setText(QString::number(0));
m_ui->leParticipant->setEnabled(m_isValid);
}
void EquipPlayer::retranslate()
{
translate(m_ui, tr("Equip Player") );
m_uiRequirements->clear();
m_uiRequirements->addRequirement({m_ui->lblParticpant, [this]() { return checkEqNr(); },
tr("Set to a valid Number or Equipment Number already exists!")});
m_uiRequirements->addRequirement({m_ui->label, [this]() { return m_isValid; },
tr("Only Participants are Allowed!")});
}
bool EquipPlayer::apply()
{
if (m_ui->leParticipant->text().toInt() < 0)
return false;
SendEquipmentRegistrationRequest req;
req.equipmentNumber(m_ui->leParticipant->text().toInt());
req.participantId(m_selectedParticipantId);
bool ret = m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendEquipmentRegistrationRequest(req, this);
});
//if( ret)
{
if (m_ppmDtc->participant(m_selectedParticipantId).equipmentNumber().is_set())
{
ParticipantManagement::RegisterParticipantRequest req3;
req3.participantId(m_selectedParticipantId);
req3.equipmentNumber(0);
req3.assignState(ParticipantManagement::ParticipantAssignState::NotAssigned);
m_requestHelper->startSingleRequest([req3, this]()
{
return m_ppmFtc->registerParticipantRequest(req3, this);
});
}
ParticipantManagement::RegisterParticipantRequest req2;
req2.participantId(m_selectedParticipantId);
req2.equipmentNumber(req.equipmentNumber());
req2.assignState(ParticipantManagement::ParticipantAssignState::HandoutExcon);
m_requestHelper->startSingleRequest([req2, this]()
{
return m_ppmFtc->registerParticipantRequest(req2, this);
});
}
return ret;
}
bool EquipPlayer::checkEqNr()
{
m_ui->lblError->setText(QString());
if (!m_isValid)
{
m_ui->lblError->setText(tr("No valid Participant selected!"));
return false;;
}
if(m_ui->leParticipant->text().isEmpty())
{
m_ui->lblError->setText(tr("Equipment Number is not valid!"));
return false;;
}
int equipNr = m_ui->leParticipant->text().toInt();
if (equipNr <= 0)
return true;
std::vector<ParticipantManagement::ParticipantData> data = m_model->participantData(false);
for (const auto &part : data)
{
if (!part.equipmentNumber().is_set())
continue;
if (part.equipmentNumber().is_set() && part.equipmentNumber().get() == equipNr)
{
m_ui->lblError->setText(tr("Equipment Number already exists!"));
return false;;
}
}
return true;
}
} // namespace OcSituationClient
@@ -0,0 +1,73 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - Fault Message Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#pragma once
#include <LtsWidgets/lts_dialog.h>
#include <LtsSession/lts_session.h>
#include <OcSituationClient/logger.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsUtilsGuiDds/request_helper.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <Plugins/TrainingAreaBaseOC/taboc_data_plugin_interface.h>
#include <ParticipantManagement/Gui/Common/participant_edit_model.h>
#include <Plugins/ParticipantManagement/ppm_gui_combobox_plugin_interface.h>
namespace Ui
{
class EquipPlayer;
}
namespace OcSituationClient
{
class EquipPlayer : public LtsWidgets::LtsDialog
, private OcSituationClient::Interface::Ftc::SendEquipmentRegistrationReplyHandler
, private ParticipantManagement::Interface::Ftc::RegisterParticipantReplyHandler
{
Q_OBJECT
public:
explicit EquipPlayer(LtsSession::LtsSession *session, QWidget *parent = nullptr);
~EquipPlayer();
bool init(const std::shared_ptr<Interface::Ftc> &ftc);
void onSendEquipmentRegistrationReply(const Core::FunctionReplyObject &replyObject) override { m_requestHelper->requestReply(replyObject); }
void onRegisterParticipantReply(const ParticipantManagement::RegisterReply &replyObject) override { m_requestHelper->requestReply(replyObject); }
private Q_SLOTS:
void onSlotSelectionChanged();
private:
void retranslate() override;
bool apply() override;
bool checkEqNr();
private:
LtsSession::LtsSession *m_session;
LtsUtils::RequestHelper *m_requestHelper;
int m_selectedParticipantId;
int m_maxChars;
int m_maxPartChars;
bool m_isValid;
ParticipantManagement::ParticipantEditModel *m_model;
LtsWidgets::LtsColumnFilterProxyModel *m_proxyModel;
std::shared_ptr<OcSituationClient::Interface::Ftc> m_ftc;
std::shared_ptr<ParticipantManagement::Interface::Ftc> m_ppmFtc;
std::shared_ptr<TrainingAreaBaseOC::Interface::Dtc> m_tabocDtc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> m_ppmDtc;
std::shared_ptr<ParticipantManagement::ForeignGuiComboboxInterface> m_ppmCbxGui;
Ui::EquipPlayer *m_ui;
LOGGER_T m_logger;
};
} // namespace OcSituationClient
@@ -0,0 +1,156 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>EquipPlayer</class>
<widget class="QWidget" name="EquipPlayer">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>726</width>
<height>442</height>
</rect>
</property>
<property name="windowTitle">
<string notr="true">MessagingView</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<layout class="QHBoxLayout" name="horizontalLayout_2">
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>Party:</string>
</property>
</widget>
</item>
<item>
<widget class="LtsWidgets::LtsComboBox" name="cbParty"/>
</item>
<item>
<spacer name="horizontalSpacer">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item>
<widget class="LtsDataView::LtsDataView" name="dvParticipants" native="true">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="MinimumExpanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="showColumnCount" stdset="0">
<bool>false</bool>
</property>
<property name="toolButtonsVisible" stdset="0">
<bool>false</bool>
</property>
</widget>
</item>
<item>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="2">
<layout class="QHBoxLayout" name="horizontalLayout_3">
<item>
<widget class="QLabel" name="lblMinEq">
<property name="text">
<string notr="true">&lt;COUNT&gt;</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label_7">
<property name="text">
<string notr="true">/</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="lblMaxEq">
<property name="text">
<string notr="true">&lt;MAX&gt;</string>
</property>
</widget>
</item>
</layout>
</item>
<item row="0" column="0">
<widget class="QLabel" name="lblParticpant">
<property name="text">
<string>Equipment Number:</string>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLineEdit" name="leParticipant">
<property name="sizePolicy">
<sizepolicy hsizetype="MinimumExpanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="maximumSize">
<size>
<width>200</width>
<height>16777215</height>
</size>
</property>
<property name="toolTip">
<string>Participant</string>
</property>
</widget>
</item>
<item row="0" column="3">
<spacer name="horizontalSpacer_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item>
<widget class="QLabel" name="lblError">
<property name="text">
<string notr="true"/>
</property>
</widget>
</item>
</layout>
</widget>
<customwidgets>
<customwidget>
<class>LtsWidgets::LtsComboBox</class>
<extends>QComboBox</extends>
<header>LtsWidgets/lts_combo_box.h</header>
</customwidget>
<customwidget>
<class>LtsDataView::LtsDataView</class>
<extends>QWidget</extends>
<header>LtsDataView/lts_data_view.h</header>
<container>1</container>
</customwidget>
</customwidgets>
<tabstops>
<tabstop>cbParty</tabstop>
<tabstop>leParticipant</tabstop>
</tabstops>
<resources/>
<connections/>
</ui>
@@ -0,0 +1,216 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - Fault Message Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#include "osc_fault_message.h"
#include "ui_osc_fault_message.h"
#include <AdvancedSymbology/asb_data_plugin_interface.h>
#include <PluginInterfaces/gui_plugin_interface.h>
namespace OcSituationClient
{
FaultMessage::FaultMessage(LtsSession::LtsSession *session, QWidget *parent)
: LtsWidgets::LtsDialog(parent, LtsWidgets::ButtonCombination::OkApplyCancel)
, m_session(session)
, m_requestHelper(new LtsUtils::RequestHelper(this))
, m_selectedEqNr(-1)
, m_maxChars(255)
, m_maxPartChars(35)
, m_ownEquipmentId(0)
, m_model(nullptr)
, m_ftc(nullptr)
, m_tabocDtc(nullptr)
, m_ppmCbxGui(nullptr)
, m_ui(new Ui::FaultMessage)
, m_logger(getLogger("FaultMessageDialog"))
{
m_ui->setupUi(this);
m_ui->lblCountMax->setText(QString::number(m_maxChars));
m_ui->lblCount->setText(QString::number(0));
m_ui->lblDevCountMax->setText(QString::number(m_maxPartChars));
m_ui->lblDevCount->setText(QString::number(0));
connect(m_ui->teComment, &QPlainTextEdit::textChanged, this, &FaultMessage::onTextChanged);
connect(m_ui->leDevice, &QLineEdit::textChanged, this, &FaultMessage::onDevTextChanged);
setOnlineHelpFilename(QStringLiteral("OC-Fault_Message"));
}
FaultMessage::~FaultMessage()
{
delete m_ui;
}
bool FaultMessage::init(const std::shared_ptr<Interface::Ftc> &ftc)
{
if (!ftc)
return false;
m_ftc = ftc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> dtcPpm;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(dtcPpm))
return false;
if (!m_session->getDtc<TrainingAreaBaseOC::DataInterface>(m_tabocDtc))
return false;
if (!m_session->getForeignGuiInterface<ParticipantManagement::ForeignGuiComboboxInterface>(m_ppmCbxGui))
return false;
#ifdef TABLET_MODE
//css didn"t worked
m_ui->dvParticipants->setIconSize(QSize(50,50));
#endif
std::shared_ptr<AdvancedSymbology::ForeignDataInterface> asb;
m_session->getForeignDataInterface<AdvancedSymbology::DataInterface>(asb);
m_model = new ParticipantManagement::ParticipantEditModel(this, dtcPpm, asb);
// only needed to set recursiveFilteringEnabled
m_proxyModel = new ParticipantManagement::ParticipantTreeFilterProxyModel(this);
m_proxyModel->setSourceModel(m_model);
m_proxyModel->setRecursiveFilteringEnabled(true);
m_ui->dvParticipants->setModel(m_proxyModel);
m_ppmCbxGui->fillPartyComboBox(m_ui->cbParty);
connect(m_ui->dvParticipants, &LtsDataView::LtsDataView::signalSelectionChanged,
this, &FaultMessage::onSlotSelectionChanged);
connect(m_tabocDtc.get(), &TrainingAreaBaseOC::Interface::Dtc::specificsEquipmentChanged,
this, &FaultMessage::onSpecificsEquipmentChanged);
m_tabocDtc->specificsEquipments([this](const TrainingAreaBaseOC::SpecificsEquipment & data) { onSpecificsEquipmentChanged(data, DataModification::eAdded); });
connect(m_ui->cbParty, &LtsWidgets::LtsComboBox::currentTextChanged, this, [this]
{
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->dvParticipants->expandAll();
});
m_model->onReinitModel(m_ui->cbParty->currentData().toInt());
m_ui->dvParticipants->expandAll();
m_ui->dvParticipants->setSortIndicator(0, Qt::AscendingOrder);
m_ui->leParticipant->setValidator( new QIntValidator(1, 10000, this) );
return true;
}
void FaultMessage::onSlotSelectionChanged()
{
m_selectedEqNr = 0;
const auto selIndexes = m_ui->dvParticipants->selectedRows();
if (!selIndexes.isEmpty())
{
ParticipantManagement::ParticipantData part = m_model->getParticipantData(selIndexes.first());
if (part.equipmentNumber().is_set())
m_selectedEqNr = part.equipmentNumber().get();
else
m_selectedEqNr = -1;
}
slotChangesMade();
if (m_selectedEqNr > 0)
m_ui->leParticipant->setText(QString::number(m_selectedEqNr));
}
void FaultMessage::onTextChanged()
{
QString plainText(m_ui->teComment->toPlainText());
int currentUsedChars = plainText.toUtf8().size();
bool bNeedSetNew = false;
while (currentUsedChars > m_maxChars)
{
plainText.chop(1);
currentUsedChars = plainText.toUtf8().size();
bNeedSetNew = true; // do not set text directly, results in recursion
}
// if text longer than allowed
if (bNeedSetNew)
{
m_ui->teComment->setPlainText(plainText);
m_ui->teComment->moveCursor(QTextCursor::End);
}
m_ui->lblCount->setText(QString::number(currentUsedChars));
}
void FaultMessage::onDevTextChanged()
{
timText(m_ui->leDevice, m_ui->lblDevCount);
}
void FaultMessage::timText(QLineEdit *le, QLabel *lbl)
{
QString plainText(le->text());
int currentUsedChars = plainText.toUtf8().size();
bool bNeedSetNew = false;
while (currentUsedChars > m_maxPartChars)
{
plainText.chop(1);
currentUsedChars = plainText.toUtf8().size();
bNeedSetNew = true; // do not set text directly, results in recursion
}
// if text longer than allowed
if (bNeedSetNew)
{
le->setText(plainText);
}
lbl->setText(QString::number(currentUsedChars));
}
void FaultMessage::retranslate()
{
translate(m_ui, tr("Fault Message") );
m_uiRequirements->clear();
m_uiRequirements->addRequirement({m_ui->lblDevice, [this]() { return !m_ui->leDevice->text().isEmpty(); },
tr("Name the faulty devices.")});
m_uiRequirements->addRequirement({m_ui->lblComment, [this]()
{
return (!m_ui->teComment->toPlainText().isEmpty() &&
m_ui->teComment->toPlainText().count() <= m_maxChars);
},
tr("Add a text comment.")});
}
bool FaultMessage::apply()
{
if (m_ui->leParticipant->text().toInt() <= 0)
return false;
SendEquipmentErrorRegistrationRequest req;
req.device(m_ui->leDevice->text().toStdString());
req.faultEquipmentNumber(m_ui->leParticipant->text().toStdString());
req.text(m_ui->teComment->toPlainText().toStdString());
req.ocEquipmentNumber(m_ownEquipmentId);
return m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendEquipmentErrorRegistrationRequest(req, this);
});
}
void FaultMessage::onSpecificsEquipmentChanged(const TrainingAreaBaseOC::SpecificsEquipment &data, const DataModification &modType)
{
if (DataModification::eRemoved == modType)
return;
m_ownEquipmentId = data.equipmentNumber();
if (m_ownEquipmentId <= 0)
WARNING_LOG(m_logger) << "EquipmentNumber " << data.equipmentNumber() << " is not present ";
}
} // namespace OcSituationClient
@@ -0,0 +1,71 @@
/**
* @RDE_HEADER@
* HMI Plugin for Observer Controller - Fault Message Dialog
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#pragma once
#include <LtsWidgets/lts_dialog.h>
#include <LtsSession/lts_session.h>
#include <OcSituationClient/logger.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsUtilsGuiDds/request_helper.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <Plugins/TrainingAreaBaseOC/taboc_data_plugin_interface.h>
#include <ParticipantManagement/Gui/Common/participant_edit_model.h>
#include <Plugins/ParticipantManagement/ppm_gui_combobox_plugin_interface.h>
namespace Ui
{
class FaultMessage;
}
namespace OcSituationClient
{
class FaultMessage : public LtsWidgets::LtsDialog
, private OcSituationClient::Interface::Ftc::SendEquipmentErrorRegistrationReplyHandler
{
Q_OBJECT
public:
explicit FaultMessage(LtsSession::LtsSession *session, QWidget *parent = nullptr);
~FaultMessage();
bool init(const std::shared_ptr<Interface::Ftc> &ftc);
void onSendEquipmentErrorRegistrationReply(const Core::FunctionReplyObject &replyObject) override { m_requestHelper->requestReply(replyObject); }
private Q_SLOTS:
void onSlotSelectionChanged();
void onTextChanged();
void onDevTextChanged();
void onSpecificsEquipmentChanged(const TrainingAreaBaseOC::SpecificsEquipment &data, const DataModification &modType);
private:
void retranslate() override;
bool apply() override;
void timText(QLineEdit *le, QLabel *lbl);
private:
LtsSession::LtsSession *m_session;
LtsUtils::RequestHelper *m_requestHelper;
int m_selectedEqNr;
int m_maxChars;
int m_maxPartChars;
int m_ownEquipmentId;
ParticipantManagement::ParticipantEditModel *m_model;
LtsWidgets::LtsColumnFilterProxyModel *m_proxyModel;
std::shared_ptr<OcSituationClient::Interface::Ftc> m_ftc;
std::shared_ptr<TrainingAreaBaseOC::Interface::Dtc> m_tabocDtc;
std::shared_ptr<ParticipantManagement::ForeignGuiComboboxInterface> m_ppmCbxGui;
Ui::FaultMessage *m_ui;
LOGGER_T m_logger;
};
} // namespace OcSituationClient
@@ -0,0 +1,218 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>FaultMessage</class>
<widget class="QWidget" name="FaultMessage">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>388</width>
<height>757</height>
</rect>
</property>
<property name="windowTitle">
<string notr="true">MessagingView</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<layout class="QHBoxLayout" name="horizontalLayout_2">
<item>
<widget class="QLabel" name="label">
<property name="text">
<string>Party:</string>
</property>
</widget>
</item>
<item>
<widget class="LtsWidgets::LtsComboBox" name="cbParty"/>
</item>
<item>
<spacer name="horizontalSpacer">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item>
<widget class="LtsDataView::LtsDataView" name="dvParticipants">
<property name="showColumnCount" stdset="0">
<bool>false</bool>
</property>
<property name="toolButtonsVisible">
<bool>false</bool>
</property>
</widget>
</item>
<item>
<layout class="QGridLayout" name="gridLayout">
<item row="1" column="0">
<widget class="QLabel" name="lblDevice">
<property name="text">
<string>Device:</string>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QLabel" name="lblParticpant">
<property name="text">
<string>Participant:</string>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QLineEdit" name="leDevice">
<property name="sizePolicy">
<sizepolicy hsizetype="MinimumExpanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="toolTip">
<string>Device</string>
</property>
</widget>
</item>
<item row="1" column="2">
<layout class="QHBoxLayout" name="horizontalLayout_3">
<item>
<widget class="QLabel" name="lblDevCount">
<property name="text">
<string notr="true">&lt;COUNT&gt;</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label_7">
<property name="text">
<string notr="true">/</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="lblDevCountMax">
<property name="text">
<string notr="true">&lt;MAX&gt;</string>
</property>
</widget>
</item>
</layout>
</item>
<item row="0" column="1">
<widget class="QLineEdit" name="leParticipant">
<property name="sizePolicy">
<sizepolicy hsizetype="MinimumExpanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="toolTip">
<string>Participant</string>
</property>
</widget>
</item>
<item row="0" column="3">
<spacer name="horizontalSpacer_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
<item>
<widget class="QLabel" name="lblComment">
<property name="text">
<string>Comment:</string>
</property>
</widget>
</item>
<item>
<widget class="QPlainTextEdit" name="teComment">
<property name="toolTip">
<string>Comment</string>
</property>
</widget>
</item>
<item>
<layout class="QHBoxLayout" name="horizontalLayout_4">
<item>
<widget class="QLabel" name="label_3">
<property name="text">
<string>Characters:</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="lblCount">
<property name="text">
<string notr="true">&lt;COUNT&gt;</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="label_5">
<property name="text">
<string notr="true">/</string>
</property>
</widget>
</item>
<item>
<widget class="QLabel" name="lblCountMax">
<property name="text">
<string notr="true">&lt;MAX&gt;</string>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer_3">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
</layout>
</item>
</layout>
</widget>
<customwidgets>
<customwidget>
<class>LtsWidgets::LtsComboBox</class>
<extends>QComboBox</extends>
<header>LtsWidgets/lts_combo_box.h</header>
</customwidget>
<customwidget>
<class>LtsDataView::LtsDataView</class>
<extends>QWidget</extends>
<header>LtsDataView/lts_data_view.h</header>
<container>1</container>
</customwidget>
</customwidgets>
<tabstops>
<tabstop>cbParty</tabstop>
<tabstop>leParticipant</tabstop>
<tabstop>leDevice</tabstop>
<tabstop>teComment</tabstop>
</tabstops>
<resources/>
<connections/>
</ui>
@@ -0,0 +1,462 @@
/**
* @RDE_HEADER@
* Gui Plugin for Demand Situation
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#include "osc_terminal_gui_plugin.h"
#include "osc_fault_message.h"
#include "osc_equip_player.h"
#include "osc_demand_situation_filter.h"
#include "osc_edit_folder_content.h"
#include <OcSituationClient/logger.h>
#include <ngltools/ngltools_dtg.h>
#include <LtsSession/lts_session.h>
#include <LtsSession/lts_session_data.h>
#include <LtsUtilsSettings/settings.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <Plugins/ParticipantManagement/ppm_gui_combobox_plugin_interface.h>
#include <Map/map.h> // Interface
#include <QTimer>
#include <LtsWidgets/lts_base_layout_widget.h>
#include <QPainter>
#include <QImage>
#include <QRect>
#include <QRadialGradient>
namespace OcSituationClient
{
std::shared_ptr<GuiPluginBase::Interface> GuiPlugin::createGuiInterface(LtsSession::LtsSession *session)
{
return std::make_shared<InterfaceImpl>(session);
}
InterfaceImpl::InterfaceImpl(LtsSession::LtsSession *session)
: GuiPluginBase::Interface(session, getLogger("OcTerminal.InterfaceImpl"))
, m_timer(new QTimer(this))
, m_requestHelper( new LtsUtils::RequestHelper(this))
, m_shortcutDemandSituation(nullptr)
, m_mapTimeLabelHideTimer(new QTimer(this))
, m_demandSituation(nullptr)
{
m_timer->setInterval(3*60*1000); //3 minutes
connect(m_timer, &QTimer::timeout, this, &InterfaceImpl::onNoDataTimerTick);
m_mapTimeLabelHideTimer->setInterval(1000);
m_mapTimeLabelHideTimer->setSingleShot(true);
connect(m_mapTimeLabelHideTimer, &QTimer::timeout, this, &InterfaceImpl::onShortcutDemandSituationIconChanged);
}
InterfaceImpl::~InterfaceImpl()
{}
void InterfaceImpl::onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject)
{
m_requestHelper->requestReply(replyObject);
}
void InterfaceImpl::stopSituationDemand()
{
const int range = 0;
const int participant = 0;
const Core::GeoPosition2D pos(0,0);
std::vector<int> partyIds{};
std::vector<int> typesClass{};
SendDemandSituationRequest req(participant,
range,
dds::core::optional<Core::GeoPosition2D>(),
false,
partyIds,
typesClass);
m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendDemandSituationRequest(req, this);
});
setShortcutDemandSituationIconData(true);
}
bool InterfaceImpl::fetchInterfaces()
{
std::shared_ptr<ParticipantManagement::ForeignGuiComboboxInterface> ppmCbxGui;
if (!m_session->getDtc<ParticipantManagement::DataInterface>(m_dtcPpm))
return false;
if (!m_session->getForeignGuiInterface<ParticipantManagement::ForeignGuiComboboxInterface>(ppmCbxGui))
return false;
if (!m_session->getDtc<TrainingAreaBaseOC::DataInterface>(m_dtcTab))
return false;
if (!m_session->getFtc<OcSituationClient::DataInterface>(m_ftc))
return false;
if (!m_session->getForeignGuiInterface<SituationMap::ForeignGuiInterface>(m_sitMapGuiIfc))
return false;
return true;
}
void InterfaceImpl::clearInterfaces()
{
m_ftc = nullptr;
}
QString InterfaceImpl::menuGroup() const
{
return tr("Terminal");
}
QVector<LtsWidgets::PluginData> InterfaceImpl::getActions()
{
QVector<LtsWidgets::PluginData> ret;
LtsWidgets::PluginData plData;
plData.menuGroup = menuGroup();
if(m_shortcutDemandSituation == nullptr)
{
m_shortcutDemandSituation = m_session->createNotification(QStringLiteral("oscShortcutDemandSituation"));
m_shortcutDemandSituation->setIcon(QIcon(QStringLiteral("icon:demand_situation.svg")));
m_shortcutDemandSituation->setToolTip(tr("Demand Situation not started"));
m_shortcutDemandSituation->setAction([this]()
{
m_session->addWidget(onShowDemandSituation(nullptr), menuGroup(), QStringLiteral("oscDemandSituation"), LtsWidgets::LayoutArea::eDialogTab);
});
connect(m_dtcTab.get(), &TrainingAreaBaseOC::Interface::Dtc::participantsOverloadChanged, this, &InterfaceImpl::onParticipantsOverloadChanged);
connect(m_dtcTab.get(), &TrainingAreaBaseOC::Interface::Dtc::centralAesOverloadChanged, this, &InterfaceImpl::onCentralAesOverloadChanged);
connect(m_session->baseLayout(), &LtsWidgets::LtsBaseLayoutWidget::signalLogout,
this, [this]{
stopSituationDemand();
});
}
// Action 'Demand Situation'
plData.menuText = tr("Demand Situation");
plData.identifier = QStringLiteral("oscDemandSituation");
plData.menuIcon = QIcon(QLatin1String("icon:demand_situation.svg"));
plData.operatorRight = 0;
plData.createWidgetFunc = [this](QWidget * parent)
{
return onShowDemandSituation(parent);
};
ret.append(plData);
{
// Action 'Demand Situation Filter'
LtsWidgets::PluginData plData2;
plData2.menuGroup = menuGroup();
plData2.menuText = tr("Demand Situation Filter");
plData2.identifier = QStringLiteral("oscDemandSituationFilter");
plData2.menuIcon = QIcon(QLatin1String("icon:demand_situation_filter.svg"));
plData2.operatorRight = 0;
plData2.createWidgetFunc = [this](QWidget * parent)
{
return onShowDemandSituationFilter(parent);
};
ret.append(plData2);
}
if (strcmp(PROJECTBUILD, "guez") != 0) //not guez add fault message
{
// Action 'Equipment Fault'
plData.menuText = tr("Fault Message");
plData.identifier = QStringLiteral("oscFaultMessage");
plData.menuIcon = QIcon(QLatin1String("icon:player_equipment_fault.svg"));
plData.operatorRight = 0;
plData.createWidgetFunc = [this](QWidget * parent)
{
return onShowFaultMessage(parent);
};
ret.append(plData);
}else //is guez add folder content
{
// Action 'Edit folder content'
plData.menuText = tr(" Folder Content");
plData.identifier = QStringLiteral("oscEditFolderContent");
plData.menuIcon = QIcon(QLatin1String("icon:organize_library.svg"));
plData.operatorRight = 0;
plData.createWidgetFunc = [this](QWidget * parent)
{
return onShowEditFolderContentDialog(parent);
};
ret.append(plData);
}
if (strcmp(PROJECTBUILD, "guez") != 0)
{
// Action 'Equipment Fault'
plData.menuText = tr("Equip Player");
plData.identifier = QStringLiteral("oscEquipPlayer");
plData.menuIcon = QIcon(QLatin1String("icon:force_player_configuration.svg"));
plData.operatorRight = 0;
plData.createWidgetFunc = [this](QWidget * parent)
{
return onShowEquipPlayer(parent);
};
ret.append(plData);
}
//now send request for old
QTimer::singleShot(2000, this, &InterfaceImpl::onTimerTick);
m_dtcTab->enableParticipantsOverload();
return ret;
}
void InterfaceImpl::onTimerTick()
{
connect(m_dtcPpm.get(), &ParticipantManagement::Interface::Dtc::participantPositionChanged,
this, &InterfaceImpl::onParticipantPosition, Qt::UniqueConnection);
connect(m_dtcPpm.get(), &ParticipantManagement::Interface::Dtc::dynamicParticipantDataChanged,
this, &InterfaceImpl::onParticipantDynamic, Qt::UniqueConnection);
LtsUtils::OperatorSettings *settings = LtsUtils::OperatorSettings::getInstance();
QString ocString = QStringLiteral("ObserverControllerDemand");
const int range = settings->value(ocString, QStringLiteral("Range"), 0).toInt();
// if (range <= 0)
// return;
/// stop sending demand situation on initialization
const int participant = 0;
const Core::GeoPosition2D pos(0,0);
std::vector<int> partyIds{};
std::vector<int> typesClass{};
const QStringList partyList = settings->value(ocString, QStringLiteral("Partys"),-1).toStringList();
const QStringList typeClassList = settings->value(ocString, QStringLiteral("TypeClass"),-1).toStringList();
partyIds.reserve(partyList.size());
for (const auto &party: partyList)
{
partyIds.push_back(party.toInt());
}
typesClass.reserve(typeClassList.size());
for (const auto &typeCl: typeClassList)
{
typesClass.push_back(typeCl.toInt());
}
SendDemandSituationRequest req(participant,
range,
dds::core::optional<Core::GeoPosition2D>(),
settings->value(ocString, QStringLiteral("FilterActive"),false).toBool(),
partyIds,
typesClass);
if (pos.lat() > 0)
{
req.position().set(pos);
}
m_requestHelper->startSingleRequest([req, this]()
{
return m_ftc->sendDemandSituationRequest(req, this);
});
setShortcutDemandSituationIconData(true);
}
void InterfaceImpl::onNoDataTimerTick()
{
//We stop the timer until the first overload message arrives again
m_timer->stop();
setShortcutDemandSituationIconData(true);
}
void InterfaceImpl::onParticipantDynamic(const ParticipantManagement::DynamicParticipantData &data)
{
if (m_dtcPpm->participant(data.participantId()).equipmentNumber() == m_dtcTab->specificsEquipment(1).equipmentNumber())
return;
onParticipantData();
}
void InterfaceImpl::onParticipantPosition(const ParticipantManagement::ParticipantPosition &data)
{
if (m_dtcPpm->participant(data.participantId()).equipmentNumber() == m_dtcTab->specificsEquipment(1).equipmentNumber())
return;
onParticipantData();
}
void InterfaceImpl::onCentralAesOverloadChanged(const TrainingAreaBaseOC::CentralAesOverload &data, DataModification modType)
{
Q_UNUSED(modType)
m_hasCentralAesOverload = data.hasOverload();
setShortcutDemandSituationIconData();
m_timer->start();
}
void InterfaceImpl::onParticipantsOverloadChanged(const TrainingAreaBaseOC::ParticipantsOverload &data, DataModification modType)
{
Q_UNUSED(modType)
m_hasParticipantOverload = data.hasOverload();
setShortcutDemandSituationIconData();
m_timer->start();
}
void InterfaceImpl::onShortcutDemandSituationIconChanged()
{
if (!m_sitMapGuiIfc)
{
m_mapTimeLabelHideTimer->start();
return;
}
m_sitMapGuiIfc->map()->showTimeString(m_demandSituationActive);
m_sitMapGuiIfc->map()->setTimeString(DTG::toStringMSec(m_session->partitionTime()));
}
void InterfaceImpl::setShortcutDemandSituationIconData(bool hasToBeDisabled)
{
if (m_shortcutDemandSituation == nullptr)
return;
m_demandSituationActive = true;
if (hasToBeDisabled)
{
m_shortcutDemandSituation->setIcon(QIcon(QStringLiteral("icon:demand_situation_disabled.svg")));
m_shortcutDemandSituation->setToolTip(tr("Demand Situation not started"));
m_demandSituationActive = false;
}
else
{
m_shortcutDemandSituation->setIcon(getOverloadIcon());
m_shortcutDemandSituation->setToolTip(getOverLoadTooltip());
}
if (m_mapTimeLabelHideTimer != nullptr)
m_mapTimeLabelHideTimer->start();
}
QString InterfaceImpl::getOverLoadTooltip() const
{
if (m_hasParticipantOverload && m_hasCentralAesOverload)
{
return tr("Demand Situation: Participant and Central AES count out of range");
}
else if (m_hasParticipantOverload)
{
return tr("Demand Situation: Participant count out of range");
}
else if (m_hasCentralAesOverload)
{
return tr("Demand Situation: Central AES count out of range");
}
else
{
return tr("Demand Situation");
}
}
QIcon InterfaceImpl::getOverloadIcon() const
{
qint32 size = 100;
QImage image(size, size, QImage::Format_ARGB32);
image.fill(Qt::transparent);
QPainter painter(&image);
painter.setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform);
painter.setPen(Qt::transparent);
QColor centralAesOverloadColor = m_hasCentralAesOverload ? Qt::red : Qt::green;
QColor participantOverloadColor = m_hasParticipantOverload ? Qt::red : Qt::green;
QRect arcRect(0, 0, size , size);
QRadialGradient arcGradient(arcRect.center(), size * 0.6);
arcGradient.setColorAt(1.0, Qt::transparent);
// participant overload
arcGradient.setColorAt(0.0, participantOverloadColor);
painter.setBrush(QBrush(arcGradient));
painter.drawPie(arcRect, 90 * 16, 180 * 16);
// central aes overload
arcGradient.setColorAt(0.0, centralAesOverloadColor);
painter.setBrush(QBrush(arcGradient));
painter.drawPie(arcRect, 270 * 16, 180 * 16);
QFont font = painter.font() ;
font.setPointSize(30);
font.setBold(true);
painter.setFont(font);
painter.setBrush(QBrush(Qt::black, Qt::NoBrush));
painter.setPen(Qt::black);
painter.drawText(55, 65, tr("W"));
painter.setBrush(QBrush(Qt::black, Qt::NoBrush));
painter.setPen(Qt::black);
painter.drawText(17, 65, tr("T"));
painter.end();
return QIcon(QPixmap::fromImage(image));
}
void InterfaceImpl::onParticipantData()
{
if (!m_sitMapGuiIfc)
return;
m_sitMapGuiIfc->map()->showTimeString(m_demandSituationActive);
m_sitMapGuiIfc->map()->setTimeString(DTG::toStringMSec(m_session->partitionTime()));
}
LtsWidgets::LtsDialog *InterfaceImpl::onShowDemandSituation(QWidget *parent)
{
m_demandSituation = new DemandSituation(m_session, parent);
connect(m_demandSituation, &DemandSituation::destroyed, this,[this]()
{
m_demandSituation = nullptr;
});
connect(m_demandSituation, &DemandSituation::demandSituationStopped, this, [this]()
{
stopSituationDemand();
}, Qt::UniqueConnection);
return LtsWidgets::initDialog(m_demandSituation,
m_ftc);
}
LtsWidgets::LtsDialog *InterfaceImpl::onShowDemandSituationFilter(QWidget *parent)
{
return LtsWidgets::initDialog(new DemandSituationFilter(m_session, parent),
m_ftc);
}
LtsWidgets::LtsDialog *InterfaceImpl::onShowFaultMessage(QWidget *parent)
{
return LtsWidgets::initDialog(new FaultMessage(m_session, parent),
m_ftc);
}
LtsWidgets::LtsDialog *InterfaceImpl::onShowEquipPlayer(QWidget *parent)
{
return LtsWidgets::initDialog(new EquipPlayer(m_session, parent),
m_ftc);
}
LtsWidgets::LtsDialog *InterfaceImpl::onShowEditFolderContentDialog(QWidget *parent)
{
return LtsWidgets::initDialog(new FolderContentEditDialog(parent),m_session);
}
} // namespace OcSituationClient
@@ -0,0 +1,108 @@
/**
* @RDE_HEADER@
* Gui Plugin for Demand Situation
* $Id$
* $HeadURL$
* $Author$
* Created by Patric Karwat, SLSE, 2018-03-27
*/
#pragma once
#include <PluginInterfaces/gui_plugin_interface.h>
#include <Plugins/SituationMapPlugin/situation_map_gui_plugin_interface.h>
#include <Plugins/ParticipantManagement/ppm_data_plugin_interface.h>
#include <Plugins/TrainingAreaBaseOC/taboc_data_plugin_interface.h>
#include <Plugins/OcSituationClient/osc_terminal_gui_plugin_interface.h>
#include <Plugins/OcSituationClient/osc_data_plugin_interface.h>
#include <LtsUtilsGuiDds/request_helper.h>
#include <LtsNotification/lts_notification.h>
#include "osc_demand_situation.h"
class QTimer;
namespace OcSituationClient
{
class GuiPlugin final : public QObject, public GuiPluginBase::Plugin
{
Q_PLUGIN_METADATA(IID "gui:3:osc.terminal")
Q_INTERFACES(GuiPluginBase::Plugin)
Q_OBJECT
public:
GuiPlugin() = default;
~GuiPlugin() = default;
QString pluginName() override { return QStringLiteral("ObserverController.Terminal"); }
std::shared_ptr<GuiPluginBase::Interface> createGuiInterface(LtsSession::LtsSession *session) override;
bool availableInPartition(IDL::PartitionType partition) const override
{
return (partition == IDL::PartitionType::Exercise ||
partition == IDL::PartitionType::Replay);
}
};
class InterfaceImpl final : public QObject, public ForeignTerminalGuiInterface, public GuiPluginBase::Interface,
private OcSituationClient::Interface::Ftc::SendDemandSituationReplyHandler
{
Q_OBJECT
public:
explicit InterfaceImpl(LtsSession::LtsSession *session);
~InterfaceImpl();
void onSendDemandSituationReply(const Core::FunctionReplyObject &replyObject) override;
void stopSituationDemand();
bool fetchInterfaces() override;
void clearInterfaces() override;
QString menuGroup() const override;
QVector<LtsWidgets::PluginData> getActions() override;
bool availableInPartition(IDL::PartitionType partition) const override
{
return partition == IDL::PartitionType::Global || partition == IDL::PartitionType::Exercise;
}
private slots:
void onTimerTick();
void onNoDataTimerTick();
void onParticipantData();
void onParticipantDynamic(const ParticipantManagement::DynamicParticipantData &data);
void onParticipantPosition(const ParticipantManagement::ParticipantPosition &data);
void onCentralAesOverloadChanged(const TrainingAreaBaseOC::CentralAesOverload &data, DataModification modType);
void onParticipantsOverloadChanged(const TrainingAreaBaseOC::ParticipantsOverload &data, DataModification modType);
void onShortcutDemandSituationIconChanged();
private:
void setShortcutDemandSituationIconData(bool hasToBeDisabled = false);
QString getOverLoadTooltip() const;
QIcon getOverloadIcon() const;
private:
QTimer *m_timer;
LtsUtils::RequestHelper *m_requestHelper;
LtsWidgets::LtsDialog *onShowDemandSituation(QWidget *parent);
LtsWidgets::LtsDialog *onShowDemandSituationFilter(QWidget *parent);
LtsWidgets::LtsDialog *onShowFaultMessage(QWidget *parent);
LtsWidgets::LtsDialog *onShowEquipPlayer(QWidget *parent);
LtsWidgets::LtsDialog *onShowEditFolderContentDialog(QWidget *parent);
std::shared_ptr<SituationMap::ForeignGuiInterface> m_sitMapGuiIfc;
std::shared_ptr<ParticipantManagement::Interface::Dtc> m_dtcPpm;
std::shared_ptr<TrainingAreaBaseOC::Interface::Dtc> m_dtcTab;
std::shared_ptr<OcSituationClient::Interface::Ftc> m_ftc;
LtsNotification::LtsNotification *m_shortcutDemandSituation;
QTimer *m_mapTimeLabelHideTimer;
bool m_demandSituationActive{false};
bool m_hasParticipantOverload{false};
bool m_hasCentralAesOverload{false};
DemandSituation *m_demandSituation;
};
} // namespace OcSituationClient