/** * Handler for all exercise objects * $Id$ * $HeadURL$ * $Author$ * Created by Hanna E. Rathje, SLSE, 2015-09-03 */ #include "handler_order.h" #include "object_order.h" #include "esc_db.h" #include "main_handler.h" #include "handler_firing_explosion.h" #include "handler_firing_smoke.h" #include "control_unit_handler.h" #include "handler_tab_data.h" #include "handler_vehicle.h" #include #include namespace EffectShowClient { //============================================================================= HandlerOrder::HandlerOrder(MainHandler *mainHandler, QObject *parent) : QObject(parent) , OrderModifyRequestHandler(mainHandler->dds()->fts()) , m_mainHandler(mainHandler) , m_logger(getLogger("HandlerOrder")) {} //============================================================================= HandlerOrder::~HandlerOrder() {} //============================================================================= bool HandlerOrder::init() { bool bRet = true; // create Orders objects auto cbOrder = [this, &bRet](const Database::EscOrder & data) { ObjectOrder *ifs(new ObjectOrder(m_mainHandler, this)); Core::FunctionReplyObject ret = ifs->createObject(data); if (ret.error()) { delete ifs; ERROR_LOG(m_logger) << ret(); bRet = false; return; } m_orderObjMap.insert(ifs->getId(), ifs); }; if (!m_mainHandler->db()->select(cbOrder) || !bRet) { ERROR_LOG(m_logger) << "Error reading data from database!"; return false; } DEBUG_LOG(m_logger) << "m_orderObjMap.size() = " << m_orderObjMap.size(); return true; } //============================================================================= void HandlerOrder::createOrder(const ConvertFromTab::EffectShowOrder_t &effectShowOrder) { Database::EscOrder data; for (auto it = m_orderObjMap.begin(); it != m_orderObjMap.end(); ++it) { if (it.value()->getData().idOrder == effectShowOrder.idEffectShow) data = it.value()->getData(); } bool sendStart = ((data.orderConfirmation == EffectShowManagement::OrderConfirmation_e_def::FiringReadiness) || (data.orderConfirmation == EffectShowManagement::OrderConfirmation_e_def::Execution) || (data.orderConfirmation == EffectShowManagement::OrderConfirmation_e_def::InterruptExecution)); data.typeOfOrder = 1; data.idOrder = effectShowOrder.idEffectShow; data.startTime = effectShowOrder.startTime * 1000; // s -> msec data.duration = effectShowOrder.duration; if (data.duration < 5) data.duration = 5; data.lowerLeftPosition = QPointF(effectShowOrder.lowerLeftPosition.lon(), effectShowOrder.lowerLeftPosition.lat()); data.centerPosition = QPointF(effectShowOrder.centerPosition.lon(), effectShowOrder.centerPosition.lat()); data.areaWidth = effectShowOrder.areaWidth; data.areaDepth = effectShowOrder.areaDepth; data.areaRotation = effectShowOrder.rotation; data.numOfVolley = effectShowOrder.numOfVolley; data.shotsPerVolley = effectShowOrder.shotsInTotal; data.typeOfAmmunition = effectShowOrder.typeOfAmmunition; //data.orderConfirmation = EffectShowManagement::OrderConfirmation_e_def::WaitingForAcceptance; //no reset data.info = effectShowOrder.name; ObjectOrder *ifs(new ObjectOrder(m_mainHandler, this)); Core::FunctionReplyObject ret = ifs->createObject(data); if (ret.error()) { delete ifs; ERROR_LOG(m_logger) << ret(); return; } m_orderObjMap.insert(ifs->getId(), ifs); if (data.orderConfirmation == EffectShowManagement::OrderConfirmation_e_def::Execution && data.startTime == 0) { m_mainHandler->handlerControlUnit()->send(CommandSignal::FT_SE_CB_SICHERHEIT_WIDERRUFEN); m_mainHandler->handlerControlUnit()->send(CommandSignal::FT_SE_CB_SALVE_UNTERBRECHEN); m_mainHandler->handlerVehicle()->effectShowControl(EffectShowControl_e::Stop); } bool orignalIsTimeout = ((data.orderConfirmation == EffectShowManagement::OrderConfirmation_e_def::Execution) && data.startTime > 0 && (data.startTime + data.duration < QDateTime::currentMSecsSinceEpoch())) ; if (sendStart && !orignalIsTimeout) emit startHandlerFiring(data); } //============================================================================= void HandlerOrder::createOrder(const ConvertFromTab::RelocationOrder_t &relocationOrder) { Database::EscOrder data; data.typeOfOrder = 0; data.idOrder = relocationOrder.idRelocation; data.startTime = relocationOrder.executionTime * 1000; // s -> msec data.centerPosition = QPointF(relocationOrder.centerPosition.lon(), relocationOrder.centerPosition.lat()); data.orderConfirmation = EffectShowManagement::OrderConfirmation_e_def::WaitingForAcceptance; data.info = relocationOrder.infoText; ObjectOrder *ifs(new ObjectOrder(m_mainHandler, this)); Core::FunctionReplyObject ret = ifs->createObject(data); if (ret.error()) { delete ifs; ERROR_LOG(m_logger) << ret(); return; } m_orderObjMap.insert(ifs->getId(), ifs); } //============================================================================= void HandlerOrder::removeOrder(const ConvertFromTab::OrderRetract_t &orderRetract) { for (auto it = m_orderObjMap.begin(); it != m_orderObjMap.end(); ++it) { if (it.value()->getData().typeOfOrder == orderRetract.orderType) //ERROR_LOG(m_logger) << "current idorder =" ; if (it.value()->getData().idOrder == orderRetract.id) { int id = it.key(); Core::FunctionReplyObject ret; int def = it.value()->getData().orderConfirmation; ret = it.value()->removeObject(); if (ret.error()) ERROR_LOG(m_logger) << LOGFUNCTION << ret(); else { if (def == EffectShowManagement::OrderConfirmation_e_def::Execution || def == EffectShowManagement::OrderConfirmation_e_def::InterruptExecution || def == EffectShowManagement::OrderConfirmation_e_def::FiringReadiness) { DEBUG_LOG(m_logger) << "EndFireHandler from Remove"; emit endHandlerFiring(it.value()->getData()); //Stop the current execution m_mainHandler->handlerControlUnit()->send(CommandSignal::FT_SE_CB_SALVE_UNTERBRECHEN); m_mainHandler->handlerControlUnit()->send(CommandSignal::FT_SE_CB_SICHERHEIT_WIDERRUFEN); m_mainHandler->handlerVehicle()->effectShowControl(EffectShowControl_e::Abort); m_mainHandler->handlerVehicle()->effectShowControl(EffectShowControl_e::StopTimer); } delete it.value(); m_orderObjMap.remove(id); } } } } void HandlerOrder::sendOrderConfirmation(const ConvertToTab::OrderConfirmation_t &oc) { ERROR_LOG(m_logger) << "Send Order Confirmation to Excon " << oc.orderId << " / "; m_mainHandler->handlerTabData()->orderConfirmation(oc); } //----------------------------------------------------------------------------- void HandlerOrder::onOrderModifyRequest(const rti::core::SampleIdentity &cookie, const OrderModifyRequest &request) { DEBUG_LOG(m_logger) << "Order: " << request.id() << " Order: " << request.orderConfirmation(); if (request.id() > 0) { ObjectOrder *ifs = m_orderObjMap.value(request.id()); if (ifs == nullptr) m_mainHandler->dds()->fts()->orderModifyReply(cookie, Core::FunctionReplyObject(request.id(), tr_lts("dds", "Order with id %1 not found")).arg(request.id())); else { ifs->setOrderConfirmation(request.orderConfirmation().underlying()); auto ret = ifs->updateObject(); if (ret.error()) { m_mainHandler->dds()->fts()->orderModifyReply(cookie, ret); ERROR_LOG(m_logger) << "Update Order object failed."; return; } if (updateOrder(ifs, QString::fromStdString(request.answerText()), request.orderConfirmation())) m_mainHandler->dds()->fts()->orderModifyReply(cookie, Core::FunctionReplyObject(request.id())); else m_mainHandler->dds()->fts()->orderModifyReply(cookie, Core::FunctionReplyObject(request.id(), tr_lts("dds", "Order with id %1 not found")).arg(request.id())); } } else { m_mainHandler->dds()->fts()->orderModifyReply(cookie, Core::FunctionReplyObject(request.id())); ERROR_LOG(m_logger) << "Illegal Order ID"; } } bool HandlerOrder::updateOrder(ObjectOrder *order, const QString &answerText, EffectShowManagement::OrderConfirmation_e orderConf) { ConvertToTab::OrderConfirmation_t oc; const Database::EscOrder &escOrder = order->getData(); oc.orderId = escOrder.idOrder; oc.orderType = ConvertToTab::OrderType_e(escOrder.typeOfOrder); oc.confirmation = orderConf.underlying(); oc.answerText = answerText; sendOrderConfirmation(oc); ERROR_LOG(m_logger) << "Update Order " << oc.orderId << " / "; switch (orderConf.underlying()) { case EffectShowManagement::OrderConfirmation_e_def::FiringReadiness: emit startHandlerFiring(order->getData()); break; case EffectShowManagement::OrderConfirmation_e_def::Execution: DEBUG_LOG(m_logger) << "start execution"; m_mainHandler->handlerVehicle()->effectShowControl(EffectShowClient::EffectShowControl_e::Start); emit effectShowStarted(); break; case EffectShowManagement::OrderConfirmation_e_def::InterruptExecution: //stop current volley m_mainHandler->handlerVehicle()->effectShowControl(EffectShowClient::EffectShowControl_e::Stop); //revoke safety emit effectShowInterrupted(); break; case EffectShowManagement::OrderConfirmation_e_def::Abort: if (checkForActiveOrder(escOrder.idOrder)) { DEBUG_LOG(m_logger) << "idOrder is " << escOrder.idOrder << " send abbort as is active"; m_mainHandler->handlerControlUnit()->send(CommandSignal::FT_SE_CB_SALVE_UNTERBRECHEN); m_mainHandler->handlerVehicle()->effectShowControl(EffectShowControl_e::Abort); } Q_FALLTHROUGH(); case EffectShowManagement::OrderConfirmation_e_def::Nonacceptance: case EffectShowManagement::OrderConfirmation_e_def::OrderCarriedOut: case EffectShowManagement::OrderConfirmation_e_def::PositionReached: { if (orderConf.underlying() == EffectShowManagement::OrderConfirmation_e_def::PositionReached && oc.orderType != ConvertToTab::OrderType_e::Relocation) return true; emit endHandlerFiring(order->getData()); ConvertFromTab::OrderRetract_t oct; oct.id = escOrder.idOrder; oct.orderType = qint8(escOrder.typeOfOrder); removeOrder(oct); break; } default: ERROR_LOG(m_logger) << "Unhandled EffectShowManagement::OrderConfirmation_e_def in HandlerOrder::onOrderModifyRequest"; // todo break; } return true; } void HandlerOrder::updateOrderWithId(int orderId, const QString &answerText, EffectShowManagement::OrderConfirmation_e orderConf) { ObjectOrder *ifs = m_orderObjMap.value(orderId); if (ifs == nullptr) return; ifs->setOrderConfirmation(orderConf.underlying()); auto ret = ifs->updateObject(); if (ret.error()) ERROR_LOG(m_logger) << "Error Updating Order " << orderId << " / "; updateOrder(ifs, answerText, orderConf); } bool HandlerOrder::checkForActiveOrder(int orderId) { DEBUG_LOG(m_logger) << "check for active Order " << orderId << " "; if (orderId <= 0) return false; return ((m_mainHandler->handlerFiringExplosion()->getCurrentorderId() == orderId )||( m_mainHandler->handlerFiringSmoke()->getCurrentorderId() == orderId)); } } // Namespace EffectShowClient