129 qint32 first_comp = -1;
132 for (k = 0; k < this->
nchan; ++k) {
134 comp = this->
chs[k].chpos.coil_type >> 16;
137 else if (comp != first_comp)
138 qWarning(
"Compensation is not set equally on all MEG channels");
148 MatrixXd C1, C2, comp_tmp;
160 C1 = MatrixXd::Zero(this->
nchan, this->
nchan);
163 qWarning(
"Cannot create compensator C1\n");
164 qWarning(
"Desired compensation matrix (kind = %d) not found\n", from);
170 C2 = MatrixXd::Zero(this->
nchan, this->
nchan);
173 qWarning(
"Cannot create compensator C2\n");
174 qWarning(
"Desired compensation matrix (kind = %d) not found\n", to);
184 const MatrixXd eye = MatrixXd::Identity(this->
nchan, this->
nchan);
185 comp_tmp = (eye - C2) * (eye - C1).partialPivLu().inverse();
188 if (exclude_comp_chs) {
189 VectorXi pick = VectorXi::Zero(this->
nchan);
191 for (k = 0; k < this->
nchan; ++k) {
198 qWarning(
"Nothing remains after excluding the compensation channels\n");
202 ctf_comp.data->data.resize(npick, this->nchan);
203 for (k = 0; k < npick; ++k)
204 ctf_comp.data->data.row(k) = comp_tmp.block(pick(k), 0, 1, this->nchan);
219 MatrixXd presel, postsel;
220 qint32 k, col, c, ch = 0, row, row_ch = 0, channelAvailable;
222 for (k = 0; k < this->comps.size(); ++k) {
223 if (this->comps[k].kind == kind) {
224 this_data = this->comps[k].data;
229 presel = MatrixXd::Zero(this_data->ncol, this->nchan);
231 for (col = 0; col < this_data->ncol; ++col) {
232 channelAvailable = 0;
233 for (c = 0; c < this->ch_names.size(); ++c) {
234 if (QString::compare(this_data->col_names.at(col), this->ch_names.at(c)) == 0) {
239 if (channelAvailable == 0) {
240 qWarning(
"Channel %s is not available in data\n", this_data->col_names.at(col).toUtf8().constData());
242 }
else if (channelAvailable > 1) {
243 qWarning(
"Ambiguous channel %s", this_data->col_names.at(col).toUtf8().constData());
246 presel(col, ch) = 1.0;
251 postsel = MatrixXd::Zero(this->nchan, this_data->nrow);
253 for (c = 0; c < this->nchan; ++c) {
254 channelAvailable = 0;
255 for (row = 0; row < this_data->row_names.size(); ++row) {
256 if (QString::compare(this->ch_names.at(c), this_data->row_names.at(row)) == 0) {
261 if (channelAvailable > 1) {
262 qWarning(
"Ambiguous channel %s", this->ch_names.at(c).toUtf8().constData());
264 }
else if (channelAvailable == 1) {
265 postsel(c, row_ch) = 1.0;
268 this_comp = postsel * this_data->data * presel;
272 this_comp = defaultMatrixXd;
289 for (qint32 i = 0; i < sel.size(); ++i) {
291 res.
chs.append(this->
chs[idx]);
294 res.
nchan =
static_cast<int>(sel.size());
303 QList<FiffChInfo> newList;
307 for (k = 0; k < listFiffChInfo.size(); ++k)
308 newList.append(listFiffChInfo[k]);
310 qint32 lower_half = 65535;
311 for (k = 0; k < listFiffChInfo.size(); ++k) {
313 coil_type = listFiffChInfo[k].chpos.coil_type & lower_half;
314 newList[k].chpos.coil_type = (coil_type | (value << 16));
325 const QStringList&
bads,
326 QList<FiffChInfo>& chsp,
338 if (!stream->read_meas_info(stream->dirtree(), info, infoNode)) {
339 qCritical(
"%s : could not read measurement info", name.toUtf8().data());
345 QList<FiffChInfo> meg;
346 QList<FiffChInfo> eeg;
348 for (
int k = 0; k < info.
chs.size(); k++) {
349 if (
bads.contains(info.
chs[k].ch_name))
352 meg.append(info.
chs[k]);
353 else if (do_eeg && info.
chs[k].isValidEeg())
354 eeg.append(info.
chs[k]);
358 chsp.reserve(meg.size() + eeg.size());
375 QList<FiffChInfo> chsToWrite;
377 for (qint32 k = 0; k < this->nchan; ++k)
378 chsToWrite << this->
chs[k];
387 if (this->
meas_id.version != -1) {
400 bool have_hpi_result =
false;
401 bool have_isotrak =
false;
405 if (!this->
acq_pars.isEmpty() || !this->acq_stim.isEmpty()) {
418 if (!have_hpi_result) {
428 if (this->
dig.size() > 0 && !have_isotrak) {
430 for (qint32 k = 0; k < this->
dig.size(); ++k)
446 if (this->
bads.size() > 0) {
471 MatrixXd cals(1, nchanToWrite);
473 for (qint32 k = 0; k < nchanToWrite; ++k) {
477 chsToWrite[k].scanNo = k + 1;
479 cals(0, k) =
static_cast<double>(chsToWrite[k].cal);
491 std::cout <<
"Sample frequency: " <<
sfreq <<
"\n";
493 std::cout <<
"Number of digitizer points: " <<
dig.size() <<
"\n";
494 for (
auto& point :
dig) {
496 std::cout <<
"HPI Point " << point.ident <<
" - " << point.r[0] <<
", " << point.r[1] <<
", " << point.r[2] <<
"\n";
#define FIFF_MNE_CH_NAME_LIST
#define FIFFB_MNE_BAD_CHANNELS
FIFF binary tag-stream layer: wraps a QIODevice to read and write FIFF tags, directories,...
Full FIFF measurement metadata: everything from FIFFB_MEAS / FIFFB_MEAS_INFO needed to interpret a re...
FIFF tag-kind, block-kind and type-code numerical definitions, authoritative for FIFFLIB.
#define FIFF_GANTRY_ANGLE
#define FIFF_PARENT_BLOCK_ID
#define FIFF_EXPERIMENTER
Header-only Eigen matrix text I/O — round-trips dense matrices to whitespace-separated ASCII for cros...
FIFF file I/O, in-memory data structures and high-level readers/writers.
Shared utilities (I/O helpers, spectral analysis, layout management, warp algorithms).
One CTF software-gradient compensation matrix: grade kind, calibration flag and the gradiometer × ref...
QSharedPointer< FiffDirNode > SPtr
128-bit FIFF identifier: hardware machine ID plus creation time, stamped on every file and block.
FiffInfo pick_info(const Eigen::RowVectorXi &sel=defaultVectorXi) const
void set_current_comp(fiff_int_t value)
static bool readMegEegChannels(const QString &name, bool do_meg, bool do_eeg, const QStringList &bads, QList< FiffChInfo > &chsp, int &nmegp, int &neegp)
QList< float > hpi_coil_freqs
void writeToStream(FiffStream *p_pStream) const
QList< FiffCtfComp > comps
qint32 get_current_comp()
bool make_compensator(fiff_int_t from, fiff_int_t to, FiffCtfComp &ctf_comp, bool exclude_comp_chs=false) const
QList< FiffDigPoint > dig
FiffCoordTrans ctf_head_t
FiffCoordTrans dev_head_t
QSharedDataPointer< FiffNamedMatrix > SDPtr
FIFF tag-stream reader/writer: wraps a QIODevice and exposes typed read_* / write_* methods for every...
fiff_long_t start_block(fiff_int_t kind)
fiff_long_t write_proj(const QList< FiffProj > &projs)
QSharedPointer< FiffStream > SPtr
fiff_long_t write_dig_point(const FiffDigPoint &dig)
fiff_long_t write_int(fiff_int_t kind, const fiff_int_t *data, fiff_int_t nel=1, fiff_int_t next=FIFFV_NEXT_SEQ)
fiff_long_t write_float(fiff_int_t kind, const float *data, fiff_int_t nel=1)
fiff_long_t write_id(fiff_int_t kind, const FiffId &id=FiffId::getDefault())
fiff_long_t write_coord_trans(const FiffCoordTrans &trans)
fiff_long_t write_name_list(fiff_int_t kind, const QStringList &data)
fiff_long_t write_string(fiff_int_t kind, const QString &data)
fiff_long_t end_block(fiff_int_t kind, fiff_int_t next=FIFFV_NEXT_SEQ)
fiff_long_t write_ch_info(const FiffChInfo &ch)
fiff_long_t write_ctf_comp(const QList< FiffCtfComp > &comps)