Initial commit
This commit is contained in:
commit
b7d90b9afe
16245 files changed
+3396666
No files matched your search
+366
@@ -0,0 +1,366 @@
|
||||
/**
|
||||
* @RDE_HEADER@
|
||||
* main for BuildingControlUnit
|
||||
* $Id$
|
||||
* $HeadURL$
|
||||
* $Author$
|
||||
* Created by Christian Ehrlicher, SLSE, 2017-01-27
|
||||
*/
|
||||
|
||||
#include "main_handler.h"
|
||||
#include <QWebSocket>
|
||||
#include "VWM/vwm_types.h"
|
||||
#include "bcu_xml_reader.h"
|
||||
#include <settings.h>
|
||||
#include "ControlEffects/xmlreader.h"
|
||||
|
||||
namespace BuildingControlUnit
|
||||
{
|
||||
MainHandler::MainHandler()
|
||||
: QObject()
|
||||
, m_bsmApi(nullptr)
|
||||
, m_jsonApi(nullptr)
|
||||
, m_vwmApi(nullptr)
|
||||
, m_handelEffectsBsm(nullptr)
|
||||
, m_handleHttpRequest(nullptr)
|
||||
, m_bsmFlash(BEO_Auto)
|
||||
, m_logger(getLogger("MainHandler"))
|
||||
{}
|
||||
|
||||
MainHandler::~MainHandler()
|
||||
{
|
||||
cleanup();
|
||||
}
|
||||
|
||||
bool MainHandler::init(const QString &ammuXml,
|
||||
const QString &bldCfgXml,
|
||||
const QString &vwmXml,
|
||||
unsigned short listenPort,
|
||||
const bool initBuilding,
|
||||
const QString &controlEffectsCfg)
|
||||
{
|
||||
NOTICE_LOG(m_logger) << "----------------------------------------------------";
|
||||
NOTICE_LOG(m_logger) << "-- start BuildingControlUnit --";
|
||||
NOTICE_LOG(m_logger) << "----------------------------------------------------";
|
||||
cleanup();
|
||||
|
||||
BuildingBsmConfig bsmConfig;
|
||||
if (!parseBuildingConfigXml(bldCfgXml, bsmConfig, m_egcuConfig))
|
||||
return false;
|
||||
|
||||
m_bsmApi = new BSM::Api(this);
|
||||
//m_egcuApi = new EGCU::Api(this);
|
||||
m_jsonApi = new Json::Api(this);
|
||||
m_vwmApi = new VWM::Api(this);
|
||||
m_handleHttpRequest = new HandleHttpRequest(Settings::useHttpQueue(), this);
|
||||
m_bsmFlash = BEO_Auto;
|
||||
|
||||
if (m_egcuConfig.egcus.size() == 1 && m_egcuConfig.egcus.first().roomIds.isEmpty())
|
||||
{
|
||||
auto &egcu = m_egcuConfig.egcus.first();
|
||||
const auto &bldg = m_vwmApi->building();
|
||||
m_egcuConfig.egcus.reserve(bldg.rooms().size());
|
||||
for (const auto &room : bldg.rooms())
|
||||
egcu.roomIds.append(room.id());
|
||||
}
|
||||
if (!m_vwmApi->init(ammuXml, vwmXml, bsmConfig, initBuilding))
|
||||
{
|
||||
ERROR_LOG(m_logger) << "Can not initialize VWM API - aborting";
|
||||
return false;
|
||||
}
|
||||
if (!m_jsonApi->init(listenPort))
|
||||
{
|
||||
ERROR_LOG(m_logger) << "Can not initialize Json API - aborting";
|
||||
return false;
|
||||
}
|
||||
if (!m_bsmApi->init(bsmConfig))
|
||||
{
|
||||
ERROR_LOG(m_logger) << "Can not initialize BSM API - aborting";
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
m_handelEffectsVec.clear();
|
||||
for ( int i = 0; i < m_egcuConfig.egcus.size(); i++)
|
||||
{
|
||||
NOTICE_LOG(m_logger) << "new BuildingControlUnit::HandelEffects " << m_egcuConfig.egcus[i].hostname;
|
||||
BuildingControlUnit::HandelEffects *handleEffectsEgcu = new BuildingControlUnit::HandelEffects(this, m_egcuConfig.egcus[i].hostname);
|
||||
handleEffectsEgcu->init(controlEffectsCfg, m_egcuConfig.egcus[i].hostname, ET_Relay);
|
||||
|
||||
connect(handleEffectsEgcu, &HandelEffects::newHttpRequest, m_handleHttpRequest, &HandleHttpRequest::enqueue);
|
||||
connect(handleEffectsEgcu, &HandelEffects::sendRelayState, m_jsonApi, &Json::Api::onRelayState);
|
||||
connect(m_handleHttpRequest, &HandleHttpRequest::egcuReply, handleEffectsEgcu, &HandelEffects::handleEgcuReply);
|
||||
//connect(m_handleHttpRequest, &HandleHttpRequest::newEgcuConnection, this, &MainHandler::setInitialOverrides);
|
||||
m_handelEffectsVec.append(handleEffectsEgcu);
|
||||
}
|
||||
|
||||
|
||||
m_handelEffectsBsm = new BuildingControlUnit::HandelEffects(this, QStringLiteral("BSMs"));
|
||||
m_handelEffectsBsm->init(controlEffectsCfg, QString(), ET_BsmFlash);
|
||||
connect(m_handelEffectsBsm, &HandelEffects::triggerAllFlashlights, m_bsmApi, &BSM::Api::triggerFlashlights);
|
||||
connect(m_bsmApi, &BSM::Api::opticalShot, m_vwmApi, &VWM::Api::onHitOptical);
|
||||
connect(m_bsmApi, &BSM::Api::opticalShotOC, m_vwmApi, &VWM::Api::onHitOpticalOC);
|
||||
|
||||
connect(m_vwmApi, &VWM::Api::hitResult, this, &MainHandler::onHitResult);
|
||||
connect(m_vwmApi, &VWM::Api::unknownDirectHit, this, &MainHandler::onUnknownDirectHit);
|
||||
|
||||
connect(m_jsonApi, &Json::Api::damageStateRequest, m_vwmApi, &VWM::Api::onHitEcc);
|
||||
connect(m_jsonApi, &Json::Api::setContaminationStateRequest,m_vwmApi, &VWM::Api::onSetContaminationState);
|
||||
connect(m_jsonApi, &Json::Api::resetContaminationRequest, m_vwmApi, &VWM::Api::onResetContaminations);
|
||||
connect(m_jsonApi, &Json::Api::setFortifyFactorRequest, m_vwmApi, &VWM::Api::onFortifyFactorRequest);
|
||||
connect(m_jsonApi, &Json::Api::relayStatesRequest, m_vwmApi, &VWM::Api::onRelayStatesRequest);
|
||||
connect(m_jsonApi, &Json::Api::centralEffectSimulationHit, m_vwmApi, &VWM::Api::onHitCes);
|
||||
connect(m_jsonApi, &Json::Api::centralEffectSimulationHit3D,m_vwmApi, &VWM::Api::onHitCes3D_Evaluation);
|
||||
|
||||
connect(m_jsonApi, &Json::Api::bsmTriggerFlashlightRequest, m_bsmApi, &BSM::Api::triggerFlashlight);
|
||||
connect(m_jsonApi, &Json::Api::getBsmConfiguration, m_bsmApi, &BSM::Api::getBsmConfiguration);
|
||||
connect(m_jsonApi, &Json::Api::getBsmBitTimeout, m_bsmApi, &BSM::Api::getBsmBitTimeout);
|
||||
connect(m_jsonApi, &Json::Api::getBsmTechnicalStatus, m_bsmApi, &BSM::Api::getBsmTechnicalStatus);
|
||||
|
||||
// for debug purposes
|
||||
connect(m_jsonApi, &Json::Api::simulateBSMHit, m_vwmApi, &VWM::Api::onHitOptical);
|
||||
connect(m_jsonApi, &Json::Api::setEffectStatesRequest, m_vwmApi, &VWM::Api::onSetEffectStatesRequest);
|
||||
|
||||
connect(m_bsmApi, &BSM::Api::bsmStateChanged, m_jsonApi, &Json::Api::onBsmState);
|
||||
|
||||
connect(m_vwmApi, &VWM::Api::hitResult, m_jsonApi, &Json::Api::onHitResult);
|
||||
|
||||
connect(m_jsonApi, &Json::Api::webSocketConnected, this, &MainHandler::webSocketSendInitialData);
|
||||
connect(m_jsonApi, &Json::Api::setEffectStatesRequest, this, &MainHandler::onSetEffectStatesRequest);
|
||||
connect(m_jsonApi, &Json::Api::switchRelayRequest, this, &MainHandler::onSwitchRelayRequest);
|
||||
|
||||
connect(m_vwmApi, &VWM::Api::newOverrides, this, &MainHandler::onSetEffectStatesRequest);
|
||||
m_vwmApi->sendOverrides();
|
||||
|
||||
onHitResult(m_vwmApi->lastHitResult(), m_vwmApi->contaminationStates(), false);
|
||||
|
||||
// Set initial Overrides:
|
||||
//setInitialOverrides();
|
||||
return true;
|
||||
}
|
||||
|
||||
void MainHandler::setInitialOverrides(const QString &hostname)
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "setInitialOverrides m_handelEffectsVec.size()=" << m_handelEffectsVec.size();
|
||||
// Set initial Overrides:
|
||||
for ( int i = 0; i < m_handelEffectsVec.size(); i++)
|
||||
{
|
||||
QString hostnameLocal = m_handelEffectsVec.at(i)->hostname();
|
||||
const QVector<BcuEffectState> effectStates = m_handelEffectsVec.at(i)->getOverrides();
|
||||
DEBUG_LOG(m_logger) << "setInitialOverrides host=" << hostnameLocal
|
||||
<< " effectStates.size=" << effectStates.size();
|
||||
for (int j = 0; j < effectStates.size(); j++)
|
||||
DEBUG_LOG(m_logger) << "setInitialOverrides j=" << j
|
||||
<< " id=" << effectStates[j].id
|
||||
<< " type=" << effectStates[j].type
|
||||
<< " override=" << effectStates[j].effectOverride;
|
||||
|
||||
NOTICE_LOG(m_logger) << "'" << hostname << "'"
|
||||
<< " '" << hostnameLocal << "'";
|
||||
|
||||
if ( hostname.toLower() == hostnameLocal.toLower())
|
||||
{
|
||||
|
||||
onSetEffectStatesRequest(hostnameLocal, effectStates);
|
||||
|
||||
const QString segment = hostname ;
|
||||
const qint64 stateTime = QDateTime::currentMSecsSinceEpoch();;
|
||||
const qint64 offlineTime = QDateTime::currentMSecsSinceEpoch();
|
||||
|
||||
m_jsonApi->sendEffectOverrides(segment, stateTime, offlineTime, effectStates, nullptr);
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MainHandler::onHitResult(const HitResult &result, const QMap<int, ContaminationState> &contaminationStates, bool playSound)
|
||||
{
|
||||
Q_UNUSED(contaminationStates)
|
||||
const VWM::Charge charge = m_vwmApi->chargeFromChargeTypeId(result.chargeTypeId);
|
||||
DEBUG_LOG(m_logger) << "onHitResult chargeTypeId=" << result.chargeTypeId
|
||||
<< " result.effectSoundId=" << result.effectSoundId
|
||||
<< " damagePercentNew=" << result.damagePercentNew
|
||||
<< " destructiveFactor=" << charge.destructiveFactor;
|
||||
if (Settings::laserRangeCode() == result.chargeTypeId)
|
||||
return;
|
||||
|
||||
if (playSound)
|
||||
{
|
||||
for (HandelEffects *he : qAsConst(m_handelEffectsVec))
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "playHitSound @EGCU " << he->hostname() << ", SoundId: " << result.effectSoundId;
|
||||
he->playHitSound(result.effectSoundId);
|
||||
}
|
||||
}
|
||||
|
||||
DEBUG_LOG(m_logger) << "HitResult: " << result;
|
||||
if (result.sensorId != 0 && result.originatorId != 0 && m_bsmFlash != BEO_Off && charge.destructiveFactor > 1 )
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "BSM Flash";
|
||||
m_bsmApi->triggerFlashlight(result.sensorId);
|
||||
m_bsmApi->triggerFlashlightPulse(result.sensorId, // ??? Woher kommt der Hostname? Es blitzt ja bei trigger Flashlight Patric: Wenn Hosname Leer ist ruft er die Funktion getSocketForBsm auf
|
||||
QString(),
|
||||
Settings::numberOfFlashes(),
|
||||
Settings::pauseDuration(),
|
||||
Settings::choppedConfiguration(),
|
||||
Settings::flashDuration());
|
||||
}
|
||||
else
|
||||
DEBUG_LOG(m_logger) << "Kein BSM Flash";
|
||||
|
||||
// only once on state change (to not trigger it more than once)
|
||||
//if (result.damagePercentOld < Settings::fireThreshold() &&
|
||||
// result.damagePercentNew > Settings::fireThreshold())
|
||||
// Each Segment
|
||||
QVector<int> segmentDamage = getSegmentDamage(result.rooms, result.damagePercentNew);
|
||||
|
||||
for (int i = 0; i < m_egcuConfig.egcus.size(); i++)
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "segmentDamage.size=" << segmentDamage.size();
|
||||
if ( i < segmentDamage.size() )
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "segmentDamage[" << i <<"]=" << segmentDamage[i];
|
||||
m_handelEffectsVec[i]->startEffects(segmentDamage[i]);
|
||||
}
|
||||
else
|
||||
DEBUG_LOG(m_logger) << "No segment Damage for egcu:" << m_egcuConfig.egcus[i].hostname;
|
||||
}
|
||||
m_handelEffectsBsm->startEffects(result.damagePercentNew);
|
||||
}
|
||||
|
||||
void MainHandler::onUnknownDirectHit(int sensorId)
|
||||
{
|
||||
// unknown dus code - double flash
|
||||
m_bsmApi->triggerFlashlight(sensorId);
|
||||
m_bsmApi->triggerFlashlight(sensorId);
|
||||
}
|
||||
|
||||
void MainHandler::onSetEffectStatesRequest(const QString &hostname, const QVector<BcuEffectState> &effectStates)
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "1 BSM flash hostname='" << hostname
|
||||
<< "' isEmpty:"<< hostname.isEmpty()
|
||||
<<" isNull:" << hostname.isNull();
|
||||
m_effectStates.insert(hostname, effectStates);
|
||||
if (hostname.isEmpty())
|
||||
{
|
||||
m_bsmFlash = BEO_Auto;
|
||||
DEBUG_LOG(m_logger) << "2 BSM flash =" << m_bsmFlash;
|
||||
m_handelEffectsBsm->setOverrides(effectStates);
|
||||
for ( int i = 0; i < effectStates.size(); i++)
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "3 BSM flash =" << m_bsmFlash;
|
||||
if ( effectStates.at(i).type == BET_BsmFlash)
|
||||
{
|
||||
m_bsmFlash = effectStates.at(i).effectOverride;
|
||||
DEBUG_LOG(m_logger) << "4 BSM flash =" << m_bsmFlash;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
for (HandelEffects* hes : qAsConst(m_handelEffectsVec))
|
||||
{
|
||||
if (hes->hostname() != hostname)
|
||||
continue;
|
||||
hes->setOverrides(effectStates);
|
||||
}
|
||||
}
|
||||
|
||||
void MainHandler::onSwitchRelayRequest(const QString &hostname, const SwitchRelayValues &switchRelayValues)
|
||||
{
|
||||
for ( int i = 0; i < m_handelEffectsVec.size(); i++)
|
||||
{
|
||||
if (m_handelEffectsVec[i]->hostname() == hostname )
|
||||
{
|
||||
DEBUG_LOG(m_logger) << "switchRelay "
|
||||
<< " id=" << switchRelayValues.id
|
||||
<< " bcuRelayState=" << switchRelayValues.bcuRelayState;
|
||||
m_handelEffectsVec[i]->switchRelay(switchRelayValues);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MainHandler::webSocketSendInitialData(QWebSocket *ws)
|
||||
{
|
||||
m_jsonApi->sendBsmState(m_bsmApi->bsmStates(), ws);
|
||||
m_jsonApi->sendHitResult(m_vwmApi->lastHitResult(), m_vwmApi->contaminationStates(), ws);
|
||||
}
|
||||
|
||||
QVector<int> MainHandler::getAffectedRoomIds(const QVector<HitRoom> &allHitRooms) const
|
||||
{
|
||||
QVector<int> ret;
|
||||
for (const HitRoom &hr : allHitRooms)
|
||||
{
|
||||
if (hr.remainingEffectPercent == 0)
|
||||
continue;
|
||||
ret += hr.roomId;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int MainHandler::getHitRoomId(const QVector<HitRoom> &allHitRooms) const
|
||||
{
|
||||
for (const HitRoom &hr : allHitRooms)
|
||||
{
|
||||
if (hr.directHit)
|
||||
return hr.roomId;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
QVector<int> MainHandler::getSegmentDamage(const QVector<HitRoom> &allHitRooms, const int damagePercentNew) const
|
||||
{
|
||||
QVector<int> result;
|
||||
if (m_egcuConfig.egcus.size() == 0)
|
||||
return result;
|
||||
result.reserve(m_egcuConfig.egcus.size());
|
||||
// every egcu is responsible for one segment
|
||||
for (const Egcu &egcu : qAsConst(m_egcuConfig.egcus))
|
||||
{
|
||||
int damagePercentSegment = 0;
|
||||
for (const HitRoom &hr : allHitRooms)
|
||||
{
|
||||
if (egcu.roomIds.contains(hr.roomId))
|
||||
damagePercentSegment += hr.damagePercent;
|
||||
}
|
||||
// Can only occur when roomIds.size() > 0
|
||||
if (damagePercentNew == 0)
|
||||
result.append(0);
|
||||
else if (damagePercentNew == 100)
|
||||
result.append(100);
|
||||
else
|
||||
{
|
||||
int averageDamage = 0;
|
||||
if (egcu.roomIds.size() > 0 )
|
||||
averageDamage = damagePercentSegment / egcu.roomIds.size();
|
||||
result.append(averageDamage);
|
||||
INFO_LOG(m_logger) << "getSegmentDamage[" << egcu.hostname << "]=" << averageDamage;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
void MainHandler::flashBuildingDestructionIndicator(int egcu)
|
||||
{
|
||||
// Todo: What's this?
|
||||
ERROR_LOG(m_logger) << "TODO flashBuildingDestructionIndicator egcu=" << egcu;
|
||||
// Building Destruction Indicator
|
||||
//RelayHardwareConfig hwCfg; // TODO Config TBD
|
||||
//hwCfg.cntRepeat = 0;
|
||||
//hwCfg.damage = 100;
|
||||
//hwCfg.durationDelay = 0;
|
||||
//hwCfg.durationPulses = 500;
|
||||
//hwCfg.relayNumber = 0;
|
||||
|
||||
//m_egcuApi->startHardware(hwCfg, egcu);
|
||||
}
|
||||
|
||||
void MainHandler::cleanup()
|
||||
{
|
||||
delete m_bsmApi;
|
||||
//delete m_egcuApi;
|
||||
delete m_jsonApi;
|
||||
delete m_vwmApi;
|
||||
}
|
||||
|
||||
} // BuildingControlUnit
|
||||
Reference in new issue
Block a user