MNE-CPP 0.1.9
A Framework for Electrophysiology
Loading...
Searching...
No Matches
ecd_set.cpp
Go to the documentation of this file.
1//=============================================================================================================
37//=============================================================================================================
38// INCLUDES
39//=============================================================================================================
40
41#include "ecd_set.h"
42#include <fiff/fiff_types.h>
43
44//ToDo don't use access and unlink -> use QT stuff instead -> QFile
45#if defined(WIN32) || defined(_WIN32) || defined(__WIN32) && !defined(__CYGWIN__)
46#include <io.h>
47#else
48#include <unistd.h>
49#endif
50
51//=============================================================================================================
52// QT INCLUDES
53//=============================================================================================================
54
55#include <QDebug>
56#include <QFile>
57#include <QString>
58#include <QRegularExpression>
59
60//=============================================================================================================
61// EIGEN INCLUDES
62//=============================================================================================================
63
64//=============================================================================================================
65// USED NAMESPACES
66//=============================================================================================================
67
68using namespace INVERSELIB;
69using namespace FIFFLIB;
70
71//=============================================================================================================
72// DEFINES
73//=============================================================================================================
74
75#define X 0
76#define Y 1
77#define Z 2
78
79//=============================================================================================================
80// DEFINE STATIC METHODS
81//=============================================================================================================
82
83//TODO OBSOLETE - USE ALREADY DEFINED ONE
84static fiff_int_t swap_int (fiff_int_t source)
85{
86 unsigned char *csource = (unsigned char *)(&source);
87 fiff_int_t result;
88 unsigned char *cresult = (unsigned char *)(&result);
89
90 cresult[0] = csource[3];
91 cresult[1] = csource[2];
92 cresult[2] = csource[1];
93 cresult[3] = csource[0];
94 return (result);
95}
96
97//=============================================================================================================
98//TODO OBSOLETE - USE ALREADY DEFINED ONE
99static float swap_float (float source)
100{
101 unsigned char *csource = (unsigned char *)(&source);
102 float result;
103 unsigned char *cresult = (unsigned char *)(&result);
104
105 cresult[0] = csource[3];
106 cresult[1] = csource[2];
107 cresult[2] = csource[1];
108 cresult[3] = csource[0];
109 return result;
110}
111
112//=============================================================================================================
113
114namespace INVERSELIB {
115
116typedef struct {
117 int dipole; /* Which dipole in a multi-dipole set */
118 float begin,end; /* Fitting time range */
119 float r0[3]; /* Sphere model origin */
120 float rd[3]; /* Dipole location */
121 float Q[3]; /* Dipole amplitude */
122 float goodness; /* Goodness-of-fit */
123 int errors_computed; /* Have we computed the errors */
124 float noise_level; /* Noise level used for error computations */
125 float single_errors[5]; /* Single parameter error limits */
126 float error_matrix[5][5]; /* This fully describes the conf. ellipsoid */
127 float conf_vol; /* The xyz confidence volume */
128 float khi2; /* The khi^2 value */
129 float prob; /* Probability to exceed khi^2 by chance */
130 float noise_est; /* Total noise estimate */
132
133} // Namespace
134
135//=============================================================================================================
136// DEFINE MEMBER METHODS
137//=============================================================================================================
138
140{
141}
142
143//=============================================================================================================
144
145ECDSet::ECDSet(const ECDSet &p_ECDSet)
146: dataname(p_ECDSet.dataname)
147, m_qListDips(p_ECDSet.m_qListDips)
148{
149}
150
151//=============================================================================================================
152
154{
155}
156
157//=============================================================================================================
158
159void ECDSet::addEcd(const ECD& p_ecd)
160{
161 m_qListDips.append(p_ecd);
162}
163
164//=============================================================================================================
165
166ECDSet ECDSet::read_dipoles_dip(const QString& fileName)
167{
168 ECDSet set;
169
170 QFile inputFile(fileName);
171 if (inputFile.open(QIODevice::ReadOnly|QIODevice::Text))
172 {
173 QTextStream in(&inputFile);
174 while (!in.atEnd())
175 {
176 QString line = in.readLine();
177 QStringList list = line.split(QRegularExpression("\\s+"));
178
179 if(list[0].contains("#") || list.size() != 11) {
180 continue;
181 }
182 else {
183 ECD one;
184 one.valid = true;
185 one.time = list[1].toFloat() / 1000.0f;
186 one.rd[X] = list[3].toFloat() / 1000.0f;
187 one.rd[Y] = list[4].toFloat() / 1000.0f;
188 one.rd[Z] = list[5].toFloat() / 1000.0f;
189 one.Q[X] = list[7].toFloat() / 1e9f;
190 one.Q[Y] = list[8].toFloat() / 1e9f;
191 one.Q[Z] = list[9].toFloat() / 1e9f;
192 one.good = list[10].toFloat() / 100.0f;
193 set << one;
194 }
195 }
196 inputFile.close();
197
198 printf("Read %d dipoles in dip format from %s\n",set.size(),fileName.toUtf8().data());
199 }
200 else {
201 printf("Not able to read from: %s\n", fileName.toUtf8().data());
202 }
203
204 return set;
205}
206
207//=============================================================================================================
208
209bool ECDSet::save_dipoles_bdip(const QString& fileName)
210/*
211 * Save dipoles in the bdip format employed by xfit
212 */
213{
214 FILE *out = NULL;
215 bdipEcdRec one_out;
216 ECD one;
217 int k,p;
218 int nsave;
219
220 if (fileName.isEmpty() || this->size() == 0)
221 return true;
222
223 if ((out = fopen(fileName.toUtf8().data(),"w")) == NULL) {
224 printf(fileName.toUtf8().data());
225 return false;
226 }
227
228 for (k = 0, nsave = 0; k < this->size(); k++) {
229 one = m_qListDips[k];
230 if (one.valid) {
231 one_out.dipole = swap_int(1);
232 one_out.begin = swap_float(one.time);
233 for (p = 0; p < 3; p++) {
234 one_out.r0[p] = swap_float(0.0);
235 one_out.rd[p] = swap_float(one.rd[p]);
236 one_out.Q[p] = swap_float(one.Q[p]);
237 }
238 one_out.goodness = swap_float(one.good);
239 one_out.errors_computed = swap_int(0);
240 one_out.khi2 = swap_float(one.khi2);
241 if (fwrite(&one_out,sizeof(bdipEcdRec),1,out) != 1) {
242 printf("Failed to write a dipole");
243 goto bad;
244 }
245 nsave++;
246 }
247 }
248 if (fclose(out) != 0) {
249 out = NULL;
250 printf(fileName.toUtf8().data());
251 return false;
252 }
253 printf("Save %d dipoles in bdip format to %s\n",nsave,fileName.toUtf8().data());
254 return true;
255
256bad : {
257 if (out) {
258 fclose(out);
259 unlink(fileName.toUtf8().data());
260 }
261 return false;
262 }
263}
264
265//=============================================================================================================
266
267bool ECDSet::save_dipoles_dip(const QString& fileName) const
268{
269 FILE *out = NULL;
270 int k,nsave;
271 ECD one;
272
273 if (fileName.isEmpty() || this->size() == 0)
274 return true;
275 if ((out = fopen(fileName.toUtf8().data(),"w")) == NULL) {
276 printf(fileName.toUtf8().data());
277 return false;
278 }
279 fprintf(out,"# CoordinateSystem \"Head\"\n");
280 fprintf (out,"# %7s %7s %8s %8s %8s %8s %8s %8s %8s %6s\n",
281 "begin","end","X (mm)","Y (mm)","Z (mm)","Q(nAm)","Qx(nAm)","Qy(nAm)","Qz(nAm)","g/%");
282 for (k = 0, nsave = 0; k < this->size(); k++) {
283 one = this->m_qListDips[k];
284 if (one.valid) {
285 fprintf(out," %7.1f %7.1f %8.2f %8.2f %8.2f %8.3f %8.3f %8.3f %8.3f %6.1f\n",
286 1000*one.time,1000*one.time,
287 1000*one.rd[X],1000*one.rd[Y],1000*one.rd[Z],
288 1e9*one.Q.norm(),1e9*one.Q[X],1e9*one.Q[Y],1e9*one.Q[Z],100.0*one.good);
289 nsave++;
290 }
291 }
292 fprintf(out,"## Name \"%s dipoles\" Style \"Dipoles\"\n","ALL");
293 if (fclose(out) != 0) {
294 out = NULL;
295 printf(fileName.toUtf8().data());
296 goto bad;
297 }
298 printf("Save %d dipoles in dip format to %s\n",nsave,fileName.toUtf8().data());
299 return true;
300
301bad : {
302 if (out) {
303 fclose(out);
304 unlink(fileName.toUtf8().data());
305 }
306 return false;
307 }
308}
309
310//=============================================================================================================
311
312const ECD& ECDSet::operator[] (int idx) const
313{
314 if (idx>=m_qListDips.length())
315 {
316 qWarning("Warning: Required ECD doesn't exist! Returning ECD '0'.");
317 idx=0;
318 }
319 return m_qListDips[idx];
320}
321
322//=============================================================================================================
323
325{
326 if (idx >= m_qListDips.length())
327 {
328 qWarning("Warning: Required ECD doesn't exist! Returning ECD '0'.");
329 idx = 0;
330 }
331 return m_qListDips[idx];
332}
333
334//=============================================================================================================
335
337{
338 this->m_qListDips.append(p_ecd);
339 return *this;
340}
int k
Definition fiff_tag.cpp:324
Definitions for describing the objects in a FIFF file.
FiffDigPointSet class declaration.
Electric Current Dipole description.
Definition ecd.h:73
Eigen::Vector3f rd
Definition ecd.h:109
float time
Definition ecd.h:108
float good
Definition ecd.h:111
bool valid
Definition ecd.h:107
float khi2
Definition ecd.h:112
Eigen::Vector3f Q
Definition ecd.h:110
Holds a set of Electric Current Dipoles.
Definition ecd_set.h:81
static ECDSet read_dipoles_dip(const QString &fileName)
Definition ecd_set.cpp:166
const ECD & operator[](int idx) const
Definition ecd_set.cpp:312
bool save_dipoles_dip(const QString &fileName) const
Definition ecd_set.cpp:267
bool save_dipoles_bdip(const QString &fileName)
Definition ecd_set.cpp:209
ECDSet & operator<<(const ECD &p_ecd)
Definition ecd_set.cpp:336
void addEcd(const ECD &p_ecd)
Definition ecd_set.cpp:159
qint32 size() const
Definition ecd_set.h:193