v2.0.0
Loading...
Searching...
No Matches
inv_hpi_data_updater.cpp
Go to the documentation of this file.
1//=============================================================================================================
20
21//=============================================================================================================
22// INCLUDES
23//=============================================================================================================
24
26#include <fiff/fiff_ch_info.h>
27#include <fiff/fiff_info.h>
28#include <iostream>
29
30//=============================================================================================================
31// QT INCLUDES
32//=============================================================================================================
33
34//=============================================================================================================
35// EIGEN INCLUDES
36//=============================================================================================================
37
38#include <Eigen/Dense>
39
40//=============================================================================================================
41// USED NAMESPACES
42//=============================================================================================================
43
44using namespace INVLIB;
45using namespace FIFFLIB;
46using namespace Eigen;
47
48//=============================================================================================================
49// DEFINE GLOBAL METHODS
50//=============================================================================================================
51
52//=============================================================================================================
53// DEFINE MEMBER METHODS
54//=============================================================================================================
55
56//=============================================================================================================
57
59 : m_sensors(InvSensorSet())
60{
61 updateBadChannels(pFiffInfo);
62 updateChannels(pFiffInfo);
63 updateHpiDigitizer(pFiffInfo->dig);
64 updateSensors(m_lChannels);
65}
66
67//=============================================================================================================
68
69void InvHpiDataUpdater::updateBadChannels(FiffInfo::SPtr pFiffInfo)
70{
71 m_lBads = pFiffInfo->bads;
72}
73
74//=============================================================================================================
75
76void InvHpiDataUpdater::updateChannels(FiffInfo::SPtr pFiffInfo)
77{
78 // Get the indices of inner layer channels and exclude bad channels and create channellist
79 const int iNumCh = pFiffInfo->nchan;
80 m_lChannels.clear();
81 m_vecInnerind.clear();
82 for (int i = 0; i < iNumCh; ++i) {
83 if(pFiffInfo->chs[i].chpos.coil_type == FIFFV_COIL_BABY_MAG ||
84 pFiffInfo->chs[i].chpos.coil_type == FIFFV_COIL_VV_PLANAR_T1 ||
85 pFiffInfo->chs[i].chpos.coil_type == FIFFV_COIL_VV_PLANAR_T2 ||
86 pFiffInfo->chs[i].chpos.coil_type == FIFFV_COIL_VV_PLANAR_T3) {
87
88 // Check if the sensor is bad, if not append to innerind
89
90 if(!(pFiffInfo->bads.contains(pFiffInfo->ch_names.at(i)))) {
91 m_vecInnerind.append(i);
92 m_lChannels.append(pFiffInfo->chs[i]);
93 }
94 }
95 }
96}
97
98//=============================================================================================================
99
100void InvHpiDataUpdater::updateSensors(const QList<FIFFLIB::FiffChInfo>& lChannels)
101{
102 const Accuracy accuracy = Accuracy::high;
103 m_sensors = m_sensorSetCreator.updateSensorSet(lChannels,accuracy);
104}
105
106//=============================================================================================================
107
108void InvHpiDataUpdater::updateHpiDigitizer(const QList<FiffDigPoint>& lDig)
109{
110 // extract hpi coils from digitizer
111 QList<FiffDigPoint> lHPIPoints;
112 int iNumCoils = 0;
113
114 for(int i = 0; i < lDig.size(); ++i) {
115 if(lDig[i].kind == FIFFV_POINT_HPI) {
116 iNumCoils++;
117 lHPIPoints.append(lDig[i]);
118 }
119 }
120
121 // convert to matrix iNumCoils x 3
122 if (lHPIPoints.size() > 0) {
123 m_matHpiDigitizer = MatrixXd(iNumCoils,3);
124 for (int i = 0; i < lHPIPoints.size(); ++i) {
125 m_matHpiDigitizer(i,0) = lHPIPoints.at(i).r[0];
126 m_matHpiDigitizer(i,1) = lHPIPoints.at(i).r[1];
127 m_matHpiDigitizer(i,2) = lHPIPoints.at(i).r[2];
128 }
129 } else {
130 std::cout << "InvHpiFit::updateHpiDigitizer - No HPI coils digitized. Returning." << std::endl;
131 return;
132 }
133}
134
135//=============================================================================================================
136
138{
139 const bool bUpdate = checkIfChanged(pFiffInfo->bads,pFiffInfo->chs);
140 if(bUpdate)
141 {
142 updateBadChannels(pFiffInfo);
143 updateChannels(pFiffInfo);
144 updateHpiDigitizer(pFiffInfo->dig);
145 updateSensors(m_lChannels);
146 }
147}
148
149//=============================================================================================================
150
151bool InvHpiDataUpdater::checkIfChanged(const QList<QString>& lBads, const QList<FIFFLIB::FiffChInfo>& lChannels)
152{
153 bool bUpdate = false;
154 if(!(m_lBads == lBads) || !(m_lChannels == lChannels)) {
155 bUpdate = true;
156 }
157 return bUpdate;
158}
159
160//=============================================================================================================
161
162void InvHpiDataUpdater::prepareDataAndProjectors(const MatrixXd &matData, const MatrixXd &matProjectors)
163{
164 prepareData(matData);
165 prepareProjectors(matProjectors);
166 m_matDataProjected = m_matProjectors * m_matInnerdata;
167}
168
169//=============================================================================================================
170
171void InvHpiDataUpdater::prepareData(const Eigen::MatrixXd& matData)
172{
173 // extract data for channels to use
174 m_matInnerdata = MatrixXd(m_vecInnerind.size(), matData.cols());
175
176 for(int j = 0; j < m_vecInnerind.size(); ++j) {
177 m_matInnerdata.row(j) << matData.row(m_vecInnerind[j]);
178 }
179}
180
181//=============================================================================================================
182
183void InvHpiDataUpdater::prepareProjectors(const Eigen::MatrixXd& matProjectors)
184{
185 // check if m_vecInnerInd is alreadz initialized
186 if(m_vecInnerind.size() == 0) {
187 std::cout << "InvHpiFit::updateProjectors - No channels. Returning." << std::endl;
188 return;
189 }
190
191 //Create new projector based on the excluded channels, first exclude the rows then the columns
192 MatrixXd matProjectorsRows(m_vecInnerind.size(),matProjectors.cols());
193 MatrixXd matProjectorsInnerind(m_vecInnerind.size(),m_vecInnerind.size());
194
195 for (int i = 0; i < matProjectorsRows.rows(); ++i) {
196 matProjectorsRows.row(i) = matProjectors.row(m_vecInnerind.at(i));
197 }
198
199 for (int i = 0; i < matProjectorsInnerind.cols(); ++i) {
200 matProjectorsInnerind.col(i) = matProjectorsRows.col(m_vecInnerind.at(i));
201 }
202 m_matProjectors = matProjectorsInnerind;
203 return;
204}
#define FIFFV_COIL_BABY_MAG
#define FIFFV_COIL_VV_PLANAR_T1
#define FIFFV_COIL_VV_PLANAR_T2
#define FIFFV_COIL_VV_PLANAR_T3
#define FIFFV_POINT_HPI
FIFF channel descriptor record (FIFF_CH_INFO): per-channel logical/scanner numbers,...
Full FIFF measurement metadata: everything from FIFFB_MEAS / FIFFB_MEAS_INFO needed to interpret a re...
Pre-processing front-end for HPI fitting — re-shapes raw MEG data, projectors and digitised coils int...
FIFF file I/O, in-memory data structures and high-level readers/writers.
Inverse source estimation (MNE, dSPM, sLORETA, dipole fitting).
QSharedPointer< FiffInfo > SPtr
Definition fiff_info.h:90
void checkForUpdate(const QSharedPointer< FIFFLIB::FiffInfo > pFiffInfo)
void prepareDataAndProjectors(const Eigen::MatrixXd &matData, const Eigen::MatrixXd &matProjectors)
InvHpiDataUpdater(const QSharedPointer< FIFFLIB::FiffInfo > pFiffInfo)
Stores MEG sensor geometry (positions, orientations, weights, coil count) for a single sensor type.