init
This commit is contained in:
+159
@@ -0,0 +1,159 @@
|
||||
#include "ovpCBoxAlgorithmAcquisitionClient.h"
|
||||
#include <limits>
|
||||
|
||||
namespace OpenViBE {
|
||||
namespace Plugins {
|
||||
namespace Acquisition {
|
||||
|
||||
uint64_t CBoxAlgorithmAcquisitionClient::getClockFrequency() { return 64LL << 32; }
|
||||
|
||||
bool CBoxAlgorithmAcquisitionClient::initialize()
|
||||
{
|
||||
m_decoder = &getAlgorithmManager().getAlgorithm(getAlgorithmManager().createAlgorithm(OVP_GD_ClassId_Algorithm_AcquisitionDecoder));
|
||||
|
||||
m_decoder->initialize();
|
||||
|
||||
ip_acquisitionBuffer.initialize(m_decoder->getInputParameter(OVP_GD_Algorithm_AcquisitionDecoder_InputParameterId_MemoryBufferToDecode));
|
||||
op_bufferDuration.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_BufferDuration));
|
||||
op_experimentInfoBuffer.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_ExperimentInfoStream));
|
||||
op_signalBuffer.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_SignalStream));
|
||||
op_stimulationBuffer.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_StimulationStream));
|
||||
op_channelLocalisationBuffer.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_ChannelLocalisationStream));
|
||||
op_channelUnitsBuffer.initialize(m_decoder->getOutputParameter(OVP_GD_Algorithm_AcquisitionDecoder_OutputParameterId_ChannelUnitsStream));
|
||||
|
||||
m_lastStartTime = 0;
|
||||
m_lastEndTime = 0;
|
||||
m_connectionClient = nullptr;
|
||||
|
||||
if (getStaticBoxContext().getOutputCount() < 5)
|
||||
{
|
||||
this->getLogManager() << Kernel::LogLevel_Error << "Code expects at least 5 box outputs. Did you update the box?\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CBoxAlgorithmAcquisitionClient::uninitialize()
|
||||
{
|
||||
if (m_connectionClient)
|
||||
{
|
||||
m_connectionClient->close();
|
||||
m_connectionClient->release();
|
||||
m_connectionClient = nullptr;
|
||||
}
|
||||
|
||||
op_channelUnitsBuffer.uninitialize();
|
||||
op_channelLocalisationBuffer.uninitialize();
|
||||
op_stimulationBuffer.uninitialize();
|
||||
op_signalBuffer.uninitialize();
|
||||
op_experimentInfoBuffer.uninitialize();
|
||||
op_bufferDuration.uninitialize();
|
||||
ip_acquisitionBuffer.uninitialize();
|
||||
|
||||
m_decoder->uninitialize();
|
||||
|
||||
getAlgorithmManager().releaseAlgorithm(*m_decoder);
|
||||
|
||||
m_decoder = nullptr;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CBoxAlgorithmAcquisitionClient::processClock(Kernel::CMessageClock& /*msg*/)
|
||||
{
|
||||
if (!m_connectionClient)
|
||||
{
|
||||
CString name = FSettingValueAutoCast(*this->getBoxAlgorithmContext(), 0);
|
||||
const size_t port = FSettingValueAutoCast(*this->getBoxAlgorithmContext(), 1);
|
||||
if (name.length() == 0)
|
||||
{
|
||||
this->getLogManager() << Kernel::LogLevel_Warning <<
|
||||
"Empty server name, please set it to a correct value or set AcquisitionServer_HostName in config files. Defaulting to \"localhost\".\n";
|
||||
name = "localhost";
|
||||
}
|
||||
if (port == std::numeric_limits<size_t>::max() || port == std::numeric_limits<size_t>::min())
|
||||
{
|
||||
this->getLogManager() << Kernel::LogLevel_Error << "Invalid value for port : " << port <<
|
||||
". Please set the port to a positive non-zero integer value.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
m_connectionClient = Socket::createConnectionClient();
|
||||
m_connectionClient->connect(name, port);
|
||||
if (!m_connectionClient->isConnected())
|
||||
{
|
||||
this->getLogManager() << Kernel::LogLevel_Error << "Could not connect to server " << name << ":" << port <<
|
||||
". Make sure the server is running and in Play state.\n";
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if (m_connectionClient && m_connectionClient->isReadyToReceive() /* && getPlayerContext().getCurrentTime()>m_lastChunkEndTime */)
|
||||
{
|
||||
getBoxAlgorithmContext()->markAlgorithmAsReadyToProcess();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CBoxAlgorithmAcquisitionClient::process()
|
||||
{
|
||||
if (!m_connectionClient || !m_connectionClient->isConnected()) { return false; }
|
||||
|
||||
Kernel::IBoxIO& boxContext = this->getDynamicBoxContext();
|
||||
|
||||
op_experimentInfoBuffer = boxContext.getOutputChunk(0);
|
||||
op_signalBuffer = boxContext.getOutputChunk(1);
|
||||
op_stimulationBuffer = boxContext.getOutputChunk(2);
|
||||
op_channelLocalisationBuffer = boxContext.getOutputChunk(3);
|
||||
op_channelUnitsBuffer = boxContext.getOutputChunk(4);
|
||||
|
||||
while (m_connectionClient->isReadyToReceive())
|
||||
{
|
||||
size_t size = 0;
|
||||
if (!m_connectionClient->receiveBufferBlocking(&size, sizeof(size)))
|
||||
{
|
||||
getLogManager() << Kernel::LogLevel_Error << "Could not receive memory buffer size from the server. Is the server on 'Play'?\n";
|
||||
return false;
|
||||
}
|
||||
if (!ip_acquisitionBuffer->setSize(size, true))
|
||||
{
|
||||
getLogManager() << Kernel::LogLevel_Error << "Could not re allocate memory buffer with size " << size << "\n";
|
||||
return false;
|
||||
}
|
||||
if (!m_connectionClient->receiveBufferBlocking(ip_acquisitionBuffer->getDirectPointer(), size))
|
||||
{
|
||||
getLogManager() << Kernel::LogLevel_Error << "Could not receive memory buffer content of size " << size << "\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
m_decoder->process();
|
||||
|
||||
|
||||
if (m_decoder->isOutputTriggerActive(OVP_GD_Algorithm_AcquisitionDecoder_OutputTriggerId_ReceivedHeader)
|
||||
|| m_decoder->isOutputTriggerActive(OVP_GD_Algorithm_AcquisitionDecoder_OutputTriggerId_ReceivedBuffer)
|
||||
|| m_decoder->isOutputTriggerActive(OVP_GD_Algorithm_AcquisitionDecoder_OutputTriggerId_ReceivedEnd))
|
||||
{
|
||||
boxContext.markOutputAsReadyToSend(0, m_lastStartTime, m_lastEndTime);
|
||||
boxContext.markOutputAsReadyToSend(1, m_lastStartTime, m_lastEndTime);
|
||||
boxContext.markOutputAsReadyToSend(2, m_lastStartTime, m_lastEndTime);
|
||||
if (op_channelLocalisationBuffer->getSize() > 0) { boxContext.markOutputAsReadyToSend(3, m_lastStartTime, m_lastEndTime); }
|
||||
else { boxContext.setOutputChunkSize(3, 0, true); }
|
||||
|
||||
if (op_channelUnitsBuffer->getSize() > 0) { boxContext.markOutputAsReadyToSend(4, m_lastStartTime, m_lastEndTime); }
|
||||
else { boxContext.setOutputChunkSize(4, 0, true); }
|
||||
m_lastStartTime = m_lastEndTime;
|
||||
m_lastEndTime += op_bufferDuration;
|
||||
// @todo ?
|
||||
// const double latency=CTime(m_lastChunkEndTime).toSeconds() - CTime(this->getPlayerContext().getCurrentTime()).toSeconds();
|
||||
const double latency = double(int64_t(m_lastEndTime - this->getPlayerContext().getCurrentTime()) / (1LL << 22)) / 1024.0;
|
||||
this->getLogManager() << Kernel::LogLevel_Debug << "Acquisition inner latency : " << latency << "\n";
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
} // namespace Acquisition
|
||||
} // namespace Plugins
|
||||
} // namespace OpenViBE
|
||||
+83
@@ -0,0 +1,83 @@
|
||||
#pragma once
|
||||
|
||||
#include "../ovp_defines.h"
|
||||
#include <openvibe/ov_all.h>
|
||||
#include <toolkit/ovtk_all.h>
|
||||
|
||||
#include <socket/IConnectionClient.h>
|
||||
|
||||
namespace OpenViBE {
|
||||
namespace Plugins {
|
||||
namespace Acquisition {
|
||||
class CBoxAlgorithmAcquisitionClient final : public Toolkit::TBoxAlgorithm<IBoxAlgorithm>
|
||||
{
|
||||
public:
|
||||
|
||||
void release() override { delete this; }
|
||||
|
||||
uint64_t getClockFrequency() override;
|
||||
bool initialize() override;
|
||||
bool uninitialize() override;
|
||||
bool processClock(Kernel::CMessageClock& msg) override;
|
||||
bool process() override;
|
||||
|
||||
_IsDerivedFromClass_Final_(Toolkit::TBoxAlgorithm<IBoxAlgorithm>, OVP_ClassId_BoxAlgorithm_AcquisitionClient)
|
||||
|
||||
protected:
|
||||
|
||||
Kernel::IAlgorithmProxy* m_decoder = nullptr;
|
||||
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> ip_acquisitionBuffer;
|
||||
Kernel::TParameterHandler<uint64_t> op_bufferDuration;
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> op_experimentInfoBuffer;
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> op_signalBuffer;
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> op_stimulationBuffer;
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> op_channelLocalisationBuffer;
|
||||
Kernel::TParameterHandler<IMemoryBuffer*> op_channelUnitsBuffer;
|
||||
|
||||
Socket::IConnectionClient* m_connectionClient = nullptr;
|
||||
|
||||
uint64_t m_lastStartTime = 0;
|
||||
uint64_t m_lastEndTime = 0;
|
||||
};
|
||||
|
||||
class CBoxAlgorithmAcquisitionClientDesc final : public IBoxAlgorithmDesc
|
||||
{
|
||||
public:
|
||||
|
||||
void release() override { }
|
||||
|
||||
CString getName() const override { return CString("Acquisition client"); }
|
||||
CString getAuthorName() const override { return CString("Yann Renard"); }
|
||||
CString getAuthorCompanyName() const override { return CString("INRIA/IRISA"); }
|
||||
CString getShortDescription() const override { return CString("A generic network based acquisition client"); }
|
||||
|
||||
CString getDetailedDescription() const override
|
||||
{
|
||||
return CString("This algorithm waits for EEG data from the network and distributes it into the scenario");
|
||||
}
|
||||
|
||||
CString getCategory() const override { return CString("Acquisition and network IO"); }
|
||||
CString getVersion() const override { return CString("1.0"); }
|
||||
|
||||
CIdentifier getCreatedClass() const override { return OVP_ClassId_BoxAlgorithm_AcquisitionClient; }
|
||||
IPluginObject* create() override { return new CBoxAlgorithmAcquisitionClient; }
|
||||
CString getStockItemName() const override { return CString("gtk-connect"); }
|
||||
|
||||
bool getBoxPrototype(Kernel::IBoxProto& prototype) const override
|
||||
{
|
||||
prototype.addOutput("Experiment information", OV_TypeId_ExperimentInfo);
|
||||
prototype.addOutput("Signal stream", OV_TypeId_Signal);
|
||||
prototype.addOutput("Stimulations", OV_TypeId_Stimulations);
|
||||
prototype.addOutput("Channel localisation", OV_TypeId_ChannelLocalisation);
|
||||
prototype.addOutput("Channel units", OV_TypeId_ChannelUnits);
|
||||
prototype.addSetting("Acquisition server hostname", OV_TypeId_String, "${AcquisitionServer_HostName}");
|
||||
prototype.addSetting("Acquisition server port", OV_TypeId_Integer, "1024");
|
||||
return true;
|
||||
}
|
||||
|
||||
_IsDerivedFromClass_Final_(IBoxAlgorithmDesc, OVP_ClassId_BoxAlgorithm_AcquisitionClientDesc)
|
||||
};
|
||||
} // namespace Acquisition
|
||||
} // namespace Plugins
|
||||
} // namespace OpenViBE
|
||||
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
|
||||
// Boxes
|
||||
//---------------------------------------------------------------------------------------------------
|
||||
#define OVP_ClassId_BoxAlgorithm_AcquisitionClient OpenViBE::CIdentifier(0x35D225CB, 0x3E6E3A5F)
|
||||
#define OVP_ClassId_BoxAlgorithm_AcquisitionClientDesc OpenViBE::CIdentifier(0x7D3061B9, 0x43565E8C)
|
||||
|
||||
// Global defines
|
||||
//---------------------------------------------------------------------------------------------------
|
||||
#ifdef TARGET_HAS_ThirdPartyOpenViBEPluginsGlobalDefines
|
||||
#include "ovp_global_defines.h"
|
||||
#endif // TARGET_HAS_ThirdPartyOpenViBEPluginsGlobalDefines
|
||||
@@ -0,0 +1,15 @@
|
||||
#include "ovp_defines.h"
|
||||
|
||||
#include "box-algorithms/ovpCBoxAlgorithmAcquisitionClient.h"
|
||||
|
||||
namespace OpenViBE {
|
||||
namespace Plugins {
|
||||
namespace Acquisition {
|
||||
|
||||
OVP_Declare_Begin()
|
||||
OVP_Declare_New(CBoxAlgorithmAcquisitionClientDesc)
|
||||
OVP_Declare_End()
|
||||
|
||||
} // namespace Acquisition
|
||||
} // namespace Plugins
|
||||
} // namespace OpenViBE
|
||||
Reference in New Issue
Block a user