v2.0.0
Loading...
Searching...
No Matches
rtsourcedatacontroller.cpp
Go to the documentation of this file.
1//=============================================================================================================
12
13//=============================================================================================================
14// INCLUDES
15//=============================================================================================================
16
18#include "rtsourcedataworker.h"
20
21#include <fs/fs_label.h>
22
23#include <QThread>
24#include <QTimer>
25#include <QDebug>
26
27//=============================================================================================================
28// DEFINE MEMBER METHODS
29//=============================================================================================================
30
32 : QObject(parent)
33{
34 // Create data worker
35 m_pWorker = new DISP3DLIB::RtSourceDataWorker();
36
37 // Create and configure data thread
38 m_pWorkerThread = new QThread(this);
39 m_pWorker->moveToThread(m_pWorkerThread);
40
41 // Clean up worker when thread finishes
42 connect(m_pWorkerThread, &QThread::finished, m_pWorker, &QObject::deleteLater);
43
44 // Forward worker signals to controller signals
49
50 // Create timer for driving the streaming cadence
51 m_pTimer = new QTimer(this);
52 m_pTimer->setTimerType(Qt::PreciseTimer);
53 connect(m_pTimer, &QTimer::timeout, m_pWorker, &DISP3DLIB::RtSourceDataWorker::streamData);
54
55 // Start the data worker thread
56 m_pWorkerThread->start();
57
58 // Create interpolation matrix worker
59 m_pInterpWorker = new DISP3DLIB::RtSourceInterpolationMatWorker();
60 m_pInterpThread = new QThread(this);
61 m_pInterpWorker->moveToThread(m_pInterpThread);
62
63 connect(m_pInterpThread, &QThread::finished, m_pInterpWorker, &QObject::deleteLater);
64
65 // Forward interpolation results: auto-apply to data worker + re-emit
67 this, &RtSourceDataController::onNewInterpolationMatrixLeft);
69 this, &RtSourceDataController::onNewInterpolationMatrixRight);
70
71 m_pInterpThread->start();
72
73 qDebug() << "RtSourceDataController: Initialized with" << m_iTimeInterval << "ms interval";
74}
75
76//=============================================================================================================
77
79{
80 // Stop timer
81 if (m_pTimer) {
82 m_pTimer->stop();
83 }
84
85 // Stop the data worker thread
86 if (m_pWorkerThread) {
87 m_pWorkerThread->quit();
88 m_pWorkerThread->wait();
89 }
90
91 // Stop the interpolation worker thread
92 if (m_pInterpThread) {
93 m_pInterpThread->quit();
94 m_pInterpThread->wait();
95 }
96}
97
98//=============================================================================================================
99
100void RtSourceDataController::addData(const Eigen::VectorXd &data)
101{
102 if (m_pWorker) {
103 // Direct call is thread-safe because RtSourceDataWorker uses a mutex
104 m_pWorker->addData(data);
105 }
106}
107
108//=============================================================================================================
109
110void RtSourceDataController::setInterpolationMatrixLeft(QSharedPointer<Eigen::SparseMatrix<float>> mat)
111{
112 if (m_pWorker) {
113 m_pWorker->setInterpolationMatrixLeft(mat);
114 }
115}
116
117//=============================================================================================================
118
119void RtSourceDataController::setInterpolationMatrixRight(QSharedPointer<Eigen::SparseMatrix<float>> mat)
120{
121 if (m_pWorker) {
122 m_pWorker->setInterpolationMatrixRight(mat);
123 }
124}
125
126//=============================================================================================================
127
129{
130 m_bIsStreaming = state;
131
132 if (state) {
133 m_pTimer->start(m_iTimeInterval);
134 qDebug() << "RtSourceDataController: Streaming started at" << m_iTimeInterval << "ms interval";
135 } else {
136 m_pTimer->stop();
137 qDebug() << "RtSourceDataController: Streaming stopped";
138 }
139}
140
141//=============================================================================================================
142
144{
145 return m_bIsStreaming;
146}
147
148//=============================================================================================================
149
151{
152 m_iTimeInterval = qMax(1, msec);
153
154 if (m_bIsStreaming) {
155 m_pTimer->setInterval(m_iTimeInterval);
156 }
157
158 qDebug() << "RtSourceDataController: Time interval set to" << m_iTimeInterval << "ms";
159}
160
161//=============================================================================================================
162
164{
165 if (m_pWorker) {
166 m_pWorker->setNumberAverages(numAvr);
167 }
168}
169
170//=============================================================================================================
171
173{
174 if (m_pWorker) {
175 m_pWorker->setColormapType(name);
176 }
177}
178
179//=============================================================================================================
180
181void RtSourceDataController::setThresholds(double min, double mid, double max)
182{
183 if (m_pWorker) {
184 m_pWorker->setThresholds(min, mid, max);
185 }
186}
187
188//=============================================================================================================
189
191{
192 if (m_pWorker) {
193 m_pWorker->setLoopState(enabled);
194 }
195}
196
197//=============================================================================================================
198
200{
201 if (m_pWorker) {
202 m_pWorker->setSFreq(sFreq);
203 }
204}
205
206//=============================================================================================================
207
209{
210 if (m_pWorker) {
211 m_pWorker->clear();
212 }
213}
214
215//=============================================================================================================
216
217void RtSourceDataController::setSurfaceColor(const QVector<uint32_t> &baseColorsLh,
218 const QVector<uint32_t> &baseColorsRh)
219{
220 if (m_pWorker) {
221 m_pWorker->setSurfaceColor(baseColorsLh, baseColorsRh);
222 }
223}
224
225//=============================================================================================================
226
228{
229 if (m_pWorker) {
230 m_pWorker->setStreamSmoothedData(bStreamSmoothedData);
231 }
232}
233
234//=============================================================================================================
235
236void RtSourceDataController::setInterpolationFunction(const QString &sInterpolationFunction)
237{
238 if (m_pInterpWorker) {
239 m_pInterpWorker->setInterpolationFunction(sInterpolationFunction);
240 }
241}
242
243//=============================================================================================================
244
246{
247 if (m_pInterpWorker) {
248 m_pInterpWorker->setCancelDistance(dCancelDist);
249 }
250}
251
252//=============================================================================================================
253
254void RtSourceDataController::setInterpolationInfoLeft(const Eigen::MatrixX3f &matVertices,
255 const std::vector<Eigen::VectorXi> &vecNeighborVertices,
256 const Eigen::VectorXi &vecSourceVertices)
257{
258 if (m_pInterpWorker) {
259 m_pInterpWorker->setInterpolationInfoLeft(matVertices, vecNeighborVertices, vecSourceVertices);
260 }
261}
262
263//=============================================================================================================
264
265void RtSourceDataController::setInterpolationInfoRight(const Eigen::MatrixX3f &matVertices,
266 const std::vector<Eigen::VectorXi> &vecNeighborVertices,
267 const Eigen::VectorXi &vecSourceVertices)
268{
269 if (m_pInterpWorker) {
270 m_pInterpWorker->setInterpolationInfoRight(matVertices, vecNeighborVertices, vecSourceVertices);
271 }
272}
273
274//=============================================================================================================
275
277{
278 if (m_pInterpWorker) {
279 QMetaObject::invokeMethod(m_pInterpWorker, "computeInterpolationMatrix", Qt::QueuedConnection);
280 }
281}
282
283//=============================================================================================================
284
285void RtSourceDataController::onNewInterpolationMatrixLeft(QSharedPointer<Eigen::SparseMatrix<float>> interpMat)
286{
287 // Auto-forward to data worker so it immediately uses the new matrix
288 if (m_pWorker) {
289 m_pWorker->setInterpolationMatrixLeft(interpMat);
290 }
291 // Re-emit so external listeners can react
293}
294
295//=============================================================================================================
296
297void RtSourceDataController::onNewInterpolationMatrixRight(QSharedPointer<Eigen::SparseMatrix<float>> interpMat)
298{
299 // Auto-forward to data worker so it immediately uses the new matrix
300 if (m_pWorker) {
301 m_pWorker->setInterpolationMatrixRight(interpMat);
302 }
303 // Re-emit so external listeners can react
305}
306
307//=============================================================================================================
308
310{
311 if (m_pInterpWorker) {
312 m_pInterpWorker->setVisualizationType(iVisType);
313 }
314}
315
316//=============================================================================================================
317
318void RtSourceDataController::setAnnotationInfoLeft(const Eigen::VectorXi &vecLabelIds,
319 const QList<FSLIB::FsLabel> &lLabels,
320 const Eigen::VectorXi &vecVertNo)
321{
322 if (m_pInterpWorker) {
323 m_pInterpWorker->setAnnotationInfoLeft(vecLabelIds, lLabels, vecVertNo);
324 }
325}
326
327//=============================================================================================================
328
329void RtSourceDataController::setAnnotationInfoRight(const Eigen::VectorXi &vecLabelIds,
330 const QList<FSLIB::FsLabel> &lLabels,
331 const Eigen::VectorXi &vecVertNo)
332{
333 if (m_pInterpWorker) {
334 m_pInterpWorker->setAnnotationInfoRight(vecLabelIds, lLabels, vecVertNo);
335 }
336}
Real-time source-estimate streaming controller that owns the data worker and the per-hemisphere inter...
Background worker that builds the sparse source-to-vertex interpolation matrix for one hemisphere.
Background worker that converts streaming source vectors into smoothed per-vertex ABGR colour buffers...
Reader and in-memory representation of a FreeSurfer/MNE surface label (.label).
void setThresholds(double min, double mid, double max)
void setInterpolationMatrixLeft(QSharedPointer< Eigen::SparseMatrix< float > > mat)
void addData(const Eigen::VectorXd &data)
void setStreamSmoothedData(bool bStreamSmoothedData)
void setAnnotationInfoLeft(const Eigen::VectorXi &vecLabelIds, const QList< FSLIB::FsLabel > &lLabels, const Eigen::VectorXi &vecVertNo)
void newInterpolationMatrixRightAvailable(QSharedPointer< Eigen::SparseMatrix< float > > interpMat)
void setSurfaceColor(const QVector< uint32_t > &baseColorsLh, const QVector< uint32_t > &baseColorsRh)
void setCancelDistance(double dCancelDist)
void setInterpolationInfoRight(const Eigen::MatrixX3f &matVertices, const std::vector< Eigen::VectorXi > &vecNeighborVertices, const Eigen::VectorXi &vecSourceVertices)
void setAnnotationInfoRight(const Eigen::VectorXi &vecLabelIds, const QList< FSLIB::FsLabel > &lLabels, const Eigen::VectorXi &vecVertNo)
void newRawDataAvailable(const Eigen::VectorXd &dataLh, const Eigen::VectorXd &dataRh)
void newSmoothedDataAvailable(const QVector< uint32_t > &colorsLh, const QVector< uint32_t > &colorsRh)
void setVisualizationType(int iVisType)
void setInterpolationFunction(const QString &sInterpolationFunction)
void setColormapType(const QString &name)
void newInterpolationMatrixLeftAvailable(QSharedPointer< Eigen::SparseMatrix< float > > interpMat)
RtSourceDataController(QObject *parent=nullptr)
void setInterpolationMatrixRight(QSharedPointer< Eigen::SparseMatrix< float > > mat)
void setInterpolationInfoLeft(const Eigen::MatrixX3f &matVertices, const std::vector< Eigen::VectorXi > &vecNeighborVertices, const Eigen::VectorXi &vecSourceVertices)
Background worker for real-time source estimate streaming.
void setInterpolationMatrixLeft(QSharedPointer< Eigen::SparseMatrix< float > > mat)
void newRtRawData(const Eigen::VectorXd &dataLh, const Eigen::VectorXd &dataRh)
void newRtSmoothedData(const QVector< uint32_t > &colorsLh, const QVector< uint32_t > &colorsRh)
Background worker for computing source interpolation matrices.
void newInterpolationMatrixRightAvailable(QSharedPointer< Eigen::SparseMatrix< float > > interpMat)
void newInterpolationMatrixLeftAvailable(QSharedPointer< Eigen::SparseMatrix< float > > interpMat)